自定义的Django用户对象没有'has_module_perms'属性。

29

我的自定义用户模型用于通过电子邮件登录:

class MyUser(AbstractBaseUser):
    id = models.AutoField(primary_key=True)  # AutoField?
    is_superuser = models.IntegerField(default=False)
    username = models.CharField(unique=True,max_length=30)
    first_name = models.CharField(max_length=30, default='')
    last_name = models.CharField(max_length=30, default='')
    email = models.EmailField(unique=True,max_length=75)
    is_staff = models.IntegerField(default=False)
    is_active = models.IntegerField(default=False)
    date_joined = models.DateTimeField(default=None)

    # Use default usermanager
    objects = UserManager()

    USERNAME_FIELD = 'email'
    REQUIRED_FIELDS = ['username']

    class Meta:
        db_table = 'auth_user'

我已成功创建超级用户。但是,当我尝试使用电子邮件和密码登录时,出现以下错误:

'MyUser' object has no attribute 'has_module_perms'

我在做什么事情错了吗?

3个回答

49

您的用户实现未提供与管理模块一起使用的必需方法。

请参见https://docs.djangoproject.com/en/4.0/topics/auth/customizing/#custom-users-and-django-contrib-admin

在您的情况下,将权限mixin(PermissionsMixin)作为您的模型的超类添加:

from django.contrib.auth.models import PermissionsMixin


class MyUser(AbstractBaseUser, PermissionsMixin):
     # ...

这里描述了:https://docs.djangoproject.com/en/4.0/topics/auth/customizing/#custom-users-and-permissions 它适用于Django 1.x、2.x、3.x和4.x。
编辑:更新到Django 4.0的链接。

1
这在较新版本的Django上不起作用。请参见下面的答案。 - dan-klasson
已确认在2.1版本上可以实现。 - Cochise Ruhulessin

18

我认为你的模型缺少一些属性,例如'has_module_params'...尝试添加以下内容

class MyUser(AbstractBaseUser):
  ...
  ...

  def has_perm(self, perm, obj=None):
    return self.is_superuser

  def has_module_perms(self, app_label):
    return self.is_superuser

5
对于那些刚刚进入2017年11月以后的人来说,我认为添加或允许您的类继承PermissionsMixin并不是出路,因为这样会产生更多错误,而且您已经重新发明了轮子。
今天下午(2017年11月4日),我遇到了同样的问题,即用电话号码覆盖了用户名
class MyUserManager(BaseUserManager):
    ..
    ..

    def create_superuser(self, phone, password=None):
        if password is None:
            raise TypeError("provide password please")
        myuser = self.model(phone=phone)
        myuser.set_password(password)
        myuser.is_admin = True
        myuser.is_staff = True
        myuser.save()

        return myuser

因此,http://127.0.0.1:8000/admin/无法工作,并不断引发object has no attribute 'has_module_perms'错误,以下是我解决问题的方法:

class MyUser(AbstractBaseUser):
    ..
    ..

    def get_full_name(self):
        pass

    def get_short_name(self):
        pass

    @property
    def is_superuser(self):
        return self.is_admin

    @property
    def is_staff(self):
       return self.is_admin

    def has_perm(self, perm, obj=None):
       return self.is_admin

    def has_module_perms(self, app_label):
       return self.is_admin

    @is_staff.setter
    def is_staff(self, value):
        self._is_staff = value

我希望这能帮助到某些人。


这个答案与@Bogdan Goie的完全相同。但是你使用了is_admin而不是is_superuser。这可能会令人困惑。 - dan-klasson

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