← 全部极客知识库

主流 Agent 入门教程 / Codex

10. 管理长任务-把TaskFlow升级到2.0

原文备份 · 第 11 / 27 篇 · 查看极客时间原知识库 ↗

本篇目录 · 12 节

来源:Codex

预计学习时间:55—70 分钟
本篇目标:把一次跨多个阶段的升级做成可规划、可验证、可中断、也可恢复的长任务。

前面几篇里,我们做的任务大多能在一个会话内完成。到了真实项目,需求常常不是“改一个函数”,而是连续经历规划、实现、测试、修正和文档更新。时间一长,最容易出问题的不是 Codex 不会写代码,而是任务逐渐失去边界:已经做到哪里、哪些决定已经确认、下一步该验证什么,全都只剩在聊天记录里。

这一篇,我们把 TaskFlow 升级到 2.0,加入三个相互关联的能力:

  1. list 可以按完成状态筛选任务;
  2. 新增 stats,显示任务总数、完成数和完成率;
  3. 新增 report,把当前全部任务导出为 Markdown 报告。

这三个功能并不难,难点在于把它们作为一个长任务稳稳落地。我们会同时使用四层保障:

  • 用 Plan 模式先确认路线;
  • 用 Goal 固定最终完成条件;
  • 用仓库里的计划和状态文件保存事实;
  • 用测试、Git Diff 和实际命令证明每个阶段真的完成。

Plan 和 Goal 不是一回事。Plan 回答“准备怎么做”,Goal 回答“什么结果出现以后才算结束”。仓库里的状态文件则负责回答“即使换了会话,别人怎样知道现在做到哪里”。

一、开始前先建立可回退的基线

进入 TaskFlow 项目目录。macOS、Linux 或 WSL 可以执行:

cd /你的路径/taskflow
git status --short
python3 -m unittest 
# 二选一,选择适用于当前系统的命令
python3 -m unittest discover -s tests -v

Windows PowerShell 使用:

cd C:\你的路径\taskflow
git status --short
py -m unittest 
# 二选一,选择适用于当前系统的命令
py -m unittest discover -s tests -v

这里要确认两件事:

  • git status --short 没有出现你不认识的改动;
  • 升级开始前,原有测试可以通过。

如果测试本来就有失败,不要带着它进入升级。先保存失败命令和报错,把它作为单独问题处理。否则后面出现红灯时,你无法判断是新代码造成的,还是旧问题一直存在。

基线正常后,在同一个项目目录启动 Codex:

codex

本文以支持 Goals 的 Codex CLI 为准。Goals 从 Codex 0.128.0 起提供。如果输入 /goal 后没有对应命令,先退出并运行 codex update,再用 codex --version 检查版本。不同版本可用的斜杠命令可能有差异,最可靠的办法是在输入框键入 / 查看当前命令面板。

二、先规划,不要让第一个回答直接改代码

在 Codex 输入框中输入:

/plan

然后提交需求:

请规划 TaskFlow 2.0,暂时不要修改文件。

目标:
1. list 支持 --status all|open|done,默认 all;
2. 新增 stats 命令,显示总数、已完成、未完成和完成率;
3. 新增 report --output <path>,导出 Markdown 任务报告;
4. 保持现有 JSON 数据兼容;
5. 继续只使用 Python 标准库;
6. 更新测试和 README。

请先检查当前代码和测试,再把工作拆成“筛选、统计、报告、总体验收”四个阶段。每个阶段写明:
- 修改范围;
- 需要先确认的歧义;
- 验证命令;
- 完成标准;
- 主要风险。

Plan 模式的可见结果应该是一份实施路线,而不是一批已经修改的文件。收到计划后,重点检查下面几个问题:

  • 是否保留了 list 原来的默认行为;
  • 是否明确空任务列表的完成率;
  • 是否说明报告输出目录不存在时怎么办;
  • 是否把业务计算与终端输出分开,以便直接测试;
  • 是否把旧 JSON 数据兼容纳入了最终验收。

如果这些问题没有说清楚,先在规划阶段追问。例如:

补充计划,但仍不要改代码:
1. 空任务列表的完成率统一显示为 0%;
2. report 的父目录不存在时返回清晰错误,不自动创建;
3. 报告结构固定为标题、生成时间、统计摘要、未完成任务和已完成任务;
4. 不增加模板系统。

