AI Docs
Chat & Streaming
Transports
Structured Outputs
Tools
Middleware
UI
Chat UI Recipes
Interrupts
MCP
- MCP Server ToolsUpdated
- Managed MCP with chat()Updated
- Manual MCPUpdated
- MCP Type GenerationUpdated
- MCP Client InputUpdated
- MCP Server Tools: AdvancedNew
- MCP EventsNew
- MCP AppsUpdated
- Serve Tools over HTTPUpdated
- Serve Resources and PromptsUpdated
- Ask for InputUpdated
- Draft Text from a ToolUpdated
- MCP Server TasksUpdated
- MCP Server AuthUpdated
- MCP Server SessionsUpdated
- MCP Server on stdioUpdated
Persistence
Persistence (Advanced)
Media
- GenerationsUpdated
- Realtime Voice ChatUpdated
- Text-to-SpeechUpdated
- TranscriptionUpdated
- Transcription: AdvancedNew
- Voice CreationUpdated
- Audio RecordingUpdated
- Audio GenerationUpdated
- Image GenerationUpdated
- Image Generation: AdvancedNew
- Video GenerationUpdated
- Video Generation: AdvancedNew
- Live GenerationUpdated
- World GenerationUpdated
- Generation HooksUpdated
Embeddings
Reranking
Evaluate
Code Mode
Sandboxes
- OverviewUpdated
- Quick StartUpdated
- ProvidersUpdated
- HarnessesUpdated
- Harness AuthUpdated
- WorkspaceUpdated
- ToolsUpdated
- PolicyUpdated
- Lifecycle & SnapshotsUpdated
- Portable SnapshotsUpdated
- Keep Files After ReloadUpdated
- Save a Named VersionUpdated
- Branch From a VersionUpdated
- Send a Frozen FileUpdated
- Let the Agent Save and ForkUpdated
- Pick Which Files to KeepUpdated
- What a Snapshot StoresUpdated
- Instance DurabilityUpdated
- Durable RunsUpdated
- EventsUpdated
Sandboxes (Advanced)
Advanced
- Runtime ContextUpdated
- Bring Your Own KeyUpdated
- Debug LoggingUpdated
- Multimodal ContentUpdated
- Files APIUpdated
- Per-Model Type SafetyUpdated
- Runtime Adapter SwitchingUpdated
- Tree-ShakingUpdated
- Extend AdapterUpdated
- Extend Adapter: AdvancedNew
- Typed Pre-Configured OptionsUpdated
- Test with a Fake ModelUpdated
- Prompt CachingUpdated
- Mid-Conversation ChangesUpdated
- Approval Flow ProcessingUpdated
AI/LLM: This documentation page is available in plain markdown format at/ai/latest/docs/transports/websockets.md
Transports
WebSockets
You want one connection for the whole conversation, not one request per message. Use the built-in webSocket() adapter. It opens one socket for the conversation. If a durable run drops, it reconnects automatically.
1. Connect from the client#
ts
import { useChat, webSocket } from "@tanstack/ai-react";
const connection = webSocket("/api/chat-ws");
const { messages, sendMessage } = useChat({ connection });2. Accept the socket on the server#
On Cloudflare Workers or Durable Objects, use toWebSocketResponse:
ts
import { chat, memoryStream, toWebSocketResponse } from "@tanstack/ai";
import { openaiText } from "@tanstack/ai-openai";
export default {
fetch(request: Request): Response {
return toWebSocketResponse(request, {
durability: (ctx) => memoryStream(ctx.request),
onRun: ({ messages, threadId, runId }) =>
chat({
adapter: openaiText("gpt-5.6"),
messages,
threadId,
runId,
}),
});
},
};On other hosts, such as Node, accept the socket yourself. Then pass it to toWebSocketStream. See Resumable Streams: WebSockets for this setup, the wire protocol, and the reconnect details.
To use your own wire format or a server that you do not control, write a custom adapter. See Custom Transports.
Send two messages. Both replies stream over the same socket.