AIClaw 3.7.14:截断工具输出可恢复机制解析

AIClaw v3.7.14 通过预览与保留副本分离,让智能体能续读被截断的输出而非重跑命令。
AIClaw v3.7.14 针对「数据看到了却答错」的问题,把命令输出拆成两部分:立即展示的预览与一份更大的保留副本。命令与 Code Mode 预览预算为 24 KiB,超出时运行时保存有界副本并给出 output_id,模型可用 read_tool_output 按 UTF-8 字节偏移分页续读,无需重跑工具,副本存于本地 SQLite 并会话隔离。文章强调 hasMore=false 与 complete=false 含义不同,前者指读到保留文本末尾,后者指捕获可能不完整,即使完整也不能排除上游 API 或 shell 管道事先丢弃的行。Code Mode 则在大返回值进入脚本前先做保留,slice() 不会移除恢复引用;文件读取也改为先在完整文件定位行偏移再读取有界分页。
智能体为何会"看到数据却答错问题"
一个命令可以返回正确的数据,而智能体仍然给出错误的答案。其中一个容易被忽视的原因是:模型只看到了输出的开头,而真正相关的字段出现在很靠后的位置。

AIClaw v3.7.14 于 10 月 14 日发布,新增了一种在不重新执行命令的前提下读取截断内容之外的机制。本文基于已发布的 tag 而非未发布分支的改动进行梳理。
预览需要一条续读路径
在旧版本中,命令写入器只保留有界前缀,后续字节被直接丢弃。截断标记虽然让限制可见,却无法恢复已丢弃的内容。
设想一个包含数千行的导出结果,末尾跟有一个汇总字段。在开头几行中看不到汇总字段,并不足以证明导出结果中不存在该字段。而重复执行导出可能代价高昂、产生不同的数据,甚至重复一次写操作。
新的输出辅助模块把"立即展示的文本"与"更大的保留副本"分离开来。命令模式和 Code Mode 的预览使用 24 KiB 的内容预算。普通工具结果进入对话历史时仍使用约 32 KiB、保留开头与结尾的方式,通过历史集成完成。
当结果超出预览预算时,运行时会尝试保存一份有界副本,并提供一个 output_id。模型之后可以检查相关分页,而不是把预览当作完整结果。
UTF-8 字节偏移量:在该版本中,读取保留副本的分页接口以 UTF-8 编码的字节位置为定位单位,而非行号或字符数。这意味着一个偏移量可能恰好落在多字节字符的中间,破坏解码。为此读取器会主动校验并拒绝这类偏移量,要求调用方对齐到合法字符边界后再继续读取。
分页上限 4096 字节:每次调用最多返回 4096 字节,通过反复调用并沿 nextOffset 前进即可读完整个保留副本。设置这一上限是为了避免单次返回过大文本再次触发预览截断。
读取已保存结果无需重跑工具
read_tool_output 会话读取器接受结果 ID、UTF-8 字节偏移量,以及最大 4096 字节的分页上限。它返回:
- text:当前分页;
- nextOffset:续读位置;
- totalBytes:保留长度;
- hasMore:是否存在下一个保留分页;
- complete:保留捕获是否完整。
该读取器会拒绝落在 UTF-8 字符内部的偏移量。它在当前会话下查找 ID,而不是接受文件系统路径或调用原始命令。不同会话无法用同一个 ID 获取该副本。
副本存放在本地 SQLite 会话状态中,可以在会话恢复后继续存在,并跟随会话的删除生命周期。它们不与分叉会话共享,该功能也无法重建旧版本已丢弃的输出。
这也意味着更多工具返回文本会被本地存储。保留机制是有界存储,不是脱敏或加密功能。
有界存储:保留副本存放在本地 SQLite 会话状态中,每份上限 8 MiB,这意味着它并不是一份无损的完整日志。当命令输出、捕获或保留任一环节越过上限时,副本会明确标记为不完整,而不是静默丢弃。「有界」同时约束了空间占用与可恢复范围:超出边界的字节无法通过任何后续读取找回。
会话隔离:读取器只在当前会话下按 ID 查找副本,不接受文件系统路径,也不重新执行原始命令。因此不同会话、分叉出的会话都无法用同一个 ID 取得他处的副本。这一设计既防止了跨会话的数据泄漏,也让副本的生命周期与归档行为保持一致。
读到最后一个保留分页不等于源数据完整
每份保留副本上限为 8 MiB。命令捕获分别限制 stdout 和 stderr;保存后的合并副本同样有 8 MiB 上限。越过捕获或保留限制会让 completeness 变为 false。保存失败会明确报告恢复不可用。
因此两个标志回答的是不同问题。hasMore=false 表示读取器到达了已保存文本的末尾;complete=false 表示该文本可能仍然缺少已捕获结果的一部分。在最后一个保留分页上,两者可以同时为 false。
即便捕获是完整的,也不能说明上游 API 从未返回的行。分页、服务端过滤以及诸如 head 这样的 shell 管道,都可能在 AIClaw 看到数据之前就将其移除。系统指令要求模型在宣称"不存在"之前检查相关字段和源分页,并在无法获取证据时说明不确定性。这些指令引导模型,但并不能保证其解释一定正确。
Code Mode 在脚本切片前保留大结果
Code Mode 引入了另一个信息可能消失的位置:脚本可能收到一个很大的工具结果,但只返回一个很短的选取。
运行时桥接现在会在把过大的嵌套工具返回值传入脚本之前进行保留。它单独发出恢复元数据,同时保持脚本返回的工具值不变。因此后续的 slice() 不会移除该超大返回值的恢复引用。
这适用于预览阈值以上且保存成功的嵌套结果,并不会保留脚本选择省略的每一个小值。如果嵌套返回值本身就是一个命令预览,读取它可以揭示更大命令输出的第二个 ID;模型必须沿着正确的引用继续。
嵌套工具返回值:在 Code Mode 中,脚本可以调用工具并拿到返回值,再对其做切片或筛选。如果一个嵌套返回值体积过大,运行时桥接会在它进入脚本之前先行保留,并单独发出恢复元数据,而脚本看到的值本身保持不变。这样即使脚本只返回很短的一段选取,后续仍可通过元数据中的引用回到完整内容。该机制只作用于预览阈值以上且保存成功的嵌套结果,并不会为脚本主动省略的每一个小值都建立副本。
文件偏移量现在先于分页预算生效
同一版本修复了一个相关的文件读取问题:旧实现会先把文件截断到 256 KiB,再应用请求的行偏移量。因此,位于该前缀之后的行无法通过行参数触达。
新的文件分页器会在完整文件中定位所请求的行,然后读取一个有限分页。长行可以通过 byte_offset 继续。返回的分页保持 UTF-8 边界,文件工具也保留了其敏感路径检查。
验证所建立的是什么
已打 tag 的会话测试覆盖了恢复副本、会话隔离、显式不完整捕获,以及 Code Mode 切片后的恢复。工具测试覆盖了靠后的文件行、Unicode 分页、捕获限制和命令退出状态。
发布说明报告本地 make check 通过、一次 15 个场景的实机模型运行,以及最终改动后的四个聚焦场景。公开的场景定义包含在不重复命令的情况下找到一个合成的尾部字段。这些都是有界检查,并不证明每个模型总会检查每一个必要分页。
实际改进带来的是一条可恢复的证据链:一段简短预览、一份会话范围内的副本,以及关于该副本能建立什么的明确限制。
相关推荐

Workbuddy零基础入门:桌面AI智能体如何落地工作流
Workbuddy桌面AI智能体零基础教程解读:从安装、积分领取到文件管理与自动化工作流搭建,对比CodeX的适用场景与成本差异,帮助职场人完成从AI提问者到AI管理者的思维转变。

OpenAI智能体新栈:计算机操作、决策API与超速工作流
OpenAI Dev Day发布智能体新栈:Computer Use操作速度超越普通人,Decisions API基于Luna实现极低延迟分类,Agents API开放同源计算机操作能力,GPT-6.1 Sol成本仅为Astra七分之一。本文梳理核心更新、实测数据与开发者落地要点。

梁文峰开源推理框架DeepInfo,硬刚美国禁令
DeepSeek在开源模型后再开源推理框架DeepInfo,包含GPU/CPU交叉流水线、小模型预判大模型复核、华为昇腾与英伟达芯片全面适配等技术,直面美国联邦禁令。本文解析其对AI产业落地的意义与开源策略。