主题
工具执行框架
本文引用的源码文件
本文引用的文件
- src/background/constants.js
- src/background/tool-executor.js
- src/background/react-loop.js
- src/background/state.js
- src/background/activity-store.js
- src/background/tools/browser-tools.js
- src/background/tool-preselector.js
- src/shared/image-signature.js
- agent/src/executor.js
- agent/src/mcp/registry.js
- agent/src/skill/loader.js
- agent/src/skill/executor.js
- src/background/tools/rag-tools.js
更新摘要
所做更改
- 新增 read_image 工具的多输入源支持(文件路径、base64数据、URL)
- 实现基于用户偏好的条件性工具包含机制
- 优化工具预筛选逻辑和 PARALLELIZABLE_TOOLS 配置
- 增强图片安全验证和沙箱保护机制
目录
引言
本文件面向"工具执行框架"的开发者与维护者,系统性说明:
- 工具定义与注册机制(内置工具、MCP 动态注入、RAG 知识库工具)。
- 参数校验与安全过滤(Schema 校验、类型检查、命令白名单)。
- 并行执行策略(PARALLELIZABLE_TOOLS、子任务并发池、资源上限)。
- 超时控制(TOOL_TIMEOUT_MS、Agent 端预算延长策略、交互式工具特殊处理、用户中断)。
- 错误处理与审计(异常捕获、重试、审计日志与统计)。
- 新工具开发、执行策略配置与性能优化实践。
- 调试方法与常见问题排查。
本项目为双进程架构:Chrome 扩展端(Manifest V3)+ 独立本地代理端 Agent(Node.js)。两端版本号保持同步,当前以 2.3.1 为准;修改 Agent 源码后需重启进程,接口才会生效。
项目结构
工具执行框架横跨扩展端 background 与 Agent 端两个运行时:
- 扩展端负责工具定义聚合、动态注册、调度、并发控制、超时与交互、审计记录。
- Agent 端负责命令执行、MCP 工具发现与调用、Skill 加载与执行、RAG 能力探测。
graph TB subgraph "扩展端 Background" C["constants.js<br/>默认配置/工具聚合"] E["tool-executor.js<br/>工具注册/分发/执行"] R["react-loop.js<br/>ReAct 循环/并发/超时"] S["state.js<br/>AbortController/会话状态"] A["activity-store.js<br/>审计/统计"] BT["browser-tools.js<br/>read_image 等浏览器工具"] TP["tool-preselector.js<br/>工具预筛选"] IS["image-signature.js<br/>图片魔数验证"] end subgraph "Agent 端" X["executor.js<br/>命令执行/超时策略"] M["mcp/registry.js<br/>MCP 工具注册表"] L["skill/loader.js<br/>Skill 加载/校验"] K["skill/executor.js<br/>Skill 执行引擎"] end C --> E E --> R R --> S E --> A E --> M E --> X E --> L E --> K BT --> E TP --> E IS --> E
图示来源
- src/background/constants.js#L87-L161
- src/background/tool-executor.js#L448-L778
- src/background/react-loop.js#L3207-L3266
- src/background/tools/browser-tools.js#L380-L402
- src/background/tool-preselector.js#L1-L200
- src/shared/image-signature.js#L1-L33
- agent/src/executor.js#L165-L186
- agent/src/mcp/registry.js#L26-L108
- agent/src/skill/loader.js#L35-L65
- agent/src/skill/executor.js#L317-L401
章节来源
核心组件
- 工具定义与聚合:通过常量模块聚合 8 组内置工具,派生 BUILTIN_TOOLS、TOOL_EXECUTION_MAP、PARALLELIZABLE_TOOLS、CONFIRMATION_REQUIRED_TOOLS 等映射。
- 工具执行器:统一入口,负责 MCP/RAG 动态注册、工具选择、参数解析、执行分发、审计与统计。
- ReAct 循环:负责多轮推理、工具分组并行、plan_task 子任务调度、工具级超时与用户取消。
- Agent 命令执行器:跨平台 shell 选择、安全环境变量、流式输出、超时延长策略、进程树终止。
- MCP 注册表:管理 MCP Server 连接、工具发现、工具调用转发。
- Skill 系统:Workflow Skill JSON/YAML 加载与校验、Agent Skill SKILL.md 扫描、DAG 拓扑执行与并行。
- 新增:read_image 工具 - 支持多输入源的图片深读功能,具备严格的安全验证机制。
- 新增:工具预筛选系统 - 智能工具选择,减少模型 token 消耗。
章节来源
- src/background/constants.js#L87-L161
- src/background/tool-executor.js#L448-L778
- src/background/react-loop.js#L3207-L3266
- src/background/tools/browser-tools.js#L380-L402
- src/background/tool-preselector.js#L1-L200
- agent/src/executor.js#L165-L186
- agent/src/mcp/registry.js#L26-L108
- agent/src/skill/loader.js#L35-L65
- agent/src/skill/executor.js#L317-L401
架构总览
工具执行从 ReAct 循环发起,经工具执行器路由到具体 handler;涉及 Agent 能力的请求走 local-agent-client 调用 Agent 端 API;MCP 与 RAG 工具在运行期动态注入;命令执行由 Agent 端 executor 完成,带流式输出与超时策略。新增的 read_image 工具提供多输入源的图片分析能力,并通过严格的安全验证确保内容安全。
sequenceDiagram participant RL as "ReAct 循环<br/>react-loop.js" participant TE as "工具执行器<br/>tool-executor.js" participant AC as "Agent 客户端<br/>local-agent-client" participant AG as "Agent 执行器<br/>executor.js" participant MC as "MCP 注册表<br/>mcp/registry.js" participant RI as "read_image 工具<br/>browser-tools.js" RL->>TE : "executeToolWithTimeout(toolCall)" TE->>TE : "按 id 查找 handler / 动态注册" alt 需要 Agent 能力 TE->>AC : "调用 Agent API" AC->>AG : "命令/MCP/Skill/RAG" AG-->>AC : "结果/流式输出" AC-->>TE : "结构化结果" else 纯浏览器能力 TE-->>RL : "直接返回结果" end alt read_image 工具 TE->>RI : "executeReadImage(args)" RI->>RI : "多输入源验证 + 安全检测" RI->>AC : "downloadFile(path)" AC-->>RI : "图片数据" RI->>RI : "魔数验证 + 体积限制" RI-->>TE : "视觉分析结果" end RL->>RL : "记录审计/统计/并发控制"
图示来源
- src/background/react-loop.js#L3207-L3266
- src/background/tool-executor.js#L448-L778
- src/background/tools/browser-tools.js#L380-L402
- agent/src/executor.js#L198-L385
- agent/src/mcp/registry.js#L116-L128
详细组件分析
工具定义与注册机制
- 内置工具聚合:constants.js 将 8 个工具组合并为 RAW_TOOLS,并派生 BUILTIN_TOOLS、TOOL_EXECUTION_MAP、PARALLELIZABLE_TOOLS、CONFIRMATION_REQUIRED_TOOLS、BUILTIN_TOOLS_UI 等。
- 动态注册:
- MCP 工具:loadMcpTools 从 Agent 拉取工具列表,压缩 schema,注入 RAW_TOOLS/BUILTIN_TOOLS/TOOL_HANDLERS,重建 BG_HANDLERS,并持久化 mcpTools 供 UI 显示。
- RAG 工具:loadRagTools 检测 Agent 是否支持 RAG,若启用则注入 knowledge_search/ingest/list 三个工具,并同步 ragTools 到 storage。
- 去重与清理:使用 Set 维护已注册 ID,提供 unloadMcpToolsInternal/unloadRagToolsInternal 清理函数,并通过互斥锁防止并发加载/卸载。
flowchart TD Start(["开始"]) --> CheckGlobal["检查全局开关<br/>mcpEnabled/ragEnabled"] CheckGlobal --> |关闭| Skip["跳过加载/卸载"] CheckGlobal --> |开启| Fetch["拉取工具列表/能力探测"] Fetch --> Compress["压缩 Schema/限制深度/截断描述"] Compress --> Inject["注入 RAW_TOOLS/BUILTIN_TOOLS/TOOL_HANDLERS"] Inject --> Rebuild["rebuildBgHandlers()<br/>重建 PARALLELIZABLE/CONFIRMATION"] Rebuild --> Persist["持久化 mcpTools/ragTools"] Persist --> End(["结束"])
图示来源
- src/background/tool-executor.js#L448-L778
- src/background/tool-executor.js#L940-L1035
- src/background/tools/rag-tools.js#L5-L40
章节来源
- src/background/constants.js#L87-L161
- src/background/tool-executor.js#L448-L778
- src/background/tool-executor.js#L940-L1035
- src/background/tools/rag-tools.js#L5-L40
MCP 协议工具发现与调用
- Agent 端 MCP 注册表:initializeMcpRegistry 启动时连接所有启用的 MCP Server,getMcpTools 扁平化工具列表,callMcpTool 转发调用。
- 扩展端动态注入:loadMcpTools 获取 toolsResult 与 serversResult,构建 toolId=mcp_{serverId}_{toolName},压缩 inputSchema,注册 handler 调用 AgentClient.callMcpTool。
- 服务级开关与会话强制下发:禁用服务器被过滤;用户通过 / 指定服务可强制下发该服务全部工具,绕过关闭/排除列表。
sequenceDiagram
participant BE as "Background<br/>tool-executor.js"
participant AC as "Agent Client"
participant MR as "MCP Registry<br/>registry.js"
participant MS as "MCP Server"
BE->>AC : "getMcpTools()/getMcpServers()"
AC->>MR : "getMcpTools(serverId?)/getMcpServersStatus()"
MR-->>AC : "{tools, servers}"
BE->>BE : "压缩 Schema/注入工具"
BE->>AC : "callMcpTool(serverId, name, args)"
AC->>MR : "callMcpTool(serverId, name, args)"
MR->>MS : "JSON-RPC 2.0 调用"
MS-->>MR : "结果"
MR-->>AC : "成功/失败"
AC-->>BE : "结构化结果"
图示来源
- agent/src/mcp/registry.js#L26-L108
- agent/src/mcp/registry.js#L116-L128
- src/background/tool-executor.js#L551-L649
章节来源
- agent/src/mcp/registry.js#L26-L108
- agent/src/mcp/registry.js#L116-L128
- src/background/tool-executor.js#L551-L649
Skill 技能系统集成
- Workflow Skill:loader.js 读取 ~/.ai-helper-agent/skills/*.json/.yaml,validateWorkflowSkill 校验必填字段与步骤结构,保存/删除/种子写入 skill-creator。
- Agent Skill:扫描子目录中的 SKILL.md,作为能力扩展文档供 AI 自主调用。
- 执行引擎:executor.js 解析步骤 DAG,按拓扑排序并行执行,支持条件 when、模板变量渲染、步骤间结果传递、超时与活跃执行清理。
classDiagram
class Loader {
+loadAllSkills()
+saveSkillFile(skill)
+deleteSkillFile(name,type)
+seedSkillCreator()
}
class Executor {
+executeSkill(skill,params,onStepUpdate)
+getSkillExecutionStatus(execId)
-executeToolCall(tool,args)
-executeSkillSteps(skill,params,execId,notify)
}
class Security {
+checkPath(path)
+checkCommand(command,interactive)
}
Loader --> Executor : "提供 Skill 定义"
Executor --> Security : "路径/命令安全检查"
图示来源
- agent/src/skill/loader.js#L35-L65
- agent/src/skill/loader.js#L173-L209
- agent/src/skill/executor.js#L317-L401
- agent/src/skill/executor.js#L179-L203
章节来源
- agent/src/skill/loader.js#L35-L65
- agent/src/skill/loader.js#L173-L209
- agent/src/skill/executor.js#L317-L401
- agent/src/skill/executor.js#L179-L203
参数验证机制
- 工具定义层:每个工具的 function.parameters 必须为 object,id 与 function.name 一致,execution 取值合法,由单元测试覆盖。
- MCP Schema 压缩:compressMcpSchema 移除冗余字段、限制 properties 嵌套深度、截断 description、限制参数数量,避免撑爆上下文。
- Skill 参数校验:executor.js 兼容 JSON Schema 风格 parameters,校验 required 字段,进行 number/boolean/string 类型转换。
- 命令安全:Skill 中 agent_exec 走 checkCommand 分级(deny/confirm/allow),灰名单命令在 Workflow 中直接拒绝;路径操作走 checkPath 白名单。
flowchart TD In["输入参数"] --> ToolDef["工具定义 Schema 校验<br/>type=object/required/name/id"] ToolDef --> |通过| McpComp["MCP Schema 压缩<br/>深度/数量/描述长度"] ToolDef --> |失败| Err1["返回参数错误"] McpComp --> SkillCheck["Skill 参数校验<br/>required/type 转换"] SkillCheck --> |通过| Exec["执行工具/命令"] SkillCheck --> |失败| Err2["返回缺失/类型错误"] Exec --> Sec["安全检查<br/>checkPath/checkCommand"] Sec --> |拒绝| Err3["安全拒绝"] Sec --> |允许| Out["返回结果"]
图示来源
- test/unit/tool-definitions.unit.test.js#L32-L61
- src/background/tool-executor.js#L464-L543
- agent/src/skill/executor.js#L320-L342
- agent/src/skill/executor.js#L118-L139
章节来源
- test/unit/tool-definitions.unit.test.js#L32-L61
- src/background/tool-executor.js#L464-L543
- agent/src/skill/executor.js#L320-L342
- agent/src/skill/executor.js#L118-L139
并行执行策略
- 工具级并行:PARALLELIZABLE_TOOLS 集合标记可并行工具;rebuildBgHandlers 根据 RAW_TOOLS 重建该集合。
- ReAct 循环并行:同组工具 Promise.all 并行执行;单组内非并行或仅 1 个则顺序执行。
- 子任务并行:strategy=parallel 时使用 dispatchSubtasksParallel 并发池,maxParallel 限制并发数,tracked promise finally 自移除,避免竞态。
- 资源管理:activeExecutions 限制最大活跃 Skill 执行数,定期清理过期记录;命令执行输出缓冲区上限 5MB,防止内存无限增长。
flowchart TD
Start(["进入 ReAct 工具组"]) --> GroupSize{"组内工具数 > 1 ?"}
GroupSize --> |是| Parallel["Promise.all 并行执行"]
GroupSize --> |否| Sequential["顺序执行"]
Parallel --> PlanCheck{"plan_task 已处理?"}
Sequential --> PlanCheck
PlanCheck --> |是| Break["跳过本轮剩余工具"]
PlanCheck --> |否| Next["继续下一组/下一轮"]
图示来源
- src/background/react-loop.js#L2253-L2281
- src/background/react-loop.js#L3069-L3082
- agent/src/skill/executor.js#L236-L305
- agent/src/executor.js#L93-L116
章节来源
- src/background/react-loop.js#L2253-L2281
- src/background/react-loop.js#L3069-L3082
- agent/src/skill/executor.js#L236-L305
- agent/src/executor.js#L93-L116
超时控制机制
- 扩展端工具级超时:executeToolWithTimeout 对除 clarify_question 外的工具设置超时,支持 TOOL_TIMEOUT_MS 自定义覆盖,但受全局 toolTimeout 上限约束;同时支持 AbortController 用户中断。
- 交互式工具特殊处理:clarify_question 外层暂停整体循环超时,内部有独立澄清超时计时,面板呈现后才启动倒计时,未呈现期间轮询 Side Panel 存活性。
- Agent 端命令超时:executor.js 支持受管模式(显式 timeoutMs),基于 decideTimeoutAction 策略函数裁决延长或终止;无输出视为挂起即杀,最长延长次数 MAX_TIMEOUT_EXTENSIONS,总预算封顶 TOTAL_BUDGET_CAP_MS。
- 进程终止:Windows 使用 taskkill /T /PID,Unix 使用 SIGTERM 到进程组,5 秒后升级为 SIGKILL。
flowchart TD
Enter(["工具执行入口"]) --> IsClarify{"是否为 clarify_question?"}
IsClarify --> |是| NoOuter["不设置外层超时<br/>仅内部澄清超时"]
IsClarify --> |否| CalcTimeout["计算 effectiveTimeout<br/>min(自定义, 全局)"]
CalcTimeout --> AbortCtrl["创建 AbortController<br/>监听用户取消"]
AbortCtrl --> Run["执行工具"]
Run --> Timeout{"超时?"}
Timeout --> |是| Reject["reject 超时错误"]
Timeout --> |否| Done["resolve 结果"]
NoOuter --> Run
图示来源
- src/background/react-loop.js#L3207-L3266
- src/background/tool-executor.js#L2578-L2611
- agent/src/executor.js#L165-L186
- agent/src/executor.js#L496-L549
章节来源
- src/background/react-loop.js#L3207-L3266
- src/background/tool-executor.js#L2578-L2611
- agent/src/executor.js#L165-L186
- agent/src/executor.js#L496-L549
错误处理策略
- 异常捕获:工具执行、Skill 步骤、命令执行均包裹 try/catch,返回结构化 success/error 对象;Skill 执行部分失败返回 partial 结果。
- 重试机制:Agent 连通性检测与部分网络调用具备超时与缓存;Skill 执行引擎对步骤失败按策略 continue/skip/stop 处理。
- 审计日志:appendAuditLog 与 recordToolStats 采用内存权威态 + 防抖落盘,关键审计即时刷;Cookie/文件/命令等敏感操作均有审计记录。
flowchart TD
Call["调用工具/命令"] --> TryCatch{"try/catch"}
TryCatch --> |成功| Audit["记录审计/统计"]
TryCatch --> |失败| Strategy{"重试/回滚/继续"}
Strategy --> |重试| Retry["指数退避/次数上限"]
Strategy --> |回滚| Rollback["撤销已完成子任务"]
Strategy --> |继续| Next["继续后续步骤"]
Audit --> Done["返回结果"]
Retry --> Done
Rollback --> Done
Next --> Done
图示来源
- agent/src/skill/executor.js#L360-L401
- src/background/activity-store.js#L84-L122
- src/background/tool-executor.js#L1037-L1041
章节来源
- agent/src/skill/executor.js#L360-L401
- src/background/activity-store.js#L84-L122
- src/background/tool-executor.js#L1037-L1041
新增:read_image 工具的多输入源支持
read_image 工具是一个强大的图片分析工具,支持多种输入源并提供严格的安全验证:
支持的输入源
- 文件路径(path):代理端任意图片文件路径,通过 downloadFile 现拉
- 文档附件(file + image):会话附件文档中提取的图片,数据源为 _docImageSnapshot 中转快照
- Base64 数据:直接从本地快照读取 dataUrl
安全验证机制
- 魔数验证:使用 image-signature.js 进行严格的文件头魔数检测,支持 PNG、JPEG、GIF、BMP、WebP 格式
- 体积限制:单图大小限制在 5MB 以内,防止超大文件攻击
- 沙箱保护:代理端路径访问受 checkPath 沙箱保护,工作目录内永远放行
条件性包含机制
- 用户偏好控制:通过 visionEnabled 开关控制 read_image 工具的可用性
- 配置回落链:优先使用 imageApiBase/imageApiKey,回退到主 apiBase/apiKey
- 按需下发:当图片识别功能关闭时,自动隐藏 read_image 工具以减少 token 消耗
flowchart TD
Input["输入参数"] --> SourceCheck{"输入源检查"}
SourceCheck --> |path| PathSource["代理端路径来源"]
SourceCheck --> |file+image| DocSource["文档附件来源"]
SourceCheck --> |无效| Error["参数错误"]
PathSource --> Download["downloadFile(path)"]
Download --> Guard["魔数验证 + 体积限制"]
Guard --> |通过| Vision["视觉分析"]
Guard --> |失败| PathError["路径错误"]
DocSource --> Snapshot["_docImageSnapshot 查询"]
Snapshot --> DataUrl["dataUrl 或 path"]
DataUrl --> Guard2["魔数验证 + 体积限制"]
Guard2 --> |通过| Vision
Guard2 --> |失败| DocError["文档错误"]
Vision --> Result["返回文本分析"]
图示来源
- src/background/tools/browser-tools.js#L380-L402
- src/background/tool-executor.js#L2160-L2235
- src/shared/image-signature.js#L1-L33
章节来源
- src/background/tools/browser-tools.js#L380-L402
- src/background/tool-executor.js#L2160-L2235
- src/shared/image-signature.js#L1-L33
新增:改进的工具预筛选逻辑
工具预筛选系统通过智能选择相关工具来减少模型 token 消耗:
预筛选阈值
- 固定阈值:PRESELECT_MIN_TOOL_COUNT = 10,工具数量超过此值才启动预筛选
- 动态配置:enableToolPreselect 开关控制是否启用预筛选功能
- 智能判断:当工具总数超过阈值时,通过前置规划调用减少工具传递
预筛选流程
- 工具数量检查:如果工具数量 ≤ 阈值,跳过预筛选直接返回全部工具
- 用户问题提取:从消息列表中提取最后一条用户消息
- 历史上下文:提取最近 4 条 user+assistant 交替消息作为历史上下文
- LLM 调用:构建预筛选提示词,调用 LLM 选择合适的工具
- 结果解析:支持新 JSON 格式和旧格式的容错恢复
flowchart TD
Start(["开始预筛选"]) --> CountCheck{"工具数 > 10 ?"}
CountCheck --> |否| Skip["跳过预筛选<br/>返回全部工具"]
CountCheck --> |是| ExtractUser["提取用户问题"]
ExtractUser --> History["提取历史上下文<br/>最近4条对话"]
History --> BuildPrompt["构建预筛选提示词"]
BuildPrompt --> CallLLM["调用 LLM 选择工具"]
CallLLM --> ParseResult["解析结果<br/>新格式/旧格式容错"]
ParseResult --> Finalize["返回选定工具"]
Skip --> End(["结束"])
Finalize --> End
图示来源
章节来源
依赖关系分析
- constants.js 是工具定义的单一数据源,派生多个映射表;tool-executor.js 依赖这些映射进行执行分发与并行判定。
- react-loop.js 依赖 tool-executor.js 的工具执行与超时封装,同时依赖 state.js 的 AbortController 管理用户中断。
- Agent 端 executor.js 被 Skill 执行引擎与命令工具调用复用,提供跨平台 shell 选择与安全环境变量。
- MCP registry.js 暴露 getMcpTools/callMcpTool 供扩展端动态注入与调用。
- Skill loader.js 与 executor.js 共同构成 Skill 生命周期:加载→校验→执行→状态查询。
- 新增:browser-tools.js 提供 read_image 等浏览器工具定义,tool-preselector.js 提供智能工具选择,image-signature.js 提供图片安全验证。
graph LR CONST["constants.js"] --> EXEC["tool-executor.js"] EXEC --> LOOP["react-loop.js"] LOOP --> STATE["state.js"] EXEC --> ACT["activity-store.js"] EXEC --> REG["mcp/registry.js"] EXEC --> EXE["executor.js"] EXEC --> LOADER["skill/loader.js"] EXEC --> SKEXEC["skill/executor.js"] BT["browser-tools.js"] --> EXEC TP["tool-preselector.js"] --> EXEC IS["image-signature.js"] --> EXEC
图示来源
- src/background/constants.js#L87-L161
- src/background/tool-executor.js#L448-L778
- src/background/react-loop.js#L3207-L3266
- src/background/state.js#L320-L342
- agent/src/executor.js#L198-L385
- agent/src/mcp/registry.js#L26-L108
- agent/src/skill/loader.js#L173-L209
- agent/src/skill/executor.js#L317-L401
- src/background/tools/browser-tools.js#L380-L402
- src/background/tool-preselector.js#L1-L200
- src/shared/image-signature.js#L1-L33
章节来源
- src/background/constants.js#L87-L161
- src/background/tool-executor.js#L448-L778
- src/background/react-loop.js#L3207-L3266
- src/background/state.js#L320-L342
- agent/src/executor.js#L198-L385
- agent/src/mcp/registry.js#L26-L108
- agent/src/skill/loader.js#L173-L209
- agent/src/skill/executor.js#L317-L401
- src/background/tools/browser-tools.js#L380-L402
- src/background/tool-preselector.js#L1-L200
- src/shared/image-signature.js#L1-L33
性能与并发
- 工具预筛选:当工具总数超过 PRESELECT_MIN_TOOL_COUNT 时启用预筛选,减少模型 token 消耗。
- 并行工具组:同组工具 Promise.all 并行执行,降低端到端延迟。
- 子任务并发池:dispatchSubtasksParallel 限制 maxParallel,tracked promise finally 自移除,修复旧 indexOf(completed) 竞态导致上限失效的问题。
- 输出缓冲限制:命令 stdout/stderr 累计上限 5MB,超限时广播 truncated 消息并停止追加。
- 活跃执行清理:Skill activeExecutions 最多保留 MAX_ACTIVE_EXECUTIONS,定时清理已完成/错误记录。
- 新增:read_image 工具的图片压缩与体积限制,防止大图片影响性能。
章节来源
- src/background/constants.js#L24-L26
- src/background/react-loop.js#L2253-L2281
- src/background/react-loop.js#L3069-L3082
- agent/src/executor.js#L93-L116
- agent/src/skill/executor.js#L30-L62
超时控制
- 扩展端:
- TOOL_TIMEOUT_MS 可为单个工具设置更短超时,最终 effectiveTimeout=min(自定义, 全局 toolTimeout)。
- clarify_question 工具不设置外层超时,仅内部独立计时;Side Panel 呈现后才启动倒计时。
- 用户可通过 abortCurrentTool 触发 AbortController,立即 reject 当前等待工具。
- Agent 端:
- 受管模式下,decideTimeoutAction 根据期内是否有输出决定延长或 kill;extensions 达到 MAX_TIMEOUT_EXTENSIONS 或触及 TOTAL_BUDGET_CAP_MS 即终止。
- 断开 WS 客户端时,仅在 managed=false 或 entry.detached=true 时才取消定时器,避免 SW 空闲被回收导致误解除超时。
章节来源
- src/background/constants.js#L151-L171
- src/background/react-loop.js#L3207-L3266
- src/background/state.js#L320-L342
- agent/src/executor.js#L165-L186
- agent/src/executor.js#L455-L493
错误处理与审计
- 异常捕获:工具执行、Skill 步骤、命令执行均返回结构化结果;Skill 部分失败返回 partial。
- 重试机制:Agent 连通性检测具备 5 秒超时与缓存;Skill 执行对步骤失败按策略处理。
- 审计日志:appendAuditLog 与 recordToolStats 采用内存权威态 + 防抖落盘,关键审计即时刷;Cookie/文件/命令等敏感操作均有审计记录。
章节来源
- agent/src/skill/executor.js#L360-L401
- src/background/activity-store.js#L84-L122
- src/background/tool-executor.js#L1037-L1041
调试与故障排除
- 工具定义问题:
- 检查 id 唯一性、function.name 与 id 一致、execution 取值合法、parameters.type=object。
- 参考测试用例断言。
- MCP 工具不可见:
- 确认 mcpEnabled 全局开关;检查 Agent 是否支持 MCP;查看 mcpTools 存储是否更新;确认目标服务未被禁用。
- RAG 工具不可用:
- 确认 ragEnabled 与 Agent /api/status ragAvailable;检查 collection 是否被禁用。
- 命令执行卡死:
- 检查 Shell 选择是否正确(Git Bash/PowerShell/cmd);观察 stdout_truncated 消息;确认超时策略是否延长;必要时 detach 进程。
- 用户取消无效:
- 检查 AbortController 是否绑定;确认 sessionId 正确;查看 abortCurrentTool 是否调用成功。
- 审计日志缺失:
- 检查 appendAuditLog/recordToolStats 调用点;确认 flush 调度是否触发;SW onSuspend 兜底刷盘。
- 新增:read_image 工具问题:
- 检查 visionEnabled 开关是否开启;确认图片识别 API 配置正确;验证图片文件格式和大小;查看魔数验证日志。
- 新增:工具预筛选问题:
- 检查 enableToolPreselect 开关;确认工具数量超过阈值;查看预筛选日志输出;验证 LLM 响应格式。
章节来源
- test/unit/tool-definitions.unit.test.js#L32-L61
- src/background/tool-executor.js#L551-L649
- src/background/tool-executor.js#L940-L1035
- agent/src/executor.js#L32-L91
- agent/src/executor.js#L298-L323
- src/background/state.js#L320-L342
- src/background/activity-store.js#L84-L122
结论
工具执行框架通过统一的定义与注册机制,将内置工具、MCP 动态工具与 RAG 知识库工具整合到同一执行管线;借助 Schema 压缩与参数校验保障安全性与稳定性;通过工具级与 Agent 端双层超时控制、用户中断支持与可扩展的重试/回滚策略,确保长时间任务的健壮性;并行执行与资源上限控制提升吞吐与响应速度;完善的审计与统计为排障与优化提供依据。新增的 read_image 工具提供了强大的多输入源图片分析能力,配合严格的安全验证机制确保内容安全;改进的工具预筛选系统有效减少了模型 token 消耗,提升了整体性能。开发新工具时,建议遵循现有工具定义规范,合理设置 parallelizable/requiresConfirmation,并在必要时接入 Agent 能力与审计记录。