默认情况下,Claude 可能会在单个响应中调用多个工具。本页介绍如何运行这些调用、如何格式化消息历史记录以保持并行功能正常工作,以及在需要时如何禁用并行工具使用。有关单次调用流程,请参阅处理工具调用。
当 Claude 调用工具时,响应的 stop_reason 为 tool_use,并且可以在单个助手回合中包含多个 tool_use 块。如何运行这些调用由您决定。API 不规定执行顺序:您可以并发运行这些调用(Promise.all、asyncio.gather)、按它们出现的顺序依次运行,或以任何适合您工具的组合方式运行。
请根据工具的功能选择策略。独立的只读操作通常可以安全地并行运行以降低延迟。具有副作用、共享状态或顺序要求的工具可能更适合按顺序运行。
无论您使用哪种策略,都要为每个 tool_use 块返回一个 tool_result,并将它们全部放在下一条用户消息中。使用 tool_use_id 将每个结果与其调用匹配,并将所有 tool_result 块放在该消息中任何文本内容之前。有关完整的格式化规则,请参阅处理工具调用。如果您选择不运行某个特定调用(例如,因为您按顺序运行了批处理且较早的调用失败了),仍需为其返回一个 tool_result,并设置 is_error: true 和简短的说明。
{
"type": "tool_result",
"tool_use_id": "toolu_02",
"is_error": true,
"content": "Not executed: the preceding write_file call failed."
}**对于大多数应用程序,请使用 Tool Runner:**SDK 的 Tool Runner 会处理包含多个工具调用的响应并为您格式化结果,因此您无需自己编写此处理逻辑。当您需要直接控制调用的运行方式(例如自定义批处理、排序或错误处理)时,请使用本页上的手动模式。
以下脚本发送一个应触发并行工具调用的请求,验证响应是否包含这些调用,并格式化工具结果以保持并行功能正常工作。请在环境中设置 ANTHROPIC_API_KEY 后运行:
client = Anthropic()
# 定义工具
tools = [
{
"name": "get_weather",
"description": "Get the current weather in a given location",
"input_schema": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "The city and state, e.g. San Francisco, CA",
}
},
"required": ["location"],
},
},
{
"name": "get_time",
"description": "Get the current time in a given timezone",
"input_schema": {
"type": "object",
"properties": {
"timezone": {
"type": "string",
"description": "The timezone, e.g. America/New_York",
}
},
"required": ["timezone"],
},
},
]
# 测试包含并行工具调用的对话
messages = [
{
"role": "user",
"content": "What's the weather in SF and NYC, and what time is it there?",
}
]
# 发起初始请求
print("Requesting parallel tool calls...")
response = client.messages.create(
model="claude-opus-4-8", max_tokens=1024, messages=messages, tools=tools
)
# 检查并行工具调用
tool_uses = [block for block in response.content if block.type == "tool_use"]
print(f"\n✓ Claude made {len(tool_uses)} tool calls")
if len(tool_uses) > 1:
print("✓ Parallel tool calls detected!")
for tool in tool_uses:
print(f" - {tool.name}: {tool.input}")
else:
print("✗ No parallel tool calls detected")
# 模拟工具执行并正确格式化结果
tool_results = []
for tool_use in tool_uses:
if tool_use.name == "get_weather":
if "San Francisco" in str(tool_use.input):
result = "San Francisco: 68°F, partly cloudy"
else:
result = "New York: 45°F, clear skies"
else: # get_time
if "Los_Angeles" in str(tool_use.input):
result = "2:30 PM PST"
else:
result = "5:30 PM EST"
tool_results.append(
{"type": "tool_result", "tool_use_id": tool_use.id, "content": result}
)
# 使用工具结果继续对话
messages.extend(
[
{"role": "assistant", "content": response.content},
{"role": "user", "content": tool_results}, # All results in one message!
]
)
# 获取最终响应
print("\nGetting final response...")
final_response = client.messages.create(
model="claude-opus-4-8", max_tokens=1024, messages=messages, tools=tools
)
final_text = next(
block.text for block in final_response.content if block.type == "text"
)
print(f"\nClaude's response:\n{final_text}")
# 验证格式
print("\n--- Verification ---")
print(f"✓ Tool results sent in single user message: {len(tool_results)} results")
print("✓ No text before tool results in content array")
print("✓ Conversation formatted correctly for future parallel tool use")末尾的摘要行重申了保持并行功能正常工作的两条格式化规则:所有工具结果都在单条用户消息中返回,并且在该消息中工具结果之前不出现任何文本内容。
当请求受益于多个工具时,Claude 4 模型默认会进行并行工具调用。对于所有模型,您可以通过有针对性的提示来增加并行工具调用的可能性:
并行工具使用默认开启。要关闭它,请在 tool_choice 对象内设置 disable_parallel_tool_use: true。它不是顶级请求参数。其效果取决于 tool_choice 类型。
当 tool_choice 类型为 auto(默认值)时,设置 disable_parallel_tool_use: true 意味着 Claude 每次响应最多调用一个工具。Claude 仍然可以在不调用任何工具的情况下以纯文本回答。高亮显示的行是与标准工具使用请求相比唯一的更改:
client = Anthropic()
response = client.messages.create(
model="claude-opus-4-8",
max_tokens=1024,
tools=[
{
"name": "get_weather",
"description": "Get the current weather in a given location",
"input_schema": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "The city and state, e.g. San Francisco, CA",
}
},
"required": ["location"],
},
}
],
tool_choice={"type": "auto", "disable_parallel_tool_use": True},
messages=[
{
"role": "user",
"content": "What is the weather in San Francisco and New York?",
}
],
)
print(response.content)当 tool_choice 类型为 any 或 tool 时,设置 disable_parallel_tool_use: true 意味着 Claude 恰好调用一个工具。以下示例使用 any。相同的字段也适用于 tool:
client = Anthropic()
response = client.messages.create(
model="claude-opus-4-8",
max_tokens=1024,
tools=[
{
"name": "get_weather",
"description": "Get the current weather in a given location",
"input_schema": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "The city and state, e.g. San Francisco, CA",
}
},
"required": ["location"],
},
}
],
tool_choice={"type": "any", "disable_parallel_tool_use": True},
messages=[
{
"role": "user",
"content": "What is the weather in San Francisco and New York?",
}
],
)
print(response.content)如果 Claude 在预期情况下没有进行并行工具调用,请检查以下常见问题:
1. 工具结果格式不正确
最常见的问题是在对话历史记录中错误地格式化工具结果。这会"教导"Claude 避免并行调用。
特别是对于并行工具使用:
// Wrong: separate user messages reduce parallel tool use
[
{"role": "assistant", "content": [tool_use_1, tool_use_2]},
{"role": "user", "content": [tool_result_1]},
{"role": "user", "content": [tool_result_2]} // Separate message
]
// Correct: one user message with all results maintains parallel tool use
[
{"role": "assistant", "content": [tool_use_1, tool_use_2]},
{"role": "user", "content": [tool_result_1, tool_result_2]} // Single message
]有关其他格式化规则,请参阅处理工具调用。
2. 提示不够有力
默认提示可能不够。请使用最大化并行工具使用中更强的系统提示。
3. 衡量并行工具使用情况
要验证并行工具调用是否正常工作:
messages = [] # Message objects returned by client.messages.create across your run
tool_call_messages = [
msg for msg in messages if any(block.type == "tool_use" for block in msg.content)
]
total_tool_calls = sum(
len([block for block in msg.content if block.type == "tool_use"])
for msg in tool_call_messages
)
avg_tools_per_message = (
total_tool_calls / len(tool_call_messages) if tool_call_messages else 0.0
)
print(f"Average tools per message: {avg_tools_per_message}")
# 如果并行调用正常工作,应该 > 1.04. 批处理中的调用似乎相互依赖
执行顺序由您选择。如果您的工具有顺序依赖关系,按顺序运行批处理并在第一次失败时停止是一种有效的策略:为任何未运行的调用返回 is_error: true。如果您并行运行且某个调用因其前置条件尚未完成而失败,请返回 is_error: true 并附上自然的错误消息。Claude 将在下一回合重新发出该调用。要减少相互依赖的调用同时出现,请将以下内容添加到您的系统提示中:"Only batch tool calls that are independent of each other."(仅批处理彼此独立的工具调用。)
使用 SDK 的 Tool Runner 抽象来自动处理智能体循环、错误包装和类型安全。
解析 tool_use 块、格式化 tool_result 响应,并使用 is_error 处理错误。
指定工具架构、编写有效的描述,并控制 Claude 何时调用您的工具。
Was this page helpful?