import arrow from sqlalchemy import Column, Integer, String, Float, ForeignKey, UUID, TIMESTAMP, Boolean, SmallInteger, Numeric, func, text from sqlalchemy.orm import relationship from sqlalchemy.orm import Mapped, mapped_column from sqlalchemy_mixins.serialize import SerializeMixin from sqlalchemy_mixins.repr import ReprMixin from sqlalchemy_mixins.smartquery import SmartQueryMixin from sqlalchemy_mixins.activerecord import ActiveRecordMixin from api_controllers.postgres.engine import get_db, Base class BasicMixin( Base, ActiveRecordMixin, SerializeMixin, ReprMixin, SmartQueryMixin, ): __abstract__ = True __repr__ = ReprMixin.__repr__ @classmethod def new_session(cls): """Get database session.""" return get_db() class CrudMixin(BasicMixin): """ Base mixin providing CRUD operations and common fields for PostgreSQL models. Features: - Automatic timestamps (created_at, updated_at) - Soft delete capability - User tracking (created_by, updated_by) - Data serialization - Multi-language support """ __abstract__ = True # Primary and reference fields id: Mapped[int] = mapped_column(Integer, primary_key=True) uu_id: Mapped[str] = mapped_column( UUID, server_default=text("gen_random_uuid()"), index=True, unique=True, comment="Unique identifier UUID", ) # Common timestamp fields for all models expiry_starts: Mapped[TIMESTAMP] = mapped_column( TIMESTAMP(timezone=True), server_default=func.now(), comment="Record validity start timestamp", ) expiry_ends: Mapped[TIMESTAMP] = mapped_column( TIMESTAMP(timezone=True), default=str(arrow.get("2099-12-31")), server_default=func.now(), comment="Record validity end timestamp", ) # Timestamps created_at: Mapped[TIMESTAMP] = mapped_column( TIMESTAMP(timezone=True), server_default=func.now(), nullable=False, index=True, comment="Record creation timestamp", ) updated_at: Mapped[TIMESTAMP] = mapped_column( TIMESTAMP(timezone=True), server_default=func.now(), onupdate=func.now(), nullable=False, index=True, comment="Last update timestamp", ) class CrudCollection(CrudMixin): """ Full-featured model class with all common fields. Includes: - UUID and reference ID - Timestamps - User tracking - Confirmation status - Soft delete - Notification flags """ __abstract__ = True __repr__ = ReprMixin.__repr__ # Outer reference fields ref_id: Mapped[str] = mapped_column( String(100), nullable=True, index=True, comment="External reference ID" ) replication_id: Mapped[int] = mapped_column( SmallInteger, server_default="0", comment="Replication identifier" ) # Cryptographic and user tracking cryp_uu_id: Mapped[str] = mapped_column( String, nullable=True, index=True, comment="Cryptographic UUID" ) # Token fields of modification created_credentials_token: Mapped[str] = mapped_column( String, nullable=True, comment="Created Credentials token" ) updated_credentials_token: Mapped[str] = mapped_column( String, nullable=True, comment="Updated Credentials token" ) confirmed_credentials_token: Mapped[str] = mapped_column( String, nullable=True, comment="Confirmed Credentials token" ) # Status flags is_confirmed: Mapped[bool] = mapped_column( Boolean, server_default="0", comment="Record confirmation status" ) deleted: Mapped[bool] = mapped_column( Boolean, server_default="0", comment="Soft delete flag" ) active: Mapped[bool] = mapped_column( Boolean, server_default="1", comment="Record active status" ) is_notification_send: Mapped[bool] = mapped_column( Boolean, server_default="0", comment="Notification sent flag" ) is_email_send: Mapped[bool] = mapped_column( Boolean, server_default="0", comment="Email sent flag" )