> ## Documentation Index
> Fetch the complete documentation index at: https://docs.myrmagent.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# 错误恢复

> 14 层自愈系统，故障时 Agent 仍持续运行。

# 错误恢复

Myrm 错误恢复确保 Agent 在网络故障、模型宕机、限流与意外错误时**自动**持续运行，无需用户介入。

## 14 层恢复架构

| 层       | 机制            | 处理场景                                                                          |
| ------- | ------------- | ----------------------------------------------------------------------------- |
| **L1**  | 流恢复           | LLM 流式传输中断 — Token 级精确续传                                                      |
| **L2**  | 连续流恢复         | 连续流失败 — 多中断间保持上下文                                                             |
| **L3**  | 熔断器           | 模型提供商宕机 — 3 级冷却（auth 30min / permanent 10min / transient 1min）+ 半开探测          |
| **L4**  | 智能延迟故障转移      | 精确控制模型切换时机 — 429 限速永不切换模型（始终在同一模型上重试）；529 过载需连续 3 次失败后才切换备用模型，节省主模型配额，避免不必要降级 |
| **L5**  | Agent 恢复      | 工具执行失败 — 自动重规划替代策略                                                            |
| **L6**  | 截断恢复          | 响应被截断 — 本地 JSON 修复 + 渐进输出预算提升（2x→3x→4x）自动重试                                   |
| **L7**  | 辅助模型防护        | 小模型安全 — 摘要前动态截断消息防崩溃                                                          |
| **L8**  | 确定性回退         | 无 LLM 安全网 — 规则摘要防死锁                                                           |
| **L9**  | 图片自动缩放        | 超限图片 — 自动重编码压缩                                                                |
| **L10** | 媒体拒绝恢复        | 模型拒收媒体 — 移除媒体仅文本重试                                                            |
| **L11** | 思考签名恢复        | 思考模式签名错误 — 关闭思考模式重试                                                           |
| **L12** | 长上下文档切换       | 超标准窗口 — 自动切长上下文模型变体                                                           |
| **L13** | 空响应恢复         | 模型返回空白 — 调参重试                                                                 |
| **L14** | Grace-Call 摘要 | 达迭代上限 — 最后一次无工具 LLM 调用生成结构化摘要，用户不见空白                                          |

## 熔断器

防止模型提供商宕机时级联失败：

### 状态

```
CLOSED（正常）→ OPEN（检测到失败）→ HALF-OPEN（探测）→ CLOSED（恢复）
```

### 错误分类

| 错误类型        | 冷却    | 恢复策略          |
| ----------- | ----- | ------------- |
| `auth`      | 30 分钟 | 检查凭证，尝试其他 Key |
| `permanent` | 10 分钟 | 切换回退模型        |
| `transient` | 1 分钟  | 退避重试          |

### 凭证池

单 Key 限流时自动轮换下一可用 Key：

* 4 种分发策略（轮询、最少使用、随机、优先级）
* 按 Key 错误感知冷却
* 每 Key 指数退避
* 冷却到期自动探测

## 错误诊断

错误时提供结构化可执行反馈：

### 9 类错误

| 类别                  | 示例       | 恢复提示      |
| ------------------- | -------- | --------- |
| `FileNotFoundError` | 文件引用缺失   | 建议搜索正确路径  |
| `PermissionError`   | 权限不足     | 建议请求审批    |
| `ConnectionError`   | 网络失败     | 自动退避重试    |
| `TimeoutError`      | LLM 超时   | 增加超时或简化请求 |
| `RateLimitError`    | API 配额用尽 | 换 Key 或等待 |
| `ContextOverflow`   | 窗口超限     | 触发压缩      |
| `AuthError`         | 凭证无效     | 轮换下一 Key  |
| `ToolError`         | 工具执行失败   | 尝试替代工具    |
| `ModelError`        | 模型能力不足   | 升级到更强模型   |

每条错误含 `error_hint`、`error_category`（28 种规范化分类，由 `ToolErrorCategory` StrEnum 统一管理，4 语言 i18n 全覆盖）与建议 `RecoveryAction` — GUI 显示为可点击按钮。跨层同步测试套件（46 项）确保 harness 枚举与前端 i18n key 永不漂移。

