跳转到主要内容
函数调用(也叫 工具调用 / Tool Use)允许模型在生成回复过程中要求执行外部函数, 用于查询数据库、调用 API、读写文件等动作。OpenPAI 三套协议都完整支持,且可互通。

OpenAI 协议

from openai import OpenAI
client = OpenAI(api_key="sk-...", base_url="https://openp.ai/v1")

tools = [{
  "type": "function",
  "function": {
    "name": "get_weather",
    "description": "Get current weather for a city",
    "parameters": {
      "type": "object",
      "properties": {"city": {"type": "string"}},
      "required": ["city"],
    },
  },
}]

resp = client.chat.completions.create(
    model="gpt-5.5",
    messages=[{"role": "user", "content": "上海天气"}],
    tools=tools,
)

call = resp.choices[0].message.tool_calls[0]
print(call.function.name, call.function.arguments)
执行函数后,把结果回传:
messages = [
    {"role": "user", "content": "上海天气"},
    resp.choices[0].message,            # assistant 含 tool_calls
    {"role": "tool", "tool_call_id": call.id, "content": "上海 26°C 晴"},
]
final = client.chat.completions.create(model="gpt-5.5", messages=messages)
print(final.choices[0].message.content)

tool_choice

行为
"auto"(默认)模型自主决定
"none"强制不调用工具
"required"必须调用某个工具
{"type": "function", "function": {"name": "x"}}指定调用某个工具

parallel_tool_calls

新模型默认支持并行调用多个工具,响应中 tool_calls 是数组,需逐个执行后一次性回传。 若需禁用并行,设置 parallel_tool_calls: false

Claude 协议

from anthropic import Anthropic
client = Anthropic(api_key="sk-...", base_url="https://openp.ai")

resp = client.messages.create(
    model="claude-opus-4-8",
    max_tokens=1024,
    tools=[{
        "name": "get_weather",
        "description": "Get weather",
        "input_schema": {
            "type": "object",
            "properties": {"city": {"type": "string"}},
            "required": ["city"],
        },
    }],
    messages=[{"role": "user", "content": "上海天气"}],
)

# 找到 tool_use block
for block in resp.content:
    if block.type == "tool_use":
        result = call_my_weather(block.input["city"])
        followup = client.messages.create(
            model="claude-opus-4-8",
            max_tokens=1024,
            messages=[
                {"role": "user", "content": "上海天气"},
                {"role": "assistant", "content": resp.content},
                {"role": "user", "content": [{
                    "type": "tool_result",
                    "tool_use_id": block.id,
                    "content": result,
                }]},
            ],
        )

tool_choice(Claude)

{"type": "auto"}                      // 默认
{"type": "any"}                       // 必须调用某个工具
{"type": "tool", "name": "x"}         // 指定工具
{"type": "none"}                      // 禁用工具

Gemini 协议

from google import genai
from google.genai import types

client = genai.Client(api_key="sk-...", http_options={"base_url": "https://openp.ai"})

weather_tool = types.Tool(function_declarations=[
    types.FunctionDeclaration(
        name="get_weather",
        description="Get weather",
        parameters={
            "type": "object",
            "properties": {"city": {"type": "string"}},
            "required": ["city"],
        },
    )
])

resp = client.models.generate_content(
    model="gemini-3.1-pro-preview",
    contents="上海天气",
    config=types.GenerateContentConfig(tools=[weather_tool]),
)

for part in resp.candidates[0].content.parts:
    if part.function_call:
        print(part.function_call.name, part.function_call.args)
回传:
function_response = types.Part(function_response=types.FunctionResponse(
    name="get_weather",
    response={"city": "上海", "temp": 26}
))

followup = client.models.generate_content(
    model="gemini-3.1-pro-preview",
    contents=[
        types.Content(role="user", parts=[types.Part(text="上海天气")]),
        resp.candidates[0].content,
        types.Content(role="user", parts=[function_response]),
    ],
)

协议互通

通过 OpenPAI 的 OpenAI 兼容端点 调用 Claude / Gemini 模型时, OpenPAI 会自动将 Anthropic / Google 的工具调用结构转换为 OpenAI 的 tools / tool_calls, 反向亦然。你 无需 关心协议差异,只需选择一套写法即可。

最佳实践

详细 description

工具的 description 越具体,模型越能正确决定何时调用与传什么参数。

严格 schema

使用 requiredadditionalProperties: false,避免模型乱传字段。

错误优雅处理

工具执行失败时,把错误信息以 tool_result 形式回传,模型可重试或换策略。

并行调用

多个相互独立的工具一次调用并行执行,降低延迟。