【问题标题】:Superuser can't access Django Admin Panel. It shows "You don’t have permission to view or edit anything."超级用户无法访问 Django 管理面板。它显示“您无权查看或编辑任何内容”。
【发布时间】:2021-06-08 19:11:05
【问题描述】:

我在 Django==3.2.3 中创建了一个自定义用户模型

这是我的 model.py 文件

class MyUserManager(BaseUserManager):
""" A custom Manager to deal with emails as unique identifer """
def _create_user(self, email, password, **extra_fields):
    """ Creates and saves a user with a given email and password"""

    if not email:
        raise ValueError("The Email must be set!")

    email = self.normalize_email(email)
    user = self.model(email=email, **extra_fields)
    user.set_password(password)
    user.save(using=self._db)
    return user

def create_superuser(self, email, password, **extra_fields):
    extra_fields.setdefault('is_staff', True)
    extra_fields.setdefault('is_superuser', True)
    extra_fields.setdefault('is_active', True)

    if extra_fields.get('is_staff') is not True:
        raise ValueError('Superuser must have is_staff=True')
    if extra_fields.get('is_superuser') is not True:
        raise ValueError('Superuser must have is_superuser=True')
    return self._create_user(email, password, **extra_fields)



class User(AbstractBaseUser, PermissionsMixin):


email = models.EmailField(max_length=60, unique=True, verbose_name='Email')
first_name = models.CharField(max_length=30, verbose_name='First Name')
last_name = models.CharField(max_length=30, verbose_name='Last Name')
is_active = models.BooleanField(default=True)
is_admin = models.BooleanField(default=False)
is_staff = models.BooleanField(default=False)

USERNAME_FIELD = 'email'
REQUIRED_FIELDS = ('first_name', 'last_name')

objects = MyUserManager()

def __str__(self):
    return self.email

def get_short_name(self):
    return self.first_name

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

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

class Meta:
    verbose_name_plural = "Users"

这是我的 admin.py 文件

class MyUserAdmin(UserAdmin):
form = UserchangeForm
add_form = UserCreationForm

list_display = ('email', 'first_name', 'last_name', 'is_admin')
list_filter = ('is_admin',)
fieldsets = (
    (None, {'fields': ('email', 'password')}),
    ('Personal info', {'fields': (('first_name', 'last_name'))}),
    ('Permissions', {'fields': ('is_admin',)}),
)

add_fieldsets = (
    (None, {
        'classes': ('Wide',),
        'fields': ('email', 'first_name', 'last_name')
    }),
)
search_fields = ('email',)
ordering = ('email',)
filter_horizontal = ()


admin.site.register(User, MyUserAdmin)

迁移并创建超级用户后,当我登录管理面板时,它显示“您无权查看或编辑任何内容。”

我在 StackOverflow 和其他网站上看到了许多解决方案。他们都建议添加我已经添加的 has_module_permshas_perm

【问题讨论】:

    标签: django django-models


    【解决方案1】:

    内置用户模型有两个字段指示用户的管理员/员工状态,即is_superuseris_staff,超级用户有权执行任何操作。这里的问题是您创建了一个 extra 字段is_admin 并且还覆盖了has_perm 等(以一种糟糕的方式),因此只有一个用户将此字段设置为@987654325 @ 将拥有所有权限(其他人如果授予该权限仍然不会拥有它,因为您已经以这种方式覆盖了它)。

    您需要将is_admin 重命名为is_superuser删除您的has_permhas_module_perms

    class User(AbstractBaseUser, PermissionsMixin):
        ...
        # ... is a placeholder for your code, strikethroughs mean you should remove the line
        is_admin = models.BooleanField(default=False)
        is_superuser = models.BooleanField(default=False)
        ...
        
        def has_perm(self, perm, obj=None):
            return self.is_admin
        
        def has_module_perms(self, app_label):
            return self.is_admin
        ...
    

    同样在MyUserAdmin 中你提到了is_admin 将其重命名为is_superuser

    【讨论】:

      【解决方案2】:

      有同样的问题。然后我将 'password=password' 和 'username=username' 一起传递到函数中,如下面的粗体所示,它解决了问题:

      class MyAccountManager(BaseUserManager):
          def create_user(self, email, username, password):
              if not email:
                  raise ValueError('Please add an email address')
              if not username:
                  raise ValueError('Please add an username')
      
              **user = self.model(email=self.normalize_email(
                  email), username=username, password=password)**
      
              user.set_password(password)
              user.save(using=self._db)
              return user
      
          def create_superuser(self, email, username, password):
          #I have the below in my create_superuser function, I don't see it in your code:
              **user = self.create_user(email=self.normalize_email(
                  email), username=username, password=password)**
      

      另外,请确保将 AUTH_USER_MODEL = 'accounts.User' 添加到 settings.py

      【讨论】:

        【解决方案3】:

        所以这是一个奇怪的问题,但我希望这对某人有所帮助。以上是覆盖 Django 用户模型的很正常的方法,继承 AbstractBaseUserAbstractUser

        但是这样做,您需要创建自己的 Admin 类,这些类通常直接指向 UserCreationFormUserChangeForm,它们位于 django.contrib.auth.forms 模块中,或者指向子类中的任何一个的自定义表单。

        默认情况下,UserCreationForm 不包含 is_superuser 值,这意味着使用此表单在管理员中创建一个帐户,将此值保留为 false - 意味着您可以创建一个可以登录的帐户,但它不会'还没有明确或隐含的权限来查看任何内容。

        如果您自省 from django.contrib.auth.forms.UserCreationForm 中的实际 Form 类,这是预期的行为,来自文档字符串:

        """
        A form that creates a user, with no privileges, from the given username and password.
        """
        

        对我来说,我可以通过两种方式解决这个问题:

        1 -您可以确保将 is_superuser 手动添加到您的初始 UserCreationForm 中,方法是确保它在您的 Admin 类的 add_fieldsets 元组中明确列出,我的在这里:

        add_fieldsets = (
            (
                None,
                {
                    "classes": ("wide",),
                    "fields": (
                        "email",
                        "password1",
                        "password2",
                        "is_staff",
                        "is_active",
                        "is_superuser"
                    ),
                },
            ),
        )
        

        2 -您可以确保它被手动添加到UserChangeForm,方法是确保它在管理类fieldsets Tuple 中明确列出,这与上述相同,但被调用在ChangeForm 而不是CreationForm。无论如何,您可能都想这样做。

        【讨论】:

          猜你喜欢
          • 2019-10-16
          • 2020-03-24
          • 2016-02-06
          • 1970-01-01
          • 2020-11-25
          • 2011-04-12
          • 2015-11-25
          • 1970-01-01
          • 2021-10-17
          相关资源
          最近更新 更多