Streaming

Set stream to true and tokens arrive as they are generated, as server-sent events. The first token typically lands within a second; the whole answer follows at the model's speed.

Request#

curl -N https://api.ahurasense.com/v1/chat/completions \
  -H "Authorization: Bearer $AHURA_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "anthropic/claude-haiku-4.5",
    "messages": [{"role": "user", "content": "Count from 1 to 5."}],
    "stream": true
  }'

Wire format#

The response has Content-Type: text/event-stream. Each event is a data: line holding one chat.completion.chunk object; the stream ends with data: [DONE].

stream
data: {"id":"chatcmpl-…","object":"chat.completion.chunk","choices":[{"index":0,"delta":{"role":"assistant","content":""},"finish_reason":null}]}

data: {"id":"chatcmpl-…","object":"chat.completion.chunk","choices":[{"index":0,"delta":{"content":"1"},"finish_reason":null}]}

data: {"id":"chatcmpl-…","object":"chat.completion.chunk","choices":[{"index":0,"delta":{"content":", 2, 3, 4, 5"},"finish_reason":null}]}

data: {"id":"chatcmpl-…","object":"chat.completion.chunk","choices":[{"index":0,"delta":{},"finish_reason":"stop"}]}

data: {"id":"chatcmpl-…","object":"chat.completion.chunk","choices":[],"usage":{"prompt_tokens":15,"completion_tokens":11,"total_tokens":26}}

data: [DONE]
  • Concatenate choices[0].delta.content across chunks to rebuild the answer.
  • Tool calls stream as delta.tool_calls fragments with an index; append the arguments strings per index. The OpenAI SDKs do this for you.
  • The last chunk before [DONE] carries usage. That is the count the request is billed on, so keep reading until the end if you meter on your side too.

Headers on a stream#

Headers are sent before the first token, so anything that depends on the outcome is not in them. X-Ahura-Request-Id, X-Ahura-Model and X-Ahura-RateLimit-Remaining are present as usual; X-Ahura-Cache is streaming-skipped, because streamed answers are not served from or written to the cache.

Cancellation#

Close the connection and generation stops upstream. You are billed for the tokens generated up to that point, as reported by the backend. The SDKs cancel on break out of the loop or on an abort signal.

Reasoning tokens#

Several catalog models think before they answer. Those thinking tokens count against max_tokens and are billed as output, and they are reported in usage as reasoning_tokens or under completion_tokens_details, depending on the backend. The visible answer only begins once thinking ends.

Timeouts#

A streamed response can stay open for as long as the model generates. Set your client’s read timeout with that in mind; the SDK defaults are fine. If nothing has arrived after the connection opened, the model is still working on the first token, not stalled: the headers only tell you the request was accepted.

The Anthropic-compatible route streams too, with Anthropic’s event names; see Messages.

Something missing or wrong on this page? Tell us, and quote the page title.