API
Anthropic Messages API
Pendra translates Anthropic's Messages format to OpenAI Chat Completions under the hood, so you can point any Anthropic SDK — or Claude Code — at Pendra and get the same Anthropic-shaped responses back, served by a Pendra-managed or self-hosted worker.
Endpoint
POST https://api.pendra.ai/v1/messages Authentication
Send your Pendra API key on the x-api-key header (Anthropic
convention). The Authorization: Bearer header also works for
OpenAI-style clients.
Request
curl https://api.pendra.ai/v1/messages \
-H "x-api-key: pdr_sk_..." \
-H "anthropic-version: 2023-06-01" \
-H "Content-Type: application/json" \
-d '{
"model": "qwen3.6:27b",
"max_tokens": 1024,
"messages": [{"role": "user", "content": "Hello!"}]
}'
All standard Anthropic Messages fields are accepted:
model, max_tokens, messages,
system, temperature, top_p,
top_k, stop_sequences, tools,
tool_choice, and stream.
Response
Pendra returns the Anthropic message envelope. content
is an array of content blocks (text, tool_use, etc.). stop_reason
is "end_turn" on a natural finish or "max_tokens"
when capped. usage uses Anthropic naming
(input_tokens / output_tokens).
{
"id": "msg_01N3Xc8...",
"type": "message",
"role": "assistant",
"model": "qwen3.6:27b",
"content": [
{
"type": "text",
"text": "Hello! How can I help you today?"
}
],
"stop_reason": "end_turn",
"stop_sequence": null,
"usage": {
"input_tokens": 9,
"output_tokens": 12
}
} Anthropic SDK
import Anthropic from "@anthropic-ai/sdk";
const client = new Anthropic({
apiKey: "pdr_sk_...",
baseURL: "https://api.pendra.ai",
});
const msg = await client.messages.create({
model: "qwen3.6:27b",
max_tokens: 1024,
messages: [{ role: "user", content: "Hello!" }],
}); Streaming
Set "stream": true to receive Anthropic-format SSE events
(message_start, content_block_delta,
message_delta, message_stop). The
X-Request-Id response header is also set on streaming
responses for support and reconciliation.
event: message_start
data: {"type":"message_start","message":{"id":"msg_01N3Xc8","type":"message","role":"assistant","content":[],"model":"qwen3.6:27b","stop_reason":null,"usage":{"input_tokens":9,"output_tokens":0}}}
event: content_block_start
data: {"type":"content_block_start","index":0,"content_block":{"type":"text","text":""}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":"Hello"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":"!"}}
event: content_block_stop
data: {"type":"content_block_stop","index":0}
event: message_delta
data: {"type":"message_delta","delta":{"stop_reason":"end_turn","stop_sequence":null},"usage":{"output_tokens":2}}
event: message_stop
data: {"type":"message_stop"} Use with Claude Code
Point Claude Code at Pendra by setting two environment variables — see the full recipe in Integrations → Claude Code.