# AI工具调用指南 本文档提供了解决OpenAI API工具调用验证错误的方法和建议。 ## 常见错误 您遇到的错误是一个标准的OpenAI API参数验证错误: ``` BadRequestError: Error code: 400 - {'error': {'message': "3 validation errors for ValidatorIterator\n0.ChatCompletionMessageFunctionToolCallParam.function.arguments\n Input should be a valid string [type=string_type, input_value=None, input_type=NoneType]\n For further information visit https://errors.pydantic.dev/2.11/v/string_type\n0.ChatCompletionMessageCustomToolCallParam.custom\n Field required [type=missing, input_value={'type': 'function', 'id'...ns', 'arguments': None}}, input_type=dict]\n For further information visit https://errors.pydantic.dev/2.11/v/missing\n0.ChatCompletionMessageCustomToolCallParam.type\n Input should be 'custom' [type=literal_error, input_value='function', input_type=str]\n For further information visit https://errors.pydantic.dev/2.11/v/literal_error None", 'type': 'BadRequestError', 'param': None, 'code': 400}} ``` 这个错误表明您在调用OpenAI API时,工具调用参数验证失败。 ## 解决方案 ### 1. 确保每个工具调用都有有效的参数JSON字符串 在OpenAI API调用中,即使工具不需要任何参数,也必须提供一个空的JSON对象字符串 `"{}"`。 **错误示例:** ```python tool_call = { "type": "function", "function": { "name": "queryPositions", "arguments": None # 这会导致验证错误 } } ``` **正确示例:** ```python tool_call = { "type": "function", "function": { "name": "queryPositions", "arguments": "{}" # 即使没有参数,也提供空的JSON对象字符串 } } ``` ### 2. 修改Python客户端代码 如果您使用Python调用OpenAI API,可以使用以下模式来确保参数总是有效的JSON字符串: ```python import json from openai import OpenAI client = OpenAI(api_key="your-api-key") def call_tool(tool_name, params=None): # 确保参数是有效的JSON字符串 if params is None: params_str = "{}" elif isinstance(params, str): # 如果已经是字符串,确保是有效的JSON try: json.loads(params) # 验证JSON有效性 params_str = params except json.JSONDecodeError: params_str = "{}" # 如果无效,使用空对象 else: # 将对象转换为JSON字符串 params_str = json.dumps(params) # 调用OpenAI API response = client.chat.completions.create( model="gpt-4-turbo", messages=[{"role": "user", "content": "使用工具执行任务"}], tools=[{ "type": "function", "function": { "name": tool_name, "description": "工具描述", "parameters": { "type": "object", "properties": {}, "required": [] } } }], tool_choice={"type": "function", "function": {"name": tool_name}} ) # 处理工具调用结果 tool_calls = response.choices[0].message.tool_calls if tool_calls: tool_call = tool_calls[0] # 执行实际工具调用... return tool_call.function.arguments return None # 使用示例 result = call_tool("queryPositions", {"query": "经理"}) # 或者不带参数 result = call_tool("queryPositions") ``` ### 3. 在工具定义中添加必填参数 为避免参数验证问题,可以为每个工具添加至少一个必填参数。这样可以确保调用者必须提供参数。 ```go Tool: mcp.NewTool( "queryPositions", mcp.WithDescription("查询岗位列表"), mcp.WithString("query", mcp.Required(), mcp.Description("搜索关键词,可为空字符串但必须提供")), // 其他可选参数... ), ``` ## 在JavaScript中调用API的正确方式 如果您在前端JavaScript中调用OpenAI API,确保遵循以下模式: ```javascript async function callOpenAIWithTool(toolName, params = {}) { const response = await fetch('https://api.openai.com/v1/chat/completions', { method: 'POST', headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${OPENAI_API_KEY}` }, body: JSON.stringify({ model: 'gpt-4-turbo', messages: [{ role: 'user', content: '使用工具执行任务' }], tools: [{ type: 'function', function: { name: toolName, description: '工具描述', parameters: { type: 'object', properties: {} } } }], tool_choice: { type: 'function', function: { name: toolName } } }) }); const data = await response.json(); return data; } // 调用示例 callOpenAIWithTool('queryPositions', {query: ''}) // 提供空字符串也可以 .then(result => console.log(result)) .catch(error => console.error(error)); ``` ## 针对您的工具的特定解决方案 对于`queryPositions`工具,我建议始终提供一个空的查询参数: ```python # Python示例 result = call_tool("queryPositions", {"query": ""}) ``` ```javascript // JavaScript示例 callOpenAIWithTool('queryPositions', {query: ''}) ``` 如果您遇到同样的问题,对其他工具也采用类似的方法,始终提供至少一个参数,即使是空值。