from datetime import datetime from enum import Enum as PyEnum from typing import Optional from uuid import UUID from sqlalchemy import Column from sqlmodel import Enum, Field, Relationship, SQLModel, UniqueConstraint class UserRole(PyEnum): OWNER = "owner" CUSTOMER = "customer" EMPLOYEE = "employee" MANAGER = "manager" ADMIN = "admin" class User(SQLModel, table=True): __tablename__ = "user" __table_args__ = ( UniqueConstraint("email", "shop_id", name="uix_email_shop_id"), ) id: int = Field(primary_key=True) uuid: UUID = Field(nullable=False, unique=True) user_role: UserRole = Field(sa_column=Column(Enum(UserRole), nullable=False)) shop_id: Optional[int] = Field(foreign_key="shop.id") status: UserRole = Field(sa_column=Column(Enum(UserRole))) username: str = Field(max_length=64, nullable=False, unique=True) email: str = Field(max_length=128, nullable=False, unique=True) password: str = Field(max_length=60, nullable=False) first_name: Optional[str] = Field(max_length=64) last_name: Optional[str] = Field(max_length=64) phone_number: str = Field(max_length=16, nullable=False) profile_picture: Optional[str] = Field(max_length=100) created_at: datetime = Field(default_factory=datetime.utcnow, nullable=False) updated_at: datetime = Field(default_factory=datetime.utcnow, nullable=False) last_login: Optional[datetime] = Field(default_factory=datetime.utcnow) owned_shop: "Shop" = Relationship( back_populates="owner", sa_relationship_kwargs={"foreign_keys": "[Shop.owner_id]"} ) registered_shop: Optional["Shop"] = Relationship( back_populates="registered_users", sa_relationship_kwargs={"foreign_keys": "[User.shop_id]"} ) preferences: Optional["UserPreferences"] = Relationship(back_populates="user") statistics: Optional["UserStatistics"] = Relationship(back_populates="user") class UserPreferences(SQLModel, table=True): __tablename__ = "user_preferences" user_id: int = Field(foreign_key="user.id", primary_key=True) user: Optional["User"] = Relationship(back_populates="preferences") class UserStatistics(SQLModel, table=True): __tablename__ = "user_statistics" user_id: int = Field(foreign_key="user.id", primary_key=True) total_spend: Optional[float] = Field(default=None) user: Optional["User"] = Relationship(back_populates="statistics") __all__ = ["User", "UserPreferences", "UserRole"]