> ## Documentation Index
> Fetch the complete documentation index at: https://quwan-b8010aef.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# OpenAI 工具调用示例

> 使用OpenAI接口进行Function Calling工具调用的完整示例代码

# OpenAI 工具调用示例

以下示例展示如何使用OpenAI兼容接口进行Function Calling（工具调用），让AI能够调用外部函数来获取信息或执行操作。

## 快速开始

只需要替换 `<API-KEY>` 为你的实际API密钥即可运行。

```bash cURL theme={null}
curl -X POST "https://api.tokenops.ai/v1/chat/completions" \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer <API-KEY>" \
  -d '{
    "model": "gpt-5-2025-08-07",
    "messages": [
      {
        "role": "user",
        "content": "北京今天的天气怎么样？"
      }
    ],
    "tools": [
      {
        "type": "function",
        "function": {
          "name": "get_weather",
          "description": "获取指定城市的天气信息",
          "parameters": {
            "type": "object",
            "properties": {
              "city": {
                "type": "string",
                "description": "城市名称"
              },
              "unit": {
                "type": "string",
                "enum": ["celsius", "fahrenheit"],
                "description": "温度单位"
              }
            },
            "required": ["city"]
          }
        }
      }
    ],
    "tool_choice": "auto"
  }'
```

```python Python theme={null}
import requests
import json

# 配置API密钥和基础URL
API_KEY = "<API-KEY>"
BASE_URL = "https://api.tokenops.ai/v1"

# 定义可调用的工具函数
def get_weather(city, unit="celsius"):
    """模拟获取天气信息"""
    weather_data = {
        "北京": {"temperature": 22, "condition": "晴天", "humidity": 45},
        "上海": {"temperature": 25, "condition": "多云", "humidity": 60},
        "广州": {"temperature": 28, "condition": "小雨", "humidity": 75},
        "深圳": {"temperature": 27, "condition": "晴天", "humidity": 55}
    }
    
    if city in weather_data:
        data = weather_data[city]
        temp = data["temperature"]
        if unit == "fahrenheit":
            temp = temp * 9/5 + 32
        return {
            "city": city,
            "temperature": f"{temp}°{'C' if unit == 'celsius' else 'F'}",
            "condition": data["condition"],
            "humidity": f"{data['humidity']}%"
        }
    else:
        return {"error": f"没有找到{city}的天气信息"}

def get_stock_price(symbol):
    """模拟获取股票价格"""
    stock_data = {
        "AAPL": {"price": 150.25, "change": "+2.30", "change_percent": "+1.55%"},
        "GOOGL": {"price": 2750.80, "change": "-15.20", "change_percent": "-0.55%"},
        "TSLA": {"price": 245.67, "change": "+8.90", "change_percent": "+3.76%"}
    }
    
    symbol = symbol.upper()
    if symbol in stock_data:
        return stock_data[symbol]
    else:
        return {"error": f"没有找到股票代码{symbol}的信息"}

def calculate(expression):
    """安全的数学计算"""
    try:
        # 简单的安全检查
        allowed_chars = set('0123456789+-*/.() ')
        if not all(c in allowed_chars for c in expression):
            return {"error": "表达式包含不允许的字符"}
        
        result = eval(expression)
        return {"expression": expression, "result": result}
    except Exception as e:
        return {"error": f"计算错误: {str(e)}"}

# 工具函数映射
AVAILABLE_FUNCTIONS = {
    "get_weather": get_weather,
    "get_stock_price": get_stock_price,
    "calculate": calculate
}

def chat_with_tools(message):
    url = f"{BASE_URL}/chat/completions"
    headers = {
        "Content-Type": "application/json",
        "Authorization": f"Bearer {API_KEY}"
    }
    
    # 定义可用的工具
    tools = [
        {
            "type": "function",
            "function": {
                "name": "get_weather",
                "description": "获取指定城市的天气信息",
                "parameters": {
                    "type": "object",
                    "properties": {
                        "city": {
                            "type": "string",
                            "description": "城市名称"
                        },
                        "unit": {
                            "type": "string",
                            "enum": ["celsius", "fahrenheit"],
                            "description": "温度单位"
                        }
                    },
                    "required": ["city"]
                }
            }
        },
        {
            "type": "function",
            "function": {
                "name": "get_stock_price",
                "description": "获取股票的当前价格",
                "parameters": {
                    "type": "object",
                    "properties": {
                        "symbol": {
                            "type": "string",
                            "description": "股票代码，如AAPL, GOOGL等"
                        }
                    },
                    "required": ["symbol"]
                }
            }
        },
        {
            "type": "function",
            "function": {
                "name": "calculate",
                "description": "执行数学计算",
                "parameters": {
                    "type": "object",
                    "properties": {
                        "expression": {
                            "type": "string",
                            "description": "要计算的数学表达式"
                        }
                    },
                    "required": ["expression"]
                }
            }
        }
    ]
    
    messages = [
        {
            "role": "user",
            "content": message
        }
    ]
    
    data = {
        "model": "gpt-5-2025-08-07",
        "messages": messages,
        "tools": tools,
        "tool_choice": "auto"
    }
    
    response = requests.post(url, headers=headers, json=data)
    
    if response.status_code != 200:
        return f"错误: {response.status_code} - {response.text}"
    
    result = response.json()
    message = result['choices'][0]['message']
    
    # 检查是否需要调用工具
    if message.get('tool_calls'):
        messages.append(message)  # 添加助手的消息
        
        # 处理每个工具调用
        for tool_call in message['tool_calls']:
            function_name = tool_call['function']['name']
            function_args = json.loads(tool_call['function']['arguments'])
            
            print(f"调用工具: {function_name}")
            print(f"参数: {function_args}")
            
            # 执行函数调用
            if function_name in AVAILABLE_FUNCTIONS:
                function_response = AVAILABLE_FUNCTIONS[function_name](**function_args)
            else:
                function_response = {"error": f"未知的函数: {function_name}"}
            
            # 添加函数调用结果到消息历史
            messages.append({
                "tool_call_id": tool_call['id'],
                "role": "tool",
                "name": function_name,
                "content": json.dumps(function_response, ensure_ascii=False)
            })
        
        # 使用工具调用结果重新请求
        data["messages"] = messages
        second_response = requests.post(url, headers=headers, json=data)
        
        if second_response.status_code == 200:
            final_result = second_response.json()
            return final_result['choices'][0]['message']['content']
        else:
            return f"二次请求错误: {second_response.status_code} - {second_response.text}"
    else:
        return message['content']

# 使用示例
if __name__ == "__main__":
    # 天气查询示例
    print("=== 天气查询 ===")
    weather_response = chat_with_tools("北京今天的天气怎么样？")
    print(weather_response)
    
    print("\n=== 股票价格查询 ===")
    stock_response = chat_with_tools("AAPL的股价是多少？")
    print(stock_response)
    
    print("\n=== 数学计算 ===")
    calc_response = chat_with_tools("帮我计算 25 * 4 + 10")
    print(calc_response)
    
    print("\n=== 复合查询 ===")
    complex_response = chat_with_tools("北京的天气如何？另外帮我算一下100除以3等于多少？")
    print(complex_response)
```

