快速结论:使用 Responses API 连接(OpenAI/Azure)并开启流式输出时,如果回答因 max_output_tokens 或内容过滤而以 response.incomplete 结束,Open WebUI 的后端流式 reducer 不会把它当作终止事件,导致 usage/成本没有写进保存的消息和用量统计。优先检查该版本的后端流事件处理逻辑是否覆盖 response.incomplete。
适用环境:Issue 已确认在 Open WebUI dev 分支(f3ef8b94913d98e96bfd74c175f258043ae77f37,2026-11-03)和发行版 v0.12.5(2026-10-29)上复现;安装方式为 Git Clone;操作系统为 Windows 11。走的是 OpenAI/Azure Responses API 路径,与 Ollama 无关;复现时直接调用后端流式 reducer,不涉及浏览器。
最快修复方案:暂无确认的一步修复方案。Issue 只给出了复现探针和根因定位(reducer 对 response.incomplete 返回 current_output, None),没有提供可直接采用的补丁或配置改动。
注意事项:被截断的回答仍然是真实且计费的响应,丢掉 usage 会同时影响消息上保存的 token/成本字段和用量分析。另外,Issue 元数据中关闭时间(2026-11-03)早于所引用发行版 v0.12.5 的发布日期(2026-10-29)时序关系需自行核实;在升级前不要默认该问题已在某版本修复。
问题场景
在 Open WebUI 中配置 OpenAI 或 Azure 的 Responses API 连接并启用流式输出时,模型回答因达到 max_output_tokens 或触发内容过滤而被截断,最后一条流事件为 response.incomplete。此时保存的消息里没有来自终止事件的 token 和成本信息,用量分析也统计不到这部分消耗。
报错原文
issue: Streaming Responses-API answers that end with response.incomplete lose their usage/cost in the saved message and analytics
completed
last meta: {"usage": {"input_tokens": 1234, ..., "total_tokens": 1276}, "done": true, "response_id": "resp_1"}
output status: ['completed']
incomplete
last meta: null
output status: [None]
原因分析
最可能的原因是后端 handle_responses_streaming_event 的 reducer 只把 response.completed 视为终止事件。对 response.incomplete,代码落到最后的 else: return current_output, None,不返回任何 metadata。由于 response_metadata 为 None,中间件会跳过 usage 合并和 usage 完成事件;在没有捕获到 usage 的情况下,流式处理会把消息标记为 usage: {"incomplete": true}(Issue 指向 middleware.py:5596-5597),于是保存的消息缺少终止带来的 token 与成本字段。
另外,按 Issue 描述,API 客户端的流转换器本身已能处理 response.incomplete,问题出在 WebUI 侧这条 reducer 路径,因此不是上游接口返回格式异常。
环境排查
- 确认 Open WebUI 版本与提交:
dev是否为f3ef8b94913d98e96bfd74c175f258043ae77f37,或是否为v0.12.5;其他版本是否包含同样代码需自行比对。 - 确认使用的是 Responses API 连接(OpenAI/Azure),而不是 Completions API 或 Ollama。
- 确认后端 Python 环境中导入后端包前已设置
WEBUI_SECRET_KEY和可写的DATA_DIR(导入时会执行迁移)。 - 确认触发条件是回答被截断:上游返回
status: incomplete,常见于max_output_tokens用尽或内容过滤。 - Issue 未提供具体 Python、依赖库、CUDA、显卡版本,这些项目不作为本问题的排查依据。
解决步骤
- 先按 Issue 的复现方式确认问题存在:设置
WEBUI_SECRET_KEY和可写DATA_DIR,将PYTHONPATH指向backend。 - 运行 Issue 中的探针,把事件序列依次喂给
handle_responses_streaming_event(来自open_webui.utils.response),记录每次返回的 meta。 - 观察
response.incomplete对应的一次返回值:如果 meta 为null、输出状态为[None],即复现了本 Issue。 - 检查本地代码中该 reducer 的终止事件分支是否只处理
response.completed,以及middleware.py中usage: {"incomplete": true}的写入逻辑。 - 可优先尝试:参照
response.completed的现有处理,让response.incomplete同样返回最终输出,并返回包含usage、done: true、response_id的 metadata。该方向由 Issue 的期望行为描述得出,并非已合并的官方修复,修改后需重新跑探针验证。 - 如果不能自行改代码,升级前先在目标版本上重复上述探针,确认该版本是否已修复,不要仅凭版本号判断。
验证方法
用同一组事件重新运行探针,确认 response.incomplete 返回的 meta 不再是 null,而是包含正确的 usage(如 input_tokens、output_tokens、total_tokens)、done: true 和 response_id,且输出状态不再为 [None]。随后发起一次会被截断的 Responses API 流式对话,检查保存的消息中 token/成本字段已写入,用量分析里也能统计到该次请求。
参考来源
AI 工具推荐
想把多个 AI 模型放在一个入口?
GamsGo AI 集成 ChatGPT、DeepSeek、Gemini、Claude、Midjourney、Veo 等常用模型,适合写作、绘图、视频和日常 AI 工作流。
推广链接:通过此链接购买,我可能获得佣金,不影响你的价格。
这个方案解决了吗?
可以继续搜索完整报错,或查看同一工具的其他排查指南。
![[Bug][ROCm]: ROCM_AITER_UNIFIED_ATTN gives wrong output on gfx950 when a layer's KV cache is 2–4 GiB](https://www.chat-gpts.plus/wp-content/uploads/2026/11/62606-98eab7eb-768x403.jpg)
![[RFC]: Request level text and derender output on `/inference/v1/generate`](https://www.chat-gpts.plus/wp-content/uploads/2026/11/56851-3fbe019f-768x403.jpg)
![RuntimeError: Triton Error [CUDA]: an illegal memory access was encountered`. Because of async error reporting, it surfaces in a later, unrelated kernel. In our case it was usually the first pre](https://www.chat-gpts.plus/wp-content/uploads/2026/11/63514-6c966193-768x403.jpg)