### 交互式恢复按钮

对于常见 LLM 错误，错误卡片包含一键修复按钮，直接跳转到对应设置页面：

| 错误类型          | 按钮          | 操作    |
| ------------- | ----------- | ----- |
| API Key 无效/过期 | "更新 API 密钥" | 跳转设置页 |
| 余额不足          | "充值余额"      | 跳转设置页 |
| 模型不存在         | "切换模型"      | 跳转设置页 |

按钮标签支持 5 种语言（英/中/日/韩/德），自动匹配用户界面语言。如果诊断引擎遇到意外错误，会优雅降级 — 基础错误信息正常显示，不影响使用。

### 代码执行自动诊断

当 Agent 运行 Python 代码或 Bash 命令时，执行引擎自动分类错误并生成可操作提示：

| 分类                | 触发条件                  | 自动生成的提示                                                |
| ----------------- | --------------------- | ------------------------------------------------------ |
| `import`          | `ModuleNotFoundError` | 智能安装命令+PyPI包名映射（如 `cv2` → `pip install opencv-python`） |
| `not_found`       | 命令不存在                 | 通过工具发现引擎提供平台级安装命令                                      |
| `permission`      | 权限被拒                  | 精准路径的 `chmod` 建议                                       |
| `timeout`         | 执行超时                  | 减少输入规模或拆分任务                                            |
| `oom`             | 内存不足                  | 分块处理数据                                                 |
| `sandbox_ro`      | 只读文件系统                | 重定向写入到 `/workspace` 目录                                 |
| `network_blocked` | 网络访问被阻止               | 告知 Agent 不要用其他 HTTP 库重试                                |
| `syntax`          | 语法错误                  | 无提示（Agent 应自行修复代码）                                     |

引擎内置 import-to-PyPI 映射表（PIL → Pillow, sklearn → scikit-learn, yaml → PyYAML 等），并自动检测是否可用 `uv pip`。所有代码在 VenvManager 管理的共享虚拟环境中运行，确保用户安装的包不会污染系统 Python。

## 模型自升级

轻量模型发现无法完成任务时：

1. 输出特殊标记 `<<<NEEDS_PRO>>>`
2. `EscalationScrubber` 拦截（对用户隐藏）
3. Agent 自动切换到配置的更强模型
4. 任务无缝继续

实现成本高效路由：简单任务用便宜模型，复杂任务自动升级。

## 循环检测

7 个独立检测器识别不同类型 Agent 循环：

| 检测器         | 模式                                        | 动作                 |
| ----------- | ----------------------------------------- | ------------------ |
| **重复**      | 相同参数重复调用同一工具                              | 警告 → 中断            |
| **乒乓**      | A→B→A→B 交替                                | 警告 → 中断            |
| **无进展**     | 跨轮输出不变                                    | 警告 → 中断            |
| **发散**      | 工具调用越来越偏题（自适应阈值：探索 60% / 执行 30% / 恢复 15%） | 警告 → 中断            |
| **输出递减**    | 响应质量下降                                    | 警告 → 中断            |
| **连续失败**    | 多个工具调用连续失败                                | 警告 → 中断            |
| **跨工具错误签名** | 不同工具产生相同错误模式（行号/路径归一化后对比）                 | ToolStuckException |

渐进响应：先向上下文注入带上下文感知建议的警告，持续则强制中断（严重级别：WARNING 3-5次 → ERROR 6-9次 → CRITICAL 10+次）。

### 压缩后循环防护

当上下文溢出触发紧急压缩时，LoopGuard 精确处理过渡：

* **循环检测状态全程存活** — 滑动窗口（模式检测）和错误签名运行在 `ContextVar` 中，与压缩操作的消息列表完全解耦
* **迭代预算智能重置** — `notify_compaction()` 重置 `total_calls`，避免 Agent 因压缩前的历史累积被过早终止，同时保留 `error_signatures` 实现跨压缩边界的失败追踪
* **Agent 阶段保留** — 当前执行阶段（探索、执行等）跨压缩保持，确保上下文感知的检测阈值不变

