OpenAI Compatible Protocol
The OpenAI compatible protocol is the most widely supported AI API standard in the industry. RouteAPI fully implements the OpenAI API specification, allowing you to seamlessly integrate with existing OpenAI SDKs, tools, and clients by simply switching the Base URL and API Key.
Protocol Overview
Section titled “Protocol Overview”The OpenAI API defines a standardized set of REST interfaces for conversation generation, text embeddings, model listing, and other capabilities. Its core advantage lies in its mature ecosystem: OpenAI official SDKs, LangChain, LiteLLM, Cursor, and various coding assistants natively support this protocol.
RouteAPI compatibility scope:
- Fully compatible with OpenAI Chat Completions, Responses, Embeddings, and Models endpoints
- Consistent authentication using
Authorization: Bearerrequest headers - Consistent request/response formats, including streaming SSE and error structures
- Broader model ID range, can call OpenAI, Claude, Gemini, Mistral, and other providers
- Explicit zero-value parameters preserved, explicitly passed
0/falseare not dropped
Migrating from the official OpenAI API to RouteAPI requires only two configuration changes:
from openai import OpenAI
client = OpenAI( api_key="sk-your-routeapi-token", # Switch to RouteAPI Token base_url="https://api.routeapi.ai/v1" # Switch to RouteAPI Base URL)All other code remains unchanged.
Base URL
Section titled “Base URL”https://api.routeapi.ai/v1All OpenAI compatible endpoints use this base URL. If your client or SDK requires the full URL, simply append the endpoint path, e.g., https://api.routeapi.ai/v1/chat/completions.
Authentication
Section titled “Authentication”Identical to the official OpenAI API, using the HTTP Authorization request header:
Authorization: Bearer sk-your-routeapi-tokenContent-Type: application/jsonRouteAPI Tokens start with sk- and are generated on the API Keys page in the console. Store tokens on the server side and do not expose them in browsers, mobile apps, or public repositories.
Supported Endpoints Overview
Section titled “Supported Endpoints Overview”| Endpoint | Purpose | Detailed Documentation |
|---|---|---|
/v1/chat/completions | Conversation generation, supports multi-turn dialogue, tool calling, structured output | Chat Completions |
/v1/responses | OpenAI Responses protocol, suitable for coding agents and next-generation application frameworks | Responses |
/v1/embeddings | Text vector embeddings for semantic search, RAG, similarity calculation | Embeddings |
/v1/models | Get the list of models available to the current account | Below on this page |
Use Case Comparison
Section titled “Use Case Comparison”| Scenario | Recommended Endpoint | Reason |
|---|---|---|
| General chat, Q&A, summarization, classification | /v1/chat/completions | Most mature ecosystem, broadest compatibility |
| Coding agents (Cursor, Claude Code, Copilot) | /v1/responses or /v1/chat/completions | Depends on the protocol natively supported by the client |
| Multi-turn dialogue, conversation history | /v1/chat/completions | messages array naturally supports multiple rounds |
| Tool calling, function calling | /v1/chat/completions | Most standard tool definition and result passing structure |
| Semantic search, RAG, document retrieval | /v1/embeddings | Returns vector representations |
| Structured output, JSON Schema | /v1/chat/completions or /v1/responses | Controlled via response_format parameter |
The specific endpoint choice should prioritize the client and SDK’s native support. If the client explicitly requires a certain protocol, follow the client’s requirements.
SDK Configuration
Section titled “SDK Configuration”OpenAI Python SDK
Section titled “OpenAI Python SDK”Installation:
pip install openaiConfigure RouteAPI:
import osfrom openai import OpenAI
client = OpenAI( api_key=os.environ["ROUTEAPI_KEY"], base_url="https://api.routeapi.ai/v1")
response = client.chat.completions.create( model="gpt-5.5", messages=[ {"role": "user", "content": "Please introduce RouteAPI in one sentence"} ])
print(response.choices[0].message.content)Only the api_key and base_url parameters need to be set; all other code is identical to the official API.
OpenAI Node.js SDK
Section titled “OpenAI Node.js SDK”Installation:
npm install openaiConfigure RouteAPI:
import OpenAI from 'openai';
const client = new OpenAI({ apiKey: process.env.ROUTEAPI_KEY, baseURL: 'https://api.routeapi.ai/v1'});
const response = await client.chat.completions.create({ model: 'gpt-5.5', messages: [ { role: 'user', content: 'Please introduce RouteAPI in one sentence' } ]});
console.log(response.choices[0].message.content);LangChain
Section titled “LangChain”LangChain’s ChatOpenAI class supports custom base_url:
from langchain_openai import ChatOpenAI
llm = ChatOpenAI( model="gpt-5.5", openai_api_key=os.environ["ROUTEAPI_KEY"], openai_api_base="https://api.routeapi.ai/v1")
response = llm.invoke("Please introduce RouteAPI in one sentence")print(response.content)LiteLLM
Section titled “LiteLLM”LiteLLM’s completion() function supports custom api_base:
import litellm
response = litellm.completion( model="gpt-5.5", messages=[{"role": "user", "content": "Please introduce RouteAPI in one sentence"}], api_key=os.environ["ROUTEAPI_KEY"], api_base="https://api.routeapi.ai/v1")
print(response.choices[0].message.content)Other Compatible Clients
Section titled “Other Compatible Clients”Any client, tool, or framework that supports the OpenAI API can integrate with RouteAPI through the following configuration:
- API Key set to RouteAPI Token (starts with
sk-) - Base URL set to
https://api.routeapi.ai/v1 - Model ID use model names supported by RouteAPI (query via
/v1/models)
Core Request Parameters
Section titled “Core Request Parameters”The main endpoints of the OpenAI compatible protocol share a core set of parameters. Below is a quick reference table for common parameters; detailed explanations are in each endpoint’s dedicated documentation.
Chat Completions Parameters
Section titled “Chat Completions Parameters”| Parameter | Type | Required | Description |
|---|---|---|---|
model | string | Yes | Model ID, must be available to the current account |
messages | array | Yes | Conversation message list, each message contains role and content |
stream | boolean | No | Whether to use SSE streaming output, default false |
temperature | number | No | Sampling temperature, range 0 to 2, default 1 |
top_p | number | No | Nucleus sampling parameter, range 0 to 1 |
max_tokens | number | No | Maximum output tokens (legacy parameter name, still required by some models) |
max_completion_tokens | number | No | Maximum output tokens (new parameter name) |
tools | array | No | Tool definition list for function calling |
tool_choice | string/object | No | Tool selection strategy (auto / required / none / specific tool) |
response_format | object | No | Output format constraint (JSON mode / JSON Schema) |
stream_options | object | No | Additional streaming options, such as include_usage |
stop | string/array | No | Custom stop sequences |
presence_penalty | number | No | Presence penalty, range -2 to 2 |
frequency_penalty | number | No | Frequency penalty, range -2 to 2 |
user | string | No | End user identifier for abuse detection |
For detailed explanations and more parameters, refer to the Chat Completions documentation.
Embeddings Parameters
Section titled “Embeddings Parameters”| Parameter | Type | Required | Description |
|---|---|---|---|
model | string | Yes | Embedding model ID |
input | string/array | Yes | Text to embed, supports single string or string array |
encoding_format | string | No | Return format, float (default) or base64 |
dimensions | number | No | Output vector dimensions, depends on model support |
user | string | No | End user identifier |
For detailed explanations, refer to the Embeddings documentation.
Response Formats
Section titled “Response Formats”Standard Response (Non-streaming)
Section titled “Standard Response (Non-streaming)”Chat Completions standard response example:
{ "id": "chatcmpl_xxx", "object": "chat.completion", "created": 1730000000, "model": "gpt-5.5", "choices": [ { "index": 0, "message": { "role": "assistant", "content": "RouteAPI is an API gateway that unifies access to multiple AI model providers." }, "finish_reason": "stop" } ], "usage": { "prompt_tokens": 24, "completion_tokens": 18, "total_tokens": 42 }}Key fields:
choices[0].message.content— Model’s text responsechoices[0].finish_reason— Completion reason (stop/length/tool_calls/content_filter)usage— Token usage statistics
Streaming Response (SSE)
Section titled “Streaming Response (SSE)”Setting stream: true returns Server-Sent Events (SSE) format incremental data:
data: {"id":"chatcmpl_xxx","object":"chat.completion.chunk","created":1730000000,"model":"gpt-5.5","choices":[{"index":0,"delta":{"role":"assistant","content":""},"finish_reason":null}]}
data: {"id":"chatcmpl_xxx","object":"chat.completion.chunk","created":1730000000,"model":"gpt-5.5","choices":[{"index":0,"delta":{"content":"RouteAPI"},"finish_reason":null}]}
data: {"id":"chatcmpl_xxx","object":"chat.completion.chunk","created":1730000000,"model":"gpt-5.5","choices":[{"index":0,"delta":{"content":" is"},"finish_reason":null}]}
data: {"id":"chatcmpl_xxx","object":"chat.completion.chunk","created":1730000000,"model":"gpt-5.5","choices":[{"index":0,"delta":{},"finish_reason":"stop"}],"usage":{"prompt_tokens":24,"completion_tokens":18,"total_tokens":42}}
data: [DONE]Streaming response characteristics:
- Each line starts with
data:followed by a JSON object - Incremental content is in
choices[0].delta.content - When complete,
finish_reasonis notnull - The last line is
data: [DONE]
If you need token usage statistics in streaming mode, set stream_options: { "include_usage": true }, and usage information will be returned in the last data chunk.
Error Response
Section titled “Error Response”Error responses follow OpenAI’s standard format:
{ "error": { "message": "Invalid API key provided", "type": "invalid_request_error", "code": "invalid_api_key" }}Common error types:
| HTTP Status Code | type | Description |
|---|---|---|
| 401 | invalid_request_error | Invalid or missing API Key |
| 429 | rate_limit_error | Rate limit exceeded |
| 500 | api_error | Internal server error |
| 503 | overloaded_error | Service overloaded |
For detailed error handling, refer to the Error Handling documentation.
Differences from Official OpenAI API
Section titled “Differences from Official OpenAI API”RouteAPI’s OpenAI compatible protocol is fully compatible at the protocol level, but has some differences in model capabilities, billing, and rate limiting:
Broader Model ID Range
Section titled “Broader Model ID Range”The official OpenAI API can only call OpenAI’s own models (gpt-4o, gpt-5.5, etc.). RouteAPI supports models from multiple providers:
- OpenAI:
gpt-4o,gpt-5.5,o3-mini, etc. - Anthropic Claude:
claude-sonnet-4-5,claude-opus-4, etc. - Google Gemini:
gemini-2.0-flash,gemini-2.5-pro, etc. - Mistral:
mistral-large,mistral-small, etc. - Others: DeepSeek, Qwen, LLaMA, etc.
Query the complete list of models available to the current account via the /v1/models endpoint.
Billing and Rate Limiting Managed by RouteAPI
Section titled “Billing and Rate Limiting Managed by RouteAPI”- Billing: Charged according to RouteAPI’s rate card, which may differ from upstream providers’ official pricing
- Rate limiting: Controlled by RouteAPI’s rate limit policies, not upstream providers’ limits
- Quotas: Account balance and quotas are managed by RouteAPI, recharge and view in the console
Parameter Support Depends on Underlying Model
Section titled “Parameter Support Depends on Underlying Model”The OpenAI compatible protocol defines a complete set of parameters, but actual support depends on the selected model:
| Capability | Description |
|---|---|
Tool calling (tools) | Depends on whether the model supports function calling |
Structured output (response_format) | Depends on whether the model supports JSON mode or JSON Schema |
Visual input (image_url) | Depends on whether the model supports multimodal input |
Streaming usage (stream_options.include_usage) | Depends on whether the model and channel support streaming usage statistics |
Reasoning control (reasoning_effort) | Only supported by some reasoning models |
It’s recommended to validate the selected model’s support for key parameters in a test environment before enabling in production.
Explicit Zero-Value Parameter Handling
Section titled “Explicit Zero-Value Parameter Handling”This is a subtle but important difference. In the OpenAI compatible protocol, if optional parameters are explicitly passed as 0, 0.0, or false, RouteAPI treats them as the user’s explicit setting rather than dropping them as default values.
For example:
{ "model": "gpt-5.5", "messages": [...], "temperature": 0, "top_p": 1.0}Here, temperature: 0 will be preserved and forwarded to the upstream model, rather than being treated as unset because “the value is 0”. This ensures clients can precisely control sampling parameters.
If you don’t want to pass a certain parameter, simply remove that field from the request; don’t pass null or 0.
Compatibility Notes
Section titled “Compatibility Notes”Capabilities Depend on Selected Model
Section titled “Capabilities Depend on Selected Model”The OpenAI compatible protocol is a standard interface definition, but specific capabilities depend on the underlying model:
- Tool calling: Requires the model to support function calling, and tool definition format to match model requirements
- Structured output: Requires the model to support JSON mode or JSON Schema
- Visual input: Requires the model to support image or multimodal input
- Streaming usage: Requires the model and channel to support returning token usage in streaming mode
If the request includes parameters the model doesn’t support, behavior depends on the parameter type:
- Ignorable parameters (such as
frequency_penalty) will be silently ignored - Critical parameters (such as
tools) may trigger errors
In production, it’s recommended to fix model IDs and prepare fallback strategies for critical business flows.
Parameter Validation and Error Messages
Section titled “Parameter Validation and Error Messages”RouteAPI performs basic validation on request parameters, such as:
- Missing required parameters (such as
model,messages) - Incorrect parameter types (such as passing a string for
temperature) - Parameter values out of range (such as
temperature: 3)
When validation fails, it returns 400 Bad Request with detailed error information. If the request passes RouteAPI’s validation but is rejected by the upstream model, it returns 500 or 502 along with the upstream’s original error message.
Cross-Model Migration Considerations
Section titled “Cross-Model Migration Considerations”When switching from one model to another, even if both use the OpenAI compatible protocol, the following points need attention:
- Context length: Different models have different maximum context lengths; excessively long requests may be rejected
- Tool calling format: Some models have stricter requirements for tool description formats
- Output style: The same prompt may produce different output styles, lengths, and formats across different models
- Token counting: Different models have different tokenizers; the same text may have different token counts
- Billing price: Different models have different unit prices; switching models may affect costs
It’s recommended to validate the complete workflow in a test environment before switching models in production.
/v1/models Endpoint
Section titled “/v1/models Endpoint”The /v1/models endpoint returns a list of models available to the current account, in a format consistent with the official OpenAI API.
Request Example
Section titled “Request Example”curl https://api.routeapi.ai/v1/models \ -H "Authorization: Bearer $ROUTEAPI_KEY"Response Example
Section titled “Response Example”{ "success": true, "object": "list", "data": [ { "id": "gpt-5.5", "object": "model", "created": 1626777600, "owned_by": "openai", "supported_endpoint_types": ["openai", "openai-response"] }, { "id": "claude-sonnet-4-5", "object": "model", "created": 1626777600, "owned_by": "anthropic", "supported_endpoint_types": ["openai", "anthropic"] } ]}The returned data array contains the models available to the current Token, not the platform’s full catalog. Each model object includes:
id— Model ID, use this value when making requestsobject— Fixed as"model"owned_by— The channel type the model belongs to;customfor platform-custom modelssupported_endpoint_types— RouteAPI extension field, the endpoint types this model can be used withcreated— A fixed placeholder value1626777600, not a real listing time; do not use it for sorting
The extra top-level success field is a RouteAPI extension. OpenAI SDKs only read data, so it does not affect parsing. The ordering of data is not guaranteed to be stable.
It’s recommended to call /v1/models once when the application starts, cache the available model list, and avoid querying on every request. For field meanings and filtering rules, see Models.
Complete Examples
Section titled “Complete Examples”curl Basic Conversation
Section titled “curl Basic Conversation”curl https://api.routeapi.ai/v1/chat/completions \ -H "Authorization: Bearer $ROUTEAPI_KEY" \ -H "Content-Type: application/json" \ -d '{ "model": "gpt-5.5", "messages": [ { "role": "system", "content": "You are a rigorous technical assistant. Keep answers concise." }, { "role": "user", "content": "Please introduce RouteAPI in one sentence" } ], "temperature": 0.7 }'Python SDK Complete Example
Section titled “Python SDK Complete Example”import osfrom openai import OpenAI
# Initialize clientclient = OpenAI( api_key=os.environ["ROUTEAPI_KEY"], base_url="https://api.routeapi.ai/v1")
# Basic conversationdef basic_chat(): response = client.chat.completions.create( model="gpt-5.5", messages=[ {"role": "system", "content": "You are a rigorous technical assistant."}, {"role": "user", "content": "Please introduce RouteAPI in one sentence"} ], temperature=0.7 ) print(response.choices[0].message.content) print(f"Usage: {response.usage.total_tokens} tokens")
# Streaming conversationdef streaming_chat(): stream = client.chat.completions.create( model="gpt-5.5", messages=[ {"role": "user", "content": "Explain step by step what an API gateway is"} ], stream=True, stream_options={"include_usage": True} )
for chunk in stream: if chunk.choices: delta = chunk.choices[0].delta if delta.content: print(delta.content, end="", flush=True) # Last chunk contains usage if hasattr(chunk, 'usage') and chunk.usage: print(f"\nUsage: {chunk.usage.total_tokens} tokens")
# Tool callingdef tool_calling(): tools = [ { "type": "function", "function": { "name": "get_weather", "description": "Query the current weather for a specified city", "parameters": { "type": "object", "properties": { "city": { "type": "string", "description": "City name, e.g., Beijing" }, "unit": { "type": "string", "enum": ["celsius", "fahrenheit"] } }, "required": ["city"] } } } ]
messages = [{"role": "user", "content": "What's the weather like in Beijing right now?"}]
# First round: model requests tool call response = client.chat.completions.create( model="gpt-5.5", messages=messages, tools=tools, tool_choice="auto" )
# Check for tool calls if response.choices[0].message.tool_calls: # Simulate tool execution tool_call = response.choices[0].message.tool_calls[0] tool_result = "Beijing, sunny, temperature 23 Celsius, humidity 45%."
# Construct second round request messages.append(response.choices[0].message) messages.append({ "role": "tool", "tool_call_id": tool_call.id, "content": tool_result })
# Second round: model generates response based on tool result final_response = client.chat.completions.create( model="gpt-5.5", messages=messages, tools=tools ) print(final_response.choices[0].message.content)
# Structured outputdef structured_output(): response = client.chat.completions.create( model="gpt-5.5", messages=[ {"role": "user", "content": "Extract key information from the following text: RouteAPI is an AI API gateway supporting OpenAI, Claude, Gemini and other models."} ], response_format={ "type": "json_schema", "json_schema": { "name": "key_info", "strict": True, "schema": { "type": "object", "properties": { "product_name": {"type": "string"}, "category": {"type": "string"}, "supported_models": { "type": "array", "items": {"type": "string"} } }, "required": ["product_name", "category", "supported_models"], "additionalProperties": False } } } ) print(response.choices[0].message.content)
if __name__ == "__main__": basic_chat() print("\n" + "="*50 + "\n") streaming_chat() print("\n" + "="*50 + "\n") tool_calling() print("\n" + "="*50 + "\n") structured_output()Node.js SDK Complete Example
Section titled “Node.js SDK Complete Example”import OpenAI from 'openai';
// Initialize clientconst client = new OpenAI({ apiKey: process.env.ROUTEAPI_KEY, baseURL: 'https://api.routeapi.ai/v1'});
// Basic conversationasync function basicChat() { const response = await client.chat.completions.create({ model: 'gpt-5.5', messages: [ { role: 'system', content: 'You are a rigorous technical assistant.' }, { role: 'user', content: 'Please introduce RouteAPI in one sentence' } ], temperature: 0.7 });
console.log(response.choices[0].message.content); console.log(`Usage: ${response.usage.total_tokens} tokens`);}
// Streaming conversationasync function streamingChat() { const stream = await client.chat.completions.create({ model: 'gpt-5.5', messages: [ { role: 'user', content: 'Explain step by step what an API gateway is' } ], stream: true, stream_options: { include_usage: true } });
for await (const chunk of stream) { if (chunk.choices[0]?.delta?.content) { process.stdout.write(chunk.choices[0].delta.content); } if (chunk.usage) { console.log(`\nUsage: ${chunk.usage.total_tokens} tokens`); } }}
// Tool callingasync function toolCalling() { const tools = [ { type: 'function', function: { name: 'get_weather', description: 'Query the current weather for a specified city', parameters: { type: 'object', properties: { city: { type: 'string', description: 'City name, e.g., Beijing' }, unit: { type: 'string', enum: ['celsius', 'fahrenheit'] } }, required: ['city'] } } } ];
const messages = [ { role: 'user', content: "What's the weather like in Beijing right now?" } ];
// First round const response = await client.chat.completions.create({ model: 'gpt-5.5', messages: messages, tools: tools, tool_choice: 'auto' });
// Check for tool calls if (response.choices[0].message.tool_calls) { const toolCall = response.choices[0].message.tool_calls[0]; const toolResult = 'Beijing, sunny, temperature 23 Celsius, humidity 45%.';
// Second round messages.push(response.choices[0].message); messages.push({ role: 'tool', tool_call_id: toolCall.id, content: toolResult });
const finalResponse = await client.chat.completions.create({ model: 'gpt-5.5', messages: messages, tools: tools });
console.log(finalResponse.choices[0].message.content); }}
// Structured outputasync function structuredOutput() { const response = await client.chat.completions.create({ model: 'gpt-5.5', messages: [ { role: 'user', content: 'Extract key information from the following text: RouteAPI is an AI API gateway supporting OpenAI, Claude, Gemini and other models.' } ], response_format: { type: 'json_schema', json_schema: { name: 'key_info', strict: true, schema: { type: 'object', properties: { product_name: { type: 'string' }, category: { type: 'string' }, supported_models: { type: 'array', items: { type: 'string' } } }, required: ['product_name', 'category', 'supported_models'], additionalProperties: false } } } });
console.log(response.choices[0].message.content);}
// Run examplesasync function main() { await basicChat(); console.log('\n' + '='.repeat(50) + '\n'); await streamingChat(); console.log('\n' + '='.repeat(50) + '\n'); await toolCalling(); console.log('\n' + '='.repeat(50) + '\n'); await structuredOutput();}
main().catch(console.error);Integration Recommendations
Section titled “Integration Recommendations”- Prioritize the OpenAI compatible protocol if your client, SDK, or tool natively supports the OpenAI API
- Fix model IDs, don’t rely on temporary aliases or display names in production
- Record request metadata, including request ID, model ID, status code, latency, and token usage
- Enable failure retries, enable client retries and alternative model options for core business flows
- Validate optional capabilities, test tool calling, structured output, visual input, and other capabilities in a test environment first
- Monitor costs and quotas, regularly check usage logs and billing details in the console
- Protect API Keys, encapsulate RouteAPI Tokens on the server side and avoid exposing keys directly to business frontends
If the client only supports Claude Messages or Google Gemini protocol, use the corresponding protocol endpoints; refer to Claude Messages and Gemini API documentation.