请据此更新阶段边界和验收标准。

规划阶段多花几分钟,通常比实现后再推倒重来便宜。官方的长任务实践也强调:里程碑应足够小,而且每个里程碑都要带验收条件和验证命令。参见 Run long horizon tasks with Codex。

三、把计划和进度写进仓库

首次落盘前退出 Plan 模式(选择实施计划或按当前界面的模式切换提示),确认工作区可写;没有可写项时退出后用 codex --sandbox workspace-write --ask-for-approval on-request 重新进入并提供计划。此时只允许写 PLAN.md 和 STATUS.md,随后才授权代码阶段。

聊天记录可以恢复,却不应该成为项目唯一的状态来源。计划确认后,让 Codex 在仓库根目录创建两个短文件:

按照刚才确认的计划,创建 PLAN.md 和 STATUS.md,暂时不要实现功能。

PLAN.md 需要记录:目标、非目标、四个里程碑、每个里程碑的验收条件和验证命令。
STATUS.md 需要记录:当前阶段、已完成项、下一步、最近一次验证及结果、已知问题。

内容保持简短,不要复制整段对话。完成后展示文件摘要和 Git Diff。

随后输入 /diff 查看变化,也可以在另一个终端执行:

git diff -- PLAN.md STATUS.md

你需要看到的是清晰的项目状态,而不是泛泛的待办清单。PLAN.md 至少要能回答“每一步怎样验收”,STATUS.md 至少要能回答“现在做到哪一步、下一步是什么”。

如果项目不希望长期保留这两个文件,也可以把它们放进 docs/development/,或在任务结束后归档。关键不在文件名,而在于把长任务的核心状态放到可检查、可版本化的位置。

四、选择推进节奏,避免 Goal 越过验收点

本章采用逐阶段人工验收:先按第五节完成状态筛选,汇报后再授权下一阶段。不要同时设置覆盖整个 2.0 的活跃 Goal,否则持续推进的目标会与阶段暂停点冲突。

Goals 作为选修另做:在独立副本完成一次范围明确的小目标,例如只修一个已经复现的测试失败,并禁止进入下一功能。目标要包含结果、独立验证和约束。已设置目标后才用 /goal 查看、/goal pause 暂停、/goal resume 恢复;这些命令不是本章主线的必需步骤。

参考:官方 Goals 说明。

五、阶段一:完成状态筛选

现在开始第一个里程碑。输入:

执行 PLAN.md 的阶段一:为 list 增加 --status all|open|done。

要求:
- 默认行为与 1.0 保持一致;
- 非法状态值给出清楚提示和非零退出码;
- 测试覆盖 all、open、done、默认值和非法输入;
- 测试必须使用临时数据;
- 先运行相关测试,再运行完整测试;
- 验证通过后更新 STATUS.md,然后停下来汇报,不进入阶段二。

最终汇报请列出修改文件、运行过的命令、观察到的结果和仍然存在的风险。

Codex 停下后,不要只看“已完成”三个字。依次检查:

  1. /diff 中是否只有与筛选有关的修改;
  2. 是否真的运行了局部测试和完整测试;
  3. STATUS.md 是否写入了测试结果和下一阶段;
  4. 非法参数是否产生非零退出码。

最后一项可以亲自验证。在另一个终端使用临时数据文件;沿用已固定的全局 --data 参数;下列临时路径由你先创建,不依赖未定义的环境变量:

python3 taskflow.py --data "<临时文件绝对路径>" list --status invalid
echo $?

Windows PowerShell 对应执行:

py taskflow.py list --status invalid
$LASTEXITCODE

你应该看到可理解的错误提示,并得到非零退出码。如果命令只是打印错误但仍返回 0,自动化脚本会把失败误判成成功,这一阶段就还没有通过验收。

六、阶段二:统计功能先定规则,再写输出

继续输入:

执行 PLAN.md 的阶段二:新增 stats 命令。

输出总数、已完成数、未完成数和完成率。空任务列表的完成率显示为 0%。请把统计计算放在可直接测试的函数中,不要让测试依赖解析整段终端文本。

补齐正常数据和空数据测试,运行相关测试与完整测试。验证通过后更新 STATUS.md,并停下来汇报证据。