这种双重策略 — 更敏感地检测循环，同时给予 Agent 全新的执行预算 — 从根本上同时消除了「压缩后死循环」和「压缩后过早终止」两种失败模式。竞品无一处理此压缩×预算交叉点。

### 压缩后记忆保护

上下文压缩后，Agent 的记忆检索不会出现滞后或丢失，这得益于 5 层记忆保护架构：

1. **SystemMessage 免压缩**：用户 profile 和规则以 SystemMessage 注入，位于上下文首位，不参与压缩
2. **Learned Context 免压缩**：学习型上下文以 HumanMessage 注入，非工具调用配对，不会被压缩处理器选中
3. **PreCompactProcessor 主动召回**：压缩**前**自动触发向量数据库语义搜索，将相关记忆注入为独立消息块，确保压缩后 LLM 仍可访问关键记忆
4. **实时向量索引**：Qdrant 向量数据库写入后立即可搜索，不存在索引滞后问题
5. **记忆提取独立**：会话结束时的记忆提取使用原始对话，不受会话内压缩影响

这一架构设计从根本上消除了「压缩后记忆丢失」这一竞品需要额外补丁（如强制索引刷新）才能解决的问题。

## 迭代预算

Agent 有可配置迭代上限（默认 50），阈值基于图递归限制动态计算：

| 阈值       | 动作                                 |
| -------- | ---------------------------------- |
| \~70% 预算 | 首次警告：「审视原始目标，优先处理关键任务」             |
| \~90% 预算 | 严重警告：「立即收尾工作」                      |
| 100% 预算  | ToolStuckException → 硬停 + grace 摘要 |

阈值根据 `graph_recursion_limit` 自动推导并转换为工具调用次数，确保预算在任何配置下都能正确缩放。grace 摘要结构化总结已完成工作、剩余任务与继续建议。

## 静默工具重试

工具调用因瞬时错误（网络超时、限流、临时不可用）失败时，系统自动重试 — 用户只看到心跳计时器在跳动，永远看不到失败。

### 6 层重试架构

| 层级        | 机制                                        | 用户感知                     |
| --------- | ----------------------------------------- | ------------------------ |
| **工具执行层** | 2 次自动重试 + 指数退避 + `Retry-After` 头尊重 + 熔断器  | TOOL\_HEARTBEAT 实时更新耗时秒数 |
| **步骤计划层** | Planner 3-Strike：按错误类型计数 + 结构化尝试历史 + 自动升级 | 3 次内静默重试，超过后升级到用户审批      |
| **目标验证层** | 验证失败自动重试 + 成功后计数器重置                       | 用户无感知                    |
| **流式恢复层** | 10+ 种恢复策略（溢出/故障转移/升级/瞬时重试）                | 短暂停顿后无缝继续                |
| **沙箱恢复层** | Shadow Git + 按操作快照的沙箱状态恢复                 | GUI 一键回滚到任意检查点           |
| **前端心跳层** | SSE TOOL\_HEARTBEAT 事件实时更新 elapsed\_ms    | 用户看到"工具执行中 15s"而非卡死画面    |

### 与竞品的区别

* **非 prompt 指令**：重试逻辑是确定性代码（Pydantic schema + 计数器），不是 LLM 可能忽略的自然语言指令
* **非仅开发者可见**：不同于框架级重试配置（如 LangGraph 的 `RetryPolicy`），心跳 UI 让终端用户也能看到执行状态
* **非打扰式**：重试静默进行 — 无错误弹窗，瞬时故障无需用户决策

## 文件检查点

任何破坏性文件操作前，`AutoSnapshotInterceptor` 自动快照：

* 覆盖 6 类工具：`write_file`、`patch_file`、`delete_file`、`move_file`、`execute_terminal`、`code_execute`
* 每轮去重防冗余快照
* 快照支持 GUI 一键回滚

## 数据库安全

五级防护体系确保数据（对话、定时任务、记忆）在任何故障下零丢失：

