Perplexity Router API
Overview
Section titled “Overview”The Router API provides unified access to open-weight models hosted by Perplexity through a single API and API key. Send requests in the OpenAI Chat Completions, OpenAI Responses, or Anthropic Messages format, pick any model from the catalog, and the platform routes each request to a healthy deployment automatically — no per-provider accounts, SDKs, or failover logic on your side.
Any model in the catalog can be called through any supported schema, regardless of the model's original provider. This makes the Router a drop-in replacement for existing OpenAI or Anthropic integrations — only the base URL and API key need to change.
Use the Router API for direct model access with your own prompts and tools. For web-grounded answers with built-in citations, use the Agent API.
The base URL is https://api.perplexity.ai/router/v1, and your existing Perplexity API key works as-is.
Installation
Section titled “Installation”The Router API supports the OpenAI Chat Completions and Responses formats plus the Anthropic Messages format, so you can use either provider's official SDK — install whichever matches your integration (or both):
pip install openai # OpenAI Chat Completions and Responses formats
pip install anthropic # Anthropic Messages formatnpm install openai # OpenAI Chat Completions and Responses formats
npm install @anthropic-ai/sdk # Anthropic Messages formatAuthentication
Section titled “Authentication”Set your API key as an environment variable:
export PERPLEXITY_API_KEY="your_api_key_here"setx PERPLEXITY_API_KEY "your_api_key_here"Requests authenticate with an Authorization: Bearer header, which the SDKs set for you from the api_key parameter.
Basic Usage
Section titled “Basic Usage”Point the OpenAI SDK at the Router base URL and pass any model id from the catalog. Model ids use creator/model-name slugs, so switching providers is a one-line change:
from openai import OpenAI
import os
client = OpenAI(
api_key=os.environ.get("PERPLEXITY_API_KEY"),
base_url="https://api.perplexity.ai/router/v1"
)
response = client.chat.completions.create(
model="perplexity/kimi-k3",
max_tokens=1024,
messages=[
{"role": "user", "content": "Explain the CAP theorem in two sentences."}
]
)
print(response.choices[0].message.content)import OpenAI from 'openai';
const client = new OpenAI({
apiKey: process.env.PERPLEXITY_API_KEY,
baseURL: "https://api.perplexity.ai/router/v1"
});
const response = await client.chat.completions.create({
model: "perplexity/kimi-k3",
max_tokens: 1024,
messages: [
{ role: "user", content: "Explain the CAP theorem in two sentences." }
]
});
console.log(response.choices[0].message.content);curl -X POST 'https://api.perplexity.ai/router/v1/chat/completions' \
-H "Authorization: Bearer $PERPLEXITY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "perplexity/kimi-k3",
"max_tokens": 1024,
"messages": [
{"role": "user", "content": "Explain the CAP theorem in two sentences."}
]
}' | jqResponse
{
"id": "chatcmpl-Xr7aQ2mVb9L4tW8pDcEfGh1JkNs0y",
"object": "chat.completion",
"created": 1753747200,
"model": "perplexity/kimi-k3",
"choices": [
{
"index": 0,
"message": {
"role": "assistant",
"content": "The CAP theorem states that a distributed system can guarantee at most two of three properties: consistency, availability, and partition tolerance. Since network partitions are unavoidable in practice, designers must choose between consistency and availability when a partition occurs.",
"annotations": []
},
"logprobs": null,
"finish_reason": "stop"
}
],
"usage": {
"prompt_tokens": 18,
"completion_tokens": 52,
"total_tokens": 70,
"prompt_tokens_details": {
"cached_tokens": 0
}
}
}The response echoes the model id you requested, and you are always billed at that model's published rates no matter how the request was served.
OpenAI Responses
Section titled “OpenAI Responses”Use client.responses.create() with the same Router base URL when your integration uses the OpenAI Responses format. The Router Responses endpoint is stateless, so include the full conversation in input on each request.
from openai import OpenAI
import os
client = OpenAI(
api_key=os.environ.get("PERPLEXITY_API_KEY"),
base_url="https://api.perplexity.ai/router/v1"
)
response = client.responses.create(
model="perplexity/kimi-k3",
input="Explain the CAP theorem in two sentences.",
max_output_tokens=1024
)
print(response.output_text)import OpenAI from 'openai';
const client = new OpenAI({
apiKey: process.env.PERPLEXITY_API_KEY,
baseURL: "https://api.perplexity.ai/router/v1"
});
const response = await client.responses.create({
model: "perplexity/kimi-k3",
input: "Explain the CAP theorem in two sentences.",
max_output_tokens: 1024
});
console.log(response.output_text);curl -X POST 'https://api.perplexity.ai/router/v1/responses' \
-H "Authorization: Bearer $PERPLEXITY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "perplexity/kimi-k3",
"input": "Explain the CAP theorem in two sentences.",
"max_output_tokens": 1024
}' | jqStreaming Chat Completions
Section titled “Streaming Chat Completions”Set stream: true to receive tokens as server-sent events. To get token usage with a streamed response, also set stream_options: {"include_usage": true} — usage then arrives in a final chunk before data: [DONE]:
from openai import OpenAI
import os
client = OpenAI(
api_key=os.environ.get("PERPLEXITY_API_KEY"),
base_url="https://api.perplexity.ai/router/v1"
)
stream = client.chat.completions.create(
model="perplexity/kimi-k3",
max_tokens=1024,
messages=[
{"role": "user", "content": "Write a haiku about network latency."}
],
stream=True,
stream_options={"include_usage": True}
)
for chunk in stream:
if chunk.choices and chunk.choices[0].delta.content:
print(chunk.choices[0].delta.content, end="")
if chunk.usage:
print(f"\n\nTokens used: {chunk.usage.total_tokens}")import OpenAI from 'openai';
const client = new OpenAI({
apiKey: process.env.PERPLEXITY_API_KEY,
baseURL: "https://api.perplexity.ai/router/v1"
});
const stream = await client.chat.completions.create({
model: "perplexity/kimi-k3",
max_tokens: 1024,
messages: [
{ role: "user", content: "Write a haiku about network latency." }
],
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(`\n\nTokens used: ${chunk.usage.total_tokens}`);
}
}curl -N -X POST 'https://api.perplexity.ai/router/v1/chat/completions' \
-H "Authorization: Bearer $PERPLEXITY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "perplexity/kimi-k3",
"max_tokens": 1024,
"messages": [
{"role": "user", "content": "Write a haiku about network latency."}
],
"stream": true,
"stream_options": {"include_usage": true}
}'Anthropic Messages
Section titled “Anthropic Messages”The same models are available in the Anthropic Messages format at /router/v1/messages, so code written against the Anthropic SDK works with a base-URL change:
from anthropic import Anthropic
import os
client = Anthropic(
api_key=os.environ.get("PERPLEXITY_API_KEY"),
base_url="https://api.perplexity.ai/router"
)
message = client.messages.create(
model="perplexity/kimi-k3",
max_tokens=1024,
messages=[
{"role": "user", "content": "Explain the CAP theorem in two sentences."}
]
)
print(message.content[0].text)import Anthropic from '@anthropic-ai/sdk';
const client = new Anthropic({
apiKey: process.env.PERPLEXITY_API_KEY,
baseURL: "https://api.perplexity.ai/router"
});
const message = await client.messages.create({
model: "perplexity/kimi-k3",
max_tokens: 1024,
messages: [
{ role: "user", content: "Explain the CAP theorem in two sentences." }
]
});
console.log(message.content[0].text);curl -X POST 'https://api.perplexity.ai/router/v1/messages' \
-H "Authorization: Bearer $PERPLEXITY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "perplexity/kimi-k3",
"max_tokens": 1024,
"messages": [
{"role": "user", "content": "Explain the CAP theorem in two sentences."}
]
}' | jqDiscovering Models
Section titled “Discovering Models”List the current catalog at any time — the response is OpenAI-compatible, sorted by model id, and includes each model's base token prices in USD per 1M tokens:
curl 'https://api.perplexity.ai/router/v1/models' \
-H "Authorization: Bearer $PERPLEXITY_API_KEY" | jqResponse
{
"object": "list",
"data": [
{
"id": "perplexity/kimi-k3",
"object": "model",
"created": 0,
"owned_by": "perplexity",
"pricing": {
"input": 3,
"output": 15,
"cache_read": 0.3,
"unit": "usd_per_1m_tokens"
}
}
]
}See the models page for the full catalog with pricing.
Next Steps
Section titled “Next Steps”Models & Pricing
The model catalog with per-token rates.
Routing & Reliability
How requests are routed and what happens when a provider fails.
Chat Completions Reference
Full request and response schema.
Responses Reference
The OpenAI Responses-compatible endpoint schema.
Messages Reference
The Anthropic-compatible endpoint schema.
Need help? Check out our community for support.