流式响应如何解析 JSON,协议层需要考虑什么?
未标记
考查重点:协议分帧与完整 JSON 聚合。按协议事件边界收片段,再按调用ID聚合参数,完整JSON才校验执行;处理UTF-8拆分、顺序、结束与重连
本题目录
参考答案
本答案基于相关资料,由 AI 辅助编写,供学习与面试准备参考。如有疏漏,欢迎反馈指正。
核心回答
先按传输协议恢复完整事件,再解析事件里的 JSON;如果业务 JSON 本身是模型分批生成的,还需要按消息或工具调用标识累计片段,等生成结束后再进行完整解析与结构校验。网络块、SSE 事件和完整业务对象是三个不同边界。
具体处理顺序是:流式 UTF-8 解码、行与事件分帧、协议消息解析、业务片段聚合、最终结构和语义校验。未完成的片段可以用于界面预览,不能直接拿来执行工具或业务写入。
为什么不能对每个 chunk 直接 JSON.parse
一次读取可能只有半个中文字符、半行 data:,也可能包含数条事件。即使外层事件的 JSON 完整,里面的工具参数也可能只生成到 {"city":"北;外层能解析,不代表参数已经完整。
例如同一工具调用的参数依次收到 {"city":、"北京"、},要按调用标识累加成完整字符串。多个并行调用分别缓存,不能把所有片段拼到一个变量。
例如,一个接口可在 content_block_start 中建立调用与 index 的映射,把后续 input_json_delta 中的 partial_json 归入对应缓冲,到 content_block_stop 再解析。这些名称是具体接口的约定;其他接口需要映射为各自的调用标识与结束信号。
协议层需要约定的内容
SSE使用空行结束事件,多行data以换行合并;保留跨读取的残行,并正确处理CRLF被拆开的情况。- 明确文本是增量还是累计全文,避免累计响应被重复追加;
[DONE]等结束标记属于具体应用约定,不是所有SSE的标准内容。 - 分别处理正常终止、截断、超时、错误和取消。连接关闭而业务对象未结束时,保留失败状态,不擅自补括号并当作成功。
- 对总长度、嵌套深度和并行调用数设限制;完整后验证
JSON Schema,再检查字段权限和业务规则。
若协议需要边生成边消费独立对象,可选择每行一个完整对象的 NDJSON 等格式,并提前定义边界。给普通 JSON 随意补逗号或拆括号,无法可靠处理字符串转义和嵌套。
对应教程
- 电商问数第15章:API接口基础与FastAPI入门:回看流式响应与
SSE消息格式。 - 电商问数第17章:前后端联调与日志追踪:回看
progress、result、error的前后端约定。
参考资料
- 国内:阿里云:传统 HTTP 模式与 SSE:对照外层
data与业务JSON,并留意累计文本示例,说明业务响应不能一概按增量追加。 - 国内:阿里云百炼:流式输出:采用
delta.content片段拼接与流式结构化输出的区别,说明完整事件不等于完整业务对象。 - 国内:CloudWeGo:Hertz SSE:采用事件读取器负责分帧、业务方再处理
Data的分工,组织解析层次。 - 国内:阿里云点金:Agent 事件数据模型:采用工具事件中的
toolCallId与参数字段,说明多个调用片段需要分别归属。 - 国外:WHATWG:Server-sent events:核对
UTF-8解码、CR/LF/CRLF和多行data,说明网络块不能直接当事件。 - 国外:Microsoft:Fetch Event Source:采用
Fetch响应检查与事件解析分离的方式,说明不能对每次读取直接JSON.parse。 - 国外:Anthropic:Streaming messages:核对工具输入的
partial_json片段按内容块index聚合、结束后形成对象的机制,补充外层事件完整而参数尚未完整的例子。