| 层级          | 防护                                             | 时机        |
| ----------- | ---------------------------------------------- | --------- |
| **迁移前快照**   | 每次升级迁移前自动备份                                    | 应用启动      |
| **三级容灾**    | 抢救（`.dump`）→ 备份恢复 → 内存降级                       | DB 初始化失败  |
| **定期热备份**   | 每 6 小时 SQLite 备份 + 关闭时快照                       | 运行中       |
| **框架级备份管理** | SHA-256 校验 + manifest + retention + quarantine | harness 层 |
| **健康探针**    | 双层探活 + 自动修复                                    | 持续        |

多步表重建迁移（如 `CREATE TABLE AS SELECT → DROP → RENAME`）被完整保护：即使进程中断，迁移前快照提供干净的恢复点。

## 子Agent错误摘要防污染

当子Agent崩溃产生长篇错误信息时，系统自动压缩错误后再返回父Agent — 防止上下文污染导致父Agent推理质量下降。

| 方面       | 实现                                                             |
| -------- | -------------------------------------------------------------- |
| **策略**   | 头部 + 截断标记 + 尾部（头部保留错误类型，尾部保留最近栈帧）                              |
| **默认上限** | 2000 字符（\~500 tokens）— 通过 `SubagentConfig.max_error_chars` 可配置 |
| **纵深防御** | 双层：executor 错误路径 + notifications 格式化层                          |
| **节省**   | 典型 8000 字符 traceback → 2000 字符（75% 压缩，每次失败节省 \~1500 tokens）    |
| **禁用**   | 设置 `max_error_chars=0` 可透传原始错误                                 |

这防止了多Agent系统中的常见故障模式：子Agent的冗长崩溃输出占满父Agent的上下文窗口，导致层级间级联推理退化。

## 子Agent失败时保留部分进展

当子Agent执行到中途失败（LLM 错误、预算耗尽、超时或运行时异常），所有已完成的工作将被保留并返回给父Agent —— 永不丢失。

| 失败路径                     | 发生什么               | 父Agent收到                                               |
| ------------------------ | ------------------ | ------------------------------------------------------ |
| **LLM 错误**（MyrmLLMError） | 模型服务返回错误，但已有部分工作完成 | `SubAgentResult(success=False, result="已完成的80%工作...")` |
| **预算耗尽**                 | Token/费用限制在任务中途触发  | `SubAgentResult(success=False, result="预算触顶前的工作...")`  |
| **超时**                   | 任务超过截止时间           | `SubAgentResult(success=False, result="超时前的进展...")`    |
| **运行时异常**                | 非预期崩溃              | `SubAgentResult(success=False, result="所有已累积的输出...")`  |

### 为什么重要

如果没有部分进展保留，一个完成了80%复杂任务后遇到限速的子Agent会**丢失所有工作**。父Agent不得不从零开始 —— 浪费已消耗的Token，成本翻倍。

Myrm 的方式：

* 父Agent收到所有已完成的结构化输出
* 父Agent可从子Agent停止的地方继续
* 成功部分消耗的Token不浪费
* 过长的部分输出自动截断（通过 `max_error_chars * 2` 可配置）

### 竞品对比

| 能力        |   Myrm  | Claude Code |   OpenClaw  | Hermes |
| --------- | :-----: | :---------: | :---------: | :----: |
| 失败时保留部分进展 | 4条路径全覆盖 |      无      |      无      |    无   |
| 结构化错误状态   |  12种状态  |     仅退出码    | tool\_error |  超时/崩溃 |
| 截断保护      |    自动   |      无      |      无      |    无   |

## 级联错误防护体系

Myrm 在 Agent 层级的每个层面提供纵深防御，防止级联故障：

| 层级         | 机制                                             | 范围        |
| ---------- | ---------------------------------------------- | --------- |
| **基础设施**   | 熔断器（CLOSED → OPEN → HALF\_OPEN 三态）             | 每模型/每浏览器池 |
| **终端错误**   | 硬熔断（网络/沙箱不可用）                                  | 会话级       |
| **行为模式**   | LoopGuard（7 类模式检测）+ FrequencyGuard（滑窗限频）       | 会话级       |
| **子Agent** | `_cascade_cancel_descendants` — 递归取消所有后代 Agent | Agent 层级  |
| **紧急停机**   | E-Stop（KILL\_ALL）— 立即停止所有工具执行                  | 全局        |

