← LearnClaude API · Core API

How to Implement Claude Streaming for Chat Interfaces

To implement Claude streaming for chat interfaces, set `"stream": true` in your API request or use the SDK's dedicated streaming method, then iterate over the returned event stream to render each text chunk immediately as it arrives. This makes responses appear word-by-word instead of all at once, dramatically lowering perceived latency.

To implement Claude streaming for a chat interface, you include a streaming flag in your API request and then process each small chunk of text as it arrives over a persistent HTTP connection — displaying it to the user immediately rather than waiting for the full response. The result is a familiar, typewriter-style experience that feels fast and responsive even for long answers.

What Is Claude Streaming and How Does It Work?

Streaming is a method of receiving Claude API responses incrementally as the model generates them, rather than waiting for the complete response before delivery. Under the hood it uses the Server-Sent Events (SSE) protocol: the server sends a continuous sequence of small event chunks over a persistent HTTP connection, allowing your application to process and display output in real time.

This approach has two primary practical benefits:

  • Lower perceived latency. Users see the first tokens of a response almost instantly instead of staring at a spinner for several seconds while the model finishes generating.
  • Prevention of HTTP gateway timeouts. Long responses that would exceed the default timeout window of many infrastructure components — causing errors like 504 — are delivered safely because the connection stays alive via continuous SSE events.

Streaming is available through the raw HTTP API and through all official Anthropic SDKs (Python, TypeScript, PHP). It works with all Claude models and all API usage tiers, and is compatible with tool use, prompt caching, and extended thinking. See the official Claude streaming documentation for the full protocol reference.

How Do You Set Up Claude Streaming Step by Step?

  1. Obtain an API key. Get an Anthropic API key from the Anthropic Console at console.anthropic.com.
  2. Install the SDK. For Python, run pip install anthropic. For TypeScript, run npm install @anthropic-ai/sdk.
  3. Open a streaming context. Use the SDK's dedicated streaming method — client.messages.stream(...) in Python or TypeScript — inside a with block. Alternatively, set "stream": true in a raw POST request to the messages endpoint.
  4. Iterate over the event stream. In the Python SDK, use stream.text_stream for simple text iteration, or iterate over the raw stream to handle all event types such as text_delta, tool_use, and thinking_delta.
  5. Render each chunk immediately. Print or push each chunk to your UI as it arrives. In Python, use end='' and flush=True so output appears incrementally rather than buffered.
  6. Close the stream. The with statement closes the stream context manager automatically, releasing the underlying HTTP connection. For tool use, call stream.get_final_message() after streaming to get the fully accumulated message object, then inspect stop_reason and handle any tool use blocks.

What Does a Basic Streaming Chat Example Look Like?

Here is the minimal working pattern for streaming a response to the terminal in Python. This is the foundation for all more complex streaming use cases:

import anthropic

client = anthropic.Anthropic()

with client.messages.stream(
    model="claude-sonnet-4-5-20250929",
    max_tokens=256,
    messages=[{"role": "user", "content": "Write a haiku about rain."}]
) as stream:
    for text in stream.text_stream:
        print(text, end="", flush=True)
print()  # newline after stream ends

Each word appears on screen as it is generated, not all at once. For a chat interface, replace the print call with whatever mechanism pushes text to your frontend — a WebSocket message, a Server-Sent Event to the browser, or a streaming HTTP response.

How Do You Track Token Usage While Streaming?

A common production need is combining real-time display with accurate billing data. Token usage is only finalized at the end of the stream, so you must wait until the stream completes before reading counts:

import anthropic

client = anthropic.Anthropic()

with client.messages.stream(
    model="claude-sonnet-4-5-20250929",
    max_tokens=512,
    messages=[{"role": "user", "content": "Explain how HTTPS works."}]
) as stream:
    for text in stream.text_stream:
        print(text, end="", flush=True)
    final = stream.get_final_message()

print(f"\n\n--- Usage ---")
print(f"Input tokens:  {final.usage.input_tokens}")
print(f"Output tokens: {final.usage.output_tokens}")

Reading usage statistics mid-stream produces partial counts that will mislead rate-limit and billing logic. Always make budget or logging decisions only after the stream context manager exits or after get_final_message() returns.

When Should You Use Streaming vs. Non-Streaming?

Situation Recommended Approach Reason
Chat interface or live document drafting Streaming Users see output immediately; perceived latency drops dramatically
Very long generation (e.g., contract analysis) Streaming with get_final_message() Keeps HTTP connection alive and prevents gateway timeouts without requiring real-time display
Agentic task with intermediate reasoning Streaming Operators can watch each step as it happens rather than receiving a single opaque final result
Batch classification or offline data pipeline Non-streaming (synchronous) Latency is not user-facing; simpler code; only the final result matters
Server-side tool use with no real-time display Non-streaming Simplicity of code is the priority; tool latency dominates anyway

