"""清理 GlobalTags 重复标签（name_zh + level 组合去重）。"""

import asyncio
import uuid
from sqlalchemy import select, text

from app.db import async_session
from app.models.literature import GlobalTag


async def clean():
    async with async_session() as db:
        result = await db.execute(select(GlobalTag).order_by(GlobalTag.name_zh, GlobalTag.level, GlobalTag.id))
        tags = result.scalars().all()

        # 按 name_zh + level 分组，保留每组第一个（最早插入的 ID）
        seen: dict[tuple[str, int], uuid.UUID] = {}
        keep_ids: set[uuid.UUID] = set()
        remove_ids: set[uuid.UUID] = set()
        for t in tags:
            key = (t.name_zh, t.level)
            if key not in seen:
                seen[key] = t.id
                keep_ids.add(t.id)
            else:
                remove_ids.add(t.id)

        print(f"Total: {len(tags)}, Keep: {len(keep_ids)}, Remove: {len(remove_ids)}")

        if not remove_ids:
            print("No duplicates to clean")
            return

        # old → new UUID 映射（被删的 → 保留的）
        id_map: dict[uuid.UUID, uuid.UUID] = {}
        for t in tags:
            if t.id in remove_ids:
                key = (t.name_zh, t.level)
                id_map[t.id] = seen[key]

        tables_to_update = [
            ("global_tags", "parent_id"),
            ("global_literature_tags", "tag_id"),
            ("user_subscriptions", "tag_id"),
            ("drug_approvals", "cancer_type_tag_id"),
            ("guideline_versions", "cancer_type_tag_id"),
            ("global_tag_tree_numbers", "tag_id"),
            ("user_dismissed_tags", "tag_id"),
        ]

        for old_id, new_id in id_map.items():
            for table, column in tables_to_update:
                if table == "global_tags" and column == "parent_id":
                    # 跳过自引用 — 在最后一步由 ON DELETE SET NULL 处理
                    continue

                # 先删除重复引用
                await db.execute(
                    text(
                        f"DELETE FROM {table} "
                        f"WHERE {column} = :old_id "
                        f"AND EXISTS (SELECT 1 FROM {table} sub WHERE sub.{column} = :new_id)"
                    ),
                    {"old_id": old_id, "new_id": new_id},
                )
                # 再更新剩余引用
                await db.execute(
                    text(f"UPDATE {table} SET {column} = :new_id WHERE {column} = :old_id"),
                    {"new_id": new_id, "old_id": old_id},
                )

            # 更新子标签 parent_id（global_tags 自引用）
            await db.execute(
                text("UPDATE global_tags SET parent_id = :new_id WHERE parent_id = :old_id"),
                {"new_id": new_id, "old_id": old_id},
            )

            # 删除重复标签
            await db.execute(text("DELETE FROM global_tags WHERE id = :old_id"), {"old_id": old_id})

        await db.commit()
        print(f"Done — removed {len(remove_ids)} duplicate tags")


if __name__ == "__main__":
    asyncio.run(clean())
