如何在django的User模型中添加自定义权限?

wf82jlnq  于 2023-05-19  发布在  Go
关注(0)|答案(5)|浏览(181)

在django中,当syncdb在安装了django.contrib.auth的情况下运行时,它会在每个模型上创建默认权限...例如foo.can_change、foo.can_delete和foo.can_add。要向模型添加自定义权限,可以添加 meta:并在那里定义权限,如此处所述https://docs.djangoproject.com/en/4.1/topics/auth/customizing/#custom-permissions
我的问题是,如果我想向User模型添加自定义权限,我应该怎么做?例如foo.can_view。我可以用下面的代码片段来实现这一点,

ct = ContentType.objects.get(app_label='auth', model='user')
perm = Permission.objects.create(codename='can_view', name='Can View Users', 
                                  content_type=ct)
perm.save()

但是我想要一些能很好地与syncdb配合的东西,例如我的自定义模型下的 meta。我应该只在课堂上有这些元:因为这是扩展用户模型的方法。但这是正确的方法吗这难道不会将其与UserProfile模型联系起来吗?

ghhkc1vu

ghhkc1vu1#

你可以这样做:
在Django应用的__init__.py中添加:

from django.db.models.signals import post_syncdb
from django.contrib.contenttypes.models import ContentType
from django.contrib.auth import models as auth_models
from django.contrib.auth.models import Permission

# custom user related permissions
def add_user_permissions(sender, **kwargs):
    ct = ContentType.objects.get(app_label='auth', model='user')
    perm, created = Permission.objects.get_or_create(codename='can_view', name='Can View Users', content_type=ct)
post_syncdb.connect(add_user_permissions, sender=auth_models)
xjreopfe

xjreopfe2#

我不认为这里有一个“正确”的答案,但我使用了与您完全相同的代码,只是我将Permission.objects.create更改为Permission.objects.get_or_create,并且可以使用find与syncdb同步

hs1rzwqc

hs1rzwqc3#

Django 1.8的更新答案。使用信号pre_migrate而不是pre_syncdb,因为syncdb已被弃用,并且如果信号会改变数据库,文档建议使用pre_migrate而不是post_migrate。此外,@receiver用于将add_user_permissions连接到信号。

from django.db.models.signals import pre_migrate
from django.contrib.contenttypes.models import ContentType
from django.contrib.auth import models as auth_models
from django.contrib.auth.models import Permission
from django.conf import settings
from django.dispatch import receiver

# custom user related permissions
@receiver(pre_migrate, sender=auth_models)
def add_user_permissions(sender, **kwargs):
    content_type = ContentType.objects.get_for_model(settings.AUTH_USER_MODEL)
    Permission.objects.get_or_create(codename='view_user', name='View user', content_type=content_type)
lsmepo6l

lsmepo6l4#

这是一个有点hacky,但在这里提到它无论如何参考。
我的网站有一个名为Setting的通用模型,它存储了有关网站的各种设置,我希望某些用户能够编辑,而不需要通过我的开发人员(如注册限制,或地址,或项目的成本等)。
所有不能很好地Map到其他模型的权限(例如“向学生发送密码提醒电子邮件”,“生成付款对账报告”,“生成PDF收据”),这些权限实际上只是与在管理区域中查看的页面相关,被转储到这个Setting模型中。
例如,下面是模型:

class Setting(models.Model):
    name = models.CharField(max_length=50, unique=True)
    slug = models.SlugField(editable=False)
    description = models.TextField()
    value = models.TextField()
    class Meta:
        #for permissions that don't really relate to a particular model, and I don't want to programmatically create them.
        permissions = (
            ("password_reminder", "Send Password Reminder"),
            ("generate_payment_reconciliation_report", "Generate Payment Reconciliation Report"),
            ("generate_pdf_receipt", "Generate PDF Receipt"),
        )

这些设置中的每一个都与Setting模型严格相关吗?不,所以我才说这有点古怪。但是很高兴我现在可以在这里转储所有这些权限,Django的迁移命令将负责其余的工作。

4uqofj5v

4uqofj5v5#

正如@leech在其answer的评论中指出的那样,您不能将name参数直接传递给get_or_create。您必须将name作为defaults dict的一部分。否则,您将得到重复的关键字错误。
将来自@Dzejkob的answerget_or_create调用更改为如下所示:

perm, created = Permission.objects.get_or_create(
    content_type=ct,
    codename='can_view', 
    defaults={'name': 'Can View Users'},
)

相关问题