"""SQLAlchemy model for vehicle file attachments.""" import uuid from datetime import datetime from typing import TYPE_CHECKING from sqlalchemy import DateTime, ForeignKey, Integer, String, func from sqlalchemy.dialects.postgresql import UUID from sqlalchemy.orm import Mapped, mapped_column, relationship from app.database import Base if TYPE_CHECKING: from app.models.vehicle import Vehicle class File(Base): """File attachment entity linked to a vehicle.""" __tablename__ = "files" id: Mapped[uuid.UUID] = mapped_column( UUID(as_uuid=True), primary_key=True, default=uuid.uuid4, ) vehicle_id: Mapped[uuid.UUID] = mapped_column( UUID(as_uuid=True), ForeignKey("vehicles.id", ondelete="CASCADE"), nullable=False, index=True, ) original_filename: Mapped[str] = mapped_column(String(255), nullable=False) stored_filename: Mapped[str] = mapped_column(String(255), nullable=False) file_path: Mapped[str] = mapped_column(String(512), nullable=False) mime_type: Mapped[str] = mapped_column(String(100), nullable=False) file_size: Mapped[int] = mapped_column(Integer, nullable=False) thumbnail_path: Mapped[str | None] = mapped_column(String(512), nullable=True) created_at: Mapped[datetime] = mapped_column( DateTime(timezone=True), nullable=False, server_default=func.now(), ) updated_at: Mapped[datetime] = mapped_column( DateTime(timezone=True), nullable=False, server_default=func.now(), onupdate=func.now(), ) vehicle: Mapped["Vehicle"] = relationship("Vehicle", back_populates="files") def __repr__(self) -> str: return f"" def to_dict(self) -> dict: """Serialize file for API responses.""" return { "id": str(self.id), "vehicle_id": str(self.vehicle_id), "original_filename": self.original_filename, "stored_filename": self.stored_filename, "file_path": self.file_path, "mime_type": self.mime_type, "file_size": self.file_size, "thumbnail_path": self.thumbnail_path, "created_at": (self.created_at.isoformat() if self.created_at else None), "updated_at": (self.updated_at.isoformat() if self.updated_at else None), }