"""启动时补齐新增列（已有库无需手工迁移）。"""

from sqlalchemy import inspect, text

from database import engine


def run_migrations() -> None:
    insp = inspect(engine)
    with engine.begin() as conn:
        if insp.has_table("words"):
            cols = {c["name"] for c in insp.get_columns("words")}
            if "total_train_seconds" not in cols:
                conn.execute(
                    text(
                        "ALTER TABLE words ADD COLUMN total_train_seconds "
                        "INTEGER NOT NULL DEFAULT 0"
                    )
                )
            if "train_count" not in cols:
                conn.execute(
                    text("ALTER TABLE words ADD COLUMN train_count INTEGER NOT NULL DEFAULT 0")
                )

        if insp.has_table("quiz_records"):
            cols = {c["name"] for c in insp.get_columns("quiz_records")}
            if "duration_seconds" not in cols:
                conn.execute(
                    text(
                        "ALTER TABLE quiz_records ADD COLUMN duration_seconds "
                        "INTEGER NOT NULL DEFAULT 0"
                    )
                )

        if insp.has_table("user_settings"):
            cols = {c["name"] for c in insp.get_columns("user_settings")}
            if "active_book_id" not in cols:
                conn.execute(text("ALTER TABLE user_settings ADD COLUMN active_book_id INTEGER"))

        if not insp.has_table("user_book_settings"):
            conn.execute(
                text(
                    """
                    CREATE TABLE user_book_settings (
                        id INTEGER PRIMARY KEY AUTO_INCREMENT,
                        user_id INTEGER NOT NULL,
                        book_id INTEGER NOT NULL,
                        daily_target INTEGER NOT NULL DEFAULT 12,
                        master_required_count INTEGER NOT NULL DEFAULT 3,
                        weak_wrong_threshold INTEGER NOT NULL DEFAULT 2,
                        CONSTRAINT uq_user_book_settings UNIQUE (user_id, book_id),
                        FOREIGN KEY(user_id) REFERENCES users (id),
                        FOREIGN KEY(book_id) REFERENCES word_books (id)
                    )
                    """
                )
            )

        if insp.has_table("words"):
            cols = {c["name"] for c in insp.get_columns("words")}
            if "book_id" not in cols:
                conn.execute(
                    text("ALTER TABLE words ADD COLUMN book_id INTEGER NOT NULL DEFAULT 0")
                )
                conn.execute(text("CREATE INDEX ix_words_book_id ON words (book_id)"))
            if "book_entry_id" not in cols:
                conn.execute(text("ALTER TABLE words ADD COLUMN book_entry_id INTEGER"))

        if insp.has_table("words") and insp.has_table("quiz_records"):
            conn.execute(
                text(
                    """
                    UPDATE words w SET
                      train_count = (
                        SELECT COUNT(*) FROM quiz_records q WHERE q.word_id = w.id
                      ),
                      total_train_seconds = (
                        SELECT COALESCE(SUM(duration_seconds), 0)
                        FROM quiz_records q WHERE q.word_id = w.id
                      )
                    WHERE train_count = 0 AND EXISTS (
                      SELECT 1 FROM quiz_records q WHERE q.word_id = w.id
                    )
                    """
                )
            )