```javascript JavaScript/Node.js theme={null}
const axios = require('axios');

// 配置API密钥和基础URL
const API_KEY = '<API-KEY>';
const BASE_URL = 'https://api.tokenops.ai/v1';

// 定义可调用的工具函数
function getWeather(city, unit = 'celsius') {
    const weatherData = {
        '北京': { temperature: 22, condition: '晴天', humidity: 45 },
        '上海': { temperature: 25, condition: '多云', humidity: 60 },
        '广州': { temperature: 28, condition: '小雨', humidity: 75 },
        '深圳': { temperature: 27, condition: '晴天', humidity: 55 }
    };
    
    if (weatherData[city]) {
        const data = weatherData[city];
        let temp = data.temperature;
        if (unit === 'fahrenheit') {
            temp = temp * 9/5 + 32;
        }
        return {
            city: city,
            temperature: `${temp}°${unit === 'celsius' ? 'C' : 'F'}`,
            condition: data.condition,
            humidity: `${data.humidity}%`
        };
    } else {
        return { error: `没有找到${city}的天气信息` };
    }
}

function getStockPrice(symbol) {
    const stockData = {
        'AAPL': { price: 150.25, change: '+2.30', change_percent: '+1.55%' },
        'GOOGL': { price: 2750.80, change: '-15.20', change_percent: '-0.55%' },
        'TSLA': { price: 245.67, change: '+8.90', change_percent: '+3.76%' }
    };
    
    symbol = symbol.toUpperCase();
    if (stockData[symbol]) {
        return stockData[symbol];
    } else {
        return { error: `没有找到股票代码${symbol}的信息` };
    }
}

function calculate(expression) {
    try {
        // 简单的安全检查
        const allowedChars = /^[0-9+\-*/.() ]+$/;
        if (!allowedChars.test(expression)) {
            return { error: '表达式包含不允许的字符' };
        }
        
        const result = eval(expression);
        return { expression: expression, result: result };
    } catch (error) {
        return { error: `计算错误: ${error.message}` };
    }
}

// 工具函数映射
const AVAILABLE_FUNCTIONS = {
    get_weather: getWeather,
    get_stock_price: getStockPrice,
    calculate: calculate
};

async function chatWithTools(message) {
    const url = `${BASE_URL}/chat/completions`;
    const headers = {
        'Content-Type': 'application/json',
        'Authorization': `Bearer ${API_KEY}`
    };
    
    // 定义可用的工具
    const tools = [
        {
            type: 'function',
            function: {
                name: 'get_weather',
                description: '获取指定城市的天气信息',
                parameters: {
                    type: 'object',
                    properties: {
                        city: {
                            type: 'string',
                            description: '城市名称'
                        },
                        unit: {
                            type: 'string',
                            enum: ['celsius', 'fahrenheit'],
                            description: '温度单位'
                        }
                    },
                    required: ['city']
                }
            }
        },
        {
            type: 'function',
            function: {
                name: 'get_stock_price',
                description: '获取股票的当前价格',
                parameters: {
                    type: 'object',
                    properties: {
                        symbol: {
                            type: 'string',
                            description: '股票代码，如AAPL, GOOGL等'
                        }
                    },
                    required: ['symbol']
                }
            }
        },
        {
            type: 'function',
            function: {
                name: 'calculate',
                description: '执行数学计算',
                parameters: {
                    type: 'object',
                    properties: {
                        expression: {
                            type: 'string',
                            description: '要计算的数学表达式'
                        }
                    },
                    required: ['expression']
                }
            }
        }
    ];
    
    let messages = [
        {
            role: 'user',
            content: message
        }
    ];
    
    const data = {
        model: 'gpt-5-2025-08-07',
        messages: messages,
        tools: tools,
        tool_choice: 'auto'
    };
    
    try {
        const response = await axios.post(url, data, { headers });
        const responseMessage = response.data.choices[0].message;
        
        // 检查是否需要调用工具
        if (responseMessage.tool_calls) {
            messages.push(responseMessage); // 添加助手的消息
            
            // 处理每个工具调用
            for (const toolCall of responseMessage.tool_calls) {
                const functionName = toolCall.function.name;
                const functionArgs = JSON.parse(toolCall.function.arguments);
                
                console.log(`调用工具: ${functionName}`);
                console.log(`参数:`, functionArgs);
                
                // 执行函数调用
                let functionResponse;
                if (AVAILABLE_FUNCTIONS[functionName]) {
                    functionResponse = AVAILABLE_FUNCTIONS[functionName](...Object.values(functionArgs));
                } else {
                    functionResponse = { error: `未知的函数: ${functionName}` };
                }
                
                // 添加函数调用结果到消息历史
                messages.push({
                    tool_call_id: toolCall.id,
                    role: 'tool',
                    name: functionName,
                    content: JSON.stringify(functionResponse)
                });
            }
            
            // 使用工具调用结果重新请求
            data.messages = messages;
            const secondResponse = await axios.post(url, data, { headers });
            return secondResponse.data.choices[0].message.content;
        } else {
            return responseMessage.content;
        }
    } catch (error) {
        return `错误: ${error.response?.status} - ${error.response?.data || error.message}`;
    }
}

// 使用示例
(async () => {
    try {
        console.log('=== 天气查询 ===');
        const weatherResponse = await chatWithTools('北京今天的天气怎么样？');
        console.log(weatherResponse);
        
        console.log('\n=== 股票价格查询 ===');
        const stockResponse = await chatWithTools('AAPL的股价是多少？');
        console.log(stockResponse);
        
        console.log('\n=== 数学计算 ===');
        const calcResponse = await chatWithTools('帮我计算 25 * 4 + 10');
        console.log(calcResponse);
    } catch (error) {
        console.error('错误:', error.message);
    }
})();
```

