2023-07-19 14:36:23 +03:00
|
|
|
from typing import List, Optional, Union
|
2023-07-11 11:00:06 +03:00
|
|
|
from uuid import UUID
|
|
|
|
|
2023-07-13 18:54:23 +03:00
|
|
|
from auth.auth_bearer import get_current_user
|
|
|
|
from fastapi import Depends, HTTPException, status
|
2023-08-21 15:05:13 +03:00
|
|
|
from models import UserIdentity
|
2023-08-21 13:25:16 +03:00
|
|
|
from repository.brain import get_brain_for_user
|
2023-09-22 12:44:09 +03:00
|
|
|
from repository.brain.get_brain_details import get_brain_details
|
|
|
|
|
2023-08-03 11:37:13 +03:00
|
|
|
from routes.authorizations.types import RoleEnum
|
2023-07-19 14:36:23 +03:00
|
|
|
|
|
|
|
|
|
|
|
def has_brain_authorization(
|
|
|
|
required_roles: Optional[Union[RoleEnum, List[RoleEnum]]] = RoleEnum.Owner
|
|
|
|
):
|
2023-07-13 18:54:23 +03:00
|
|
|
"""
|
2023-07-19 14:36:23 +03:00
|
|
|
Decorator to check if the user has the required role(s) for the brain
|
|
|
|
param: required_roles: The role(s) required to access the brain
|
2023-07-13 18:54:23 +03:00
|
|
|
return: A wrapper function that checks the authorization
|
|
|
|
"""
|
|
|
|
|
2023-08-21 15:05:13 +03:00
|
|
|
async def wrapper(
|
|
|
|
brain_id: UUID, current_user: UserIdentity = Depends(get_current_user)
|
|
|
|
):
|
2023-07-19 14:36:23 +03:00
|
|
|
nonlocal required_roles
|
|
|
|
if isinstance(required_roles, str):
|
|
|
|
required_roles = [required_roles] # Convert single role to a list
|
2023-07-13 18:54:23 +03:00
|
|
|
validate_brain_authorization(
|
2023-07-19 14:36:23 +03:00
|
|
|
brain_id=brain_id, user_id=current_user.id, required_roles=required_roles
|
2023-07-13 18:54:23 +03:00
|
|
|
)
|
2023-07-11 11:00:06 +03:00
|
|
|
|
2023-07-13 18:54:23 +03:00
|
|
|
return wrapper
|
2023-07-11 11:00:06 +03:00
|
|
|
|
|
|
|
|
|
|
|
def validate_brain_authorization(
|
|
|
|
brain_id: UUID,
|
|
|
|
user_id: UUID,
|
2023-07-19 14:36:23 +03:00
|
|
|
required_roles: Optional[Union[RoleEnum, List[RoleEnum]]] = RoleEnum.Owner,
|
2023-07-11 11:00:06 +03:00
|
|
|
):
|
2023-07-13 18:54:23 +03:00
|
|
|
"""
|
2023-07-19 14:36:23 +03:00
|
|
|
Function to check if the user has the required role(s) for the brain
|
2023-07-13 18:54:23 +03:00
|
|
|
param: brain_id: The id of the brain
|
|
|
|
param: user_id: The id of the user
|
2023-07-19 14:36:23 +03:00
|
|
|
param: required_roles: The role(s) required to access the brain
|
2023-07-13 18:54:23 +03:00
|
|
|
return: None
|
|
|
|
"""
|
|
|
|
|
2023-09-22 12:44:09 +03:00
|
|
|
brain = get_brain_details(brain_id)
|
|
|
|
|
|
|
|
if brain and brain.status == "public":
|
|
|
|
return
|
|
|
|
|
2023-07-19 14:36:23 +03:00
|
|
|
if required_roles is None:
|
2023-07-11 11:00:06 +03:00
|
|
|
raise HTTPException(
|
|
|
|
status_code=status.HTTP_400_BAD_REQUEST,
|
|
|
|
detail="Missing required role",
|
|
|
|
)
|
|
|
|
|
2023-08-03 11:37:13 +03:00
|
|
|
user_brain = get_brain_for_user(user_id, brain_id)
|
2023-07-11 11:00:06 +03:00
|
|
|
if user_brain is None:
|
|
|
|
raise HTTPException(
|
2023-09-26 11:35:52 +03:00
|
|
|
status_code=status.HTTP_403_FORBIDDEN,
|
2023-07-11 11:00:06 +03:00
|
|
|
detail="You don't have permission for this brain",
|
|
|
|
)
|
|
|
|
|
2023-07-19 14:36:23 +03:00
|
|
|
# Convert single role to a list to handle both cases
|
|
|
|
if isinstance(required_roles, str):
|
|
|
|
required_roles = [required_roles]
|
|
|
|
|
|
|
|
# Check if the user has at least one of the required roles
|
2023-08-03 11:37:13 +03:00
|
|
|
if user_brain.rights not in required_roles:
|
2023-07-11 11:00:06 +03:00
|
|
|
raise HTTPException(
|
|
|
|
status_code=status.HTTP_403_FORBIDDEN,
|
2023-07-19 14:36:23 +03:00
|
|
|
detail="You don't have the required role(s) for this brain",
|
2023-07-11 11:00:06 +03:00
|
|
|
)
|