这里真正要学的不是如何算百分比,而是如何把“规则”变成可验证行为。完成后,用三组数据检查结果:

  • 空列表:总数 0,完成率 0%;
  • 全部完成:完成率 100%;
  • 完成一半:完成率 50%。

如果 Codex 为了测试方便,把统计逻辑抽成一个小函数,这是合理结构调整;如果它顺手重写了存储层或 CLI 框架,就已经超出阶段范围。长任务依靠小而清楚的 Diff 保持可审查,而不是靠一次性生成大量代码提高“完成感”。

七、阶段三:只实现已经确认的报告范围

本课 report 导出当前数据文件的全部任务快照,不按周筛选,因此统一称“任务报告”。若以后需要周报,先新增时间字段、时区、周起止和归属规则,再增加跨周测试。

报告功能最容易膨胀。模板、主题、配置文件、HTML 导出都很有诱惑力,但不属于本次 2.0。输入:

执行 PLAN.md 的阶段三:实现 report --output <path>。

报告采用已经确认的固定结构:标题、生成时间、统计摘要、未完成任务、已完成任务。

要求:
- 父目录不存在时给出清晰错误并返回非零退出码;
- 不增加模板系统;
- 测试核对文件被创建、关键标题存在、统计数字正确、任务分组正确;
- 使用临时目录,不向仓库留下测试报告;
- 更新 README 中的命令示例;
- 运行相关测试和完整测试,更新 STATUS.md 后停下来汇报。

完成后,除了看测试,还要实际打开一次产物。先准备一份临时数据,再让 report 写入临时目录。由于不同操作系统的临时路径和 TaskFlow 数据路径参数可能不同,可以直接让 Codex 给出适合当前项目的命令:

请根据当前 TaskFlow 的真实参数,给我一组不会读写 data/tasks.json 的手工冒烟命令:创建临时数据,加入一条已完成和一条未完成任务,生成 Markdown 报告,再打印报告内容。暂时不要执行。

检查命令没有指向真实数据后再执行。报告中应该同时出现:

  • 正确的总数、完成数和完成率;
  • 一条未完成任务;
  • 一条已完成任务;
  • 合法的 Markdown 标题。

“文件成功生成”只能证明写入发生了,不能证明内容正确。打开产物,是这一阶段不可省略的验证。

八、中断后怎样可靠恢复

如果今天做到一半需要离开,先让 Codex 更新状态:

准备暂停本次任务。请根据 Git 状态和实际验证结果更新 STATUS.md,写清已经完成、尚未完成、最近一次验证、下一步和已知阻塞。不要开始新阶段。

如果另做选修并有活跃 Goal,先暂停它;主线未设 Goal 则直接退出:

/goal pause

退出 Codex。下次回到同一个项目目录时,在终端执行:

codex resume

该命令会打开会话选择器。如果就是继续最近一次会话,可以执行:

codex resume --last

恢复后,不要直接说“继续”。先让 Codex 重新核对事实:

先不要修改文件。请读取 PLAN.md、STATUS.md、AGENTS.md,并检查 git status、git diff 和最近可运行的测试。

请列出:
1. 已完成且有证据的阶段;
2. 声称完成但仍缺少证据的项目;
3. 当前未提交改动;
4. 下一步最小动作;
5. 进入下一阶段前需要确认的风险。

确认状态无误后,主线直接授权下一阶段;只有选修中已暂停的 Goal 才使用:

/goal resume

这里的顺序很重要:会话记忆帮助你找回上下文,Git、项目文件和测试帮助你恢复事实。两者发生冲突时,以当前仓库和重新运行的验证为准。

九、上下文变长时,压缩还是分叉

长任务经过多轮讨论后,可以先输入:

/status

它用于查看当前会话和上下文状态。如果目标没变,只是聊天记录太长,可以输入:

/compact

压缩后立刻做一次核对:

请根据压缩后的上下文以及 PLAN.md、STATUS.md,列出当前 Goal、已完成阶段、未完成阶段、关键约束和最近一次验证结果。只报告,不修改。

如果摘要漏掉重要决定,把决定补到项目文件里。真正重要的信息不应只依赖上下文压缩是否完整。

如果目标已经发生分歧,就不要继续往同一个会话里塞内容。例如,你想比较“固定报告格式”和“可配置模板系统”,可以退出当前交互界面,在终端执行:

