API Reference

OpenClacky exposes a set of OpenAI-compatible HTTP APIs covering text chat, image generation, video generation, and text-to-speech. If you're already using the OpenAI, Anthropic, or any major SDK, just swap base_url to ours and api_key to a key you've topped up at OpenClacky — no other code changes required.

This page is for developers. It covers four things: how to authenticate, what endpoints exist, what each request/response looks like, and how to read errors.


Basics

Item Value
Base URL https://api.openclacky.com
Auth HTTP header: Authorization: Bearer <YOUR_API_KEY>
Content type Content-Type: application/json
Get an API key Top up at the OpenClacky dashboard and generate one
Billing Pay-as-you-go from your credit balance. Only 200 OK responses are charged (4xx/5xx are free).

Authentication

Pass the bearer token on every request:

curl https://api.openclacky.com/chat/completions \
  -H "Authorization: Bearer sk-oc-xxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d '{ ... }'

x-api-key: sk-oc-xxxxxxxxxxxx is also accepted (some SDKs prefer this).


Endpoint catalog

Endpoint Purpose Compatible protocol
POST /chat/completions Text chat / tool use / multi-turn OpenAI Chat Completions
POST /images/generations Text-to-image OpenAI Images
POST /videos/generations Text/image-to-video OpenAI-style (custom)
POST /audio/speech Text-to-speech OpenAI Audio Speech
POST /model/{model}/converse Text chat (Bedrock-style) AWS Bedrock Runtime
POST /anthropic/v1/messages Text chat Anthropic Messages
POST /vertex/v1beta1/models/{model}:generateContent Native Gemini (multi-part, image edit, tools) Google Gemini generateContent
POST /vertex/v1beta1/models/{model}:streamGenerateContent Native Gemini (streaming) Google Gemini streamGenerateContent
POST /vertex/v1beta1/models/{model}:predictLongRunning Native Veo (video generation, async submit) Google Veo predictLongRunning
POST /vertex/v1beta1/models/{model}:fetchPredictOperation Native Veo (poll async result) Google Veo fetchPredictOperation
GET /models List available models OpenAI Models
GET /balance Check credit balance & quota Custom

The four most-used endpoints are documented below.


1. Chat — POST /chat/completions

Request body (standard OpenAI Chat Completions):

{
  "model": "or-claude-sonnet-4-6",
  "messages": [
    { "role": "system", "content": "You are a helpful assistant." },
    { "role": "user", "content": "Hello!" }
  ],
  "temperature": 0.7,
  "stream": false
}

Response body (standard OpenAI shape + our cost_usd):

{
  "id": "chatcmpl-xxx",
  "object": "chat.completion",
  "model": "or-claude-sonnet-4-6",
  "choices": [
    {
      "index": 0,
      "message": { "role": "assistant", "content": "Hi there!" },
      "finish_reason": "stop"
    }
  ],
  "usage": {
    "prompt_tokens": 12,
    "completion_tokens": 4,
    "total_tokens": 16
  },
  "cost_usd": 0.000084
}

Model alias rules

Prefix Upstream Examples
or-* OpenRouter / Vertex aggregator or-claude-sonnet-4-6, or-gpt-5-1, or-gemini-3-pro, or-deepseek-v3-2, or-glm-4-7, or-qwen-3-coder, or-grok-4-3, or-kimi-k2
dsk-* DeepSeek direct dsk-chat, dsk-reasoner
abs-* AWS Bedrock direct (must use /model/{model}/converse) abs-claude-opus-4-7

The full model list lives at AI Key Supported Models. Newly launched models are added there.

Streaming

Set "stream": true and you'll get a standard OpenAI SSE stream (data: {...}\n\ndata: [DONE]\n\n). Works with the Python openai SDK, Vercel AI SDK, and similar clients out of the box.


2. Image generation — POST /images/generations

Request body (OpenAI Images standard):

{
  "model": "or-gemini-3-pro-image",
  "prompt": "a corgi astronaut on Mars, photo-realistic",
  "n": 1,
  "size": "1024x1024"
}

