Optimize permission check

Convert the user permission check from a double Python loop
to a single ORM query.

Add methods to the Role model to grant or revoke permissions.

Rename the method requester_has_this to user_has_this for clarity.

Signed-off-by: Roberto Rosario <Roberto.Rosario@mayan-edms.com>
This commit is contained in:
Roberto Rosario
2019-01-13 22:57:59 -04:00
parent 65ccbd3b7b
commit 9d8c8f4833
+15 -16
View File
@@ -59,7 +59,7 @@ class StoredPermission(models.Model):
def natural_key(self): def natural_key(self):
return (self.namespace, self.name) return (self.namespace, self.name)
def requester_has_this(self, user): def user_has_this(self, user):
""" """
Helper method to check if an user has been granted this permission. Helper method to check if an user has been granted this permission.
The check is done sequentially over all of the user's groups and The check is done sequentially over all of the user's groups and
@@ -73,20 +73,13 @@ class StoredPermission(models.Model):
) )
return True return True
# Request is one of the permission's holders? if Role.objects.filter(groups__user=user, permissions=self).exists():
for group in user.groups.all(): return True
for role in group.roles.all(): else:
if self in role.permissions.all(): logger.debug(
logger.debug( 'Fallthru: Permission "%s" not granted to user "%s"', self, user
'Permission "%s" granted to user "%s" through role "%s"', )
self, user, role return False
)
return True
logger.debug(
'Fallthru: Permission "%s" not granted to user "%s"', self, user
)
return False
@python_2_unicode_compatible @python_2_unicode_compatible
@@ -120,8 +113,14 @@ class Role(models.Model):
return self.label return self.label
def get_absolute_url(self): def get_absolute_url(self):
return reverse('permissions:role_list') return reverse(viewname='permissions:role_list')
def grant(self, permission):
self.permissions.add(permission.stored_permission)
def natural_key(self): def natural_key(self):
return (self.label,) return (self.label,)
natural_key.dependencies = ['auth.Group', 'permissions.StoredPermission'] natural_key.dependencies = ['auth.Group', 'permissions.StoredPermission']
def revoke(self, permission):
self.permissions.remove(permission.stored_permission)