让Agent一次就把工具用对:8条工具设计原则(附反例)

📅 2026/10/5 ✍️ 小文 📖 约 1 分钟

Agent失败的根源往往不在模型,而在工具设计。本文用8条可落地原则拆解工具命名、参数、错误返回与幂等性,附大量正反例对照。

几乎所有”Agent用错工具”的锅,最后都被算到模型头上。但把同一个模型接上不同设计的工具,成功率能差出三四倍——问题常常出在工具本身长得太难用。

工具是 Agent 的”手”。手不趁手,脑子再聪明也白搭。下面 8 条原则,是我踩了一堆坑之后总结的。

一、名字要能”望文生义”

模型选工具的第一依据是名字和描述。do_stuff、process_data、handle_v2 这种名字等于让模型瞎猜。

  • ❌ manage_user
  • ✅ get_user_by_email / deactivate_user_account

动词要具体,名词要明确。名字里带 get/create/delete/list 前缀,模型对行为语义的理解会稳定很多。

二、描述写”什么时候用”,不只是”是什么”

大多数工具描述只说了它做什么,没说该在什么场景调用。Agent 最需要的恰恰是后者。

❌ 描述:搜索数据库。
✅ 描述:按关键词检索已入库的产品资料。当用户询问具体产品参数、
        价格或库存时调用。不要用于查询订单状态(请用 get_order_status)。

描述里如果能写”什么时候不要用”,能过滤掉大量误调用。

三、参数越少越好,能推断的不要暴露

每个必填参数都是模型犯错的机会。能从上下文或已有状态推断出来的值(如 user_id、session_id),让服务端自己填,不要交给模型。

参数太多时,把强相关的字段打包成一个对象,减少顶层字段数量。

四、用枚举约束,别靠模型自觉

任何有限集合的参数,都要用 enum 而不是自由字符串。

{"status": {"type": "string", "enum": ["active", "paused", "closed"]}}

自由文本参数(如日期、金额单位)要给出明确格式示例,并在服务端做校验和归一化。

五、返回值要为”下一步决策”服务

工具返回不是给人看的日志,是给模型看的决策依据。几百行原始 JSON 会把上下文冲垮。

  • 只返回该决策需要的字段;
  • 大列表默认分页并给出 total 和 next_cursor;
  • 用稳定的字段名,别每版换个 key。

六、错误信息要”可行动”

Error: 500 对模型毫无价值。好的错误返回要告诉它为什么失败、能不能重试、怎么修。

{
  "ok": false,
  "error_code": "RATE_LIMITED",
  "message": "调用过于频繁,请在约30秒后重试",
  "retryable": true,
  "suggestion": "降低并发或稍后重试同名工具"
}

模型看到 retryable: true 才会去重试;看到 suggestion 才知道怎么绕。

七、尽量做到幂等

Agent 会因超时、重试、判断失误而重复调用同一个工具。如果 create_order 重跑一次就下一个新单,后果灾难。

给写操作加幂等键(idempotency key),或设计成”先查后写”:先确认目标状态,再执行变更。读取类工具天然幂等,写类工具必须显式处理。

八、控制工具数量与职责边界

一个模型面前摆 40 个工具,选择准确率会肉眼可见地下滑。经验红线:

  • 单次可选的工具尽量控制在 15 个以内;
  • 职责重叠的工具(两个都能”搜资料”)必须合并或明确边界;
  • 按任务阶段动态挂载工具(规划阶段只给只读工具),远比一次全塞进去有效。

一个自查清单

上生产前,对你的每个工具问这几句:

  1. 光看名字和描述,能判断什么时候用吗?
  2. 必填参数能否再减?
  3. 返回值会不会太长?
  4. 报错时模型知不知道下一步干嘛?
  5. 重试两次会不会产生副作用?

五问全过,你的 Agent 用错工具的概率会大幅下降。

结语

工具设计是 Agent 工程里投入产出比最高的一环:改一个描述、减两个参数、加一行 retryable,就能顶上一次模型升级。 与其反复换更强的模型,不如先把工具这双手打磨趁手。

📤 分享到