"""Business logic för tenant-hantering.""" from typing import Optional from uuid import UUID from sqlalchemy.ext.asyncio import AsyncSession from sqlalchemy import select, func from fastapi import HTTPException, status from app.models import Tenant from app.schemas import TenantCreate, TenantUpdate class TenantService: def __init__(self, db: AsyncSession): self.db = db async def get_by_id(self, tenant_id: UUID) -> Optional[Tenant]: result = await self.db.execute(select(Tenant).where(Tenant.id == tenant_id)) return result.scalar_one_or_none() async def get_by_slug(self, slug: str) -> Optional[Tenant]: result = await self.db.execute(select(Tenant).where(Tenant.slug == slug.lower().strip())) return result.scalar_one_or_none() async def list_tenants(self, skip: int = 0, limit: int = 100) -> tuple[list[Tenant], int]: total_result = await self.db.execute(select(func.count()).select_from(Tenant)) total = total_result.scalar_one() result = await self.db.execute( select(Tenant).offset(skip).limit(limit).order_by(Tenant.created_at.desc()) ) return result.scalars().all(), total async def create_tenant(self, data: TenantCreate) -> Tenant: existing = await self.get_by_slug(data.slug) if existing: raise HTTPException( status_code=status.HTTP_409_CONFLICT, detail="Tenant with this slug already exists", ) tenant = Tenant( name=data.name.strip(), slug=data.slug.lower().strip(), description=data.description.strip() if data.description else None, ) self.db.add(tenant) await self.db.commit() await self.db.refresh(tenant) return tenant async def update_tenant(self, tenant_id: UUID, data: TenantUpdate) -> Tenant: tenant = await self.get_by_id(tenant_id) if tenant is None: raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Tenant not found") if data.name is not None: tenant.name = data.name.strip() if data.description is not None: tenant.description = data.description.strip() if data.description else None await self.db.commit() await self.db.refresh(tenant) return tenant async def delete_tenant(self, tenant_id: UUID) -> None: tenant = await self.get_by_id(tenant_id) if tenant is None: raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Tenant not found") await self.db.delete(tenant) await self.db.commit()