Day 068AI 协作手记 Working with AI约 8 分钟

两天用了 70% 的 Codex weekly usage,我才发现 AI 开发的消耗不只发生在写代码时

70% of weekly Codex usage in two days

一天用了接近 50%,第二天又用了 20% 以上。

两天过去,Codex 的 weekly usage 已经消耗了超过 70%。

看到这个数字时,我的第一反应是:是不是模型选得太贵?是不是开了太多任务?是不是测试和发布浪费了大量额度?

但回头翻任务记录,我发现这两天并不是没有产出。

几个功能完成了开发和发布,也做了数据库迁移演练、生产验证、Bug 修复和发布记录。问题在于,这些成果散落在不同的功能、修复和流程任务中。

如果有人问我:

这 70% 的 usage,最终换来了哪个清晰可见的产品进展?

我一时很难回答。

不是没有做事,而是做了很多事,却缺少一个完整的“成果感”。

我没有精确到每次调用的 token 账本,下面也不是对这 70% usage 的财务审计。它更像是一次工作流复盘:AI 到底把时间和消耗花在了哪里,哪些是必要成本,哪些本来可以避免。

Usage 并不只花在写代码上

以前我会下意识地把 Codex usage 理解成“写了多少代码”。

复盘后才发现,代码只是其中一部分。

一次 AI 开发任务的消耗,大致还包括:

  • 阅读产品和技术文档;
  • 理解代码库、数据结构和历史决策;
  • 检查当前分支、工作区和其他任务的状态;
  • 在多个任务之间协调共享依赖;
  • Review、测试、迁移和发布;
  • 工具失败后的重试;
  • 修复开发工作流本身的问题。

AI 看起来一直在工作,并不代表产品一直在以同样的速度前进。

它可能读了很多文件,输出了很长的分析,跑了几轮检查,也建立了新的工作区。但这些动作不一定都形成了新的代码、明确的决策或已经发布的成果。

第一处消耗:同一份上下文被反复读取

其中一个功能包发布后,我为下一个功能创建了新的独立任务和工作区。

从工程管理的角度看,这很合理:任务边界清楚,也不容易覆盖上一轮的修改。

但新任务启动后,又需要重新阅读:

  • 当前阶段的产品方案;
  • 技术设计;
  • 数据库结构;
  • API 和前端实现;
  • 上一轮的交接说明;
  • 构建和发布限制。

这些内容很多已经在上一轮确认过了。

结果是,我以为 AI 已经在“推进下一步”,它实际上花了相当多的时间重新建立对项目的理解,最后当天主要完成了技术方案审查,还没有进入完整实现。

这并不是无意义的工作。

但它让我意识到:

任务拆得越多,不代表推进得越快。每一个独立长任务,都有自己的启动成本。

边界明确、上下文很少的小任务,适合拆开。

但如果连续几个任务共享大量产品、架构和代码背景,拆得太碎,反而会不断重复支付上下文成本。

第二处消耗:非绝对独立任务同时运行

当时有几条工作线在相近的时间窗口推进。

为了避免互相覆盖,它们使用不同的分支或 worktree,修改的文件看起来也不完全相同。

但其中一些任务共享:

  • API;
  • 数据库迁移;
  • shared types;
  • 数据模型;
  • 公共组件;
  • 尚未完全稳定的产品决策。

一旦其中一条工作线改变了这些共享内容,另一条就可能需要暂停、等待交接、重新同步,再做一次验证。

这让我修正了一个之前很粗糙的判断:

文件不重叠,只能说明它们不会直接覆盖彼此;不能说明它们在逻辑上真正独立。

判断是否适合并行,应该看 shared contract 是否已经稳定,而不只是看双方会不会修改同一个文件。

我后来把它总结成一句话:

并行看契约,不只看文件。

真正适合长任务并行的情况,通常需要同时满足:

  • 输出相互独立;
  • 共享接口和数据结构已经稳定;
  • 没有未解决的上游依赖;
  • 最后的整合很简单。

否则,看起来是两个 agent 同时工作,实际可能只是更早制造了等待、同步和返工。

第三处消耗:谨慎逐渐变成了重复验证

测试、Review 和发布验证当然不是浪费。

不做这些,最后产生的返工可能更贵。

问题在于,验证很容易从“必要证据”变成一种固定仪式:

  • 每完成一小步,就做一次全面检查;
  • 不同任务重复运行相同测试;
  • 已经确认过的授权和边界,被新的任务再次询问;
  • 每一次交接,都重新生产一遍同样的证据。

其中有一次,某个任务临时选择的模型和 effort,被错误地写成了项目级默认配置。

