Perplexity API Guide for Developers — 2026
Advertisement
Introduction
Why This Matters
The Perplexity API exposes the same real-time web search capability that powers perplexity.ai, accessible via an OpenAI-compatible endpoint. This means you can build applications that answer questions with current, cited information without implementing your own search pipeline. For developer tools, documentation assistants, research bots, and anything requiring answers based on live web content, the Perplexity API fills the gap that pure LLM APIs cannot.
How the Perplexity API Works
The Perplexity API is OpenAI-compatible — it uses the same message format as the OpenAI Chat Completions API. This means:
- Same Python and JavaScript SDKs (openai package)
- Same message structure (
role,content) - Different base URL and API key
- Responses include citation URLs in the response metadata
You can often swap Perplexity into an existing OpenAI integration with minimal changes.
Authentication and Setup
# Get your API key at perplexity.ai/settings/api
export PERPLEXITY_API_KEY="pplx-..."
# Use the openai Python package — no additional library needed
pip install openaiPricing:
- $5 per 1,000 requests (included with Perplexity Pro)
- Additional context pricing at $1 per 1M tokens for very long contexts
Basic API Call
from openai import OpenAI
client = OpenAI(
api_key="pplx-...", # Or use PERPLEXITY_API_KEY env variable
base_url="https://api.perplexity.ai",
)
def search_and_answer(question: str, model: str = "llama-3.1-sonar-large-128k-online") -> str:
"""
Ask a question with real-time web search.
Returns the answer text.
"""
response = client.chat.completions.create(
model=model,
messages=[
{
"role": "system",
"content": (
"You are a technical research assistant. "
"Provide accurate, current information with specific details. "
"Mention version numbers and dates when relevant."
),
},
{"role": "user", "content": question},
],
max_tokens=1024,
temperature=0.2,
)
return response.choices[0].message.content
answer = search_and_answer(
"What is the latest stable version of Rust and what changed in the most recent release?"
)
print(answer)Available Models
Perplexity offers two model families:
Sonar models — Perplexity's own models with web search built in. The primary production choice.
| Model | Context | Search | Best For |
|---|---|---|---|
| sonar | 128K | Yes | Quick, cost-effective lookups |
| sonar-pro | 200K | Yes | Complex research, detailed answers |
| sonar-reasoning | 128K | Yes | Multi-step reasoning with search |
Non-online models — Standard LLM inference without web search. Use only when you do not need current information.
Use llama-3.1-sonar-large-128k-online as your default production model.
Extracting Citations
Perplexity responses often include source URLs in the response metadata. Access them to build citation-aware applications:
from openai import OpenAI
client = OpenAI(
api_key="pplx-...",
base_url="https://api.perplexity.ai",
)
def search_with_citations(question: str) -> dict:
"""Return both the answer and its citations."""
response = client.chat.completions.create(
model="llama-3.1-sonar-large-128k-online",
messages=[{"role": "user", "content": question}],
max_tokens=1024,
temperature=0.2,
)
answer = response.choices[0].message.content
# Citations are in the response object under citations attribute
citations = getattr(response, "citations", [])
return {
"answer": answer,
"citations": citations,
"model": response.model,
}
result = search_with_citations(
"What are the breaking changes in React 19?"
)
print(result["answer"])
print("\nSources:")
for url in result.get("citations", []):
print(f" - {url}")Building a Library Research Pipeline
A practical use case: automatically research library updates as part of your CI/CD pipeline:
from openai import OpenAI
import json
client = OpenAI(
api_key="pplx-...",
base_url="https://api.perplexity.ai",
)
def check_library_update(library_name: str, current_version: str) -> dict:
"""Check if a library has been updated and what changed."""
question = (
f"What is the latest stable version of {library_name}? "
f"The version I'm currently using is {current_version}. "
f"If there is a newer version, what are the key changes and any breaking changes?"
)
response = client.chat.completions.create(
model="llama-3.1-sonar-large-128k-online",
messages=[
{
"role": "system",
"content": (
"Return your answer as a JSON object with fields: "
"latest_version, is_update_available, breaking_changes, "
"key_changes, upgrade_recommended. "
"For upgrade_recommended: true if major security or performance improvements, false otherwise."
),
},
{"role": "user", "content": question},
],
max_tokens=512,
temperature=0.0,
)
try:
text = response.choices[0].message.content
# Extract JSON from response
start = text.find("{")
end = text.rfind("}") + 1
return json.loads(text[start:end])
except Exception:
return {"error": "Could not parse response", "raw": response.choices[0].message.content}
# Check multiple dependencies
dependencies = [
("fastapi", "0.103.0"),
("pydantic", "2.4.0"),
("httpx", "0.25.0"),
]
for lib, version in dependencies:
result = check_library_update(lib, version)
print(f"\n{lib} ({version}):")
print(f" Latest: {result.get('latest_version', 'unknown')}")
print(f" Update available: {result.get('is_update_available', 'unknown')}")
if result.get("breaking_changes"):
print(f" Breaking changes: {result['breaking_changes']}")Multi-Turn Research Session
from openai import OpenAI
client = OpenAI(
api_key="pplx-...",
base_url="https://api.perplexity.ai",
)
class ResearchSession:
"""A multi-turn research session using Perplexity."""
def __init__(self, topic: str):
self.messages = [
{
"role": "system",
"content": (
f"You are a research assistant helping investigate: {topic}. "
"Use current web search for all answers. "
"Be specific with versions, dates, and sources."
),
}
]
def ask(self, question: str) -> str:
self.messages.append({"role": "user", "content": question})
response = client.chat.completions.create(
model="llama-3.1-sonar-large-128k-online",
messages=self.messages,
max_tokens=1024,
temperature=0.2,
)
answer = response.choices[0].message.content
self.messages.append({"role": "assistant", "content": answer})
return answer
# Research a technology decision
session = ResearchSession("Choosing between PostgreSQL and MongoDB in 2026")
print(session.ask("What are the current production adoption rates?"))
print(session.ask("What do recent benchmarks show for write performance?"))
print(session.ask("Are there any significant updates to either in the past 6 months?"))Common Mistakes
- Not using the
base_urlparameter — the request goes to OpenAI's endpoint instead - Using a non-online model when current information is needed — the
sonarmodels have-onlinevariants - Expecting 100% citation accuracy — citations are extracted heuristically; always verify important claims
- Using Perplexity for complex code generation — it searches for examples but does not generate and test code
- Not setting
temperature=0.0for research tasks where determinism matters
Best Practices
- Default to
llama-3.1-sonar-large-128k-onlinefor general research tasks - Use
temperature=0.0-0.2for factual research queries to reduce hallucination - Always extract and display citations in user-facing applications — they are the main trust signal
- Combine Perplexity (for current research) with Claude or GPT-4o (for implementation) in your AI pipeline
- Cache Perplexity responses for frequently repeated queries to reduce costs
Key Takeaways
- The Perplexity API is OpenAI-compatible — use the
openaipackage with a differentbase_url - Sonar online models (
sonar,sonar-pro) include real-time web search on every request - Citations are available in the response object under the
citationsattribute - At $5 per 1,000 requests, Perplexity API is cost-effective for research-heavy workloads
- Perplexity is the right API for "what is current" queries; use Claude or GPT-4o for "how do I implement"
- Multi-turn conversations work the same as with OpenAI — maintain message history and resend the full array
temperature=0.0is optimal for factual research queries where you need consistent, accurate output- For high-value decisions, always verify Perplexity citations against the original source pages
Advertisement