TOBATSU 2.0 · CC 独立审查 · 2026-06-11

这套"新世界"现在到底能不能用?

审查人:tobatsu-cc(独立证据门),全部结论来自第一手取证:自己跑的 grep / sha256 / ssh / 只读 DB 查询。零改动。

一句话答案:有人盯着的时候真能跑通,没人盯着就不能用。派发 → 容器 → 交付这条关键路是真的(M5、P3 两次真实出片为证),但它现在缺三样东西:不会自愈、没法重新部署、镜像供应链断了一截。三件都是工程活,不需要推倒重来。

0 个
scheduler 进程(3 台机全查)
+7384 行
未提交的核心运行时代码
18 层
systemd drop-in 叠加出的 API 配置
16 步
手工拷贝拼出的部署链
P0 之一 · 调度 / 自愈

任务卡死了,没有任何东西会去救它

代码里其实写了一整套自愈:卡死任务回收、重试次数用完判失败、定时任务派发、审核超时处理。但这套东西只活在一个叫 main.py scheduler 的独立进程里——我把 admin、worker2、worker3 三台机器的进程、systemd、PM2 全部翻了一遍:没有任何人在跑它。API 进程里也没有内嵌(启动代码里零接线,我逐行查过)。

这不是理论风险,库里现在就躺着两具尸体:

  • 任务 e3e203dd(r8_proof):状态 running,从 6 月 7 日卡到现在 4 天,一动不动。按代码本意,10 分钟后就该被回收重排。
  • 任务 8cb14946(auto_ad_revision_router):在 default 队列里 queued7 天——这个队列根本没有 worker,而且就算 scheduler 跑起来,"排了队但没人接"这种情况也没有任何超时和告警

这两个就是你在 Admin 页面看到的红卡。换句话说:现在发现卡死任务的机制,是你的眼睛。

连带后果:worker 半路挂掉 = 它手里的任务永久卡死;定时任务(recurring)在 2.0 上根本不会被派发

P0 之二 · 源码管理

线上跑的代码,git 里找不到

我把四个地方的代码指纹(sha256)逐一对了一遍,结果是:没有任何一个 git 提交能复原线上任何一台机器正在跑的代码。

GIT 世界 线上世界(git 之外) master 分支 还是 1.x 老代码 2.0 分支 tip 2891843 已推 GitHub,但缺 7384 行 /tmp 工作区 +7384 行没提交 /tmp 补丁文件 后 8 次部署只活在这里 admin API(线上) app.py 1fd47d31 16 个 release 目录 手工 copy + 覆盖文件拼成 worker 机 release w2 / w3 各 6-9 个目录 LEGEND 墨蓝=正在服务的线上代码 · 暖灰=中间产物 · 虚线=本该存在但断掉的链路

要害不在"乱",在"不可恢复":/tmp 一被清(重启就可能清),后 8 次部署的来源就永远没了;工作区一丢,2.0 的核心实现就只剩线上那份没有历史的拷贝。

具体数字:未提交的 7384 行里约 5000 行是承重墙——claim 隔离、镜像 reconcile、写围栏租约、/resolve 路由、整个 2.0 API 面。而且连这个工作区都只对应 6 月 8 日的中间版本,之后 8 次部署(bodysha → R10 → S4 → R0 → R9 M1-M4)每一步都是"拷贝上一个 release 目录、替换两个文件、加一层 drop-in"手工拼的。这条 16 步链我和 codex 各自独立核对过,每一步的 sha 都对上了。

P0 之三 · 部署 / 重启

你说"重启半天不干净"——有结构性根因

repo 里没有任何部署物:没有部署脚本、没有 systemd 单元文件、没有环境变量模板,只有一份手工 runbook。线上的真实形态是:

API(admin 机)

  • 真实配置 = 服务文件 + 18 个 drop-in 按文件名字典序层层覆盖,每做一步实验加一层,.bak 文件也混在目录里。
  • 重启后的环境变量是这 18 层叠加的结果——没人能心算出来,这就是"重启不干净"的来源。
  • 回滚方式 = 删掉某层 drop-in。没有版本概念。

