"""Схемы API первичных файлов (spec primary-files, documents-api; design D-4, D-11). `UploadResult` — ответ загрузки (частичный успех: принятые и отклонённые файлы). `FileOut`/`JobBrief`/`DocumentBrief` — карточка файла для чтения (Task 9 Среза 2c): статус файла, текущее задание с причиной ошибки и предупреждениями, документы файла. """ import datetime import uuid from pydantic import BaseModel, ConfigDict from src.models.enums import ( DocumentCheckResult, DocumentStatus, DocumentType, FileStatus, FileType, PeriodQuarter, RecognitionStatus, ) class AcceptedOut(BaseModel): """Принятый файл: `stored_file.id`, `recognition_job.id` и очищенное имя.""" file_id: uuid.UUID job_id: uuid.UUID name: str class RejectedOut(BaseModel): """Отклонённый файл: имя, код (`UNSUPPORTED_FILE`, `FILE_TOO_LARGE`, `DUPLICATE_FILE`, `STORAGE_UNAVAILABLE`), пояснение; `file_id` — существующий файл при `DUPLICATE_FILE`.""" name: str code: str message: str file_id: uuid.UUID | None = None class UploadResult(BaseModel): """Ответ `POST /legal-entities/{id}/files`: 201, если принят хотя бы один файл, иначе 422.""" accepted: list[AcceptedOut] rejected: list[RejectedOut] class JobBrief(BaseModel): """Текущее задание распознавания файла: статус, причина ошибки сервиса (`error_code`/`error_message`) и маппинга (`mapping_error` — `metrics.mapping_error`: файл в `ERROR` после маппинга при задании `done`), предупреждения сервиса (`metrics.warnings`) и маппинга (`metrics.mapping_warnings`).""" id: uuid.UUID status: RecognitionStatus error_code: str | None error_message: str | None mapping_error: str | None warnings: list[str] mapping_warnings: list[str] finished_at: datetime.datetime | None class DocumentBrief(BaseModel): """Документ файла в карточке файла.""" model_config = ConfigDict(from_attributes=True) id: uuid.UUID document_type: DocumentType osv_account_code: str | None period_year: int | None period_quarter: PeriodQuarter | None is_cumulative: bool | None status: DocumentStatus period_check: DocumentCheckResult | None counterparty_check: DocumentCheckResult | None locator: str | None class FileOut(BaseModel): """Карточка файла: поля `stored_file`, текущее задание и документы.""" id: uuid.UUID legal_entity_id: uuid.UUID original_name: str | None file_type: FileType status: FileStatus version_no: int size_bytes: int | None content_hash: str | None uploaded_at: datetime.datetime | None uploaded_by: uuid.UUID | None superseded_by_file_id: uuid.UUID | None job: JobBrief | None documents: list[DocumentBrief]