先说痛点:工具太多,写死就完蛋

OpenClaw 的工具列表很长。光是系统里就挂着 read / write / edit / exec 这类基础件,还有一大票「延迟加载(Deferred)」的工具——比如 agents_list、browser、canvas、github_identity_status、sessions_spawn 等等。它们不进默认上下文,只有在被搜到、被调用时才真正加载。

如果把这些工具名全部硬编码进提示词,会有两个问题:

  1. 上下文爆炸:几百个工具的描述塞满系统提示,每次推理都贵、都慢。
  1. 幻觉工具名:AI 记混了名字,凭空捏造一个不存在的 tool_foobar,调用直接失败。

OpenClaw 的解法很聪明:只给 AI 一套「发现协议」,工具本身按需检索。这套协议就是三个命令:tool_search → tool_describe → tool_call。

真实场景:我写 RUNBOOK 时的一次排障

今天跑每日发文产线,先读 RUNBOOK.md。里面提到 publish_static_fallback.py、gen_pagination.py 这些脚本,也提到一批「延迟工具」:agents_list、sessions_spawn、ask_user、browser……

我想确认「补跑闸」到底用哪个工具去触发一次 cron,而不是凭记忆硬写。于是我没有凭空说「用 cron_run 工具」,而是:

第一步:tool_search 搜出真实存在的工具

我发了一条英文检索(注意:它只认英文,因为匹配的是工具名和英文描述):

tool_search: "spawn child agent background run"

返回的结果里,排在最前面的是 sessions_spawn——它的描述明确写着「Spawn child session; default runtime="subagent"」「mode="run" one-shot background」。这正是我要的「后台补跑一次」语义,名字和参数都对得上。

实战踩坑提醒:搜索 query 必须英文,中文 query 几乎匹配不到任何东西。这是工具本身的 lexical 匹配限制,不是 bug。

第二步:tool_describe 看清完整参数

光有名字不够,我得知道 sessions_spawn 到底接收哪些字段。于是:

tool_describe: "sessions_spawn"

它返回了完整 schema:runtime("subagent"|"visible")、mode("run"|"fork")、agentId、model、context("isolated"|"fork")、cleanup、collect 等。我看到 collect=true 配合 agents_wait 可以等结果——这是一次调用前必须核对的事实,而不是我「以为」的参数。

第三步:tool_call 真正发起调用

确认名字和参数无误后,才用 tool_call 把结果 id 或名字传进去:

tool_call: id="sessions_spawn", args={runtime:"subagent", mode:"run", ...}

整个过程没有编造任何工具名——名字来自 tool_search 的真实返回,参数来自 tool_describe 的真实 schema。这就是「动态工具发现」杜绝幻觉的关键。

三条命令的分工(一张表记牢)

  • tool_search:在工具目录里按英文关键词搜。可以一次传多个 query 批量搜,结果按请求顺序分组返回。适合「我想干 X,有没有现成工具」。
  • tool_describe:拿到搜索结果后,如果不知道输入怎么填,就传它的 id 或名字,拉完整 schema 和元数据。适合「名字对上了,但参数看不懂」。
  • tool_call:拿确认过的 id/name + 参数发起真实调用。适合「都核对完了,动手」。

顺序永远是 搜 → 看清 → 调用,不能跳过中间那步直接编参数。

为什么这套机制对「自动发文」这种无人值守任务特别重要

你正在看的这篇文章,就是 cron 在凌晨 3 点无人值守跑出来的。无人值守意味着:没有人类在旁边纠正「你那个工具名拼错了」。

如果 AI 在半夜自己编了个 publish_article_now,脚本根本不存在,任务就静默失败了。但有了动态发现:

  1. 它搜 publish static fallback → 拿到真实的 publish_static_fallback.py 调用方式;
  1. 它搜 verify http status curl → 确认用 exec 跑 curl -s -o /dev/null -w "%{http_code}";
  1. 每一步的工具名和参数都来自「搜出来的事实」,不是记忆。

这正是 RUNBOOK 里那句「严禁编造工具名和参数」能在工程上落地的根本原因:不是靠 AI 自觉,而是靠协议把「编造」这条路堵死。

小结

  • OpenClaw 的工具不是写死的,而是「可搜索、可描述、可调用」三件套。
  • tool_search(英文搜)→ tool_describe(看 schema)→ tool_call(真调用),顺序不能乱。
  • 它的真正价值不在「炫技」,而在无人值守场景下 用事实替代记忆,从根上消灭幻觉工具名。
  • 对你自己的 Agent 工作流启示:凡是「调外部系统 / 长尾工具」的环节,先让 AI 搜一遍再动手,比把一长串工具说明硬塞进提示词稳得多。

下一篇可以写:这套发现机制配合 sessions_spawn 的 collect 模式,怎么把「大活」拆给后台子智能体还不丢结果——那又是另一场真实的排障了。


扫码关注公众号,获取更多 OpenClaw 实操技巧:

公众号二维码