与传统微服务的依赖链不同，LLM Agent 中工具之间不存在显式 DAG 依赖 — 调用顺序由 LLM 推理链动态决定。Myrm 在正确的抽象层面解决级联错误：基础设施熔断 + 行为模式检测 + 层级级联取消，而非试图建模不存在的工具依赖图。

**实测验证**：级联错误防护全模块 604 项测试通过（LoopGuard、FrequencyGuard、E-Stop、ToolCallBroadcaster、SubagentExecutor、CircuitBreaker、ToolGuards）。

## 重试风暴与预算防护

Myrm 主动防止失控重试循环并保护 API 预算：

| 守卫                              | 功能                                         | 响应                                        |
| ------------------------------- | ------------------------------------------ | ----------------------------------------- |
| **LoopGuard**                   | 检测 7 类循环模式（重复/乒乓/无进展/发散/输出递减/连续失败/跨工具错误签名） | WARN → BREAK                              |
| **FrequencyGuard**              | 滑窗限频（全局 100 次/分钟 + 单工具 30 次/分钟）            | 80% 告警 → 100% 熔断                          |
| **MultidimensionalBudgetGuard** | 会话/日/单次调用 3 维 USD 预算限制                     | OK → WARNING → FINALIZATION → EXCEEDED    |
| **迭代预算**                        | 基于递归限制动态计算工具调用预算                           | 70% 告警 → 90% 严重 → 100% ToolStuckException |

这是**主动截断**（立即停止执行），不是被动监控（仅记录和告警）。检测到重试风暴时，Agent 被强制停止并输出当前最佳结果 — 同时保护云托管算力成本和本地 API Key 余额。

**实测验证**：重试防护全模块 330 项测试通过（LoopGuard、FrequencyGuard、BudgetGuard、MultidimensionalBudgetGuard、BudgetBoundaryMiddleware）。

## 预算防护体系

Myrm 在所有部署模式下提供全面的预算控制：

* **MultidimensionalBudgetGuard**：会话/日/单次调用 3 维 USD 限制，4 级渐进响应（OK → WARNING → FINALIZATION → EXCEEDED）
* **动态预算提示**：当预算降至 WARNING 或 FINALIZATION 时，自动将真实剩余 USD 金额注入 LLM 提示词 — AI 精确知道还能花多少钱并自动调整行为
* **BudgetBadge**：聊天输入区实时预算徽章，显示使用百分比和颜色编码状态
* **BudgetExceededDialog**：预算超限弹窗，一键充值或升级套餐
* **ChannelBudget**：每个 IM 渠道（Telegram、微信等）独立预算限额
* **BudgetPolicySection**：完整的预算策略配置 UI，支持 finalization reserve
* **DailyChart**：30 天用量趋势图 + 缓存命中率叠加折线

**实测验证**：预算防护全模块 181 项测试通过（harness 框架层 102 passed，server 业务层 79 passed）。

## 数据生命周期管理

Myrm 自动管理所有存储引擎的数据保留 — 无需手动清理：

* **9 大自动调度器**：Context 文件 3 级清理（30d/14d/7d）、Auth 日志可配置轮转、Chat 回收站 30 天自动清除、SQLite WAL checkpoint（每 6h）、数据库轮转备份、Qdrant segment 优化、Browser zombie 检测（48h 阈值）、Kanban GC、Incognito 1h 自动清除
* **MemoryGuardian**：自适应维护频率 — 健康时每 6h，异常时缩短至每 2h。健康分数驱动（70 normal / 35 critical），连续 2 次不健康后强制维护
* **文件引用追踪**：通过 `file_access_tracker` 防止误删被引用的上下文文件
* **调度器健康 API**：所有后台调度器的实时 green/yellow/red 状态监控
* **热备份**：每次维护周期后自动 SQLite 热备份

