Offline Coding API
Self-hosted, coding-only completion API at api.misar.io/coder/offline/* — REST, SSE and WebSocket over one schema.
A separate surface from the cloud gateway
This is the offline coding API, hosted at https://api.misar.io/coder/offline. It runs
MisarCoder's own self-hosted models (Ollama, CPU) — no cloud AI provider — and is
deliberately coding-only. It is distinct from the cloud MoE gateway at api.misar.io/coder
documented on the other pages in this section.
Base URL: https://api.misar.io/coder/offline
Auth: Authorization: Bearer <key> on every call.
Models: coder (qwen2.5-coder 7B, default) · coder-fast (qwen2.5-coder 3B, faster on CPU).
Endpoints
| Transport | Endpoint | Purpose |
|---|---|---|
| REST | POST /v1/code/completions | buffered code completion / chat |
| SSE | POST /v1/code/completions with "stream": true | text/event-stream token stream |
| WebSocket | /v1/code/session | interactive, cancellable coding session |
| REST | GET /v1/code/models | model catalogue |
| REST | GET /health | liveness |
REST — code completion
/v1/code/completionsGenerate a code completion. Provide either prompt (single-shot) or messages
(multi-turn). Set stream: true for SSE; otherwise a single JSON object is returned.
Request body
promptstringbodySingle-shot instruction. Provide this or messages.
messagesArray<{role, content}>bodyMulti-turn conversation. Provide this or prompt. role is system | user | assistant.
modelstringbodycoder (default) or coder-fast. Unknown values fall back to coder.
systemstringbodyOverride the default coding system prompt.
temperaturenumberbodySampling temperature. Defaults to the server's coding default.
max_tokensintegerbodyMaximum tokens to generate.
streambooleanbodyWhen true, returns a text/event-stream instead of a JSON body.
curl -X POST https://api.misar.io/coder/offline/v1/code/completions \
-H "Authorization: Bearer $MISARCODER_API_KEY" \
-H "Content-Type: application/json" \
-d '{"model":"coder","prompt":"Write a Python is_prime(n) function. Return only code."}'{
"id": "cmpl_1a2b3c…",
"object": "code.completion",
"created": 1750000000,
"model": "coder",
"resolved_model": "qwen2.5-coder:7b-instruct-q4_K_M",
"choices": [
{ "index": 0, "message": { "role": "assistant", "content": "def is_prime(n): …" }, "finish_reason": "stop" }
],
"usage": { "prompt_tokens": 24, "completion_tokens": 96, "total_tokens": 120 }
}An invalid or missing bearer key returns 401. A request with neither prompt nor
messages returns 400.
SSE — token stream
Send the same body with "stream": true. The response is text/event-stream. Each
delta is a data: line; a terminal event carries done: true + usage, followed by
data: [DONE].
data: {"id":"cmpl_…","model":"coder","delta":"def "}
data: {"id":"cmpl_…","model":"coder","delta":"is_prime"}
data: {"id":"cmpl_…","model":"coder","done":true,"finish_reason":"stop","usage":{"prompt_tokens":24,"completion_tokens":96,"total_tokens":120}}
data: [DONE]WebSocket — interactive session
Connect to wss://api.misar.io/coder/offline/v1/code/session. Authenticate with a ?key=<key>
query param, an Authorization header, or a first {"type":"auth","token":"…"} frame.
Client → server
| Message | Fields |
|---|---|
{"type":"prompt", …} | prompt | messages, plus optional model, system, temperature, max_tokens, id |
{"type":"cancel"} | abort the in-flight turn |
{"type":"ping"} | heartbeat → server replies {"type":"pong"} |
Server → client
| Message | Meaning |
|---|---|
{"type":"start","id","model","resolved_model"} | turn began |
{"type":"delta","id","text"} | streamed token(s) |
{"type":"done","id","finish_reason","usage"} | turn complete |
{"type":"error","message"} | failure |
SDKs
Same params, same response shape
Both SDK clients mirror this contract exactly across REST, SSE and WebSocket.
import { CoderClient } from "@misar/agent-sdk";
const coder = new CoderClient({
baseUrl: "https://api.misar.io/coder/offline",
apiKey: process.env.MISARCODER_API_KEY,
});
// REST
const { content } = await coder.complete({ prompt: "Write is_prime(n) in Python." });
// SSE
await coder.stream({ prompt: "reverse a string in python", model: "coder-fast" },
(t) => process.stdout.write(t));
// WebSocket
const session = await coder.session();
await session.prompt({ prompt: "quicksort in Go" }, { onDelta: (t) => process.stdout.write(t) });
session.close();from misarcoder import CoderClient
coder = CoderClient(api_key="csk_…") # base_url defaults to api.misar.io/coder/offline
r = coder.complete(prompt="Write is_prime(n) in Python.")
print(r["choices"][0]["message"]["content"])
for chunk in coder.stream(prompt="reverse a string", model="coder-fast"):
if chunk.get("delta"):
print(chunk["delta"], end="")Latency (CPU inference)
The offline models run on a CPU-only backend. Expect roughly ~1.4 tok/s (coder, 7B)
and ~2.4 tok/s (coder-fast, 3B) when warm; the first request to a cold model adds
~25–60 s of load time. Prefer coder-fast for interactive use.