from datetime import date, datetime from sqlalchemy import BigInteger, Date, DateTime, ForeignKey, Index, String, Text from sqlalchemy.orm import Mapped, mapped_column from app.models.base import Base, TimestampMixin, SoftDeleteMixin class GeneratedResource(Base, TimestampMixin, SoftDeleteMixin): """统一生成资源账本。 只记录生成成功后的图片/视频资源,不直接绑定具体业务外键, 通过 source_model + source_id 兼容 ChatGenerationTask、GenerationRecord 以及后续新模块。 """ __tablename__ = "generated_resources" id: Mapped[str] = mapped_column(String(32), primary_key=True) user_id: Mapped[str] = mapped_column( String(32), ForeignKey("users.id", ondelete="CASCADE"), index=True, nullable=False ) resource_type: Mapped[str] = mapped_column(String(16), index=True, nullable=False) # image / video resource_url: Mapped[str] = mapped_column(Text, nullable=False) remote_url: Mapped[str | None] = mapped_column(Text, nullable=True) storage_type: Mapped[str] = mapped_column(String(32), default="local", nullable=False) storage_path: Mapped[str | None] = mapped_column(Text, nullable=True) file_name: Mapped[str | None] = mapped_column(String(255), nullable=True,comment="文件名,平台素材名称") file_size_bytes: Mapped[int] = mapped_column(BigInteger, default=0, nullable=False) source_model: Mapped[str] = mapped_column(String(64), index=True, nullable=False) source_model_module: Mapped[str | None] = mapped_column(String(255), nullable=True) source_id: Mapped[str] = mapped_column(String(32), index=True, nullable=False) engine_id: Mapped[str | None] = mapped_column(String(32), nullable=True, index=True) engine_type: Mapped[str | None] = mapped_column(String(32), nullable=True) provider: Mapped[str | None] = mapped_column(String(64), nullable=True) model_name: Mapped[str | None] = mapped_column(String(128), nullable=True) generated_at: Mapped[datetime | None] = mapped_column(DateTime(timezone=True), nullable=True, index=True) resource_month: Mapped[date] = mapped_column(Date, index=True, nullable=False) extra_json: Mapped[str | None] = mapped_column(Text, nullable=True) Index("ix_generated_resources_user_month", GeneratedResource.user_id, GeneratedResource.resource_month) Index("ix_generated_resources_source", GeneratedResource.source_model, GeneratedResource.source_id) Index("ix_generated_resources_active_user", GeneratedResource.user_id, GeneratedResource.deleted_at)