メインコンテンツへスキップ
ARouter はすべてのモデルのストリーミングレスポンスをサポートしています。ストリーミングを有効にすると、トークンは生成されるにつれてリアルタイムで配信されます。 ストリーミングを有効にするには、リクエスト本文に stream: true を設定してください。
from openai import OpenAI

client = OpenAI(
    base_url="https://api.arouter.ai/v1",
    api_key="lr_live_xxxx",
)

stream = client.chat.completions.create(
    model="openai/gpt-5.4",
    messages=[{"role": "user", "content": "How would you build the tallest building ever?"}],
    stream=True,
)

for chunk in stream:
    content = chunk.choices[0].delta.content
    if content:
        print(content, end="", flush=True)

# Final chunk includes usage stats
# Access via: stream.get_final_completion().usage

Anthropic ストリーミング

Anthropic SDK は独自のストリーミング形式を使用します:
import anthropic

client = anthropic.Anthropic(
    base_url="https://api.arouter.ai",
    api_key="lr_live_xxxx",
)

with client.messages.stream(
    model="claude-sonnet-4.6",
    max_tokens=1024,
    messages=[{"role": "user", "content": "How would you build the tallest building ever?"}],
) as stream:
    for text in stream.text_stream:
        print(text, end="", flush=True)

Gemini ストリーミング

Gemini は generateContent の代わりに streamGenerateContent を使用します:
import google.generativeai as genai

genai.configure(
    api_key="lr_live_xxxx",
    transport="rest",
    client_options={"api_endpoint": "https://api.arouter.ai"},
)

model = genai.GenerativeModel("gemini-2.5-flash")
response = model.generate_content("How would you build the tallest building ever?", stream=True)

for chunk in response:
    print(chunk.text, end="", flush=True)

SSE フォーマット

内部的には、ストリーミングは Server-Sent Events を使用しています。各コンテンツイベントは次のようになります:
data: {"id":"chatcmpl-xxx","object":"chat.completion.chunk","model":"openai/gpt-5.4","choices":[{"index":0,"delta":{"content":"Hello"},"finish_reason":null}]}

data: {"id":"chatcmpl-xxx","object":"chat.completion.chunk","model":"openai/gpt-5.4","choices":[{"index":0,"delta":{"content":" world"},"finish_reason":null}]}

data: {"id":"chatcmpl-xxx","object":"chat.completion.chunk","model":"openai/gpt-5.4","choices":[{"index":0,"delta":{},"finish_reason":"stop"}]}
[DONE] の直前の最後のチャンクには使用量データが含まれ、choices 配列は空になります:
data: {"id":"chatcmpl-xxx","object":"chat.completion.chunk","model":"openai/gpt-5.4","choices":[],"usage":{"prompt_tokens":10,"completion_tokens":20,"total_tokens":30,"prompt_tokens_details":{"cached_tokens":0},"completion_tokens_details":{"reasoning_tokens":0}}}

data: [DONE]
ARouter は接続タイムアウトを防ぐために、SSE コメント(: で始まる行)を時折送信することがあります。SSE 仕様に従い、これらは安全に無視できます。

推奨 SSE クライアントライブラリ

一部の SSE クライアント実装では、ペイロードを正しく解析できない場合があります。以下を推奨します:

ストリームのキャンセル

ストリーミングリクエストは接続を中断することでキャンセルできます。対応プロバイダーでは、これによりモデルの処理が即座に停止します。
import OpenAI from "openai";

const client = new OpenAI({
  baseURL: "https://api.arouter.ai/v1",
  apiKey: "lr_live_xxxx",
});

const controller = new AbortController();

try {
  const stream = await client.chat.completions.create(
    {
      model: "openai/gpt-5.4",
      messages: [{ role: "user", content: "Write a long story" }],
      stream: true,
    },
    { signal: controller.signal },
  );

  for await (const chunk of stream) {
    const content = chunk.choices[0]?.delta?.content;
    if (content) process.stdout.write(content);
  }
} catch (error) {
  if (error.name === "AbortError") {
    console.log("Stream cancelled");
  } else {
    throw error;
  }
}

// To cancel:
controller.abort();

ストリーミング中のエラー処理

ARouter は、エラーが発生したタイミングに応じて異なる方法でストリーミング中のエラーを処理します。

トークンが送信される前のエラー

トークンがストリーミングされる前にエラーが発生した場合、ARouter は適切な HTTP ステータスコードを持つ標準的な JSON エラーレスポンスを返します:
{
  "error": {
    "code": 400,
    "message": "Invalid model specified"
  }
}
一般的な HTTP ステータスコード:
コード意味
400Bad Request — 無効なパラメータ
401Unauthorized — 無効な API key
402Payment Required — クレジット不足
429Too Many Requests — レート制限中
502Bad Gateway — プロバイダーエラー
503Service Unavailable — 利用可能なプロバイダーなし

トークン送信後のエラー(ストリーム途中)

一部のトークンがストリーミングされた後にエラーが発生した場合、ARouter は HTTP ステータスコードを変更できません(すでに 200 OK)。エラーは SSE イベントとして送信されます:
data: {"id":"chatcmpl-xxx","object":"chat.completion.chunk","model":"openai/gpt-5.4","error":{"code":"server_error","message":"Provider disconnected unexpectedly"},"choices":[{"index":0,"delta":{"content":""},"finish_reason":"error"}]}
主な特徴:
  • エラーは標準レスポンスフィールドとともにトップレベルに表示されます
  • ストリームを終了するために finish_reason: "error" を含む choices 配列が含まれます
  • ヘッダーが既に送信されているため、HTTP ステータスは 200 OK のままです

エラー処理のコード例

from openai import OpenAI, APIStatusError

client = OpenAI(
    base_url="https://api.arouter.ai/v1",
    api_key="lr_live_xxxx",
)

try:
    stream = client.chat.completions.create(
        model="openai/gpt-5.4",
        messages=[{"role": "user", "content": "Write a story"}],
        stream=True,
    )
    for chunk in stream:
        content = chunk.choices[0].delta.content
        if content:
            print(content, end="", flush=True)
except APIStatusError as e:
    print(f"\nError {e.status_code}: {e.message}")