What Are the Most Common Streaming Pitfalls?

Treating all events as text

Not every event in the stream is a text chunk. When using tool use or extended thinking, the stream also contains input_json_delta and thinking_delta events. Check the event type before printing. Only render text_delta events to the user interface; buffer tool input events separately. Printing raw JSON tool parameters directly to a chat UI will corrupt the output.

Batching output before display

Collecting all chunks before rendering defeats the entire purpose of streaming. Push each chunk to the UI immediately as it arrives. In Python this means using flush=True; in a web server context it means flushing the HTTP response buffer or sending a WebSocket frame per chunk.

No handling for mid-stream disconnections

Network interruptions mid-stream waste all tokens generated so far. Wrap your streaming loop in a try/except block, accumulate partial output in a variable, and on failure construct a continuation request that includes the partial assistant response plus a user instruction to continue from where it left off.

Confusing error types on stream initialization

A server-overloaded error is different from a rate-limit error. Implement separate handling for each: use exponential backoff with jitter and respect any server-provided retry guidance. Do not apply the same fixed retry interval to both error types.

Manually parsing raw SSE payloads

Writing custom SSE parsing logic is fragile and breaks with multi-block responses. Use the official Anthropic SDK's streaming context managers and event handlers, which correctly handle interleaved event types without custom parsing. As the Claude streaming documentation makes clear, the SDK abstracts this complexity for you.

What Advanced Streaming Features Are Available?

Extended thinking with streaming. When using extended thinking mode, the stream includes thinking_delta events that surface the model's reasoning chain as it develops. This lets you show users a side panel of reasoning before the final answer renders — giving insight into how conclusions were reached. You can also configure thinking content to be omitted from the stream for lower latency while preserving the signature needed for multi-turn continuity. See the extended thinking documentation for details.

Fine-grained tool streaming. Tool input parameters now stream incrementally via input_json_delta events rather than being buffered and delivered as a single block. This is generally available on all models and platforms.

Prompt caching with streaming. You can combine streaming with prompt caching — for example, caching a large system prompt such as a full technical manual and streaming answers to user questions against it. This combines cache-hit cost savings with low-latency streamed replies.

Stream recovery. If a stream is interrupted, you can resume by appending the partial response as an assistant turn and requesting continuation — without breaking the context window.

Is Claude Streaming Worth Implementing for Chat?

For any user-facing chat interface, yes — streaming is essentially the standard expectation. Users have come to expect the typewriter effect from AI chat tools, and a loading spinner that blocks for several seconds before showing a wall of text feels noticeably worse. The implementation overhead is low: the SDK handles the SSE protocol, and the core pattern is just a few lines of code. The main work is wiring the chunk output into your frontend delivery mechanism (WebSocket, SSE to browser, or streaming HTTP response).

For purely server-side or batch workloads where no human is watching in real time, non-streaming is simpler and equally correct. But for chat — stream.

Frequently asked questions

Do I need to use a special Claude model to enable streaming?

No. Streaming works with all Claude models and all API usage tiers. You enable it by using the SDK's streaming method or setting the stream flag in your API request, not by choosing a specific model.

Can I use streaming together with tool use and prompt caching?

Yes. Streaming is compatible with tool use, prompt caching, and extended thinking. When using tool use, iterate over the stream for real-time text output, then call get_final_message() afterward to inspect tool use blocks and stop reason.

Why does my chat interface still show a delay even with streaming enabled?

The most common cause is batching output before rendering — collecting all chunks before pushing them to the UI. Render each chunk immediately as it arrives and flush the output buffer on every chunk to get the true incremental display effect.

How do I get accurate token counts when streaming?

Token usage is only finalized at the end of the stream. Call get_final_message() after the stream context manager exits and read usage from the returned message object. Reading counts mid-stream produces incomplete data.

What happens if the network drops mid-stream?

Without error handling, you lose the partial response and waste all tokens generated so far. Best practice is to accumulate partial output in a variable inside a try/except block, then on failure send a continuation request that includes the partial assistant response.

Is streaming available in TypeScript and PHP as well as Python?

Yes. All official Anthropic SDKs — Python, TypeScript, and PHP — wrap the raw SSE handling in convenient context managers and iterators, so you don't need to parse the SSE protocol manually in any of these languages.

Go deeper

Streaming is one of 85 features in Claude Master — the independent, always-current manual with worked examples, the pitfalls, and the workflows that make Claude pay.

Get Claude Master — founding price

Independent product. Not affiliated with or endorsed by Anthropic. "Claude" is a trademark of Anthropic, used here only to describe the subject of this guide.

CLAUDEMASTER
An independent publication.
Independent product. Not affiliated with or endorsed by Anthropic. “Claude” is a trademark of Anthropic, used here only to describe the subject of this manual.
© 2026 Claude Master — All rights reserved.