这意味着我在界面中为新任务选择的模型,可能被项目配置覆盖。

随后又需要重新审查配置影响、提交修复、发布,再验证固定配置已经被移除。

这次额外工作不是为了修产品,而是在修 AI 工作流本身。

它也说明了一个问题:

一次任务中的临时选择,不应该在没有明确授权的情况下变成长期规则。

应该减少的不是测试,而是同一份证据被反复生产。

更合理的节奏是:

  • 开发过程中,运行与当前修改直接相关的 targeted checks;
  • 一个成果接近完成时,再做一次受影响范围的完整验证;
  • 发布后,只做必要的生产验证。

强模型和高 effort 让漏水变得更快

当我看到 usage 快速下降时,最先想到的是模型成本。

但模型更像一个放大器。

高风险判断、复杂架构冲突和难以定位的 Bug,确实需要更强的模型和更高的 effort。

但常规实现、测试、迁移和已经明确的发布步骤,并不需要全程使用最高配置。

如果工作流里本来就存在:

  • 重复加载上下文;
  • 不成熟的并行;
  • 反复确认;
  • 过度验证;

那么把所有任务都交给最强模型,并不会解决这些问题,只会让同一条路径消耗得更快。

我后来开始用一个更简单的问题选择模型:

当前最难的是执行,还是判断?

如果难点只是按照清楚的方案完成实现,用够用的模型即可。

如果难点在于复杂调试、架构权衡、权限或数据风险,再提高模型和 reasoning effort。

最高档位应该留给真正尚未解决、错误代价又很高的问题。

重新定义 AI 开发的工作单位

复盘以后,我不再默认用“一个小功能”或“一次对话”作为工作单位。

我现在更倾向于按一个完整、可验证的成果来组织任务:

一个明确的可验证成果 → 一个主要任务 → 一个主要写入者(active writer) → 开发中做针对性检查 → 接近完成时做一次完整验证 → 发布与必要的生产验证 → 一次性交接

这里的“一个 active writer”,不是说整个项目永远只能有一个 agent。

它的意思是:一个连续、长链路的成果,默认由一个主要 agent 负责实际写入和推进,避免几个 agent 同时解释相同的产品和技术边界。

只有任务真正独立时,才启动长任务并行。

一个成果,一个主任务,一个 active writer;并行看契约,不只看文件。

把经验写进规则,而不是每次临时提醒

如果每一次开发,都需要我重新提醒 AI:

  • 不要重复读取无关材料;
  • 不要随意开启长任务并行;
  • 不要每一步都做全面 Review;
  • 不要把临时选择写成项目默认值;
  • 不要在已经授权后反复询问;

那这些经验就还没有真正进入工作流。

所以我把这次复盘写进了项目规则:

  • 默认一个长任务、一个主要 writer;
  • 并行前检查 shared contracts 和上游依赖;
  • 开发中使用 targeted checks;
  • 接近发布时再做完整验证;
  • 自动 code review 不作为每一步的固定仪式;
  • 模型和 effort 不被永久固定在项目配置中;
  • usage 出现异常下降时暂停归因,但不反复轮询数字。

用户仍然负责目标优先级,以及会改变产品、架构、风险、成本和外部状态的决定。

AI 则应该负责缩小 scope、控制上下文、选择最小充分验证,并主动避免重复工作。

调整后

之后,我用这套方式完成了一个新的高风险跨端发布任务:

  • 使用独立工作区;
  • 保持一个 serial writer;
  • 开发中运行 targeted checks;
  • 发布前做一次完整回归;
  • 完成一次 migration rehearsal;
  • 做一次非付费 UAT;
  • 最后统一完成发布和 release record。

我现在还不能说,新的工作方式已经显著降低了 usage。

没有同口径的前后数据,这样的结论并不诚实。

但至少有几件事变清楚了:

  • 这次究竟要交付什么;
  • 谁负责实际写入;
  • 哪些工作可以并行;
  • 哪些验证现在必须做;
  • 哪些可以等到发布前统一完成。

对一个使用 AI 开发的项目来说,这种清晰本身就有价值。

比额度消耗更重要的是,「产出」是什么?

Usage 仍然需要看。

但我不再只问:

这次用了多少?

我更关心:

这些消耗最终换来了什么?

是可以运行的代码、通过的验证、明确的决策和完成的发布?

还是又一次上下文重载、重复确认、任务间协调,以及工作流自身制造的返工?

AI 开发的成本,不只来自模型价格和 token。

它也来自任务怎样被切分、上下文怎样被传递、并行怎样被组织,以及验证是否与当前风险相称。

模型决定每一步走得多快,工作流决定这些步是不是走向同一个地方。