多轮工具调用怎么选?DeepSeek V4.1 Flash、Gemini 3.8 Flash 与 Qwen3.8 Flash 小规模实测

让 DeepSeek、Gemini、Qwen 完成同一套订单查询和故障重试,比较真实输出、工具调用次数、耗时与 token 用量,并检查结果能否直接解析为 JSON。

蓝灰背景上的望远镜黑色线稿、浅色卡纸、金色圆形及 DeepSeek / Gemini / Qwen 标题。

DeepSeek V4.1 Flash、Gemini 3.8 Flash 和 Qwen3.8 Flash 都完成了我们设计的合成订单查询流程,也都从一次注入的可重试工具错误中恢复了。这是一个有用的起点,但不足以选出可靠性赢家。每个模型对每个案例只运行了一次,而且所有最终回答都带有 Markdown 代码围栏,而不是裸 JSON。

因此,实际选择时应针对应用的契约验证完整工具调用流程:参数是否正确、工具结果是否匹配、重试次数是否受限、最终回答是否合格,以及用量是否有记录。模型返回工具调用,只是这个流程的起点。

本文列出测试任务、观察到的结果和可运行的测试套件,并在DeepSeek、Gemini 与 Qwen 综合比较的基础上,补充范围有限的真实 API 测试证据。订单数据和故障都是人工构造的;模型请求则是真实发送的。

测试的具体流程

用户查询订单 A17。唯一可用的工具 lookup_order 接受一个字符串类型的 order_id。我们的本地函数会返回一条固定且不含敏感信息的记录:

{"order_id":"A17","status":"shipped","amount_eur":42,"next_action":"track_delivery"}

正常情况下,第一次调用就会成功。在故障案例中,工具第一次返回的结果则是:

{"error":"temporarily_unavailable","retryable":true}

接下来一次有效查询会返回订单信息。这是应用层的工具故障,不是模拟 HTTP 429,也不是服务提供商故障。区分这一点很重要,以免把这里成功重试的结果宣传成模型服务具备故障恢复能力的证据。

提示词要求模型调用工具、不要猜测、遇到可重试错误时恰好重试一次,并以 JSON 返回四个指定字段。测试框架限制每个案例最多发送四次模型请求。它没有提供任何可以扣款、发送消息或修改订单的工具。

Ofox 公开英文 DeepSeek 代码示例中的 API 精确标识

实际模型页面代码界面截图,拍摄于 10 月 12 日。这是一个基础连接示例,不是多轮评测成功的证明,也不是多轮评测截图。

请求内容与测量指标

三个模型都通过 Ofox 的 /v1/chat/completions 路由调用,并设置了 max_tokens: 1800。我们使用了完整的命名空间 ID:

deepseek/deepseek-v4.1-flash
google/gemini-3.8-flash
qwen/qwen3.8-flash

没有显式设置温度或推理配置。这次测试使用的是网关当前默认值,并非在相同推理预算下进行的受控比较;测试也没有覆盖各服务提供商的原生直连接口。

模型正常案例:工具调用次数 / 请求时间合计重试案例:工具调用次数 / 请求时间合计报告的总 token 数,正常 / 重试
DeepSeek V4.1 Flash1 / 3.14 秒2 / 5.03 秒899 / 1,474
Gemini 3.8 Flash1 / 4.52 秒2 / 6.40 秒532 / 945
Qwen3.8 Flash1 / 3.36 秒2 / 4.35 秒1,008 / 1,527

时间是每个流程中客户端观测到的模型请求耗时之和。它们不是延迟百分位,也不等同于纯模型推理时间。token 总数是各轮 API 用量之和,其中包含重复发送的历史消息。由于分词器和计量方式不同,报告的 token 较少并不一定意味着工作量更少或账单更低。

在运行完整测试套件之前,DeepSeek 的一次初始尝试遇到了传输层代理断连。该次尝试单独记录,未计入此表。不能把这一排除误读为零失败的可用性结果。表格描述的是已完成的案例,并非准备过程中发起的每一次网络请求。

哪些检查通过了,哪些没有

每个已完成的正常案例都进行了一次有效查询;每个已完成的故障案例都进行了两次有效查询,从而从注入的首次错误中恢复。所有最终回答都包含预期的订单值。没有模型在收到成功结果之前编造订单状态。

不过,六个回答都带有 Markdown 代码围栏。DeepSeek 的重试案例还附加了一句解释重试的说明。如果应用要求整段文本必须能解析为一个 JSON 值,那么即使这些回答包含了正确数据,也不符合严格契约。