## 工具调用的工作流程

1. **定义工具**: 在请求中定义可用的函数及其参数
2. **AI决策**: AI根据用户输入决定是否需要调用工具
3. **函数调用**: AI生成函数调用请求
4. **执行函数**: 客户端执行相应的函数
5. **返回结果**: 将函数结果发送回AI
6. **生成回复**: AI基于函数结果生成最终回复

## 工具定义格式

```json theme={null}
{
  "type": "function",
  "function": {
    "name": "function_name",
    "description": "函数的描述",
    "parameters": {
      "type": "object",
      "properties": {
        "param1": {
          "type": "string",
          "description": "参数1的描述"
        }
      },
      "required": ["param1"]
    }
  }
}
```

## 应用场景

* **信息查询**: 天气、股票、新闻等实时信息
* **数据计算**: 数学计算、数据分析
* **系统操作**: 文件操作、数据库查询
* **外部API**: 调用第三方服务
* **业务逻辑**: 执行特定的业务流程

## 最佳实践

1. **清晰的函数描述**: 提供准确的函数和参数描述
2. **参数验证**: 在函数中进行输入参数验证
3. **错误处理**: 妥善处理函数执行中的错误
4. **安全考虑**: 避免执行危险的操作
5. **性能优化**: 对于耗时操作考虑异步处理

## 注意事项

* 工具调用需要两次API请求（决策+生成回复）
* 确保函数执行的安全性，避免恶意代码注入
* 合理设置 `tool_choice` 参数控制工具使用
* 函数返回结果应该是JSON可序列化的格式


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.