SuperAI Agent v0.2.26
SuperAI Agent v0.2.26
在不稳定的网络上,连接中断后会自动重试,不再需要手动发「hi?」把对话「叫醒」。
问题修复
-
流式响应中断后,整轮对话直接结束,且不重试:有用户在企业网络上反馈,几乎每次提问、模型刚开始「思考」时就报错,然后要手动发两三次「hi?」「hello?」才能恢复正常——每个问题都要重复一遍,本地任务和联网任务都一样。
这个「手动重试」的动作,其实就是本应用自己该做的事。流式请求失败后会退回非流式重试;若该次重试返回的内容为空,代码是把错误信息当作助手消息「输出」,而不是「抛出」,于是
withRetry的重试预算(10 次,带退避)根本没有机会执行,本轮对话就此结束。更直接的证据是那条错误信息本身的结尾就写着「请重试」——把本应自动完成的重试,交给了用户手动完成。现在这种情况会抛出可重试的错误,交由既有的退避重试机制处理。
-
但代理的拦截页不会重试:代理返回的 URL 过滤页属于策略性拒绝,重试多少次都是同一个页面,只会让用户白等。因此仅对「连接层面」的失败(连接被中断、响应被截断)自动重试,拦截页仍然立即如实报错。
-
重试全部失败时,仍然保留诊断信息:不会退化成一句笼统的「连接错误」。此前几个版本积累的诊断内容(
route=、proxy_source=、拦截页原文、被拒绝的地址)会随错误一起传递,最终照常显示。
需要说明的(不含糊其辞)
本次改动没有解释你的连接为什么会中断。 它把手动重试变成了自动重试,症状应当基本消失或大幅减轻,但底层的中断原因仍未查明。目前有两个尚未区分的可能:
- 本应用在连续 90 秒没有收到任何数据时会主动中止流式请求(可用
CLAUDE_STREAM_IDLE_TIMEOUT_MS调整)。若代理对响应做内容检查并进行缓冲,「思考」期间客户端就会一个字节也收不到,从而触发该超时——这也能解释为什么「hi?」这类瞬间就能答完的短问题反而正常。 - 代理会关闭空闲的 CONNECT 隧道,于是停顿之后的第一个请求撞上一个已经失效的连接。
要区分这两者,需要日志。 调试日志默认开启,无需重新安装、也无需任何开关,就在:
%USERPROFILE%\.claude\debug\
出错后取最新的一个文件,把包含 Streaming idle timeout、Error streaming、Streaming stall detected、zero content blocks 的行发来即可定位,并据此判断是否应当调整空闲超时。
验证情况
新增 5 项测试,共 22 项通过。两项新增防护均经过「故意改坏使其失败」的验证:删掉保留诊断的分支会让相应测试失败;把重试判定改成「一律重试」会让拦截页用例失败。src/services/api 与服务端测试套件在改动前后按测试名逐一比对,失败集合完全一致,既有的 27 项失败没有任何变动。
此外,判定逻辑被提取为可测试的独立函数——它位于流式生成器内部,此前两个版本我都只是记下「这里无法测试」而没有解决,这次补上了。