"""子智能体专用终端，实现工具白名单与完成工具。"""

import json
from pathlib import Path
from typing import Dict, Optional, List

from core.web_terminal import WebTerminal
from config import PROMPTS_DIR

FORBIDDEN_SUB_AGENT_TOOLS = {"update_memory", "todo_create", "todo_update_task", "todo_finish", "todo_finish_confirm"}


class SubAgentTerminal(WebTerminal):
    """子智能体 Web 终端，限制工具并提供 finish_sub_agent。"""

    def __init__(
        self,
        *,
        workspace_dir: str,
        data_dir: str,
        metadata: Dict,
        message_callback=None,
    ):
        super().__init__(
            project_path=workspace_dir,
            thinking_mode=True,
            message_callback=message_callback,
            data_dir=data_dir,
        )
        self.sub_agent_meta = metadata
        self.finish_callback = None
        self._system_prompt_cache: Optional[str] = None

    def set_finish_callback(self, callback):
        self.finish_callback = callback

    def load_prompt(self, name: str) -> str:
        if name != "main_system":
            return super().load_prompt(name)

        if self._system_prompt_cache:
            return self._system_prompt_cache

        template_path = Path(PROMPTS_DIR) / "sub_agent_system.txt"
        if not template_path.exists():
            return super().load_prompt(name)

        template = template_path.read_text(encoding="utf-8")
        data = {
            "summary": self.sub_agent_meta.get("summary", ""),
            "task": self.sub_agent_meta.get("task", ""),
            "workspace": self.sub_agent_meta.get("workspace_dir", ""),
            "references": self.sub_agent_meta.get("references_dir", ""),
            "deliverables": self.sub_agent_meta.get("deliverables_dir", ""),
            "target_project_dir": self.sub_agent_meta.get("target_project_dir", ""),
            "agent_id": self.sub_agent_meta.get("agent_id", ""),
            "task_id": self.sub_agent_meta.get("task_id", ""),
        }
        self._system_prompt_cache = template.format(**data)
        return self._system_prompt_cache

    def define_tools(self) -> List[Dict]:
        tools = super().define_tools()
        filtered: List[Dict] = []
        for tool in tools:
            name = tool.get("function", {}).get("name")
            if name in FORBIDDEN_SUB_AGENT_TOOLS:
                continue
            filtered.append(tool)

        filtered.append({
            "type": "function",
            "function": {
                "name": "finish_sub_agent",
                "description": (
                    "当你确定交付成果已准备完毕时调用此工具。调用前请确认 deliverables 文件夹存在 result.md，"
                    "其中包含交付说明。参数 reason 用于向主智能体总结本轮完成情况。"
                ),
                "parameters": {
                    "type": "object",
                    "properties": {
                        "reason": {
                            "type": "string",
                            "description": "向主智能体说明任务完成情况、交付内容、下一步建议。"
                        }
                    },
                    "required": ["reason"]
                }
            }
        })
        return filtered

    async def handle_tool_call(self, tool_name: str, arguments: Dict) -> str:
        if tool_name == "finish_sub_agent":
            result = self._finalize_sub_agent(arguments or {})
            return json.dumps(result, ensure_ascii=False)
        return await super().handle_tool_call(tool_name, arguments)

    def _finalize_sub_agent(self, arguments: Dict) -> Dict:
        deliverables_dir = Path(self.sub_agent_meta.get("deliverables_dir", self.project_path))
        result_md = deliverables_dir / "result.md"
        if not result_md.exists():
            return {
                "success": False,
                "error": "deliverables 目录缺少 result.md，无法结束任务。"
            }
        content = result_md.read_text(encoding="utf-8").strip()
        if not content:
            return {
                "success": False,
                "error": "result.md 为空，请写入任务总结与交付说明后再结束任务。"
            }
        reason = (arguments.get("reason") or "").strip()
        if not reason:
            return {
                "success": False,
                "error": "缺少 reason 字段，请说明完成情况。"
            }
        result = {
            "success": True,
            "message": "子智能体任务已标记为完成。",
            "reason": reason,
        }
        if self.finish_callback:
            try:
                self.finish_callback(result)
            except Exception:
                pass
        return result