worker(w2 / w3)

  • 同一台机器上两套管理并存:test/material worker 走 systemd,mai worker 挂在 PM2 老监管下。重启、排障路径完全不同。
  • release 目录同样手工拷贝,没有 current 链接。

镜像供应链断在最后一步

CI(GitHub Actions → GHCR)确实建了,但它只把镜像 digest 打印到构建日志里,不写进数据库的 runtime_profiles 表——登记和激活全靠手敲 SQL。更糟的是 CI 构建不传依赖清单哈希(默认 unknown),而容器里的身份自检会把 unknown 判为不合格直接退出——CI 产出的镜像在 image_owned 模式下天生不可用。线上能跑,是因为用的全是手工构建、手工推到 DockerHub 的镜像。等于说:自动化管道是装好但坏的,真供应链是一个人的手。

P1 · 会咬人的高风险项

九件事,迟早出场

编号问题什么时候咬你
P1-1排了队但没 worker 接的任务,永远没人发现(scheduler 修好后依然存在——回收只看 running,不看 queued)队列名拼错 / worker 没起,任务静默消失
P1-2worker 和控制面失联只打一条日志,之后继续按旧镜像跑任务;拉镜像失败也只是攒错误升级镜像那天,部分机器悄悄跑旧版本
P1-3NFS 双重单点:worker 启动硬依赖两个挂载,w2/w3 还都挂着 admin 的共享目录admin 一挂,worker 不能重启 + 在途任务 I/O 全烂
P1-4claim 查询的 4 路 OR 条件用不上索引(迁移文件自己承认)队列一深,每次领任务都是全表扫
P1-51.x 的 scheduler 若连到共享库,会去碰 2.0 的定时任务(没有版本过滤)现在没人连(我查过),但这是埋着的雷
P1-6写租约续约失败时静默退出,agent 继续干活但之后每次写都 409长任务后半程全部写入失败,白跑
P1-7老模板迁移靠"踩一个坑补一条规则":宿主路径改写是硬编码清单,没有通用预检每迁一个带宿主路径/环境变量的老模板,先跑挂一次
P1-8每个任务容器把宿主的 ~/.claude、CODEX_HOME 以读写挂进去凭据/状态串扰,"全隔离"的说法被它一票否决
P1-9TEMPLATE_RELEASE_ENVIRONMENT 默认 test,上 prod 忘改就会拿 test 快照派活,无护栏未来切 prod 的第一天

完整清单(含 P2 工程债 6 条和每条的代码位置)在 /tmp/cc-review-tobatsu2-newworld-FULL-20260611.md

公平地说

哪些东西是真的、好的

所以判词不是"全错重做",是:骨架对,但现在是一台需要作者本人在场才能运转的原型机。

修复顺序 · 每件一个 cc 门禁 · 最小修复

按这个顺序修,五步从"原型"到"能用"

#动作修掉哪个 P0/P1
1先锁源码:把工作区 +7384 行按模块拆成可审的提交推上分支;后 8 次部署的 /tmp 补丁同样入库P0-2(防丢失,其余一切的前提)
2把 scheduler 跑起来:一个 systemd 单元连 2.0 库,验证 e3e203dd 这类卡死被自动回收P0-1(自愈层上线)
3坍缩部署面:18 层 drop-in 收成 1 个环境文件 + 1 个干净单元;release 制作写成脚本进 repo;worker 统一到 systemdP0-3(重启从此可预测)
4接通镜像管道:CI 补依赖清单哈希 + digest 自动登记为 candidateP1 之首(供应链闭环)
5queued 无人接的侦测告警、容器摘掉宿主 ~/.claude 挂载、其余 P1 按 owner 节奏P1 渐进清账

全程规矩不变:codex 改、cc 逐件验收;每件只修观察到的真问题,禁止顺手加框架、加旗标、加"未来可能用上"的东西。