我的项目使用自定义身份验证后端来管理用户权限,使身份验证本身保持不变(由 Django 处理)。后端本身工作正常,但在使用 Django WebTest 构建的测试中开始失败。经过一番挑选,我发现罪魁祸首是 DWT 将另一个身份验证后端注入settings.AUTHENTICATION_BACKENDS
.
我的后端直接扩展了 Django 的ModelBackend
,而 DWT 自己的后端是基于 offRemoteUserBackend
的,最终也是ModelBackend
. 这一点很重要,因为虽然 DWT 没有定义has_perm
方法,但它仍然存在于其后端。
执行测试时,缓存有问题的用户对象的权限django.contrib.auth.backends.ModelBackend
:get_all_permissions()
has_perm
if not hasattr(user_obj, '_perm_cache'):
user_obj._perm_cache = {
*self.get_user_permissions(user_obj),
*self.get_group_permissions(user_obj),
}
return user_obj._perm_cache
由于 DWT 的后端首先出现在测试中,缓存被填充并且不会包含我的后端设置的权限,最终导致has_perm
测试失败。参考 Django 中的代码片段:
def _user_has_perm(user, perm, obj):
"""
A backend can raise `PermissionDenied` to short-circuit permission checking.
"""
for backend in auth.get_backends():
if not hasattr(backend, 'has_perm'):
continue
try:
if backend.has_perm(user, perm, obj):
return True
except PermissionDenied:
return False
return False
我在后端做错了什么还是 DWT 作者的疏忽?在测试中如何继续使用我的自定义权限逻辑?