120 lines
5.3 KiB
Python
120 lines
5.3 KiB
Python
from __future__ import annotations
|
|
|
|
from typing import Optional
|
|
|
|
from sqlalchemy import select, and_, text
|
|
from sqlalchemy.orm import Session
|
|
|
|
from adapters.db.models.business_permission import BusinessPermission
|
|
from adapters.db.repositories.base_repo import BaseRepository
|
|
|
|
|
|
class BusinessPermissionRepository(BaseRepository[BusinessPermission]):
|
|
def __init__(self, db: Session) -> None:
|
|
super().__init__(db, BusinessPermission)
|
|
|
|
def get_by_user_and_business(self, user_id: int, business_id: int) -> Optional[BusinessPermission]:
|
|
"""دریافت دسترسیهای کاربر برای کسب و کار خاص"""
|
|
stmt = select(BusinessPermission).where(
|
|
and_(
|
|
BusinessPermission.user_id == user_id,
|
|
BusinessPermission.business_id == business_id
|
|
)
|
|
)
|
|
return self.db.execute(stmt).scalars().first()
|
|
|
|
def create_or_update(self, user_id: int, business_id: int, permissions: dict) -> BusinessPermission:
|
|
"""ایجاد یا بهروزرسانی دسترسیهای کاربر برای کسب و کار"""
|
|
existing = self.get_by_user_and_business(user_id, business_id)
|
|
|
|
if existing:
|
|
# Preserve existing permissions and enforce join=True
|
|
existing_permissions = existing.business_permissions or {}
|
|
|
|
# Always ignore incoming 'join' field from clients
|
|
incoming_permissions = dict(permissions or {})
|
|
if 'join' in incoming_permissions:
|
|
incoming_permissions.pop('join', None)
|
|
|
|
# Merge and enforce join flag
|
|
merged_permissions = dict(existing_permissions)
|
|
merged_permissions.update(incoming_permissions)
|
|
merged_permissions['join'] = True
|
|
|
|
existing.business_permissions = merged_permissions
|
|
self.db.commit()
|
|
self.db.refresh(existing)
|
|
return existing
|
|
else:
|
|
# On creation, ensure join=True exists by default
|
|
base_permissions = {'join': True}
|
|
incoming_permissions = dict(permissions or {})
|
|
if 'join' in incoming_permissions:
|
|
incoming_permissions.pop('join', None)
|
|
|
|
new_permission = BusinessPermission(
|
|
user_id=user_id,
|
|
business_id=business_id,
|
|
business_permissions={**base_permissions, **incoming_permissions}
|
|
)
|
|
self.db.add(new_permission)
|
|
self.db.commit()
|
|
self.db.refresh(new_permission)
|
|
return new_permission
|
|
|
|
def delete_by_user_and_business(self, user_id: int, business_id: int) -> bool:
|
|
"""حذف دسترسیهای کاربر برای کسب و کار"""
|
|
existing = self.get_by_user_and_business(user_id, business_id)
|
|
if existing:
|
|
self.db.delete(existing)
|
|
self.db.commit()
|
|
return True
|
|
return False
|
|
|
|
def get_user_businesses(self, user_id: int) -> list[BusinessPermission]:
|
|
"""دریافت تمام کسب و کارهایی که کاربر دسترسی دارد"""
|
|
stmt = select(BusinessPermission).where(BusinessPermission.user_id == user_id)
|
|
return self.db.execute(stmt).scalars().all()
|
|
|
|
def get_business_users(self, business_id: int) -> list[BusinessPermission]:
|
|
"""دریافت تمام کاربرانی که دسترسی به کسب و کار دارند"""
|
|
stmt = select(BusinessPermission).where(BusinessPermission.business_id == business_id)
|
|
return self.db.execute(stmt).scalars().all()
|
|
|
|
def get_user_member_businesses(self, user_id: int) -> list[BusinessPermission]:
|
|
"""دریافت تمام کسب و کارهایی که کاربر عضو آنها است (دسترسی join)"""
|
|
# ابتدا تمام دسترسیهای کاربر را دریافت میکنیم
|
|
all_permissions = self.get_user_businesses(user_id)
|
|
|
|
# سپس فیلتر میکنیم
|
|
member_permissions = []
|
|
for perm in all_permissions:
|
|
# Normalize legacy/non-dict JSON values to dict before access
|
|
raw = perm.business_permissions
|
|
normalized = {}
|
|
if isinstance(raw, dict):
|
|
normalized = raw
|
|
elif isinstance(raw, list):
|
|
# If legacy stored as list, try to coerce to dict if it looks like key-value pairs
|
|
try:
|
|
# e.g., [["join", true], ["sales", {"read": true}]] or [{"join": true}, ...]
|
|
if all(isinstance(item, list) and len(item) == 2 for item in raw):
|
|
normalized = {k: v for k, v in raw if isinstance(k, str)}
|
|
elif all(isinstance(item, dict) for item in raw):
|
|
# Merge list of dicts
|
|
merged: dict = {}
|
|
for item in raw:
|
|
merged.update({k: v for k, v in item.items()})
|
|
normalized = merged
|
|
except Exception:
|
|
normalized = {}
|
|
elif raw is None:
|
|
normalized = {}
|
|
else:
|
|
# Unsupported type, skip safely
|
|
normalized = {}
|
|
|
|
if normalized.get('join') == True:
|
|
member_permissions.append(perm)
|
|
|
|
return member_permissions |