工具调用:让智能体真正行动

智能体如何可靠地选择与调用外部函数——schema 设计、参数校验与失败恢复。

beginner · Claude / GPT-5 / Gemini / DeepSeek
#工具调用#函数调用#智能体

从输出到行动

纯语言模型只能产出文本。工具调用把它变成智能体:模型发出结构化请求,你的代码负责执行,结果再回到上下文。

模型 → { name: "search_orders", args: { customer_id: "C1024" } }
你的代码 → 执行 → 返回数据行
模型 → 基于数据推理 → 作答

模型自己从不执行任何东西,执行的是你的代码。模型只决定「调什么」和「传什么参数」。

Schema 设计几乎决定成败

工具描述本身就是提示词。描述写得差,调用就会出错,或者干脆不被调用。

要把「做什么」和「边界在哪」都写清楚:

反例:get_data — 获取数据。

正例:get_order_history — 返回单个客户的订单记录,按时间倒序。接受客户 id,不接受邮箱或姓名。最多返回 50 行,需要更早数据请使用 before 参数翻页。

三条规则能挡掉大部分故障:

  1. 枚举就穷举。 参数若为 day|week|month,就逐个列出,别写「一个时间范围」。
  2. 写明不接受什么。 「接受客户 id,不接受邮箱」直接消灭一整类错误调用。
  3. 交代限制。 最大行数、默认排序、翻页方向——模型猜不出你的 API 契约。

失败处理:别陷入重试死循环

工具调用失败的原因很固定:参数非法、瞬时错误、权限不足。把失败作为数据返回给模型,而不是抛异常把整轮对话打死。

{ ok: false, error: "客户 ID C1024 未找到", hint: "id 形如 C1000-C9999" }

模型通常能根据描述性错误自我纠正,但面对堆栈跟踪什么都做不了。

防死循环:给每轮的工具调用次数设上限,并检测重复的 (工具名, 参数) 组合。同一个失败调用出现两次就停下来交给人处理。

常见故障模式

症状可能原因
工具从不被调用描述缺少用户会用的触发关键词
参数每次都错未穷举枚举、未说明单位
多个工具时选错工具描述高度重叠,需拉开差异
报错后无限重试错误以异常抛出,而非可检查的数据
结果凭空捏造返回值从未真正回到上下文