"""
意图匹配工具：基于关键词 + embedding 语义相似度的两层确认意图判断

策略：
  第一层：关键词子串匹配（零延迟，覆盖 90%+ 常见表达）
  第二层：embedding 语义相似度匹配（兜底，捕获罕见/创意表达）
"""

from typing import List, Optional

# ──────────────────────────────────────────────
# 确认意图短语表（信息充足 / 开始行动）
# ──────────────────────────────────────────────
CONFIRM_PHRASES: List[str] = [
    # 直接确认
    "确认", "是的", "对", "好的", "没问题", "行", "可以", "OK",
    # 信息充足
    "足够", "够了", "齐了", "信息完整", "不用补充", "不需要补充",
    "就这些", "没有了", "信息够了", "不用再加了", "信息齐了",
    # 开始行动
    "开始诊断", "开始操作", "开始吧", "继续", "开始",
    # 复合确认
    "确认并继续", "正确", "没错", "对的", "是的开始", "就这样",
]

# 预计算的短语 embedding 缓存
_phrase_embeddings: Optional[List[List[float]]] = None


async def _ensure_phrase_embeddings() -> None:
    """确保确认短语的 embedding 已预计算（懒加载，仅首次调用时执行）"""
    global _phrase_embeddings
    if _phrase_embeddings is not None:
        return
    from modelsAPI.model_api import OpenaiAPI
    _phrase_embeddings = await OpenaiAPI.get_embeddings_batch_async(CONFIRM_PHRASES)
    print(f"[intent_matcher] 确认短语 embedding 预计算完成，共 {len(CONFIRM_PHRASES)} 条")


async def is_confirmation_intent(user_query: str, threshold: float = 0.78) -> bool:
    """
    判断用户输入是否为确认意图

    Args:
        user_query: 用户输入文本
        threshold: embedding 语义相似度阈值（默认 0.78）

    Returns:
        True 表示用户表达了确认/信息充足的意图
    """
    if not user_query or not user_query.strip():
        return True

    # 第一层：关键词子串匹配（零延迟）
    if any(kw in user_query for kw in CONFIRM_PHRASES):
        return True

    # 第二层：embedding 语义相似度匹配（兜底）
    await _ensure_phrase_embeddings()
    from modelsAPI.model_api import OpenaiAPI

    query_embedding = await OpenaiAPI.get_embeddings_async(user_query)
    similarities = OpenaiAPI.cosine_similarity_batch(query_embedding, _phrase_embeddings)
    max_sim = max(similarities) if similarities else 0.0

    if max_sim >= threshold:
        matched_phrase = CONFIRM_PHRASES[similarities.index(max_sim)]
        print(f"[intent_matcher] embedding 兜底命中: sim={max_sim:.3f}, "
              f"matched='{matched_phrase}', query='{user_query}'")
        return True

    return False

