"""global_digests + digest_topics 테이블 ORM (Phase 4)"""

from datetime import date, datetime

from sqlalchemy import (
    BigInteger,
    Boolean,
    Date,
    DateTime,
    Float,
    ForeignKey,
    Integer,
    String,
    Text,
)
from sqlalchemy.dialects.postgresql import JSONB
from sqlalchemy.orm import Mapped, mapped_column, relationship

from core.database import Base


class GlobalDigest(Base):
    """하루 단위 digest run 메타데이터"""

    __tablename__ = "global_digests"

    id: Mapped[int] = mapped_column(BigInteger, primary_key=True)
    digest_date: Mapped[date] = mapped_column(Date, nullable=False, unique=True)
    window_start: Mapped[datetime] = mapped_column(DateTime(timezone=True), nullable=False)
    window_end: Mapped[datetime] = mapped_column(DateTime(timezone=True), nullable=False)
    decay_lambda: Mapped[float] = mapped_column(Float, nullable=False)

    total_articles: Mapped[int] = mapped_column(Integer, nullable=False, default=0)
    total_countries: Mapped[int] = mapped_column(Integer, nullable=False, default=0)
    total_topics: Mapped[int] = mapped_column(Integer, nullable=False, default=0)

    generation_ms: Mapped[int | None] = mapped_column(Integer)
    llm_calls: Mapped[int] = mapped_column(Integer, nullable=False, default=0)
    llm_failures: Mapped[int] = mapped_column(Integer, nullable=False, default=0)
    status: Mapped[str] = mapped_column(String(20), nullable=False, default="success")

    created_at: Mapped[datetime] = mapped_column(
        DateTime(timezone=True), nullable=False, default=datetime.now
    )

    topics: Mapped[list["DigestTopic"]] = relationship(
        back_populates="digest",
        cascade="all, delete-orphan",
        order_by="DigestTopic.country, DigestTopic.topic_rank",
    )


class DigestTopic(Base):
    """country × topic 단위 cluster 결과"""

    __tablename__ = "digest_topics"

    id: Mapped[int] = mapped_column(BigInteger, primary_key=True)
    digest_id: Mapped[int] = mapped_column(
        BigInteger,
        ForeignKey("global_digests.id", ondelete="CASCADE"),
        nullable=False,
    )

    country: Mapped[str] = mapped_column(String(10), nullable=False)
    topic_rank: Mapped[int] = mapped_column(Integer, nullable=False)

    topic_label: Mapped[str] = mapped_column(Text, nullable=False)
    summary: Mapped[str] = mapped_column(Text, nullable=False)

    article_ids: Mapped[list] = mapped_column(JSONB, nullable=False)
    article_count: Mapped[int] = mapped_column(Integer, nullable=False)

    importance_score: Mapped[float] = mapped_column(Float, nullable=False)
    raw_weight_sum: Mapped[float] = mapped_column(Float, nullable=False)

    centroid_sample: Mapped[dict | None] = mapped_column(JSONB)
    llm_model: Mapped[str | None] = mapped_column(String(100))
    llm_fallback_used: Mapped[bool] = mapped_column(
        Boolean, nullable=False, default=False
    )

    created_at: Mapped[datetime] = mapped_column(
        DateTime(timezone=True), nullable=False, default=datetime.now
    )

    digest: Mapped["GlobalDigest"] = relationship(back_populates="topics")
