""" Re-export dei modelli SQLAlchemy dal backend. Il worker usa gli stessi modelli ORM del backend per leggere/scrivere nel DB. Importa da una base comune tramite il package condiviso. Nota: i modelli sono definiti nel backend. Il worker li ridefinisce qui come classi identiche (stessa struttura) per non creare dipendenza circolare. Tuttavia, poiché i due container condividono lo stesso DB PostgreSQL, utilizziamo i modelli del backend ricopiando solo le parti necessarie. """ # I modelli completi sono già in backend/app/models/. # Il worker li importa dalla propria copia locale per evitare # una dipendenza del package worker → backend. # In un monorepo reale si userebbe un shared/ package. import uuid from datetime import datetime from sqlalchemy import ( ARRAY, BigInteger, Boolean, DateTime, Enum, ForeignKey, Integer, String, Text, func, ) from sqlalchemy.dialects.postgresql import UUID from sqlalchemy.orm import DeclarativeBase, Mapped, mapped_column class Base(DeclarativeBase): pass MailboxStatus = Enum( "active", "paused", "error", "deleted", name="mailbox_status", create_type=False, ) PecDirection = Enum("inbound", "outbound", name="pec_direction", create_type=False) PecState = Enum( "draft", "queued", "sent", "accepted", "delivered", "anomaly", "failed", "received", name="pec_state", create_type=False, ) PecMsgType = Enum( "posta_certificata", "accettazione", "non_accettazione", "presa_in_carico", "avvenuta_consegna", "mancata_consegna", "errore_consegna", "preavviso_mancata_consegna", "rilevazione_virus", "unknown", name="pec_msg_type", create_type=False, ) class Mailbox(Base): __tablename__ = "mailboxes" id: Mapped[uuid.UUID] = mapped_column(UUID(as_uuid=True), primary_key=True) tenant_id: Mapped[uuid.UUID] = mapped_column(UUID(as_uuid=True), nullable=False) email_address: Mapped[str] = mapped_column(String(255), nullable=False) display_name: Mapped[str | None] = mapped_column(String(255), nullable=True) provider: Mapped[str | None] = mapped_column(String(100), nullable=True) imap_host_enc: Mapped[str] = mapped_column(Text, nullable=False) imap_port_enc: Mapped[str] = mapped_column(Text, nullable=False) imap_user_enc: Mapped[str] = mapped_column(Text, nullable=False) imap_pass_enc: Mapped[str] = mapped_column(Text, nullable=False) imap_use_ssl: Mapped[bool] = mapped_column(Boolean, nullable=False, default=True) smtp_host_enc: Mapped[str] = mapped_column(Text, nullable=False) smtp_port_enc: Mapped[str] = mapped_column(Text, nullable=False) smtp_user_enc: Mapped[str] = mapped_column(Text, nullable=False) smtp_pass_enc: Mapped[str] = mapped_column(Text, nullable=False) smtp_use_tls: Mapped[bool] = mapped_column(Boolean, nullable=False, default=True) status: Mapped[str] = mapped_column(MailboxStatus, nullable=False, default="active") last_sync_at: Mapped[datetime | None] = mapped_column(DateTime(timezone=True), nullable=True) last_sync_uid: Mapped[int | None] = mapped_column(BigInteger, nullable=True) sync_error_msg: Mapped[str | None] = mapped_column(Text, nullable=True) sync_error_count: Mapped[int] = mapped_column(Integer, nullable=False, default=0) created_by: Mapped[uuid.UUID | None] = mapped_column(UUID(as_uuid=True), nullable=True) created_at: Mapped[datetime] = mapped_column(DateTime(timezone=True), server_default=func.now()) updated_at: Mapped[datetime] = mapped_column( DateTime(timezone=True), server_default=func.now(), onupdate=func.now() ) class Message(Base): __tablename__ = "messages" id: Mapped[uuid.UUID] = mapped_column( UUID(as_uuid=True), primary_key=True, default=uuid.uuid4 ) tenant_id: Mapped[uuid.UUID] = mapped_column(UUID(as_uuid=True), nullable=False) mailbox_id: Mapped[uuid.UUID] = mapped_column(UUID(as_uuid=True), nullable=False) message_id_header: Mapped[str | None] = mapped_column(Text, nullable=True) imap_uid: Mapped[int | None] = mapped_column(BigInteger, nullable=True) imap_folder: Mapped[str] = mapped_column(String(255), nullable=False, default="INBOX") direction: Mapped[str] = mapped_column(PecDirection, nullable=False) pec_type: Mapped[str] = mapped_column(PecMsgType, nullable=False, default="posta_certificata") state: Mapped[str] = mapped_column(PecState, nullable=False) subject: Mapped[str | None] = mapped_column(Text, nullable=True) from_address: Mapped[str | None] = mapped_column(String(255), nullable=True) to_addresses: Mapped[list[str] | None] = mapped_column(ARRAY(Text), nullable=True) cc_addresses: Mapped[list[str] | None] = mapped_column(ARRAY(Text), nullable=True) sent_at: Mapped[datetime | None] = mapped_column(DateTime(timezone=True), nullable=True) received_at: Mapped[datetime | None] = mapped_column(DateTime(timezone=True), nullable=True) size_bytes: Mapped[int | None] = mapped_column(BigInteger, nullable=True) body_text: Mapped[str | None] = mapped_column(Text, nullable=True) body_html: Mapped[str | None] = mapped_column(Text, nullable=True) has_attachments: Mapped[bool] = mapped_column(Boolean, nullable=False, default=False) parent_message_id: Mapped[uuid.UUID | None] = mapped_column( UUID(as_uuid=True), ForeignKey("messages.id"), nullable=True ) is_read: Mapped[bool] = mapped_column(Boolean, nullable=False, default=False) is_starred: Mapped[bool] = mapped_column(Boolean, nullable=False, default=False) is_archived: Mapped[bool] = mapped_column(Boolean, nullable=False, default=False) archived_at: Mapped[datetime | None] = mapped_column(DateTime(timezone=True), nullable=True) raw_eml_path: Mapped[str | None] = mapped_column(Text, nullable=True) created_at: Mapped[datetime] = mapped_column(DateTime(timezone=True), server_default=func.now()) updated_at: Mapped[datetime] = mapped_column( DateTime(timezone=True), server_default=func.now(), onupdate=func.now() )