Bei der Erstellung einer Nachricht können Sie "stream": true
setzen, um die Antwort inkrementell mithilfe von Server-Sent Events (SSE) zu streamen.
Streaming mit SDKs
Unsere Python und TypeScript SDKs bieten mehrere Möglichkeiten zum Streaming. Das Python SDK ermöglicht sowohl synchrone als auch asynchrone Streams. Weitere Details finden Sie in der Dokumentation der jeweiligen SDKs.
import anthropic
client = anthropic.Anthropic()
with client.messages.stream(
max_tokens=1024,
messages=[{"role": "user", "content": "Hello"}],
model="claude-3-7-sonnet-20250219",
) as stream:
for text in stream.text_stream:
print(text, end="", flush=True)
Ereignistypen
Jedes Server-Sent Event enthält einen benannten Ereignistyp und zugehörige JSON-Daten. Jedes Ereignis verwendet einen SSE-Ereignisnamen (z.B. event: message_stop
) und enthält den entsprechenden Ereignis-type
in seinen Daten.
Jeder Stream verwendet den folgenden Ereignisablauf:
message_start
: enthält ein Message
-Objekt mit leerem content
.
- Eine Reihe von Inhaltsblöcken, von denen jeder ein
content_block_start
, ein oder mehrere content_block_delta
-Ereignisse und ein content_block_stop
-Ereignis hat. Jeder Inhaltsblock hat einen index
, der seinem Index im endgültigen Message content
-Array entspricht.
- Ein oder mehrere
message_delta
-Ereignisse, die Änderungen auf oberster Ebene am endgültigen Message
-Objekt anzeigen.
- Ein abschließendes
message_stop
-Ereignis.
Ping-Ereignisse
Event-Streams können auch eine beliebige Anzahl von ping
-Ereignissen enthalten.
Fehlerereignisse
Gelegentlich können wir Fehler im Event-Stream senden. Zum Beispiel können Sie während Zeiten hoher Auslastung einen overloaded_error
erhalten, der normalerweise einem HTTP 529 in einem nicht-streamenden Kontext entsprechen würde:
Andere Ereignisse
Gemäß unserer Versionierungsrichtlinie können wir neue Ereignistypen hinzufügen, und Ihr Code sollte unbekannte Ereignistypen problemlos verarbeiten können.
Delta-Typen
Jedes content_block_delta
-Ereignis enthält ein delta
eines Typs, der den content
-Block an einem bestimmten index
aktualisiert.
Text-Delta
Ein text
-Inhaltsblock-Delta sieht wie folgt aus:
Eingabe-JSON-Delta
Die Deltas für tool_use
-Inhaltsblöcke entsprechen Aktualisierungen für das input
-Feld des Blocks. Um maximale Granularität zu unterstützen, sind die Deltas partielle JSON-Strings, während das endgültige tool_use.input
immer ein Objekt ist.
Sie können die String-Deltas akkumulieren und das JSON parsen, sobald Sie ein content_block_stop
-Ereignis erhalten, indem Sie eine Bibliothek wie Pydantic für partielles JSON-Parsing verwenden oder unsere SDKs nutzen, die Hilfsfunktionen für den Zugriff auf geparste inkrementelle Werte bieten.
Ein tool_use
-Inhaltsblock-Delta sieht wie folgt aus:
Hinweis: Unsere aktuellen Modelle unterstützen nur die Ausgabe einer vollständigen Schlüssel- und Werteigenschaft von input
auf einmal. Daher kann es bei der Verwendung von Tools zu Verzögerungen zwischen Streaming-Ereignissen kommen, während das Modell arbeitet. Sobald ein input
-Schlüssel und -Wert akkumuliert sind, geben wir sie als mehrere content_block_delta
-Ereignisse mit gestückeltem partiellem JSON aus, sodass das Format automatisch eine feinere Granularität in zukünftigen Modellen unterstützen kann.
Thinking-Delta
Wenn Sie erweitertes Denken mit aktiviertem Streaming verwenden, erhalten Sie Denkinhalte über thinking_delta
-Ereignisse. Diese Deltas entsprechen dem thinking
-Feld der thinking
-Inhaltsblöcke.
Für Denkinhalte wird kurz vor dem content_block_stop
-Ereignis ein spezielles signature_delta
-Ereignis gesendet. Diese Signatur wird verwendet, um die Integrität des Denkblocks zu überprüfen.
Ein typisches Thinking-Delta sieht wie folgt aus:
Das Signatur-Delta sieht wie folgt aus:
Rohe HTTP-Stream-Antwort
Wir empfehlen dringend, unsere Client-SDKs im Streaming-Modus zu verwenden. Wenn Sie jedoch eine direkte API-Integration erstellen, müssen Sie diese Ereignisse selbst verarbeiten.
Eine Stream-Antwort besteht aus:
- Einem
message_start
-Ereignis
- Möglicherweise mehreren Inhaltsblöcken, von denen jeder enthält:
a. Ein
content_block_start
-Ereignis
b. Möglicherweise mehrere content_block_delta
-Ereignisse
c. Ein content_block_stop
-Ereignis
- Einem
message_delta
-Ereignis
- Einem
message_stop
-Ereignis
Es können auch ping
-Ereignisse über die Antwort verteilt sein. Weitere Details zum Format finden Sie unter Ereignistypen.
Einfache Streaming-Anfrage
In dieser Anfrage bitten wir Claude, ein Tool zu verwenden, um uns das Wetter mitzuteilen.
event: message_start
data: {"type":"message_start","message":{"id":"msg_014p7gG3wDgGV9EUtLvnow3U","type":"message","role":"assistant","model":"claude-3-haiku-20240307","stop_sequence":null,"usage":{"input_tokens":472,"output_tokens":2},"content":[],"stop_reason":null}}
event: content_block_start
data: {"type":"content_block_start","index":0,"content_block":{"type":"text","text":""}}
event: ping
data: {"type": "ping"}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":"Okay"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":","}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":" let"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":"'s"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":" check"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":" the"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":" weather"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":" for"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":" San"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":" Francisco"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":","}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":" CA"}}
event: content_block_delta
data: {"type":"content_block_delta","index":0,"delta":{"type":"text_delta","text":":"}}
event: content_block_stop
data: {"type":"content_block_stop","index":0}
event: content_block_start
data: {"type":"content_block_start","index":1,"content_block":{"type":"tool_use","id":"toolu_01T1x1fJ34qAmk2tNTrN7Up6","name":"get_weather","input":{}}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":""}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":"{\"location\":"}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":" \"San"}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":" Francisc"}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":"o,"}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":" CA\""}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":", "}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":"\"unit\": \"fah"}}
event: content_block_delta
data: {"type":"content_block_delta","index":1,"delta":{"type":"input_json_delta","partial_json":"renheit\"}"}}
event: content_block_stop
data: {"type":"content_block_stop","index":1}
event: message_delta
data: {"type":"message_delta","delta":{"stop_reason":"tool_use","stop_sequence":null},"usage":{"output_tokens":89}}
event: message_stop
data: {"type":"message_stop"}
Streaming-Anfrage mit erweitertem Denken
In dieser Anfrage aktivieren wir erweitertes Denken mit Streaming, um Claudes schrittweise Überlegungen zu sehen.
event: message_start
data: {"type": "message_start", "message": {"id": "msg_01...", "type": "message", "role": "assistant", "content": [], "model": "claude-3-7-sonnet-20250219", "stop_reason": null, "stop_sequence": null}}
event: content_block_start
data: {"type": "content_block_start", "index": 0, "content_block": {"type": "thinking", "thinking": ""}}
event: content_block_delta
data: {"type": "content_block_delta", "index": 0, "delta": {"type": "thinking_delta", "thinking": "Lass mich das Schritt für Schritt lösen:\n\n1. Zuerst zerlegen wir 27 * 453"}}
event: content_block_delta
data: {"type": "content_block_delta", "index": 0, "delta": {"type": "thinking_delta", "thinking": "\n2. 453 = 400 + 50 + 3"}}
event: content_block_delta
data: {"type": "content_block_delta", "index": 0, "delta": {"type": "thinking_delta", "thinking": "\n3. 27 * 400 = 10.800"}}
event: content_block_delta
data: {"type": "content_block_delta", "index": 0, "delta": {"type": "thinking_delta", "thinking": "\n4. 27 * 50 = 1.350"}}
event: content_block_delta
data: {"type": "content_block_delta", "index": 0, "delta": {"type": "thinking_delta", "thinking": "\n5. 27 * 3 = 81"}}
event: content_block_delta
data: {"type": "content_block_delta", "index": 0, "delta": {"type": "thinking_delta", "thinking": "\n6. 10.800 + 1.350 + 81 = 12.231"}}
event: content_block_delta
data: {"type": "content_block_delta", "index": 0, "delta": {"type": "signature_delta", "signature": "EqQBCgIYAhIM1gbcDa9GJwZA2b3hGgxBdjrkzLoky3dl1pkiMOYds..."}}
event: content_block_stop
data: {"type": "content_block_stop", "index": 0}
event: content_block_start
data: {"type": "content_block_start", "index": 1, "content_block": {"type": "text", "text": ""}}
event: content_block_delta
data: {"type": "content_block_delta", "index": 1, "delta": {"type": "text_delta", "text": "27 * 453 = 12.231"}}
event: content_block_stop
data: {"type": "content_block_stop", "index": 1}
event: message_delta
data: {"type": "message_delta", "delta": {"stop_reason": "end_turn", "stop_sequence": null}}
event: message_stop
data: {"type": "message_stop"}