2026 OPENCLAW
FALLBACK_
CONFIG_
DRIFT.
当你在 2026 年为 OpenClaw 配置了主模型 + 降级链路,最怕的不是短时的 429,而是fallback 成功后把运行时模型写回 `openclaw.json`**——从此配置文件里的「主模型」再也不是你以为的那一个,渠道路由也可能跟着漂移。本文给出症状三元识别(配置漂移 vs 会话态漂移 vs provider 解析分叉)、五步无损纠偏 Runbook(停 Gateway→备份→还原 agents 段落→清理陈旧会话映射→分层重启验证),以及远程 Mac 常驻 launchd场景下的顺序清单;可与《429 降级与日志》《sessions.json 膨胀》《Gateway token LaunchAgent》交叉阅读。
1. 痛点拆解:fallback 本来是救生筏,写回配置会变成锚
1)会话态污染配置意图:运行时为了渡过超时把模型切到备用档,若持久化逻辑未区分「用户显式切换」与「自动 fallback」,磁盘上的真源就被改写。2)provider + model 双字段不同步:只写了 model id 却没带上限定 provider 时,解析器可能回落到默认上游,表现为「配置看起来对,流量走错」。3)sessions.json 映射陈旧:Gateway 重启后仍引用旧会话键,会在 UI 里体现为随机路由或 silent noop。4)远程 launchd 与交互 shell 分裂:你在 SSH 里改的 JSON 未同步 plist 环境,重启后又回到漂移态。
2. 症状分层对照表
| 表象 | 优先怀疑 | 不推荐 |
|---|---|---|
| 磁盘上的主模型突然变成备用名 | fallback 写回 agents.list | 手工 Git revert 但不删会话映射 |
| 仅单个渠道走错模型 | 会话条目携带 runtime provider | 全局重装忽略 sessions.json |
| doctor 显示模型允许列表不匹配 | 配置与 sessions 分叉 | 反复 npm 升级不改 JSON |
| 远程 Mac 必现、本机偶发 | launchd 环境未加载最新 JSON | 复制粘贴半份 plist |
3. 五步纠偏 Runbook(生产向)
Step 1 宣告停机窗口并停止 Gateway
systemctl / launchctl 路径择一;确保没有 half-open WebSocket 仍在写会话。
Step 2 备份三元组
备份 openclaw.json、sessions.json、相关 *.jsonl(若体量过大至少备份映射键集合截图+digest)。
Step 3 还原「配置意图」段落
把 agents.list[].model、agents.defaults.model.primary、fallbacks[] 与注释内的变更单对齐;禁止只改模型不改 provider。
Step 4 清理陈旧会话映射
删除指向 fallback 运行态且缺显式用户授权的会话键;记录删除列表附工单。
Step 5 分层重启与探针
先本地 openclaw doctor,再起 Gateway,再用最小渠道探针消息验证三回合;每回合抓取 openclaw logs 片段。若渠道包含流式输出,务必记录首包与最终模型指纹两个时间点,避免把中间路由抖动误判为完成态。
4. 决策矩阵:热修 vs 计划停机 vs 临时禁用 fallback
| 信号 | 首选 | 次选 |
|---|---|---|
| 生产渠道可用但模型错 | 临时收窄允许列表 + 纠偏 JSON | 直接清空所有会话(丢上下文) |
| 多处 agents 共用 Gateway | 分 persona 冻结变更 | 全局单模型硬覆盖 |
| 远程 launchd 频繁复活旧 env | 校验 plist WorkingDirectory 与 JSON 路径 | 依赖交互 shell 临时 export |
5. 深度案例:一次「fallback 成功」如何把主模型永久降级(含审计复盘)
「供应商间歇超时触发 fallback,当晚对话恢复正常;两周后审计发现 disk 上的 primary 已被写成备用小模型。」
某运维团队在高峰期启用三家供应商降级。一次主模型 45s 超时后,fallback 模型接管并完成回合——符合预期。但由于会话写回路径未区分来源,agents.list[0].model 被持久化为备用 id;后续即便主线路恢复,Gateway 仍优先解析会话态里的「最后一次成功模型」。他们在工单里执行本文 Runbook:备份→纠偏→清理映射→分层重启,并在 MR 模板新增「禁止把 fallback 选择写回 agents.list」的静态检查提示。此后类似漂移工单归零。教训:降级要可观测,更要可逆。
复盘会议上,他们把事故等级定为「配置完整性」而非「可用性」,因为渠道并未宕机但合规标签全部错位;后续在内控报表新增模型字段哈希日报,一旦磁盘段落变化而无 CR 编号即触发复核。此类治理成本远低于再次面对审计追问与口径争议。
6. 行业洞察:多模型世界里的配置治理
2026 年的 Agent 网关不再是单一路由器,而是「策略 + 会话 + 供应商策略」三层叠加;任何一层把运行时态写进静态配置,都会在两周后以诡异路由回报。建议把 JSON diff 纳入变更评审,与基础设施 Terraform 同级对待。
对 macgpu.com 读者而言,常在远程 Mac 上常驻 Gateway:散热与电源稳定,但SSH 便利也会诱使人们跳过 plist 真源对齐。把纠偏 Runbook 存进内部 wiki,并在值班手册附上「远程 launchd 三步自检」,可以把半夜迷糊编辑的伤害降到最低。
Windows/Linux 节点当然可以跑 Gateway,但在图形/多媒体工具链与 Apple Silicon 一键脚本生态上,Mac 仍减少摩擦;若团队已在其它 OS 上踩坑、希望获得更可预期的 Metal 侧兼容与 7×24 远程 Mac SLA,可考虑租赁 MACGPU 节点承载 Gateway,以便把本 Runbook 与 launchd 模板原样复用。
观测层面,建议把「最后一次成功回合所用的 qualified model」打到结构化日志字段,而不是混在自由文本里;值班检索时可以用同一工单号串联 Gateway、供应商 HTTP 日志与磁盘 JSON 变更记录。若组织已有 SIEM,可把「agents.list.model 变更事件」做成低噪声告警:仅在无对应变更单号时触发页面。
变更节奏上,可把 fallback 链路分成实验通道与生产通道:实验通道允许频繁切换模型别名用于压测,生产通道只允许更改超时与重试参数,模型别名冻结在评审通过的 digest。这样可以把「救火的便捷性」与「配置的合法性」隔离,减少 fallback 成功后的隐性持久化。
7. Provider 解析与「限定路径」自检(避免隐性分叉)
当 agents.list[].model 仅为裸模型名时,解析栈通常会拼接默认 provider;一旦会话曾经成功使用过具备前缀的限定路径(例如 vendor/model),下一次回合就可能出现同名不同路由。建议在变更模板里强制填写显式 provider + model二元组,并在 CI 或预提交脚本中用 jq 断言字段齐全。对于多渠道部署(Telegram + Web UI + Cron),还要核对渠道级覆盖是否复制了旧的会话指针——某个渠道仍指向备用 persona,会让值班误以为全局已恢复。
远程 Mac 场景中,常见缺口是「SSH 会话里的 jq 修改」未触发 launchd 重新加载 plist;结果是磁盘 JSON 已正确,但进程环境仍缓存旧变量。Runbook 要求在重启 Gateway 前执行plist 与进程环境对齐三步:打印 launchctl 注入环境、对照 openclaw doctor 输出的路径、再用最小消息验证模型指纹。
8. 可引用数字门槛(附在变更单)
① 纠偏前后至少各跑 3 轮探针消息并保存日志指纹。② 任意供应商切换必须在工单记录时间戳与 HTTP 状态。③ 单周若出现 ≥2 次「磁盘模型与意图不符」事件,应冻结新的 fallback 链接改动直至代码路径审计。④ 任意涉及会话目录变更的操作必须附带备份校验和(sha256)以防事后争议。
9. FAQ
问:能否只删 sessions.json?答:若 openclaw.json 已被写歪,仅删会话会在下一次写入时复发。问:Docker 部署有何不同?答:注意 volume 挂载路径与容器内 HOME,备份三元组要在容器视角一致。问:需要升级版本吗?答:先完成纠偏与映射清理,再评估升级;否则漂移会在迁移时放大。问:多人协作如何避免互相覆盖 JSON?答:使用锁文件或变更窗口,并在合并冲突时优先以 Git 历史中的「意图段落」为准。 问:要不要禁用全部 fallback?答:不建议一刀切;应收窄允许列表并加超时,而不是移除整条救生筏。问:能否灰度只对部分账号启用新 fallback 链?答:可以,但必须在配置文件里显式拆分 persona,并为每条链单独维护 digest 与工单编号,避免灰度与生产共用同一 agents.list 段落。