Response body (OpenAI Images standard):

{
  "created": 1718465432,
  "data": [
    { "b64_json": "iVBORw0KGgoAAAANSUhEU..." }
  ],
  "model": "or-gemini-3-pro-image",
  "cost_usd": 0.134
}

The image comes back as inline base64, not a URL. Buffer.from(b64_json, "base64") straight to disk.

Supported models

Alias Upstream Use case
or-gemini-3-pro-image Gemini 3 Pro Image Preview Highest quality, default pick
or-gemini-3-1-flash-image Gemini 3.1 Flash Image Faster + cheaper, everyday use
or-gpt-image-2 OpenAI GPT Image 2 OpenAI flavor

Image size

Accepts OpenAI-standard 1024x1024 / 1792x1024 / 1024x1792. We auto-map them to the upstream's supported aspect ratios (1:1 / 16:9 / 9:16); arbitrary pixel dimensions aren't supported.

Image editing (image input)

The same endpoint also does image editing: pass one or more input images alongside the prompt and the model edits them instead of generating from scratch. Best paired with the Gemini ("Nano Banana") models.

{
  "model": "or-gemini-3-1-flash-image",
  "prompt": "make the cat blue and add a party hat",
  "image": "data:image/png;base64,iVBORw0KGgo..."
}
Field Type Notes
image string A single input image: raw base64, or a data URL (data:image/png;base64,...). Bare base64 defaults to image/png.
images string or array One or more input images. Takes precedence over image when both are present.
  • No image → text-to-image generation (the default above).
  • With image(s) → image edit. Response shape is identical ({ data: [{ b64_json }] }).
# edit an existing PNG: turn its background to night
B64=$(base64 -i input.png)
curl https://api.openclacky.com/images/generations \
  -H "Authorization: Bearer sk-oc-xxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d "{
    \"model\": \"or-gemini-3-1-flash-image\",
    \"prompt\": \"change the background to a starry night sky\",
    \"image\": \"$B64\"
  }" | jq -r '.data[0].b64_json' | base64 -d > edited.png

3. Video generation — POST /videos/generations

Request body:

{
  "model": "or-veo-3",
  "prompt": "a golden retriever surfing a wave at sunset, cinematic",
  "aspect_ratio": "16:9",
  "duration_seconds": 8,
  "image": null
}
Field Type Required Notes
model string yes Veo alias, see table below
prompt string yes Video description
aspect_ratio string no 16:9 (default) or 9:16
duration_seconds int no 4 / 6 / 8 (default 8)
image object no First frame for image-to-video: { "b64_json": "...", "mime_type": "image/png" }

Response body (MP4 inline base64):

{
  "created": 1718465432,
  "data": [
    { "b64_json": "AAAAGGZ0eXBpc29t...", "mime_type": "video/mp4" }
  ],
  "model": "or-veo-3",
  "usage": { "duration_seconds": 8 },
  "cost_usd": 1.344
}

Supported models

Alias Upstream Default output
or-veo-3 Veo 3 Video + audio, 720p/1080p
or-veo-3-fast Veo 3 Fast Video + audio, 720p
or-veo-3-1 Veo 3.1 Video + audio, 720p/1080p
or-veo-3-1-fast Veo 3.1 Fast Video + audio, 720p

Notes

  • Video generation is a long-running task — expect 1–3 minutes per request. Set your client timeout to at least 8 minutes.
  • We handle the submit + poll loop internally; from your perspective it's a single synchronous HTTP call.
  • Veo always emits audio (generateAudio=true); this can't be turned off.

4. Text-to-speech — POST /audio/speech

Request body:

{
  "model": "or-tts-gemini-2-5-flash",
  "input": "Hello, this is OpenClacky speaking.",
  "voice": "Kore"
}
Field Type Required Notes
model string yes TTS alias, see table below
input string yes Text to read aloud
voice string no Voice name, default Kore. Gemini TTS supports 30+ prebuilt voices (Kore/Puck/Charon/Fenrir/Aoede/Leda/Orus/Zephyr and more)