为自动化任务选择模型时,这一点很重要。面向用户的客服助手或许可以接受带围栏的回答;期待 JSON 对象的后台任务则未必可以。应先定义验收标准,再进行测量,并将语义正确性、语法和工具行为分开记录。

验收检查项已完成案例中的观察结果
使用允许的工具,并传入正确的订单 ID六个案例全部通过
注入错误后恰好多查询一次三个故障案例全部通过
最终回答包含预期订单值六个案例全部包含
返回不带围栏或说明文字的裸 JSON六个案例全部失败
整体生产可靠性未测量

在不同轮次之间保留 assistant 消息

测试框架会先追加返回的 assistant 消息,再追加每个工具结果。不要只根据最终可见文本重建对话历史:后续轮次可能需要工具调用 ID 和服务提供商特有的续接字段。在这次网关测试中,续接元数据确实存在,并且被保留在下一次请求中。

核心流程如下:

message = response["choices"][0]["message"]
messages.append(message)

for call in message.get("tool_calls", []):
    # Validate name and arguments before executing any application action.
    result = lookup_validated_order(call)
    messages.append({
        "role": "tool",
        "tool_call_id": call["id"],
        "content": json.dumps(result),
    })

lookup_validated_order 代表应用的校验边界,而不是对模型返回的工具名称进行任意执行。我们提供的可下载实现只允许调用 lookup_order,且参数必须严格为 {"order_id":"A17"}。生产实现还应检查请求的记录是否在经过身份验证的用户授权范围内。

如果要直接接入服务提供商的原生接口,应使用它各自的消息和工具结果契约,而不要盲目照搬这种 OpenAI 兼容格式。DeepSeek 工具调用指南和 Gemini 函数调用文档介绍了各自独立的接口。通过这项网关测试,并不能证明未经测试的原生适配器也能正常工作。

扩大测试前先复现

下载并解压测试套件,检查脚本,并在隔离的 Python 环境中安装 requests。通过常规的密钥管理方式设置 OFOX_API_KEY。脚本会发起可能产生费用的模型请求,不包含任何关于免费额度的假设。

运行工具测试套件,并将结果保存到新目录:

python3 -m venv .venv
source .venv/bin/activate
python -m pip install requests
python tool_suite.py --output ./tool-results

脚本会在达到配置的轮次上限时停止每个案例,记录 HTTP 或传输故障,并保留失败案例。应阅读响应文本并验证其结构,不要把 HTTP 200 当作应用层测试通过。分享结果时,不要公开原始续接元数据或凭据;提供的证据已移除推理字段。

接下来,将单个固定样例替换为带标签的自有案例。加入未知订单、缺少参数、多次工具调用、无效 JSON 参数、不可重试错误和工具超时等情况。验证协议时应使用只读工具。涉及副作用的工具需要额外保护措施,例如幂等性和明确授权;仅靠重试指令并不能保证安全。

根据通过验收的任务做选择

对于小规模集成试用,这三个模型都值得考虑,因为它们都完成了这次特定的工具调用流程。观察到的耗时顺序太不稳定,不能据此排出生产环境的名次。应按照应用实际会使用的输入长度、并发量和推理设置重复测试。

记录通过验收的任务比例、端到端延迟、请求次数和核对后的支出。将失败的初始尝试、格式修复尝试和回退方案都计入任务成本。还应单独衡量用户可见结果的正确性,避免低成本但无效的结果抬高表面上的成功率。

部署前,应在应用中设置最大轮次和每个工具的重试次数上限。模型这次遵循了只重试一次的要求,但服务不能永远依赖模型都会这样做。应将服务提供商错误、工具错误和输出校验失败分别记录,因为它们需要不同的处理方式。

如果接下来要解决的是结构化信息提取,而不是工具调用流程,Haiku 迁移评测也展示了为什么应分别检查语法、结构和事实。

常见问题

哪个模型的工具调用最可靠?
这项六案例测试无法得出这个结论。三个模型都完成了一个正常流程和一个注入错误的流程。应使用有代表性的带标签数据集进行测试,并在选出可靠性赢家之前报告失败情况。
你们测试了服务提供商限流后的恢复能力吗?
没有。注入的错误来自我们的本地合成订单工具,不是服务提供商的 HTTP 错误、限流或服务中断。
我可以执行模型请求的任何工具吗?
不可以。应将工具名称加入允许列表、校验参数,并在执行前验证记录授权。我们的固定样例只能读取一条合成订单,不能执行外部操作。