首页 文章

使用django自定义用户模型的python社交认证

提问于
浏览
1

我正在使用 python-social-auth (不是django-social-auth,因为它已被折旧)用于Django REST后端应用程序中的身份验证,如下所述 Custom User Model .

from django.contrib.auth.models import AbstractBaseUser, UserManager

class User(AbstractBaseUser):

    class Gender():
        MALE = 0
        FEMALE = 1
        UNKNOWN = 2
        CHOICES = [(MALE, 'Male'), (FEMALE, 'Female'), (UNKNOWN, 'Unknown')]

    username = models.CharField(_('username'), max_length=30, unique=True,
        help_text=_('Required. 30 characters or fewer. Letters, digits and '
                    '@/./+/-/_ only.'),
        validators=[
            validators.RegexValidator(r'^[\w.@+-]+$', _('Enter a valid username.'), 'invalid')
        ])
    first_name = models.CharField(max_length=30, blank=True)
    last_name = models.CharField(max_length=30, blank=True)
    email = models.EmailField(blank=True)
    is_staff = models.BooleanField(default=False)
    is_active = models.BooleanField(_('active'), default=True)
    date_joined = models.DateTimeField(default=timezone.now)

    gender = models.IntegerField(choices=Gender.CHOICES, default=Gender.UNKNOWN)
    birthday = models.DateField(default=timezone.now)
    facebook_id = models.CharField(max_length=30, blank=True)

    USERNAME_FIELD = 'username'
    REQUIRED_FIELDS = ['email']
    objects = UserManager()

    def __unicode__(self):
        return self.username

    def save(self, *args, **kwargs):
        """ ensure instance has usable password when created """
        if not self.pk and self.has_usable_password() is False:
            self.set_password(self.password)

        super(User, self).save(*args, **kwargs)

请注意,我没有实现自定义 UserManager . 社会认证的pipline也很简单 .

AUTHENTICATION_BACKENDS = (
      'social.backends.facebook.FacebookOAuth2',
      'django.contrib.auth.backends.ModelBackend',
  )

SOCIAL_AUTH_PIPELINE = (
    'social.pipeline.social_auth.social_details',
    'social.pipeline.social_auth.social_uid',
    'social.pipeline.social_auth.auth_allowed',
    'social.pipeline.social_auth.social_user',
    'social.pipeline.user.get_username',
    'social.pipeline.social_auth.associate_by_email',
    'social.pipeline.user.create_user',
    'social.pipeline.social_auth.associate_user',
    'social.pipeline.social_auth.load_extra_data',
    'social.pipeline.user.user_details'
)

但是,当我尝试使用Facebook进行身份验证时,会出现如下错误

TypeError at /api-token/login/facebook/ 'is_superuser' is an invalid keyword argument for this function

问题可能是 python-social-auth 尝试使用django自己的用户而不是我定义的自定义用户模型 . 在 django-social-auth 中有一个设置的参数,如 SOCIAL_AUTH_USER_MODEL 但我在 python-social-auth 找不到任何方法

如何才能在python-social-auth中使用我的自定义用户模型?

1 回答

  • 0

    必须有一个自定义UserManager,如下所述 . 我在创建新用户时删除了 is_superuser=is_superuser 字段 .

    class UserManager(BaseUserManager):
    
        def _create_user(self, username, email, password,
                         is_staff, is_superuser, **extra_fields):
            """
            Creates and saves a User with the given username, email and password.
            """
            now = timezone.now()
            if not username:
                raise ValueError('The given username must be set')
            email = self.normalize_email(email)
            user = self.model(username=username, email=email,
                              is_staff=is_staff, is_active=True, last_login=now,
                              date_joined=now, **extra_fields)
            user.set_password(password)
            user.save(using=self._db)
            return user
    
        def create_user(self, username, email=None, password=None, **extra_fields):
            return self._create_user(username, email, password, False, False,
                                     **extra_fields)
    
        def create_superuser(self, username, email, password, **extra_fields):
            return self._create_user(username, email, password, True, True,
                                     **extra_fields)
    

相关问题