Response body (WAV inline base64):

{
  "created": 1718465432,
  "data": [
    { "b64_json": "UklGRn...", "mime_type": "audio/wav" }
  ],
  "model": "or-tts-gemini-2-5-flash",
  "voice": "Kore",
  "usage": {
    "prompt_tokens": 9,
    "completion_tokens": 33,
    "total_tokens": 42
  },
  "cost_usd": 0.000281
}

The WAV is 24kHz / 16-bit / mono — natively playable in browsers and most players.

Supported models

Alias Upstream Use case
or-tts-gemini-2-5-flash Gemini 2.5 Flash TTS Daily voiceover, notifications
or-tts-gemini-2-5-pro Gemini 2.5 Pro TTS Long-form narration, professional voiceover

5. Native Vertex AI — POST /vertex/v1beta1/models/{model}:<method>

For full access to native Gemini / Veo capabilities (multi-part contents, inline image editing, tools, systemInstruction, structured output, video generation), call the native Vertex AI endpoints directly. Request and response bodies are raw Vertex AI format — we only handle auth and billing, the payload is passed through verbatim.

Supported methods:

method Purpose Supported models
generateContent Gemini text/multimodal synchronous generation or-gemini-*
streamGenerateContent Gemini streaming generation or-gemini-*
predictLongRunning Veo video async generation (submit) or-veo-*
fetchPredictOperation Veo async operation polling or-veo-*

Discussed separately below.

5.1 Gemini — :generateContent / :streamGenerateContent

The native Gemini surface, more flexible than the OpenAI-shaped endpoints above.

Path:

POST /vertex/v1beta1/models/{model}:generateContent        # single response
POST /vertex/v1beta1/models/{model}:streamGenerateContent  # SSE stream

{model} accepts our or-gemini-* aliases (e.g. or-gemini-3-1-pro, or-gemini-3-1-flash-image) or the real Gemini model id.

Request body (native Gemini generateContent):

{
  "contents": [
    {
      "role": "user",
      "parts": [
        { "text": "Describe this image in one sentence." },
        { "inlineData": { "mimeType": "image/png", "data": "iVBORw0KGgo..." } }
      ]
    }
  ],
  "generationConfig": { "temperature": 0.7 }
}

Response body — the native Gemini shape, with our usageMetadata:

{
  "candidates": [
    {
      "content": { "role": "model", "parts": [{ "text": "A corgi in a spacesuit on Mars." }] },
      "finishReason": "STOP"
    }
  ],
  "usageMetadata": {
    "promptTokenCount": 264,
    "candidatesTokenCount": 11,
    "totalTokenCount": 275
  }
}

Image editing via native API

Image editing is just a generateContent call with image inlineData parts plus a text instruction — generation and editing share one interface:

B64=$(base64 -i cat.png)
curl "https://api.openclacky.com/vertex/v1beta1/models/or-gemini-3-1-flash-image:generateContent" \
  -H "Authorization: Bearer sk-oc-xxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d "{
    \"contents\": [{
      \"role\": \"user\",
      \"parts\": [
        { \"text\": \"make the cat blue\" },
        { \"inlineData\": { \"mimeType\": \"image/png\", \"data\": \"$B64\" } }
      ]
    }]
  }"

The edited image comes back as an inlineData part inside candidates[].content.parts[].

Streaming

Use the :streamGenerateContent path for a native Gemini SSE stream (data: {...}\n\n chunks). Each chunk is a partial GenerateContentResponse; usage is reported on the final chunk.

