Django 1.7 - 以编程方式添加权限无法按预期工作
Django 1.7 - Adding permissions programmatically does not work as expected
这是怎么回事?
> from django.contrib.auth.models import Permission
> from django.contrib.contenttypes.models import ContentType
> p = Permission.objects.filter(
content_type = ContentType.objects.get_for_model(Transaction)
).get(
codename = 'add_transaction'
)
> user.user_permissions.add(p)
> user.user_permissions.all()
[<Permission: myapp | Transaction | Can add Transaction>]
> user.get_all_permissions()
set([])
> user.has_perm('add_transaction')
False
> user.has_perm('myapp.add_transaction')
False
我是不是遗漏了什么地方的存档?
我相信用户实例有一个权限缓存,当它第一次从数据库中被拉出时就会被填充。在调用 has_perm
之前尝试删除缓存:
delattr(user, '_perm_cache')
之后,has_perm
应该会按预期工作。通常这不是问题,因为您很少添加然后立即测试同一用户实例的权限(无需再次将其从数据库中拉出)。不过,当您在 python shell 中进行测试时,肯定会绊倒您。
ModelBackend
缓存用户对象的权限。 Django docs 建议您在更改权限后从数据库重新加载用户。
user.user_permissions.add(p)
user = User.objects.get(pk=user.pk)
dgel
的回答正确但不完整。 _perm_cache
和 _user_perm_cache
都需要清除才能强制重新加载。
for attr in ('_perm_cache', '_user_perm_cache'):
delattr(user, attr)
这是怎么回事?
> from django.contrib.auth.models import Permission
> from django.contrib.contenttypes.models import ContentType
> p = Permission.objects.filter(
content_type = ContentType.objects.get_for_model(Transaction)
).get(
codename = 'add_transaction'
)
> user.user_permissions.add(p)
> user.user_permissions.all()
[<Permission: myapp | Transaction | Can add Transaction>]
> user.get_all_permissions()
set([])
> user.has_perm('add_transaction')
False
> user.has_perm('myapp.add_transaction')
False
我是不是遗漏了什么地方的存档?
我相信用户实例有一个权限缓存,当它第一次从数据库中被拉出时就会被填充。在调用 has_perm
之前尝试删除缓存:
delattr(user, '_perm_cache')
之后,has_perm
应该会按预期工作。通常这不是问题,因为您很少添加然后立即测试同一用户实例的权限(无需再次将其从数据库中拉出)。不过,当您在 python shell 中进行测试时,肯定会绊倒您。
ModelBackend
缓存用户对象的权限。 Django docs 建议您在更改权限后从数据库重新加载用户。
user.user_permissions.add(p)
user = User.objects.get(pk=user.pk)
dgel
的回答正确但不完整。 _perm_cache
和 _user_perm_cache
都需要清除才能强制重新加载。
for attr in ('_perm_cache', '_user_perm_cache'):
delattr(user, attr)