"""
Summary Service - 处理录音标题和摘要生成
"""
import os
import logging
from datetime import datetime

from src.clients import db
from src.models import Recording, SystemSetting
from src.services.llm_service import (
    call_llm_completion,
    clean_llm_response,
    format_transcription_for_llm,
    preprocess_long_transcription,
    format_api_error_message
)
from src.services.embedding_service import process_recording_chunks
from src.clients.llm_client import client, TEXT_MODEL_NAME

# 查询模式开关
ENABLE_INQUIRE_MODE = os.environ.get('ENABLE_INQUIRE_MODE', 'false').lower() == 'true'

logger = logging.getLogger(__name__)


def generate_title_task(app_context, recording_id):
    """
    为录音生成标题（仅标题）
    
    Args:
        app_context: Flask 应用上下文
        recording_id: 录音 ID
    """
    with app_context:
        recording = db.session.get(Recording, recording_id)
        if not recording:
            logger.error(f"错误：未找到录音 {recording_id}，无法生成标题。")
            return
            
        if client is None:
            logger.warning(f"跳过录音 {recording_id} 的标题生成：OpenRouter 客户端未配置。")
            # 即使无法生成标题，仍标记为完成
            recording.status = 'COMPLETED'
            recording.completed_at = datetime.utcnow()
            db.session.commit()
            return
            
        if not recording.transcription or len(recording.transcription.strip()) < 10:
            logger.warning(f"录音 {recording_id} 的转录文本为空或过短，跳过标题生成。")
            # 即使无法生成标题，仍标记为完成
            recording.status = 'COMPLETED'
            recording.completed_at = datetime.utcnow()
            db.session.commit()
            return
        
        # 获取可配置的转录文本长度限制，并格式化为 LLM 可理解的格式
        transcript_limit = SystemSetting.get_setting('transcript_length_limit', 30000)
        if transcript_limit == -1:
            raw_transcription = recording.transcription
        else:
            raw_transcription = recording.transcription[:transcript_limit]
            
        # 将 ASR JSON 转换为干净的文本格式
        transcript_text = format_transcription_for_llm(raw_transcription)
        
        
        # 获取用户语言偏好
        user_output_language = None
        if recording.owner:
            user_output_language = recording.owner.output_language
            
        language_directive = f"请使用 {user_output_language} 提供标题。" if user_output_language else ""
        
        prompt_text = f"""为这段对话创建一个简短标题：

{transcript_text}

要求：
- 最多 8 个词
- 不要使用类似"关于...的讨论"或"...的会议"这样的短语
- 直接点明主题

{language_directive}

标题："""

        system_message_content = "你是一个 AI 助手，为音频转录文本生成简洁的标题。只回复标题本身。"
        if user_output_language:
            system_message_content += f" 确保你的回复使用 {user_output_language}。"
        
            
        try:
            completion = call_llm_completion(
                messages=[
                    {"role": "system", "content": system_message_content},
                    {"role": "user", "content": prompt_text}
                ],
                temperature=0.7,
                max_tokens=5000
            )
            
            
            raw_response = completion.choices[0].message.content
            reasoning = getattr(completion.choices[0].message, 'reasoning', None)
            
            # 如果主内容为空，使用推理内容作为后备（针对推理模型的降级处理）
            if not raw_response and reasoning:
                logger.info(f"录音 {recording_id} 的标题生成：使用推理字段作为后备")
                # 尝试从推理字段中提取标题
                lines = reasoning.strip().split('\n')
                # 查找可能是标题的最后一行
                for line in reversed(lines):
                    line = line.strip()
                    if line and not line.startswith('I') and len(line.split()) <= 8:
                        raw_response = line
                        break
            
            title = clean_llm_response(raw_response) if raw_response else ""
            
            if title:
                recording.title = title
                logger.info(f"录音 {recording_id} 已生成标题：{title}")
            else:
                logger.warning(f"录音 {recording_id} 生成的标题为空")
                
        except Exception as e:
            logger.error(f"为录音 {recording_id} 生成标题时出错：{str(e)}")
            logger.error(f"异常详情：", exc_info=True)
        
        # 标题生成后（无论成功与否）始终将状态设置为 COMPLETED
        # 这确保转录处理被标记为完成
        recording.status = 'COMPLETED'
        recording.completed_at = datetime.utcnow()
        db.session.commit()
        
        # 完成后处理分块以进行语义搜索（如果启用了 inquire 模式）
        if ENABLE_INQUIRE_MODE:
            try:
                process_recording_chunks(recording_id)
            except Exception as e:
                logger.error(f"处理已完成录音 {recording_id} 的分块时出错：{e}")


