Initial commit

This commit is contained in:
belviskhoremk
2026-03-06 22:57:58 +00:00
commit c4d836a0f9
60 changed files with 5423 additions and 0 deletions

View File

@@ -0,0 +1,134 @@
"""Agency CRUD service."""
from __future__ import annotations
from datetime import datetime, timezone
from typing import Optional
from app.core.exceptions import ForbiddenException, NotFoundException
from app.core.supabase import get_supabase_admin
class AgencyService:
def __init__(self):
self.db = get_supabase_admin()
def get_agency(self, agency_id: str) -> dict:
result = self.db.table("agencies").select("*").eq("id", agency_id).execute()
if not result.data:
raise NotFoundException("Agency not found")
return result.data[0]
def get_agency_by_user(self, user_id: str) -> dict:
result = self.db.table("agencies").select("*").eq("user_id", user_id).execute()
if not result.data:
raise NotFoundException("Agency not found for this user")
return result.data[0]
def create_agency(self, user_id: str, data: dict) -> dict:
now = datetime.now(timezone.utc).isoformat()
agency_data = {
"user_id": user_id,
**data,
"verified": False,
"created_at": now,
"updated_at": now,
}
result = self.db.table("agencies").insert(agency_data).execute()
if not result.data:
raise Exception("Failed to create agency")
return result.data[0]
def update_agency(self, agency_id: str, user_id: str, user_role: str, data: dict) -> dict:
# Check ownership or admin
agency = self.get_agency(agency_id)
if user_role != "admin" and agency["user_id"] != user_id:
raise ForbiddenException("Not authorized to update this agency")
update_data = {k: v for k, v in data.items() if v is not None}
if not update_data:
return agency
update_data["updated_at"] = datetime.now(timezone.utc).isoformat()
result = (
self.db.table("agencies")
.update(update_data)
.eq("id", agency_id)
.execute()
)
if not result.data:
raise NotFoundException("Agency not found")
return result.data[0]
def list_agencies(
self,
page: int = 1,
page_size: int = 20,
verified_only: bool = False,
) -> dict:
query = self.db.table("agencies").select("*", count="exact")
if verified_only:
query = query.eq("verified", True)
offset = (page - 1) * page_size
result = (
query.order("created_at", desc=True)
.range(offset, offset + page_size - 1)
.execute()
)
return {
"agencies": result.data,
"total": result.count or 0,
"page": page,
"page_size": page_size,
}
def verify_agency(self, agency_id: str, requester_role: str) -> dict:
if requester_role != "admin":
raise ForbiddenException("Only admins can verify agencies")
now = datetime.now(timezone.utc).isoformat()
result = (
self.db.table("agencies")
.update({"verified": True, "updated_at": now})
.eq("id", agency_id)
.execute()
)
if not result.data:
raise NotFoundException("Agency not found")
# Also verify the associated user
agency = result.data[0]
self.db.table("users").update(
{"verified": True, "updated_at": now}
).eq("id", agency["user_id"]).execute()
return result.data[0]
def revoke_verification(self, agency_id: str, requester_role: str) -> dict:
if requester_role != "admin":
raise ForbiddenException("Only admins can revoke agency verification")
now = datetime.now(timezone.utc).isoformat()
result = (
self.db.table("agencies")
.update({"verified": False, "updated_at": now})
.eq("id", agency_id)
.execute()
)
if not result.data:
raise NotFoundException("Agency not found")
return result.data[0]
def delete_agency(self, agency_id: str) -> dict:
# Fetch first to get user_id for cascade deletion
agency_result = self.db.table("agencies").select("user_id").eq("id", agency_id).execute()
if not agency_result.data:
raise NotFoundException("Agency not found")
user_id = agency_result.data[0]["user_id"]
# Delete messages belonging to this agency (avoids orphaned rows)
self.db.table("messages").delete().eq("agency_id", agency_id).execute()
self.db.table("agencies").delete().eq("id", agency_id).execute()
# Delete the associated user account to avoid orphaned records
self.db.table("users").delete().eq("id", user_id).execute()
return {"message": "Agency deleted"}