Docs Menu & Search

Documentation

Streaming

Get chat replies token by token with Server-Sent Events.

Set "stream": true on /v1/chat/completions and the reply arrives as it is generated, as Server-Sent Events — the same format as OpenAI’s API, so any OpenAI SDK streams without changes. Streaming works on every chat model.

curl -N https://api.nabh.cloud/v1/chat/completions \
  -H "Authorization: Bearer nbh_your_key_here" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "gpt-oss-20b",
    "stream": true,
    "messages": [{"role": "user", "content": "Write a haiku about the monsoon"}]
  }'

The Event Stream

Each event is a data: line holding one JSON chunk; the text is in choices[0].delta.content. The stream ends with data: [DONE].

data: {"choices":[{"index":0,"delta":{"role":"assistant","content":""}}], ...}

data: {"choices":[{"index":0,"delta":{"content":"Clouds"}}], ...}

data: {"choices":[{"index":0,"delta":{"content":" gather"}}], ...}

data: {"choices":[],"usage":{"prompt_tokens":14,"completion_tokens":21,"total_tokens":35}, ...}

data: [DONE]
  • Token usage comes last. nabh.cloud always asks for usage on streams, so the final chunk (with an empty choices array) carries usage for the whole request. You don’t need to send stream_options yourself.
  • Reasoning models may send their thinking first in delta.reasoning_content before any delta.content. Show it or skip it — only content is the answer.
  • Cost. Non-streaming replies include cost_inr and balance_inr in the JSON body. A stream can’t carry them (the cost is known only at the end), so use the usage chunk with the model’s prices, or look the request up by its ID in your request log.
  • Request ID. Every response, streamed or not, has an X-Request-ID header. Keep it — it identifies the request in your request log and for support.

Timeouts and Stopping

A stream stays open as long as the model keeps sending; it is closed if the model goes quiet for 100 seconds (504 GATEWAY_TIMEOUT before the first byte). Errors that happen before streaming starts (bad key, insufficient credits, rate limit) come back as a normal JSON error — see Errors.