Notes

  • This endpoint is billed by token from usageMetadata, using the same per-model rates and Vertex promotional discount as the or-gemini-* aliases. Unlike the OpenAI-shaped endpoints, the response does not carry a cost_usd field (it's the raw upstream body); the authoritative charge is recorded server-side and shown in your dashboard.
  • Only Gemini models we price are accepted; unknown models return 400. For Veo models, see section 5.2 below.

5.2 Veo — :predictLongRunning / :fetchPredictOperation

Veo video generation is an asynchronous long-running operation (typically 1–3 minutes), in two steps:

Step 1: Submit POST /vertex/v1beta1/models/{model}:predictLongRunning

{
  "instances": [
    {
      "prompt": "a corgi riding a skateboard through a neon-lit Tokyo alley",
      "image": { "bytesBase64Encoded": "...", "mimeType": "image/png" }
    }
  ],
  "parameters": {
    "aspectRatio": "16:9",
    "durationSeconds": 8,
    "sampleCount": 1,
    "generateAudio": true,
    "personGeneration": "allow_adult"
  }
}

Returns an operation object:

{
  "name": "projects/your-project/locations/us-central1/publishers/google/models/veo-3.1-fast-generate-001/operations/abc123",
  "metadata": { ... },
  "done": false
}

Note: Billing occurs at submit time. Charge = durationSeconds × per-second rate × 1.05 (service fee) × Vertex discount. The submit returns immediately; you are charged regardless of whether you poll the result.

Step 2: Poll POST /vertex/v1beta1/models/{model}:fetchPredictOperation

{
  "operationName": "projects/.../operations/abc123"
}

Poll until done: true:

{
  "name": "projects/.../operations/abc123",
  "done": true,
  "response": {
    "videos": [
      {
        "bytesBase64Encoded": "AAAAIGZ0eXBpc29t...",
        "mimeType": "video/mp4"
      }
    ]
  }
}

fetchPredictOperation has no additional charge (already billed at submit).

Supported models:

Alias Upstream model Per-second rate
or-veo-3 veo-3.0-generate-001 $0.40
or-veo-3-fast veo-3.0-fast-generate-001 $0.10
or-veo-3-1 veo-3.1-generate-001 $0.40
or-veo-3-1-fast veo-3.1-fast-generate-001 $0.10

If you prefer a synchronous call, use the OpenAI-shaped POST /videos/generations endpoint — it handles submit + poll internally and returns the MP4 inline as base64.


6. List models — GET /models

Returns the models available to the API key making the request.

Request: GET /models, authenticated with a Bearer Token.

Response:

{
  "object": "list",
  "data": [
    { "id": "abs-claude-sonnet-4-6", "object": "model", "owned_by": "openclacky" },
    { "id": "dsk-deepseek-v4-pro", "object": "model", "owned_by": "openclacky" }
  ]
}
  • If the API key has allowed_models configured, only the intersection is returned.
  • Without a whitelist, all available models are listed.

7. Balance & quota — GET /balance

Returns the account balance and key-level quota usage for the API key making the request.

Request: GET /balance, authenticated with a Bearer Token.

Response:

{
  "is_available": true,
  "balance_infos": [
    { "currency": "USD", "total_balance": "5.0" }
  ],
  "quota": {
    "enabled": true,
    "amount": 10.0,
    "used": 3.5,
    "remaining": 6.5,
    "reset_period": "monthly"
  }
}
Field Description
is_available Whether balance ≥ $1.00 (minimum threshold)
balance_infos[].total_balance Account balance (string)
quota.enabled Whether quota is enabled for this key
quota.amount Total quota amount (USD)
quota.used Amount currently used
quota.remaining Amount remaining
quota.reset_period Reset period: daily / weekly / monthly

Note: The quota field only appears when quota is enabled and quota_amount is set on the key. Keys without quota will not include this field.


Pricing at a glance

Prices already include our 5% service markup. Vertex-hosted models (with or-gemini-*/or-veo-*/or-tts-* upstreams) currently get a 0.80x promotional discount (subject to change — actual charges in cost_usd are authoritative).

Chat (per-token)

Token rates vary per model. Look up the exact price at AI Key Supported Models before you commit; the cost_usd field on every response is the authoritative charge.

Image generation

Model Approximate price
or-gemini-3-pro-image ~$0.134 / 1024×1024 image
or-gemini-3-1-flash-image ~$0.067 / 1024×1024 image
or-gpt-image-2 ~$0.04–0.08 / image (token-based)

Video generation (per output second)

Model Price
or-veo-3 / or-veo-3-1 Video + audio, 720p/1080p: $0.40/s
or-veo-3-fast / or-veo-3-1-fast Video + audio, 720p: $0.10/s

A typical 8-second or-veo-3 clip: 8 × 0.40 × 1.05 ≈ $3.36, ~$1.34 after the Vertex discount.

Text-to-speech (per token; audio output = 25 tokens / second)

Model Input (text) Output (audio)
or-tts-gemini-2-5-flash $0.50 / 1M $10.00 / 1M
or-tts-gemini-2-5-pro $1.00 / 1M $20.00 / 1M

A 10-second Flash TTS clip is ~250 audio tokens, so about $0.0026.


Error codes

Every error returns this JSON envelope:

{
  "error": {
    "code": "invalid_api_key",
    "message": "invalid api key",
    "type": "auth_error"
  },
  "error_message": "invalid api key"
}
HTTP code Meaning
400 (various) Bad field — missing model, empty prompt, unknown model alias
401 invalid_api_key Key not found or malformed
403 api_key_revoked Key has been revoked
403 api_key_expired Key has expired
402 insufficient_credit Account balance too low — top up at the dashboard
429 quota_exceeded Per-key rate limit hit
405 Wrong HTTP method (must be POST)
502 Upstream model failure — safe to retry
500 internal_error Internal error

Retry guidance: 429 / 502 are safely retryable with exponential backoff (start at 1 s, max 3 attempts). Don't retry 400/401/402/403.


SDK examples

We're OpenAI-compatible — use the OpenAI SDK as-is, just swap base_url and api_key.

Python (openai SDK)

from openai import OpenAI

client = OpenAI(
    base_url="https://api.openclacky.com",
    api_key="sk-oc-xxxxxxxxxxxx",
)

resp = client.chat.completions.create(
    model="or-claude-sonnet-4-6",
    messages=[{"role": "user", "content": "Hello"}],
)
print(resp.choices[0].message.content)

Node.js (openai SDK)

import OpenAI from "openai";

const client = new OpenAI({
  baseURL: "https://api.openclacky.com",
  apiKey: process.env.OPENCLACKY_API_KEY,
});

const resp = await client.chat.completions.create({
  model: "or-gpt-5-1",
  messages: [{ role: "user", content: "Hello" }],
});
console.log(resp.choices[0].message.content);

curl (image generation)

curl https://api.openclacky.com/images/generations \
  -H "Authorization: Bearer sk-oc-xxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "or-gemini-3-1-flash-image",
    "prompt": "a futuristic Tokyo street at night",
    "size": "1024x1024"
  }' | jq -r '.data[0].b64_json' | base64 -d > out.png

curl (TTS)

curl https://api.openclacky.com/audio/speech \
  -H "Authorization: Bearer sk-oc-xxxxxxxxxxxx" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "or-tts-gemini-2-5-flash",
    "input": "Welcome to OpenClacky.",
    "voice": "Kore"
  }' | jq -r '.data[0].b64_json' | base64 -d > out.wav

FAQ

Q: Do you support streaming?
A: Yes for /chat/completions (set stream: true) and for native Gemini via :streamGenerateContent. The other endpoints are single-response.

Q: Can I generate multiple images / videos in one call?
A: Images: n=1..4 (upstream-limited). Video: one clip per request.

Q: Are there rate limits?
A: Each key has a generous default RPM cap. Hitting it returns 429 quota_exceeded — back off and retry, or contact us for a higher quota.

Q: Can I get a URL instead of base64?
A: All media endpoints currently return inline base64. Persist it to S3/OSS yourself if needed.

Q: How do I reconcile costs?
A: Every response carries cost_usd — that's the authoritative charge for that call. Monthly invoices and per-call breakdown are in the dashboard.