工具调用

定义函数工具、校验模型参数并回传结果,完成受控的工具调用循环。

查看 Markdown

工具调用的职责

工具调用让模型返回函数名与参数,由你的应用执行函数,再把结果提交给模型。网关负责协议转发,不执行你的函数。收到 tool_calls 不代表外部操作已经完成。

先选择支持工具调用的模型,再检查接入通道是否支持对应字段。本文使用 GFW 模型 ID deepseek-v4-pro 演示,并只定义一个本地无副作用函数。响应结构是示意;示例不是实际模型调用记录。

协议选择与交互步骤

推荐通过 POST /v1/chat/completions 实现完整循环:

  1. 随消息提交 tools 中的函数名、描述和 JSON Schema。
  2. 接收助手消息,检查 tool_calls,不要要求 content 一定有文本。
  3. 将完整助手消息加入历史,校验每个工具名与参数,执行允许的函数。
  4. 添加 role=tool 的结果消息,tool_call_id 必须与对应调用的 id 相同。
  5. 再次提交历史,直到收到普通回复或达到应用设置的轮数上限。

Anthropic 非流式 Messages 会转换 tools、tool_use 和 tool_result,也可实现基本循环。当前 Responses 输出转换只构造文本消息,不完整返回 function_call 项,输入转换也不支持完整的 function_call_output,因此不要使用它完成本页流程。

tool_choice=auto 允许模型直接回答;required 或指定函数的行为由模型及通道决定。parallel_tool_calls 也不是所有模型都支持的通用开关。本页示例不依赖强制或并行调用。

完整调用示例

设置 GFW_API_KEY。cURL 展示第一轮声明工具;Python(依赖 openai 包)包含最多三轮的完整执行与回传流程。

curl --fail-with-body --silent --show-error \
  --max-time 120 \
  https://api.gfw.net/v1/chat/completions \
  -H "Authorization: Bearer ${GFW_API_KEY:?请先设置 GFW_API_KEY}" \
  -H 'Content-Type: application/json' \
  --data '{
    "model": "deepseek-v4-pro",
    "messages": [{"role": "user", "content": "调用 normalize_label,把 Example Label 转成统一标签。"}],
    "tools": [{
      "type": "function",
      "function": {
        "name": "normalize_label",
        "description": "清理标签首尾空格并转换为小写。",
        "parameters": {
          "type": "object",
          "properties": {"text": {"type": "string"}},
          "required": ["text"],
          "additionalProperties": false
        }
      }
    }],
    "tool_choice": "auto",
    "max_tokens": 512,
    "stream": false
  }'

响应与回传格式

以下助手消息为结构示意;arguments 在 Chat Completions 中是 JSON 字符串,而不是直接嵌入的对象:

{
  "role": "assistant",
  "content": null,
  "tool_calls": [{
    "id": "call_example",
    "type": "function",
    "function": {"name": "normalize_label", "arguments": "{\"text\":\"Example Label\"}"}
  }]
}

对应的结果消息示意:

{
  "role": "tool",
  "tool_call_id": "call_example",
  "content": "{\"label\":\"example label\"}"
}

保留所有助手工具请求和每个对应结果,不能仅把工具结果作为新的 user 文本提交。一个助手消息可能包含多个工具调用;应用应明确其执行顺序,不能把“收到多个请求”自动解释为可安全并行。

参数校验与流式工具

JSON Schema 有助于模型组织参数,但应用仍必须校验工具名、字段类型、长度、权限与业务限制。不要使用 eval 执行模型返回的参数,也不要将模型给出的函数名直接映射成任意程序调用。

执行有副作用的函数时,记录工具调用 ID 与执行状态,避免网络重试导致重复操作;重复结果应可识别。工具结果只返回必要数据,错误也应形成明确结果或终止流程。

流式 Chat Completions 的工具名和 arguments 可能分多次增量返回,按 delta.tool_calls[].index 聚合,直到调用参数完整、结束原因合理后再执行。不要逐片段解析半个 JSON。Anthropic 工具流为基础转换实现,不应假定复杂并行场景与原生事件完全一致。

注意事项与相关文档

多轮工具流程会发起多次模型请求,每轮的历史消息也参与输入。控制工具轮数、结果长度与请求总时限,避免不断回传大段数据。工具本身的成本与模型 Token 费用应分别记录。

相关文档:OpenAI 兼容 API、Anthropic 兼容 API、流式输出、结构化输出、计费与充值。

本页目录