from __future__ import annotations from datetime import datetime, timezone from decimal import Decimal from enum import Enum from sqlalchemy import CheckConstraint, DateTime, Enum as SqlEnum, ForeignKey, Numeric from sqlalchemy.orm import Mapped, mapped_column, relationship from app.models.base import Base class OrderStatusEnum(str, Enum): pending = "pending" paid = "paid" class Order(Base): __tablename__ = "orders" __table_args__ = ( CheckConstraint("total_amount >= 0", name="ck_orders_total_amount_non_negative"), ) id: Mapped[int] = mapped_column(primary_key=True) user_id: Mapped[int] = mapped_column(ForeignKey("users.id"), nullable=False, index=True) total_amount: Mapped[Decimal] = mapped_column(Numeric(10, 2), nullable=False) status: Mapped[OrderStatusEnum] = mapped_column( SqlEnum(OrderStatusEnum, native_enum=False), default=OrderStatusEnum.pending, nullable=False, ) created_at: Mapped[datetime] = mapped_column( DateTime(timezone=True), default=lambda: datetime.now(timezone.utc), nullable=False, ) paid_at: Mapped[datetime | None] = mapped_column(DateTime(timezone=True), nullable=True) user = relationship("User", back_populates="orders") items = relationship( "OrderItem", back_populates="order", cascade="all, delete-orphan", lazy="selectin", )