🛠️ IndieKit

AI 编程不缺模型,缺的是外层控制系统

2026-06-14 · 13 分钟阅读 · AI编程, Codex, Loop Engineering, AI Agent, 工程实践, 开源

English version

最近几周,我越来越强烈地感觉到:AI 编程的瓶颈已经不只是模型能力。

模型当然还有差距。不同模型在推理、代码风格、上下文稳定性上都不一样。但对很多真实工程任务来说,今天的模型已经“够能干”了。真正难的是另一件事:

当 AI 已经能连续写代码、改代码、跑测试以后,我们怎么管理它产生的工作?

这就是我写 codex-orchestrator 的原因。

它不是又一个“更会写代码”的工具。它更像是 Codex App 外面的一层工程控制系统:负责拆任务、隔离 worktree、记录状态、定时巡检、发现卡住、验收分支、合并干净结果、清理现场,然后继续推进路线图。

起点:不是想做产品,只是想让 Codex 多干点活

最开始的问题很朴素。

我在做一个比较大的项目重写,模块很多:前台、后台、移动端、后端服务、报表、支付、打印、同步、权限。单个 Codex session 可以完成一个小任务,但当项目变大以后,问题开始变成:

所以我一开始做的不是写工具,而是写规则。

每个任务单独开 worktree。worker 只负责提交自己的 branch。它不能 merge、不能 push、不能清理 worktree。统领 session 负责巡检、验收、合并、推送和清理。

这个流程跑起来以后,我很快发现:规则写在聊天里不够。

聊天会压缩,任务 ID 会过期,heartbeat 会漏跑,worker 状态和 git 状态会不一致。于是 codex-orchestrator 从一个 skill 文档,慢慢长出了一层 Go helper CLI。

关键转变:不要把 Agent 当成神奇员工,要当成可验收的交付单元

很多人说“多 Agent 协作”,听起来像多招几个 AI 员工。

我后来觉得这个比喻不太对。

更准确的理解是:每个 worker branch 都应该是一个可验收、可拒绝、可清理的交付单元。

也就是说,worker 完成后,不是看它说了什么,而是看这些东西:

这套检查比“让 AI 再聪明一点”更实际。

因为在真实项目里,AI 最危险的地方往往不是不会写代码,而是把证据说过头。比如:

codex-orchestrator 里一直强调 evidence label,就是为了挡住这种过度乐观。

为什么需要 ledger

最开始我以为,让统领 session 记住当前任务就够了。

后来发现不够。

一个长跑的编排流程里,状态会散在很多地方:

这些东西只靠聊天记忆,很快会乱。

所以 helper 里有了 .codex-orchestrator/ledger.json。它不是为了替代 Codex App,而是为了给 Codex App 的外层循环一个本地状态账本。

一个任务从 pending setup,到 active,到 completed-unreviewed,到 accepted、merged、pushed、cleaned,应该有迹可循。

这解决的不是“AI 怎么写代码”,而是“明天早上醒来,我怎么知道昨晚到底发生了什么”。

Heartbeat 也不是魔法

我曾经以为,有 heartbeat 就能无人值守。

后来被现实教育了。

Codex App 的 heartbeat 可以定时唤醒 thread,但它不等于操作系统级 daemon。电脑睡眠、App 没调度、automation 没投递,都可能导致中间有空档。

所以现在我更保守地描述它:

这听起来不酷,但更真实。

工程系统不是靠一句“全自动”变可靠的。可靠性来自承认边界,然后给边界加观测、日志、告警和恢复策略。

状态页为什么重要

另一个很深的教训是:没有状态页,人就像盲人。

编排系统一直在跑,但你不知道它现在是在:

早期我只看命令输出和聊天总结,后来发现这对长期使用不够。

于是加了 status.mdstatus.html。它们不是漂亮 dashboard,而是让人快速判断:

状态页的目标不是炫技,而是降低“我不知道它在干什么”的焦虑。

最大的坑:为了填满并发槽而乱派任务

codex-orchestrator 最早有一个很诱人的错误:既然默认最多两个 worker,那有空槽是不是就该派一个?

真实使用下来,这会把项目做乱。

因为“安全可做”和“值得现在做”不是一回事。

如果今天的主线是 Customer checkout,就不应该为了填满并发槽,顺手派一个 Staff/RBAC,再派一个 KDS,再派一个报表。每个任务都能验收,但日报写出来像东一榔头西一棒槌。

后来我把规则改成 feature package 优先:

这是一个很重要的变化。

AI 编排不是多开几个 session,而是推进一个功能闭环。

为什么说它是 Loop Engineering

我理解的 Loop Engineering,不是写一个 while 循环让 Agent 一直跑。

它至少包括这些东西:

codex-orchestrator 做的就是这层外循环。

Codex App 仍然是执行者。它读代码、改代码、跑测试、提交 branch。

codex-orchestrator 是外层纪律:让每个 worker 的工作可恢复、可审查、可拒绝、可合并、可清理。

它现在不是什么

我不想把这个项目说得过头。

它现在不是:

更准确地说,它是一个 Codex App-first 的工程编排工作流,加一个本地 helper。

skill 负责让 Codex App 学会这套工作方式。helper 负责 ledger、status、preflight、routine、policy/eval、self-update 这些本地辅助能力。

真正创建 session、读代码、写代码、执行 worker 的,仍然是 Codex App。

模型越来越接近,外层系统会越来越重要

我最近一个感受是:模型之间当然还有差距,但很多工程场景里,差距已经不是最主要的问题。

当模型都足够能写代码以后,差异会更多体现在:

这也是为什么我对 codex-orchestrator 这个方向越来越确定。

它不是押注某一个模型。它是在押注一个判断:AI coding 会越来越像一个需要控制系统的工程过程。

模型是发动机。

但真实项目还需要方向盘、仪表盘、刹车、行车记录仪和维修手册。

下一步我想做什么

接下来我会把重点放在四件事上。

第一,让状态页更像真正的驾驶舱。少一点机器字段,多一点人能直接看懂的判断:现在在做哪个产品包,为什么等,为什么不派发,哪里需要人。

第二,把失败沉淀成 fixture。每次遇到“pendingWorktreeId 没落账”“availableSlots 误导派发”“local proof 被写成 direct”这种问题,都应该能变成 policy/eval,而不是只靠我下次记得。

第三,把异模型 review 做成更自然的 checkpoint。小切片不一定需要,但一个 feature package 收口后,很适合生成 review pack,交给另一个模型做第二视角审查。

第四,继续用真实项目打磨。只有真实长跑才会暴露这些问题:heartbeat 漏跑、worker setup race、ledger 滞后、status 误导、文档漂移、证据过度声明。demo 很难测出来。

结语

codex-orchestrator 的由来,其实不是“我想做一个开源工具”。

它是我在真实项目里被这些问题反复打到以后,逐步整理出来的一套工程纪律。

一开始只是几条 prompt 规则。

后来变成 skill。

再后来有了 helper、ledger、status、routine、policy、eval、self-update。

但核心一直没变:

不要只让 AI 写更多代码。要让 AI 的工作进入一个可观察、可验收、可恢复、可持续推进的工程循环。

如果你也在用 Codex App 做真实项目,而不是只做一次性小任务,可以试试:

github.com/indiekitai/codex-orchestrator