from datetime import datetime, date from typing import TYPE_CHECKING from sqlalchemy import ForeignKey, Table, Column from sqlalchemy.orm import Mapped, mapped_column, relationship from models import BaseModel if TYPE_CHECKING: from models import User expenses_expense_tags = Table( 'expenses_expense_tags', BaseModel.metadata, Column('expense_id', ForeignKey('expenses.id', ondelete='CASCADE'), primary_key=True), Column('expense_tag_id', ForeignKey('expense_tags.id'), primary_key=True), ) class Expense(BaseModel): __tablename__ = 'expenses' 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() 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["ExpenseTag"]] = relationship( secondary=expenses_expense_tags, lazy='selectin', back_populates='expenses', cascade='all, delete', ) class ExpenseTag(BaseModel): __tablename__ = 'expense_tags' id: Mapped[int] = mapped_column(primary_key=True) name: Mapped[str] = mapped_column(unique=True) expenses: Mapped[list["Expense"]] = relationship( secondary=expenses_expense_tags, lazy='selectin', back_populates='tags', )