跳到主要内容
SUN / 笔记
← 全部文章

工具发现与动态加载

当工具数量较多时,应按权限、任务阶段和语义相关性动态暴露少量 Schema,而不是把全部工具永久放入上下文。

工具很多时如何选择

如果系统有几百或几千个工具,不能无脑把全部 Schema 塞进上下文,否则会:

  • 占用大量 Token;
  • 增加延迟和成本;
  • 让相似工具互相干扰;
  • 降低工具选择和参数生成准确率;
  • 破坏稳定的 Prompt Cache 前缀。

常见方案有四种。

静态小工具集

工具数量很少且长期稳定时,直接全部注册:

text
search_code、read_file、apply_patch、run_test、git_diff

Harness 每轮筛选工具

Harness 在调用主模型前,根据任务状态筛选:

text
定位阶段:search_code、list_files、read_file
修改阶段:read_file、apply_patch、git_diff
验证阶段:run_test、read_log、git_diff

筛选依据包括:

  • 用户权限与租户;
  • 当前任务阶段;
  • 项目语言和运行环境;
  • 工具风险和副作用;
  • 上一步结果;
  • 硬编码规则、关键词、Embedding 或路由模型。

这一步发生在主模型调用之前,主模型看不到未暴露的工具。

Tool Search 延迟加载

开始只暴露高层 Namespace、MCP Server 描述和 tool_search 能力,模型需要时再搜索并加载少量具体工具 Schema。

MCP 动态发现

Harness 作为 MCP Client,通过 tools/list 获取 name、description 和 inputSchema,转换为模型工具定义;模型返回 Tool Call 后,再通过 tools/call 调用真实 MCP Server。

MCP Tools 规范将工具定义为模型可发现和调用的能力;MCP TypeScript Client 指南展示了 listTools() → 交给模型 → callTool() → 回填结果的完整流程。

相关笔记

工具调用上的渐进式披露

工具渐进披露的是“可以执行什么”以及具体参数接口。

text
L0:Namespace 或 MCP Server 名称、简介
          ↓
L1:Tool Search 加载相关工具完整 Schema
          ↓
L2:模型生成 Tool Call
          ↓
L3:Harness 执行并回填结果

例如模型最初只看到:

json
{
  "type": "namespace",
  "name": "crm",
  "description": "客户、订单、物流和退款管理"
}

需要查询物流时,再加载:

text
crm.get_order_status
crm.get_tracking_events
crm.get_shipping_eta

Skill 与 Tool 的区别:

维度 Skill 渐进披露 Tool 渐进披露
披露内容 工作流、规范和方法 可执行接口和参数 Schema
第一层 Skill 名称和描述 Namespace/Server 名称和描述
第二层 完整 SKILL.md 具体 Tool Definition
第三层 References/Scripts/Assets Tool Call 与 Tool Result
作用 告诉 Agent 应该怎么做 让 Agent 真的能够执行

Harness 每轮筛选与 Tool Search 的区别

不能简单理解为“一个完全在 Harness,一个完全在模型”。

机制 谁决定发起 谁检索候选工具 谁最终选择具体工具
Harness 预筛选 Harness Harness 的规则、检索器或路由模型 主模型
Hosted Tool Search 主模型 模型服务平台 主模型
Client-executed Tool Search 主模型 Harness/应用程序 主模型

Harness 预筛选

发生在主模型调用之前:

python
active_tools = route_before_model(
    request=user_request,
    state=task_state,
    permissions=user_permissions
)

response = call_model(tools=active_tools)

其中 route_before_model() 可以使用传统代码、检索器或另一个小模型,但对主模型而言,未选工具不可见。

模型判断自己需要搜索工具;平台在请求中已声明的 Deferred Tools、Namespaces 或 MCP Servers 中检索,并直接把相关 Schema 注入上下文。

模型产生 tool_search_call 和搜索目标;Harness 自己查询动态工具目录,然后返回 tool_search_output。

官方文档建议:候选工具在创建请求时已经确定,可优先使用 Hosted Tool Search;工具发现依赖项目、租户或应用自有状态时,使用 Client-executed Tool Search。OpenAI Docs:Tool search types


Tool Search 具体如何搜索

标准执行链

text
模型看到 Namespace/Tool Search
        ↓
模型判断缺少某类能力
        ↓
生成 tool_search_call 和搜索意图
        ↓
平台或 Harness 检索候选工具
        ↓
返回 tool_search_output 和完整 Schema
        ↓
模型从候选工具中生成真正的 function_call

例如用户说:

text
帮我查订单 42 什么时候能到。

模型可能生成:

json
{
  "type": "tool_search_call",
  "arguments": {
    "goal": "查询订单的预计送达时间和物流进度"
  }
}

搜索系统返回:

json
{
  "type": "tool_search_output",
  "tools": [
    {
      "type": "function",
      "name": "get_shipping_eta",
      "description": "查询指定订单的预计送达时间",
      "parameters": {
        "type": "object",
        "properties": {
          "order_id": {"type": "string"}
        },
        "required": ["order_id"]
      }
    }
  ]
}

模型随后调用:

json
{
  "type": "function_call",
  "name": "get_shipping_eta",
  "arguments": {
    "order_id": "42"
  }
}

Hosted Search 的匹配算法是否公开

当前官方文档公开了 Hosted Tool Search 的输入输出和行为,但没有公开内部究竟使用 Embedding、BM25、LLM Reranker 还是其他混合算法。因此不能直接断言 Hosted Tool Search 一定使用向量数据库或余弦相似度。

可以确认的是:开发者声明 Deferred Tool、Namespace 或 MCP Server,模型决定发起搜索,平台返回相关工具子集。OpenAI Docs:Hosted Tool Search

Client-executed Search 的常见语义匹配

自己实现时,通常采用:

text
权限、租户和环境过滤
        ↓
关键词/BM25 召回
        ↓
Embedding 语义召回
        ↓
融合与业务规则加权
        ↓
Cross-Encoder 或 LLM 重排
        ↓
返回 Top-K 工具完整 Schema

工具检索文档不应只有工具名,可以拼接:

text
Namespace: logistics
Name: get_shipping_eta
Description: 查询订单预计发货和送达时间
Use when: 用户询问什么时候到、配送进度、ETA、预计到货时间
Do not use when: 取消订单、创建退款
Inputs: order_id
Outputs: shipping_status, estimated_delivery_date
Side effect: none
Tags: 物流, 配送, ETA, 到货, 发货

混合评分示例:

text
final_score =
    0.55 × semantic_similarity
  + 0.25 × keyword_score
  + 0.10 × namespace_score
  + 0.10 × business_rule_score

这样即使用户说“东西啥时候到”,也能与 get_shipping_eta 的“预计送达时间”建立语义联系。

权限过滤必须在检索前执行,工具执行前还要再次鉴权:

text
权限/租户过滤 → 语义检索 → 返回候选 → 模型选择 → 执行前再次鉴权

工具描述应包含“做什么、何时使用、何时不使用、输入输出、是否有副作用和常见同义词”。Namespace 也应有清晰的业务描述。官方文档建议优先使用 Namespace 或 MCP Server 组织 Deferred Tools,并建议每个 Namespace 尽量少于 10 个函数以改善 Token 效率和模型表现。OpenAI Docs:Tool Search 与 Namespace


相关文章

强化学习笔记 →上下文工程 →Mission: 掌握多模态 LoRA 与 QLoRA →