**实测验证**：数据生命周期管理全模块 413 项测试通过（server lifecycle 265 passed，harness lifecycle 90 passed，cron + memory 58 passed）。

## 技能进化 — 自我改进的 Agent

Myrm 的 Agent 能从失败中学习并自主进化技能：

* **自动进化**：当技能失败或收到负反馈时，系统生成进化提案直接更新技能文件本身 — 而非临时的 prompt 补丁
* **审查生命周期**：安全变更自动应用，风险变更变成可审查的 growth case（approve/reject 工作流）
* **语义去重**：similarity\_checker 防止技能熵增 — 重复或近似技能在保存前被拦截
* **经验账本**：每个进化事件（14 种类型）永久记录，用于审计和分析
* **质量告警**：技能质量下降时通过 Webhook 通知，支持主动维护

**实测验证**：技能进化全模块 489 项测试通过（server 107 passed，harness 框架层 382 passed）。

## 用户体验

恢复对用户透明：

* **模型宕机？** — 毫秒级切换备用
* **网络断开？** — 流从断点 Token 续传
* **限流？** — Key 轮换或退避后重试
* **API Key 过期？** — 错误卡片中一键跳转设置页更新
* **Agent 循环？** — 早期检测，避免浪费预算
* **响应截断？** — 文本截断：无缝 keep+continue 渐进输出提升（2x/3x/4x，上限32768）；工具截断：丢弃无效内容+自动重试；JSON截断：本地修复。Output Cap 自适应恢复覆盖 5 种提供商格式（Anthropic/OpenRouter/LM Studio/vLLM/DashScope）。SSE 状态通知支持5种语言。**388项output-cap专项 + 294项截断/恢复测试已验证（2026-07）**
* **升级中断？** — 迁移前快照自动恢复数据
* **子Agent崩溃？** — 错误自动压缩，父Agent仅收到精简摘要，推理不受污染
* **工具调用失败？** — 静默重试 + 心跳计时，你看到的是"执行中 15s"而非报错
* **流式错误可恢复？** — 错误消息附带 `recovery_actions` 可点击按钮（重试、切换模型、安装依赖），直接在聊天界面操作。结构化 `diagnostic_result` 提供 i18n 错误诊断 + 分步修复指引，无需猜测原因
* **反复失败？** — 3-Strike 协议自动升级请求协助 — 不会无限循环
* **环境异常？** — Doctor 诊断面板并行执行 9 项探针（Python 版本、依赖、LLM 连通性、网络、工作区存储、数据库、浏览器、Hook 系统、桌面控制），GUI 健康卡片一目了然，一键修复按钮快速恢复。无需打开终端执行命令，所有诊断和修复操作均在图形界面完成
* **SSE 断线了？** — 目标进度面板自动清除过期指示器，重新同步服务端最新状态，已完成的步骤保留展示。不会出现幽灵转圈或 Agent 已停止却仍显示「进行中」的误导
* **取消正在运行的任务？** — 端到端取消信号在 0.5s 内传播到整条执行链（CancellationMonitor 轮询间隔）。后台任务被 kill，子代理级联取消，资源清理，token 注册表注销
* **长任务中断连了？** — 宽限期容忍机制保持任务存活。持续断连时，OfflineDurableTask 自动注册后台继续运行，完成后推送通知
* **服务器重启时目标正在执行？** — 孤儿目标自动暂停并标注原因。持久任务在下次启动时从 LangGraph checkpoint 恢复 — 零重复工作
* **普通对话中进程崩溃了？** — InterruptedTurnMarker 在每次 Agent 流启动前写入持久化预写记录。重启后自动扫描符合条件的标记并在后台续跑，包含聊天历史重新加载、消息持久化、崩溃循环断路器（最多 2 次尝试）、15 分钟新鲜度窗口、成功/失败用户通知。可通过 `autoContinueInterruptedTurns` 设置控制（默认启用）
* **需要紧急全停？** — E-Stop API (`/freeze`) 一键取消所有活跃 Agent 流 — 生产环境的紧急熔断按钮
