from uuid import UUID from fastapi import APIRouter, Depends from pydantic import BaseModel from app.api.deps import AsyncSession, CurrentUser, get_current_user, get_db, require_tenant from app.schemas.common import ( ContactCreate, ContactOut, ContactSourceCreate, ContactSourceOut, ) from app.services.contact_service import ContactService router = APIRouter() class CSVImportBody(BaseModel): csv_text: str class ResolveBody(BaseModel): source_id: UUID | None = None query: dict | None = None channel: str = "sms" @router.get("/manual", response_model=list[ContactOut]) async def list_manual_contacts( tenant_id: UUID = Depends(require_tenant), session: AsyncSession = Depends(get_db), _: CurrentUser = Depends(get_current_user), ): return await ContactService(session).list_manual(tenant_id) @router.post("/manual", response_model=ContactOut, status_code=201) async def create_manual_contact( body: ContactCreate, tenant_id: UUID = Depends(require_tenant), session: AsyncSession = Depends(get_db), user: CurrentUser = Depends(get_current_user), ): return await ContactService(session).create_manual( tenant_id, body.model_dump(), actor_id=user.user_id ) @router.post("/manual/import-csv", response_model=list[ContactOut], status_code=201) async def import_csv( body: CSVImportBody, tenant_id: UUID = Depends(require_tenant), session: AsyncSession = Depends(get_db), user: CurrentUser = Depends(get_current_user), ): return await ContactService(session).import_csv( tenant_id, body.csv_text, actor_id=user.user_id ) @router.get("/sources", response_model=list[ContactSourceOut]) async def list_sources( tenant_id: UUID = Depends(require_tenant), session: AsyncSession = Depends(get_db), _: CurrentUser = Depends(get_current_user), ): return await ContactService(session).list_sources(tenant_id) @router.post("/sources", response_model=ContactSourceOut, status_code=201) async def create_source( body: ContactSourceCreate, tenant_id: UUID = Depends(require_tenant), session: AsyncSession = Depends(get_db), user: CurrentUser = Depends(get_current_user), ): return await ContactService(session).create_source( tenant_id, body.model_dump(), actor_id=user.user_id ) @router.post("/resolve") async def resolve_contacts( body: ResolveBody, tenant_id: UUID = Depends(require_tenant), session: AsyncSession = Depends(get_db), _: CurrentUser = Depends(get_current_user), ): resolved = await ContactService(session).resolve( tenant_id, source_id=body.source_id, query=body.query, channel=body.channel, ) return [ { "address": r.address, "display_name": r.display_name, "external_ref": r.external_ref, "source_type": r.source_type, } for r in resolved ]