47 lines
1.7 KiB
Python
47 lines
1.7 KiB
Python
"""HostExecutor:in-process 工具调用,沿用原 `Tool.execute` 行为。
|
|
|
|
用途:
|
|
- 本地 dogfood / 单租户 / Step 1 默认 backend
|
|
- Step 3 docker backend 引入后,承担"信任域 = host"那一半(read/write/edit/glob/
|
|
grep/load_skill/web_*/seedream/seedance,§7.5 #6),DockerExecutor 内部组合本类
|
|
+ docker exec 处理 shell/run_python。
|
|
|
|
行为兼容性:错误分支与原 `AgentLoop._execute_tool_call` 三段(unknown tool /
|
|
bad args / 抛异常)语义对齐 —— 都包成 `[Error] ...` content 返回,exit_code
|
|
区分内部用。
|
|
"""
|
|
from __future__ import annotations
|
|
|
|
from typing import Any, Dict, List
|
|
|
|
from .executor import ExecCtx, Executor, ToolResult
|
|
from tools.base import Tool
|
|
|
|
|
|
class HostExecutor(Executor):
|
|
def __init__(self, tools: Dict[str, Tool]) -> None:
|
|
self._tools = tools
|
|
|
|
def has_tool(self, name: str) -> bool:
|
|
return name in self._tools
|
|
|
|
def schemas(self) -> List[Dict[str, Any]]:
|
|
return [t.schema for t in self._tools.values()]
|
|
|
|
def call_tool(self, name: str, args: Dict[str, Any], ctx: ExecCtx) -> ToolResult:
|
|
tool = self._tools.get(name)
|
|
if tool is None:
|
|
return ToolResult(content=f"[Error] unknown tool: {name}", exit_code=2)
|
|
try:
|
|
result = tool.execute(**args)
|
|
except TypeError as e:
|
|
return ToolResult(content=f"[Error] bad arguments to {name}: {e}", exit_code=2)
|
|
except Exception as e:
|
|
return ToolResult(
|
|
content=f"[Error executing {name}] {type(e).__name__}: {e}",
|
|
exit_code=1,
|
|
)
|
|
if not isinstance(result, str):
|
|
result = str(result)
|
|
return ToolResult(content=result, exit_code=0)
|