def generate_summary_only_task(app_context, recording_id):
    """仅生成录音摘要（无标题，无JSON响应）。

    参数：
        app_context: Flask应用上下文
        recording_id：录音的唯一标识
    """
    with app_context:
        recording = db.session.get(Recording, recording_id)
        if not recording:
            logger.error(f"录音 {recording_id} 未找到，无法生成摘要。")
            return
            
        if client is None:
            logger.warning(f"跳过录音 {recording_id} 的摘要生成：OpenRouter 客户端未配置。")
            recording.summary = "[摘要已跳过：OpenRouter 客户端未配置]"
            db.session.commit()
            return
            
        recording.status = 'SUMMARIZING'
        db.session.commit()
        
        logger.info(f"正在为录音 {recording_id} 请求摘要生成，使用模型 {TEXT_MODEL_NAME}...")
        
        if not recording.transcription or len(recording.transcription.strip()) < 10:
            logger.warning(f"录音 {recording_id} 的转录文本过短或为空，跳过摘要生成。")
            recording.summary = "[摘要已跳过：转录文本过短]"
            recording.status = 'COMPLETED'
            db.session.commit()
            return
        
        # 获取用户偏好和标签自定义提示词
        user_summary_prompt = None
        user_output_language = None
        tag_custom_prompt = None
        
        # 按标签添加到录音的顺序收集所有自定义提示词
        tag_custom_prompts = []
        if recording.tags:
            for tag in recording.tags:
                if tag.custom_prompt and tag.custom_prompt.strip():
                    tag_custom_prompts.append({
                        'name': tag.name,
                        'prompt': tag.custom_prompt.strip()
                    })
                    logger.info(f"录音 {recording_id} 找到标签 '{tag.name}' 的自定义提示词")
        
        # 如果有多个标签提示词则合并
        if tag_custom_prompts:
            if len(tag_custom_prompts) == 1:
                tag_custom_prompt = tag_custom_prompts[0]['prompt']
                logger.info(f"录音 {recording_id} 使用单个标签 '{tag_custom_prompts[0]['name']}' 的自定义提示词")
            else:
                # 将多个提示词无缝合并为统一指令
                merged_parts = []
                for tag_prompt in tag_custom_prompts:
                    merged_parts.append(tag_prompt['prompt'])
                tag_custom_prompt = "\n\n".join(merged_parts)
                tag_names = [tp['name'] for tp in tag_custom_prompts]
                logger.info(f"录音 {recording_id} 合并了 {len(tag_custom_prompts)} 个标签的自定义提示词（{', '.join(tag_names)}）")
        else:
            tag_custom_prompt = None
        
        if recording.owner:
            user_summary_prompt = recording.owner.summary_prompt
            user_output_language = recording.owner.output_language
        
        # 将转录文本格式化为 LLM 可理解的格式（将 JSON 转换为干净文本）
        raw_transcription = format_transcription_for_llm(recording.transcription)
        formatted_transcription = preprocess_long_transcription(raw_transcription)

        # 获取可配置的转录文本长度限制
        transcript_limit = SystemSetting.get_setting('transcript_length_limit', 30000)
        if transcript_limit == -1:
            transcript_text = formatted_transcription
        else:
            transcript_text = formatted_transcription[:transcript_limit]
        
        language_directive = f"重要：你必须使用 {user_output_language} 提供摘要。整个回复必须使用 {user_output_language}。" if user_output_language else ""
        
        # 确定使用哪个摘要生成指令
        # 优先级：标签自定义提示词 > 用户摘要提示词 > 管理员默认提示词 > 硬编码默认值
        summarization_instructions = ""
        if tag_custom_prompt:
            logger.info(f"录音 {recording_id} 使用标签自定义提示词")
            summarization_instructions = tag_custom_prompt
        elif user_summary_prompt:
            logger.info(f"录音 {recording_id} 使用用户自定义提示词")
            summarization_instructions = user_summary_prompt
        else:
            # 从系统设置中获取管理员默认提示词
            admin_default_prompt = SystemSetting.get_setting('admin_default_summary_prompt', None)
            if admin_default_prompt:
                logger.info(f"录音 {recording_id} 使用管理员默认提示词")
                summarization_instructions = admin_default_prompt
            else:
                # 如果管理员未设置，使用硬编码默认值
                summarization_instructions = """生成一个全面的摘要，包含以下部分：
- **讨论的关键问题**：主要话题的要点列表
- **做出的关键决策**：达成的决策要点列表
- **行动项**：分配的任务要点列表，包括负责人（如果提及）"""
                logger.info(f"录音 {recording_id} 使用硬编码默认提示词")
        
        # 构建上下文信息
        current_date = datetime.now().strftime("%Y年%m月%d日")
        context_parts = []
        context_parts.append(f"当前日期：{current_date}")
        
        # 添加选中标签信息
        if recording.tags:
            tag_names = [tag.name for tag in recording.tags]
            context_parts.append(f"用户为此转录应用的标签：{', '.join(tag_names)}")
        
        context_section = "上下文：\n" + "\n".join(f"- {part}" for part in context_parts)
        
        # 构建 SYSTEM 消息：初始指令 + 上下文 + 语言要求
        system_message_content = "你是一个 AI 助手，专门为会议转录文本生成全面摘要。仅以 Markdown 格式回复摘要内容。不要使用 Markdown 代码块。"
        system_message_content += f"\n\n{context_section}"
        if user_output_language:
            system_message_content += f"\n\n语言要求：你必须使用 {user_output_language} 生成整个摘要。这是强制性的。"
        
        # 构建 USER 消息：转录文本 + 摘要指令 + 语言要求
        prompt_text = f"""转录内容：
\"\"\"
{transcript_text}
\"\"\"

摘要指令：
{summarization_instructions}

{language_directive}"""
            
        # 调试日志：记录发送给 LLM 的完整提示词
        logger.info(f"向 LLM 发送摘要提示词（长度：{len(prompt_text)} 字符）。设置 LOG_LEVEL=DEBUG 可查看完整提示词详情。")
        logger.debug(f"=== 录音 {recording_id} 摘要生成调试 ===")
        logger.debug(f"系统消息：{system_message_content}")
        logger.debug(f"用户提示词（长度：{len(prompt_text)} 字符）：\n{prompt_text}")
        logger.debug(f"=== 录音 {recording_id} 摘要生成调试结束 ===")
            
        try:
            completion = call_llm_completion(
                messages=[
                    {"role": "system", "content": system_message_content},
                    {"role": "user", "content": prompt_text}
                ],
                temperature=0.5,
                max_tokens=int(os.environ.get("SUMMARY_MAX_TOKENS", "3000"))
            )
            
            raw_response = completion.choices[0].message.content
            logger.info(f"录音 {recording_id} 的 LLM 原始响应：'{raw_response}'")
            
            summary = clean_llm_response(raw_response) if raw_response else ""
            logger.info(f"录音 {recording_id} 的处理后摘要长度：{len(summary)} 字符")
            
            if summary:
                recording.summary = summary
                db.session.commit()
                logger.info(f"录音 {recording_id} 摘要生成成功")

                # 如果用户启用了事件提取，则在标记完成前执行
                if recording.owner and recording.owner.extract_events:
                    from src.services.event_service import extract_events_from_transcript
                    extract_events_from_transcript(recording_id, formatted_transcription, summary)

                # 事件提取完成后标记为已完成
                recording.status = 'COMPLETED'
                recording.completed_at = datetime.utcnow()
                db.session.commit()
            else:
                logger.warning(f"录音 {recording_id} 生成的摘要为空")
                recording.summary = "[摘要未生成]"
                recording.status = 'COMPLETED'
                db.session.commit()
                
        except Exception as e:
            error_msg = format_api_error_message(str(e))
            logger.error(f"录音 {recording_id} 摘要生成出错：{str(e)}")
            recording.summary = error_msg
            recording.status = 'COMPLETED'
            recording.completed_at = datetime.utcnow()
            db.session.commit()