codex fork --last

它会基于最近会话的历史创建一个新会话。新分支适合调查另一条真正不同的方向;原会话继续负责已经确认的 2.0 范围。注意,分叉的是会话,不会自动隔离同一工作目录里的文件改动。若两个方向都要实际修改代码,应使用不同 Git 分支或 worktree,避免互相覆盖。

一个简单判断是:

  • 目标相同、上下文太长:用 /compact;
  • 目标不同、但需要继承历史:用 codex fork;
  • 只是临时问一个问题:在当前 Codex CLI 中使用 /side;它会临时分出一条对话,不会打断主聊天。

/side 和 codex fork 的区别在于:Side Chat 适合快速核对一个问题,结束后回到原聊天;Fork 会创建一个拥有新 ID 的持久分支,适合继续探索另一套方案。/side 不能在另一个 Side Chat 或 Review 模式里使用。若本机没有该命令,先输入 / 核对当前命令面板,再用 codex --version 与 codex update 检查版本。

十、总体验收:不要在最后一轮继续加功能

三个功能完成后,最后一个阶段只做整体验收和必要修复:

执行 PLAN.md 的总体验收阶段,不增加新功能。

请完成:
1. 运行完整测试;
2. 用临时数据实际执行 add、list --status all|open|done、stats 和 report;
3. 打开生成的 Markdown 报告,核对统计与任务分组;
4. 用一份 1.0 格式的 JSON 数据验证向后兼容;
5. 对照 README 逐条核查示例;
6. 审查完整 Git Diff,只修复阻塞 2.0 发布的问题;
7. 更新 STATUS.md,汇总修改文件、验证命令、实际结果和已知限制。

只有证据满足当前 Goal 时,才可以把任务标记为完成。若有失败,先报告失败证据和最小修复方案。

你最终至少应该拿到下面这些证据:

验收项 合格证据
状态筛选 三种筛选结果正确,默认行为兼容,非法值返回非零退出码
统计 空、全完成、部分完成三组数据结果正确
报告 临时目录中生成文件,内容和任务分组与输入一致
数据兼容 1.0 JSON 可以直接读取,不要求手工迁移
回归 完整测试通过,并记录实际命令和结果
文档 README 示例与当前参数一致,可以照着执行
改动范围 Git Diff 中没有真实任务数据、缓存、临时报告或无关重构

验收通过后,先在终端检查:

git status --short
git diff --check
git diff --stat

git diff --check 没有输出,通常表示没有空白错误;它不等于功能测试通过。确认文件范围无误后,再按项目习惯提交。不要因为教程给了示例就机械执行 git add .,更稳妥的做法是明确添加本次确认过的文件。

十一、把六种工具放回正确位置

工具 它解决的问题 不应该替代什么
/plan 实现前拆路线、找歧义和风险 不能证明功能已经完成
/goal 跨多轮保留可验证的完成条件 不能替代具体实施计划
PLAN.md 把阶段和验收方式放进项目 不能替代当前进度记录
STATUS.md 保存已完成、下一步和最近证据 不能只靠 Codex 自述更新
codex resume 回到已有会话继续工作 不能替代恢复后的事实核查
/compact / /side / codex fork 分别处理“同目标但过长”“临时岔开一问”和“方向已分开” 不能替代 Git 分支或 worktree 的文件隔离

如果只记住一个原则,可以记住这句:聊天负责协作,仓库保存状态,验证决定是否完成。

本篇小结

管理长任务,不是把一个巨大提示词扔给 Codex 后等待更久,而是把工作拆成可以单独验收的阶段,并让目标、状态和证据都能在中断后找回来。

在这次 TaskFlow 2.0 升级里,Plan 模式让我们先确认路径,Goal 固定最终完成条件,PLAN.md 和 STATUS.md 把状态放进仓库,codex resume 负责恢复会话,/compact、/side 和 codex fork 则分别处理上下文过长、临时问题与方向分歧。每完成一段工作,我们都用测试、实际产物和 Git Diff 重新建立事实。

下一篇,我们会把视野从一个项目扩展到 Codex 的能力扩展体系,分清 Skills、Plugins、MCP 和 Apps 各自解决什么问题,并为 TaskFlow 做一个真正可复用的发布检查能力。