from datetime import datetime, date from typing import TYPE_CHECKING from sqlalchemy import ForeignKey, Table, Column, text from sqlalchemy.orm import Mapped, mapped_column, relationship from models import BaseModel if TYPE_CHECKING: from models import User transactions_transaction_tags = Table( 'transactions_transaction_tags', BaseModel.metadata, Column('transaction_id', ForeignKey('transactions.id', ondelete='CASCADE'), primary_key=True), Column('transaction_tag_id', ForeignKey('transaction_tags.id'), primary_key=True), ) class Transaction(BaseModel): __tablename__ = 'transactions' id: Mapped[int] = mapped_column(primary_key=True) created_at: Mapped[datetime] = mapped_column(nullable=False) spent_date: Mapped[date] = mapped_column(nullable=False) name: Mapped[str] = mapped_column() comment: Mapped[str] = mapped_column() amount: Mapped[float] = mapped_column() is_income: Mapped[bool] = mapped_column(server_default=text("false"), nullable=False) created_by_user_id: Mapped[int] = mapped_column(ForeignKey("users.id"), nullable=False) created_by_user: Mapped["User"] = relationship(foreign_keys=[created_by_user_id], lazy="selectin") tags: Mapped[list["TransactionTag"]] = relationship( secondary=transactions_transaction_tags, lazy='selectin', back_populates='transactions', cascade='all, delete', ) class TransactionTag(BaseModel): __tablename__ = 'transaction_tags' id: Mapped[int] = mapped_column(primary_key=True) name: Mapped[str] = mapped_column(index=True) is_income: Mapped[bool] = mapped_column(server_default=text("false"), nullable=False) transactions: Mapped[list["Transaction"]] = relationship( secondary=transactions_transaction_tags, lazy='selectin', back_populates='tags', )