Added Alembic
Breaking: Changed a lot of column names
This commit is contained in:
1 parent
9383cf84d4
commit
3cd7ff11f6
30 files changed
+2050
-561
No files matched your search
@@ -1,93 +0,0 @@
|
||||
import uuid
|
||||
from brewman.models.auth import Group, Role
|
||||
|
||||
from fastapi import APIRouter
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
|
||||
@router.post("/new") # "Users"
|
||||
def save(request):
|
||||
group = Group(request.json_body["name"])
|
||||
request.dbsession.add(group)
|
||||
add_permissions(group, request.json_body["permissions"], request.dbsession)
|
||||
transaction.commit()
|
||||
return group_info(group.id, request.dbsession)
|
||||
|
||||
|
||||
@router.put("/{id}") # "Users"
|
||||
def update(request):
|
||||
id_ = request.matchdict.get("id", None)
|
||||
group = request.dbsession.query(Group).filter(Group.id == uuid.UUID(id_)).one()
|
||||
group.name = request.json_body["name"]
|
||||
add_permissions(group, request.json_body["permissions"], request.dbsession)
|
||||
transaction.commit()
|
||||
return group_info(group.id, request.dbsession)
|
||||
|
||||
|
||||
def add_permissions(group, permissions, dbsession):
|
||||
for permission in permissions:
|
||||
id_ = uuid.UUID(permission["id"])
|
||||
gp = [p for p in group.roles if p.id == id_]
|
||||
gp = None if len(gp) == 0 else gp[0]
|
||||
if permission["enabled"] and gp is None:
|
||||
group.roles.append(dbsession.query(Role).filter(Role.id == id_).one())
|
||||
elif not permission["enabled"] and gp:
|
||||
group.roles.remove(gp)
|
||||
|
||||
|
||||
@router.delete("/{id}") # "Users"
|
||||
def delete(request):
|
||||
id_ = request.matchdict.get("id", None)
|
||||
if id_ is None:
|
||||
response = Response("Group is Null")
|
||||
response.status_int = 500
|
||||
return response
|
||||
else:
|
||||
response = Response("Group deletion not implemented")
|
||||
response.status_int = 500
|
||||
return response
|
||||
|
||||
|
||||
@router.get("/{id}") # "Users"
|
||||
def show_id(request):
|
||||
return group_info(uuid.UUID(request.matchdict.get("id", None)), request.dbsession)
|
||||
|
||||
|
||||
@router.get("/new") # "Users"
|
||||
def show_blank(request):
|
||||
return group_info(None, request.dbsession)
|
||||
|
||||
|
||||
@router.get("/") # "Users"
|
||||
async def show_list(l: bool):
|
||||
list_ = request.dbsession.query(Group).order_by(Group.name).all()
|
||||
|
||||
groups = []
|
||||
for item in list_:
|
||||
group = {"id": item.id, "name": item.name, "permissions": []}
|
||||
for permission in sorted(item.roles, key=lambda p: p.name):
|
||||
group["permissions"].append(permission.name)
|
||||
groups.append(group)
|
||||
return groups
|
||||
|
||||
|
||||
def group_info(id_, dbsession):
|
||||
if id_ is None:
|
||||
group = {"name": "", "permissions": []}
|
||||
for item in dbsession.query(Role).order_by(Role.name).all():
|
||||
group["permissions"].append(
|
||||
{"id": item.id, "name": item.name, "enabled": False}
|
||||
)
|
||||
else:
|
||||
group_object = dbsession.query(Group).filter(Group.id == id_).one()
|
||||
group = {"id": group_object.id, "name": group_object.name, "permissions": []}
|
||||
for item in dbsession.query(Role).order_by(Role.name).all():
|
||||
group["permissions"].append(
|
||||
{
|
||||
"id": item.id,
|
||||
"name": item.name,
|
||||
"enabled": True if item in group_object.roles else False,
|
||||
}
|
||||
)
|
||||
return group
|
||||
@@ -0,0 +1,163 @@
|
||||
import traceback
|
||||
import uuid
|
||||
from typing import List, Optional
|
||||
|
||||
from fastapi import APIRouter, HTTPException, status, Depends, Security
|
||||
from sqlalchemy.exc import SQLAlchemyError
|
||||
from sqlalchemy.orm import Session
|
||||
|
||||
from ...schemas.auth import UserToken
|
||||
from ...core.security import get_current_active_user as get_user
|
||||
from ...db.session import SessionLocal
|
||||
from ...models.auth import Role, Permission
|
||||
import brewman.schemas.auth as schemas
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
|
||||
# Dependency
|
||||
def get_db():
|
||||
try:
|
||||
db = SessionLocal()
|
||||
yield db
|
||||
finally:
|
||||
db.close()
|
||||
|
||||
|
||||
@router.post("/", response_model=schemas.Role)
|
||||
def save(
|
||||
data: schemas.RoleIn,
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
try:
|
||||
item = Role(data.name)
|
||||
db.add(item)
|
||||
add_permissions(item, data.permissions, db)
|
||||
db.commit()
|
||||
return role_info(item, db)
|
||||
except SQLAlchemyError as e:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=str(e),
|
||||
)
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
|
||||
|
||||
@router.put("/{id_}", response_model=schemas.Role)
|
||||
def update(
|
||||
id_: uuid.UUID,
|
||||
data: schemas.RoleIn,
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
try:
|
||||
item: Role = db.query(Role).filter(Role.id == id_).first()
|
||||
item.name = data.name
|
||||
add_permissions(item, data.permissions, db)
|
||||
db.commit()
|
||||
return role_info(item, db)
|
||||
except SQLAlchemyError as e:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=str(e),
|
||||
)
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
|
||||
|
||||
def add_permissions(group: Role, permissions: List[schemas.PermissionItem], db):
|
||||
for permission in permissions:
|
||||
gp = [p for p in group.roles if p.id == permission.id_]
|
||||
gp = None if len(gp) == 0 else gp[0]
|
||||
if permission.enabled and gp is None:
|
||||
group.roles.append(db.query(Role).filter(Role.id == permission.id_).one())
|
||||
elif not permission.enabled and gp:
|
||||
group.roles.remove(gp)
|
||||
|
||||
|
||||
@router.delete("/{id_}")
|
||||
def delete(
|
||||
id_: uuid.UUID,
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
try:
|
||||
item: Role = db.query(Role).filter(Role.id == id_).first()
|
||||
if item is None:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail="Role not found",
|
||||
)
|
||||
else:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail="Role deletion not implemented",
|
||||
)
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
|
||||
|
||||
@router.get("/")
|
||||
def show_blank(
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
return role_info(None, db)
|
||||
|
||||
|
||||
@router.get("/list", response_model=List[schemas.RoleList])
|
||||
async def show_list(db: Session = Depends(get_db), user: UserToken = Security(get_user, scopes=["users"])):
|
||||
return [
|
||||
{"id": item.id, "name": item.name, "permissions": [p.name for p in sorted(item.roles, key=lambda p: p.name)]}
|
||||
for item in db.query(Role).order_by(Role.name).all()
|
||||
]
|
||||
|
||||
|
||||
@router.get("/{id_}", response_model=schemas.Role)
|
||||
def show_id(
|
||||
id_: uuid.UUID,
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
item = db.query(Role).filter(Role.id == id_).first()
|
||||
return role_info(item, db)
|
||||
|
||||
|
||||
def role_info(item: Optional[Role], db):
|
||||
if item is None:
|
||||
return {
|
||||
"name": "",
|
||||
"permissions": [
|
||||
{"id": p.id, "name": p.name, "enabled": False}
|
||||
for p in db.query(Permission).order_by(Permission.name).all()
|
||||
]
|
||||
}
|
||||
else:
|
||||
return {
|
||||
"id": item.id_,
|
||||
"name": item.name,
|
||||
"permissions": [
|
||||
{
|
||||
"id": item.id,
|
||||
"name": item.name,
|
||||
"enabled": True if item in item.roles else False,
|
||||
}
|
||||
for item in db.query(Role).order_by(Role.name).all()
|
||||
]
|
||||
}
|
||||
+199
-158
@@ -1,179 +1,220 @@
|
||||
import re
|
||||
import traceback
|
||||
import uuid
|
||||
from brewman.models.auth import User, Group
|
||||
from brewman.models.validation_exception import ValidationError
|
||||
from typing import List, Optional
|
||||
|
||||
from fastapi import APIRouter
|
||||
from fastapi import APIRouter, HTTPException, status, Depends, Security
|
||||
from sqlalchemy.exc import SQLAlchemyError
|
||||
from sqlalchemy.orm import Session
|
||||
|
||||
from ...schemas.auth import UserToken
|
||||
from ...core.security import get_current_active_user as get_user
|
||||
from ...db.session import SessionLocal
|
||||
from brewman.models.auth import User, Role
|
||||
import brewman.schemas.auth as schemas
|
||||
|
||||
router = APIRouter()
|
||||
|
||||
|
||||
class UserView(object):
|
||||
def __init__(self, request):
|
||||
self.request = request
|
||||
self.user = request.authenticated_userid
|
||||
self.permissions = None
|
||||
if self.user is not None:
|
||||
self.user = (
|
||||
request.dbsession.query(User)
|
||||
.filter(User.id == request.authenticated_userid)
|
||||
.one()
|
||||
)
|
||||
# Dependency
|
||||
def get_db():
|
||||
try:
|
||||
db = SessionLocal()
|
||||
yield db
|
||||
finally:
|
||||
db.close()
|
||||
|
||||
@router.post("/new") # "Users"
|
||||
def save(self):
|
||||
return self.save_user()
|
||||
|
||||
def save_user(self):
|
||||
user = User(
|
||||
self.request.json_body["name"],
|
||||
self.request.json_body["password"],
|
||||
self.request.json_body["lockedOut"],
|
||||
@router.post("/", response_model=schemas.User)
|
||||
def save(
|
||||
data: schemas.UserIn,
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
try:
|
||||
item = User(
|
||||
name=data.name,
|
||||
password=data.password,
|
||||
locked_out=data.locked_out
|
||||
)
|
||||
self.request.dbsession.add(user)
|
||||
self.add_groups(user, self.request.json_body["groups"])
|
||||
transaction.commit()
|
||||
return self.user_info(user.id)
|
||||
|
||||
@router.put("/{id}") # "Authenticated"
|
||||
def update(self):
|
||||
id_ = self.request.matchdict["id"]
|
||||
p = re.compile(
|
||||
"^[A-Fa-f0-9]{8}-[A-Fa-f0-9]{4}-[A-Fa-f0-9]{4}-[A-Fa-f0-9]{4}-[A-Fa-f0-9]{12}$"
|
||||
db.add(item)
|
||||
add_roles(item, data.roles, db)
|
||||
db.commit()
|
||||
return user_info(item, db, user)
|
||||
except SQLAlchemyError as e:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=str(e),
|
||||
)
|
||||
if p.match(id_):
|
||||
user = (
|
||||
self.request.dbsession.query(User)
|
||||
.filter(User.id == uuid.UUID(id_))
|
||||
.one()
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
|
||||
|
||||
@router.get("/me", response_model=schemas.Role)
|
||||
def show_me(
|
||||
id_: uuid.UUID,
|
||||
db: Session = Depends(get_db),
|
||||
user: User = Depends(get_user),
|
||||
):
|
||||
item = db.query(Role).filter(Role.id_ == id_).first()
|
||||
return user_info(item, db, user)
|
||||
|
||||
|
||||
@router.put("/me", response_model=schemas.User)
|
||||
def update_me(
|
||||
id_: uuid.UUID,
|
||||
data: schemas.UserIn,
|
||||
db: Session = Depends(get_db),
|
||||
user: User = Depends(get_user),
|
||||
):
|
||||
try:
|
||||
item: User = db.query(User).filter(User.id_ == id_).first()
|
||||
if "advanced-delete" in user.permissions:
|
||||
item.name = data.name
|
||||
item.locked_out = data.locked_out
|
||||
add_roles(item, data.roles, db)
|
||||
if data.password and item.password != data.password:
|
||||
item.password = data.password
|
||||
db.commit()
|
||||
return user_info(item, db, user)
|
||||
except SQLAlchemyError as e:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=str(e),
|
||||
)
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
|
||||
|
||||
@router.put("/{id_}", response_model=schemas.User)
|
||||
def update(
|
||||
id_: uuid.UUID,
|
||||
data: schemas.UserIn,
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
try:
|
||||
item: User = db.query(User).filter(User.id_ == id_).first()
|
||||
item.name = data.name
|
||||
if data.password and item.password != data.password:
|
||||
item.password = data.password
|
||||
item.locked_out = data.locked_out
|
||||
add_roles(item, data.roles, db)
|
||||
db.commit()
|
||||
return user_info(item, db, user)
|
||||
except SQLAlchemyError as e:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=str(e),
|
||||
)
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
|
||||
|
||||
def add_roles(user: User, roles: List[schemas.RoleItem], db: Session):
|
||||
for role in roles:
|
||||
ug = [g for g in user.roles if g.id_ == role.id_]
|
||||
ug = None if len(ug) == 0 else ug[0]
|
||||
if role.enabled and ug is None:
|
||||
user.roles.append(db.query(Role).filter(Role.id_ == role.id_).one())
|
||||
elif not role.enabled and ug:
|
||||
user.roles.remove(ug)
|
||||
|
||||
|
||||
@router.delete("/{id_}")
|
||||
def delete(
|
||||
id_: uuid.UUID,
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
try:
|
||||
item: Role = db.query(Role).filter(Role.id_ == id_).first()
|
||||
if item is None:
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail="User not found",
|
||||
)
|
||||
else:
|
||||
user = (
|
||||
self.request.dbsession.query(User).filter(User.name.ilike(id_)).first()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail="User deletion not implemented",
|
||||
)
|
||||
return self.update_user(user)
|
||||
|
||||
def update_user(self, user):
|
||||
if user is None:
|
||||
raise ValidationError("User name / id not found")
|
||||
if self.request.has_permission("Users"):
|
||||
user.name = self.request.json_body["name"]
|
||||
user.locked_out = self.request.json_body["lockedOut"]
|
||||
self.add_groups(user, self.request.json_body["groups"])
|
||||
|
||||
if (
|
||||
self.request.json_body["password"] != ""
|
||||
and self.request.json_body["password"] != user.password
|
||||
):
|
||||
user.password = self.request.json_body["password"]
|
||||
transaction.commit()
|
||||
return self.user_info(user.id)
|
||||
|
||||
@router.delete("/{id}") # "Users"
|
||||
def delete(self):
|
||||
id_ = self.request.matchdict.get("id", None)
|
||||
if id_ is None:
|
||||
response = Response("User is Null")
|
||||
response.status_int = 500
|
||||
return response
|
||||
else:
|
||||
response = Response("User deletion not implemented")
|
||||
response.status_int = 500
|
||||
return response
|
||||
|
||||
@router.get("/{id}") # "Authenticated"
|
||||
def show_id(self):
|
||||
id_ = self.request.matchdict["id"]
|
||||
p = re.compile(
|
||||
"^[A-Za-z0-9]{8}-[A-Za-z0-9]{4}-[A-Za-z0-9]{4}-[A-Za-z0-9]{4}-[A-Za-z0-9]{12}$"
|
||||
except Exception:
|
||||
db.rollback()
|
||||
raise HTTPException(
|
||||
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
||||
detail=traceback.format_exc(),
|
||||
)
|
||||
if p.match(id_):
|
||||
id_ = uuid.UUID(id_)
|
||||
return self.user_info(id_)
|
||||
|
||||
@router.get("/new") # "Users"
|
||||
def show_blank(self):
|
||||
return self.user_info(None)
|
||||
|
||||
@router.get("/") # "Users"
|
||||
async def show_list(l: bool):
|
||||
list_ = self.request.dbsession.query(User).order_by(User.name).all()
|
||||
users = []
|
||||
for item in list_:
|
||||
user = {
|
||||
"name": item.name,
|
||||
"lockedOut": item.locked_out,
|
||||
"groups": [g.name for g in item.groups],
|
||||
}
|
||||
users.append(user)
|
||||
return users
|
||||
@router.get("/")
|
||||
def show_blank(
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
return user_info(None, db, user)
|
||||
|
||||
@router.get("/") # "Authenticated"
|
||||
async def show_name(n: bool):
|
||||
list_ = (
|
||||
self.request.dbsession.query(User)
|
||||
.filter(User.locked_out == False)
|
||||
.order_by(User.name)
|
||||
.all()
|
||||
)
|
||||
users = [{"name": item.name} for item in list_]
|
||||
return users
|
||||
|
||||
def user_info(self, id_):
|
||||
if id_ is None:
|
||||
account = {"name": "", "lockedOut": False, "lockedOut": False, "groups": []}
|
||||
for item in self.request.dbsession.query(Group).order_by(Group.name).all():
|
||||
account["groups"].append(
|
||||
{"id": item.id, "name": item.name, "enabled": False}
|
||||
)
|
||||
return account
|
||||
@router.get("/list", response_model=List[schemas.UserList])
|
||||
async def show_list(db: Session = Depends(get_db), user: UserToken = Security(get_user, scopes=["users"])):
|
||||
return [
|
||||
{"id": item.id_, "name": item.name, "lockedOut": item.locked_out, "roles": [p.name for p in sorted(item.roles, key=lambda p: p.name)]}
|
||||
for item in db.query(User).order_by(User.name).all()
|
||||
]
|
||||
|
||||
if isinstance(id_, uuid.UUID):
|
||||
user = self.request.dbsession.query(User).filter(User.id == id_).one()
|
||||
else:
|
||||
user = (
|
||||
self.request.dbsession.query(User).filter(User.name.ilike(id_)).first()
|
||||
)
|
||||
|
||||
if self.request.has_permission("Users"):
|
||||
account = {
|
||||
"id": user.id,
|
||||
"name": user.name,
|
||||
"password": "",
|
||||
"lockedOut": user.locked_out,
|
||||
"groups": [],
|
||||
}
|
||||
for item in self.request.dbsession.query(Group).order_by(Group.name).all():
|
||||
account["groups"].append(
|
||||
{
|
||||
"id": item.id,
|
||||
"name": item.name,
|
||||
"enabled": True if item in user.groups else False,
|
||||
}
|
||||
)
|
||||
elif self.user.id == user.id:
|
||||
account = {
|
||||
"id": user.id,
|
||||
"name": user.name,
|
||||
"password": "",
|
||||
"lockedOut": user.locked_out,
|
||||
"groups": [],
|
||||
}
|
||||
else:
|
||||
response = Response("User can only update his/her password")
|
||||
response.status_int = 500
|
||||
return response
|
||||
return account
|
||||
@router.get("/active")
|
||||
async def show_active(db: Session = Depends(get_db), user: User = Depends(get_user)):
|
||||
return [
|
||||
{"name": item.name}
|
||||
for item in db.query(User).filter(User.locked_out == False).order_by(User.name)
|
||||
]
|
||||
|
||||
def add_groups(self, user, groups):
|
||||
for group in groups:
|
||||
id_ = uuid.UUID(group["id"])
|
||||
ug = [g for g in user.groups if g.id == id_]
|
||||
ug = None if len(ug) == 0 else ug[0]
|
||||
if group["enabled"] and ug is None:
|
||||
group_object = (
|
||||
self.request.dbsession.query(Group).filter(Group.id == id_).one()
|
||||
)
|
||||
user.groups.append(group_object)
|
||||
elif not group["enabled"] and ug:
|
||||
user.groups.remove(ug)
|
||||
|
||||
@router.get("/{id_}", response_model=schemas.Role)
|
||||
def show_id(
|
||||
id_: uuid.UUID,
|
||||
db: Session = Depends(get_db),
|
||||
user: UserToken = Security(get_user, scopes=["users"]),
|
||||
):
|
||||
item = db.query(Role).filter(Role.id_ == id_).first()
|
||||
return user_info(item, db, user)
|
||||
|
||||
|
||||
def user_info(item: Optional[User], db: Session, user: User):
|
||||
if item is None:
|
||||
return {
|
||||
"name": "", "lockedOut": False, "roles": [
|
||||
{"id": r.id_, "name": r.name, "enabled": False}
|
||||
for r in db.query(Role).order_by(Role.name).all()
|
||||
]
|
||||
}
|
||||
else:
|
||||
return {
|
||||
"id": item.id_,
|
||||
"name": item.name,
|
||||
"password": "",
|
||||
"lockedOut": item.locked_out,
|
||||
"roles": [
|
||||
{
|
||||
"id": r.id_,
|
||||
"name": r.name,
|
||||
"enabled": True if r in r.roles else False,
|
||||
}
|
||||
for r in db.query(Role).order_by(Role.name).all()
|
||||
] if "advanced-delete" in user.permissions else [],
|
||||
}
|
||||
Reference in new issue
Block a user