各协议形状
- Anthropic Messages
- OpenAI Chat Completions
- OpenAI Responses
- Gemini Native
在请求体里传
"stream": true。事件名匹配 Anthropic 的原生协议:响应头在第一帧 SSE 之前发出
配额 + 速率限制响应头在 HTTP 响应头里发出,早于 第一个事件。你可以在读到响应头之后关闭连接,短路一次太贵的流:output_tokens。
干净地终止
如果你有一个长流想要切断(用户点了 stop),直接关 HTTP 连接 —— 没有单独的 “abort” 接口。网关把断连传播到模型,按部分输出结算。 对 视频 生成(异步走/v1/tasks/submit),用
POST /v1/tasks/cancel
来取消 —— 关掉 submit 响应并不会取消正在渲染的任务。
流中错误
如果模型中途失败,网关发一个最终的event: error(Anthropic)或带 error 字段的最终帧(OpenAI),然后关闭连接。你已经收到的部分输出归你 —— 但流中错误的情况下,请求 不计费。失败从不计费,没有例外。
重连
SSE 支持Last-Event-ID 头做重连,但 ByteSpike 不 在服务端暂存流 —— 没有可重放的内容。流中断开就只能从头重发请求。
对担心断网的长 completion,更建议用非流式 + 充足的客户端超时,或者用 Anthropic prompt caching 让重试变便宜。
SDK 行为
三个官方 SDK 都自动处理流式:常见坑
| 现象 | 原因 | 修法 |
|---|---|---|
| 第一块之后流卡住 | 公司代理在缓冲 / 非透传 | 把 llm.bytespike.ai 加进 NO_PROXY |
| 行成块 N 个一起到 | 默认 HTTP 缓冲 —— 纯粹是显示问题 | 用 SDK 或 iter_lines() —— 语义块永远对齐 |
缺 event: 行 | 你的 parser 只读 data: 行 | 用真正的 SSE parser —— 事件名对 Anthropic-shape 和 Responses-shape 很重要 |
| 最后一帧没有 usage(OpenAI) | 没设 stream_options.include_usage: true | 设上 |
| Gemini 最后一帧缺失 | 没有 [DONE] 标记 —— 流以连接关闭收尾 | 把连接关闭当作 end-of-stream |