Django-invitations,Django-Allauth:如何从自定义邀请传递模型字段数据到(自定义)用户对象

4

我正在将django-invitations与django-allauth结合使用以进行用户邀请和注册。

我希望管理员(通过Django管理界面创建邀请时)能提供额外的数据(例如一个指向病人对象的外键)。这可以通过向(自定义的)邀请模型添加额外字段来实现:

class PatientInvitation (AbstractBaseInvitation):                                                                                                                                                                    
    email = models.EmailField(unique=True, verbose_name=_('e-mail address'),                                                                                                                                         
                              max_length=app_settings.EMAIL_MAX_LENGTH)                                                                                                                                              
    created = models.DateTimeField(verbose_name=_('created'),                                                                                                                                                        
                                   default=timezone.now)                                                                                                                                                                                                                                                                                                                       
    patient = models.ForeignKey(Patient, blank=True, null=True, on_delete=models.CASCADE)                                                                                                                            

    @classmethod                                                                                                                                                                                                     
    def create(cls, email, inviter=None, patient=None,  **kwargs):                                                                                                                                                   
        key = get_random_string(64).lower()                                                                                                                                                                          
        instance = cls._default_manager.create(                                                                                                                                                                      
            email=email,                                                                                                                                                                                             
            key=key,                                                                                                                                                                                                 
            inviter=inviter,                                                                                                                                                                                         
            patient=patient,                                                                                                                                                                                         
            **kwargs)                                                                                                                                                                                                
        return instance                                                                                                                                                                                              

    def key_expired(self):                                                                                                                                                                                           
        expiration_date = (                                                                                                                                                                                          
            self.sent + datetime.timedelta(                                                                                                                                                                          
                days=app_settings.INVITATION_EXPIRY))                                                                                                                                                                
        return expiration_date <= timezone.now()                                                                                                                                                                     

    def send_invitation(self, request, **kwargs):                                                                                                                                                                    
        current_site = kwargs.pop('site', Site.objects.get_current())                                                                                                                                                
        invite_url = reverse('invitations:accept-invite',                                                                                                                                                            
                             args=[self.key])                                                                                                                                                                        
        invite_url = request.build_absolute_uri(invite_url)                                                                                                                                                          
        ctx = kwargs                                                                                                                                                                                                 
        ctx.update({                                                                                                                                                                                                 
            'invite_url': invite_url,                                                                                                                                                                                
            'site_name': current_site.name,                                                                                                                                                                          
            'email': self.email,                                                                                                                                                                                     
            'key': self.key,                                                                                                                                                                                         
            'inviter': self.inviter,                                                                                                                                                                                 
        })                                                                     


当被邀请的用户注册时,我希望这些数据最终出现在自定义用户模型中:
class customUser(AbstractUser):                                                                                                                                                                                      
    username_validator = MyValidator()                                                                                                                                                                               
    is_patient = models.BooleanField(default=False)                                                                                                                                                                  
    patient = models.ForeignKey(Patient, null=True, blank=True, on_delete=models.CASCADE)                                                                                                                              
    username = models.CharField(                                                                                                                                                                                     
        _('username'),                                                                                                                                                                                               
        max_length=150,                                                                                                                                                                                              
        unique=True,                                                                                                                                                                                                                                                                                                                                                                                                         
    )       

我已经研究了传递数据的信号,但是没有找到如何确切地执行此操作。 另一种选择似乎是将外键的PK添加到注册表单上的隐藏字段中(尽管这似乎不安全)。

在这方面我有点困惑,所以如果有人能指点我正确的方向,我将不胜感激 :)

敬礼, Joris

1个回答

3

可以考虑使用allauth的信号,这样您将拥有更多的选项,并且仍然可以实现您想要的功能。

  1. 在您的应用程序目录中创建signals.py文件。

  2. 像这样在您的apps.py下注册信号文件:

from django.apps import AppConfig

class AccountsConfig(AppConfig):
    name = 'app_name'

    def ready(self): ###<-----------
        import app_name.signals ###<-----------

使用user_signed_up信号来更新用户的邀请数据:

signals.py

from allauth.account.signals import user_signed_up
from invitations.utils import get_invitation_model

def user_signed_up(request, user, **kwargs):
    try:
        Invitation = get_invitation_model() ### Get the Invitation model
        invite = Invitation.objects.get(email=user.email) ### Grab the Invitation instance
        user.patient = invite.patient ### Pass your invitation's patient to the related user
        user.save()
    except Invitation.DoesNotExist:
        print("this was probably not an invited user.")



网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接