Expose, honor "admin-ish" flag for roles

prevent user (un)assignment etc. unless admin is doing it
This commit is contained in:
Lance Edgar 2022-08-21 19:36:48 -05:00
parent 7b2fef5f09
commit e50356d276
2 changed files with 28 additions and 5 deletions

View file

@ -2,7 +2,7 @@
################################################################################
#
# Rattail -- Retail Software Framework
# Copyright © 2010-2021 Lance Edgar
# Copyright © 2010-2022 Lance Edgar
#
# This file is part of Rattail.
#
@ -54,6 +54,7 @@ class RoleView(PrincipalMasterView):
touchable = True
labels = {
'adminish': "Admin-ish",
'sync_me': "Sync Attrs & Perms",
}
@ -68,6 +69,7 @@ class RoleView(PrincipalMasterView):
form_fields = [
'name',
'adminish',
'session_timeout',
'notes',
'sync_me',
@ -112,6 +114,10 @@ class RoleView(PrincipalMasterView):
if role is administrator_role(self.Session()):
return self.request.is_root
# only "admin" can edit "admin-ish" roles
if role.adminish:
return self.request.is_admin
# can edit Authenticated only if user has permission
if role is authenticated_role(self.Session()):
return self.has_perm('edit_authenticated')
@ -143,6 +149,10 @@ class RoleView(PrincipalMasterView):
if role is guest_role(self.Session()):
return False
# only "admin" can delete "admin-ish" roles
if role.adminish:
return self.request.is_admin
# current user can delete their own roles, only if they have permission
user = self.request.user
if user and role in user.roles:
@ -169,6 +179,10 @@ class RoleView(PrincipalMasterView):
# name
f.set_validator('name', self.unique_name)
# adminish
if not self.request.is_admin:
f.remove('adminish')
# session_timeout
f.set_renderer('session_timeout', self.render_session_timeout)
if self.editing and role is guest_role(self.Session()):

View file

@ -27,6 +27,7 @@ User Views
from __future__ import unicode_literals, absolute_import
import six
import sqlalchemy as sa
from sqlalchemy import orm
from rattail.db.model import User, UserEvent
@ -276,13 +277,21 @@ class UserView(PrincipalMasterView):
authenticated_role(self.Session()).uuid,
]
# only allow "root" user to change admin role membership
# only allow "root" user to change true admin role membership
if not self.request.is_root:
excluded.append(administrator_role(self.Session()).uuid)
return self.Session.query(model.Role)\
.filter(~model.Role.uuid.in_(excluded))\
.order_by(model.Role.name)
# basic list, minus exclusions so far
roles = self.Session.query(model.Role)\
.filter(~model.Role.uuid.in_(excluded))
# only allow "admin" user to change admin-ish role memberships
if not self.request.is_admin:
roles = roles.filter(sa.or_(
model.Role.adminish == False,
model.Role.adminish == None))
return roles.order_by(model.Role.name)
def objectify(self, form, data=None):
model = self.model