提交前自查工作流:`codex review --uncommitted` 到底该怎么写

2026-08-09

写完一段改动、准备 git commit 之前,想先让机器扫一遍——这是我认为 Codex(OpenAI Codex)在命令行里最容易立刻见效的用法之一。它不需要你先建 PR,也不需要把代码推上去,跑完就在本地终端里出结果。

但真要把它做成一条每天都能跑的固定流程,光知道有 codex review --uncommitted 这个命令是不够的。选项写在哪个位置、沙箱要不要收紧、结果怎么留档、哪些改动它压根不看——这几件事没想清楚,跑出来的东西你自己也不敢信。下面按”命令怎么写 → 产出物长什么样 → 怎么验收 → 什么时候别用”四段说。

本文里凡是标「本机实测」的,都是在 codex-cli 0.147.0(Windows 11)上执行只读命令得到的输出;我没有发起过任何模型对话请求,所以你不会在下文看到”它给我提了几条意见”这类内容。

一、review 子命令一共就四个选项,先分清

在 codex-cli 0.147.0 上,codex review 的官方说明是 “Run a code review non-interactively”——非交互式跑一次代码评审。它自己的专有选项只有四个,加一个位置参数:

选项作用
[PROMPT]自定义评审说明;写 - 表示从 stdin 读
--uncommitted评审已暂存、未暂存和未跟踪的改动
--base <BRANCH>与指定基线分支比较
--commit <SHA>评审某个 commit 引入的改动
--title <TITLE>评审摘要里显示的可选提交标题

这张表值得逐字读一遍,尤其是 --uncommitted 那一行。它的中文直觉是”未提交的改动”,但官方措辞是三类:已暂存、未暂存、未跟踪。未跟踪(untracked)也算在内,这是最容易被忽略、也最容易出岔子的一类——后面「怎么验收」那节会专门说。

另外三个选项跟”提交前自查”这个场景关系不大:--base 是拿当前分支跟基线比,--commit 是回头看某一次提交。真要自查提交前的工作树,就是 --uncommitted

二、命令怎么写:四条可以直接抄的

1. 最常用的一条

codex -s read-only -a never review --uncommitted --title "订单导出:补空值处理"

逐项说为什么这么写:

  • 选项的位置codex --help 给的用法是 codex [OPTIONS] <COMMAND> [ARGS],顶层选项写在子命令前面。本机实测的两条命令 codex -c 'features=[unclosed' doctor --summarycodex -c model_reasoning_effortt=high --strict-config exec --help 都是这个顺序。写成 codex review --uncommitted -s read-only 是把顶层选项塞到了子命令后面,别这么试运气。
  • -s read-only--sandbox 在 0.147.0 上的取值只有三个:read-only / workspace-write / danger-full-access(写错会怎样,第四节有实测的报错原文)。自查场景里我要的是”读代码、给意见”,不是”顺手把代码改了”,所以给最紧的那档。这不是安全承诺,只是把权限收到跟任务目标一致。
  • -a never--ask-for-approval 的三个取值官方释义是:untrusted 只放行受信任命令(如 ls、cat、sed),其余升级给用户;on-request 由模型自己决定何时请求审批;never 从不询问,执行失败直接回传给模型。这里有个特别容易读反的地方:never 不等于”放开权限”,它只管”问不问你”,能不能写文件是 -s 决定的。read-only + never 组合起来的语义是:不要中途弹窗打断我,越权的操作直接失败就行。
  • --title。给评审摘要一个标题。跑多次、或者把输出留档时,这行是你事后区分”这份结果对应哪次改动”的唯一线索,建议养成习惯写上。

2. 带上你自己的关注点

codex -s read-only review --uncommitted "重点看错误处理与边界条件,忽略格式问题"

位置参数就是自定义评审说明。默认评审是通用的,而每次提交你心里其实有数——这次动的是并发、还是动的是入参校验。把它写出来,比让模型自己猜要靠谱。

如果关注点比较长、或者团队有一份固定的自查清单,用 - 从标准输入读:

# Windows(PowerShell / cmd)
type review-checklist.txt | codex -s read-only review --uncommitted -

# macOS / Linux
cat review-checklist.txt | codex -s read-only review --uncommitted -

3. monorepo 里只查一个子包

codex -C packages/api -s read-only review --uncommitted

-C, --cd <DIR> 指定 agent 的工作根目录。monorepo 下你只改了一个包,却让它对着仓库根跑,等于把无关噪音全塞进去。如果评审确实需要读到主工作区之外的目录,顶层还有 --add-dir <DIR>,它的定位是”主工作区之外额外可写目录”——注意是可写,自查场景一般用不上。

4. 把固定参数沉淀成一个 profile

天天敲同一串选项很快就会烦。顶层的 -p, --profile <CONFIG_PROFILE_V2> 会把 $CODEX_HOME/<name>.config.toml 叠加到基础用户配置之上:

# ~/.codex/review.config.toml
model = "<你要用的模型名>"
codex -p review -s read-only review --uncommitted

以上为按官方文档键位组合的示例,未逐项实测,以官方文档为准。模型名请按你自己账号可用的填,别照抄别人的。

临时改一两个值也可以不写文件,用 -c, --config <key=value>:点号路径表示嵌套(foo.bar.baz),value 按 TOML 解析,解析失败则按字面字符串处理。官方给的三个例子是 -c model="o3"-c 'sandbox_permissions=["disk-full-read-access"]'-c shell_environment_policy.inherit=all

三、产出物长什么样,能不能接下一步

review 是非交互式跑的,结果直接打在终端里。这里我必须把话说死:本机没跑过真实评审任务,所以我不知道它输出的具体版式,也不会替你描述。

想把结果接进脚本、留档或者送进 CI,0.147.0 上和”机读”相关的选项是挂在 codex exec 下面的:

  • --json:事件以 JSONL 打到 stdout
  • -o, --output-last-message <FILE>:把 agent 的最后一条消息写到文件
  • --output-schema <FILE>:一个 JSON Schema 文件路径,描述模型最终回复的结构
  • --ephemeral:不把会话文件落盘

codex exec 本身是有 review 子命令的(exec 的子命令有 resumereview)。所以理论上机读这条路是走 codex exec review。但我没有逐项核对 codex exec review 具体接受哪些选项、--uncommitted 在那条路径下叫不叫这个名字——要落地之前,自己先跑一次 codex exec review --help 确认,这是只读命令,零成本。

顺带提醒一句:网上能搜到不少”Codex JSONL 输出字段”的写法,我不清楚哪些是真的。我没跑过真实任务,就不列字段名了,你也别照抄——版本一动这类东西最容易过期。

--ephemeral 值得单独说。本机实测 codex doctor --summary 的 Notes 区里,rollouts 一项提示 405 active files · 3.07 GB on disk~/.codex/ 下的 SQLite 日志库单个文件也到了几百 MB 量级。如果你把自查做成每次提交前都跑一遍的高频动作,会话文件是会实打实堆在磁盘上的。要么定期清,要么在不需要留档的那些运行里用 exec 侧的 --ephemeral

四、怎么验收:四个检查点,和最容易翻车的那一步

检查点 1:先确认版本,别用记忆里的版本号

本机采集过程中遇到过一件事:同一台机器,开头 codex --versioncodex-cli 0.131.0,十几分钟后再执行同一命令变成了 codex-cli 0.147.0which -a codex 全程只有一个可执行文件。Codex 具备自更新能力(配置里的 check_for_update_on_startup 默认为 true)。

所以任何跟选项、默认值有关的问题,第一步都是跑一次 codex --version当次的实时输出。别拿上周记住的版本号推理今天的行为。

检查点 2:配置到底加载上没有

codex doctor --summary

本机实测:故意用 codex -c 'features=[unclosed' doctor --summary 传一段语法不合法的 TOML,命令并没有崩溃退出,doctor 照常跑完,只是多出一行:

✗ config       config could not be loaded - Fix the reported config error, then rerun codex doctor.

这条一手结论很有用——配置坏了 Codex 照样能启动,它只是安静地用了默认值。所以”我明明在 config 里设了 xxx,怎么没生效”的第一反应不该是反复改配置,而是跑 doctor 看这一行。

doctor 的输出还有几处对自查流程直接有用:Configuration 分组下的 auth(auth is configured)、sandbox(本机显示 restricted fs + restricted network · approval OnRequest)。最后那行统计格式是 17 ok · 1 idle · 1 notes · 0 warn · 0 fail ok,并提示可以用 --all 展开被截断的列表。

想把诊断结果贴给同事或者贴进 issue,用 codex doctor --json——它的官方说明是 “Emit a redacted machine-readable report”,是脱敏的。

检查点 3:登录状态

codex login status

本机实测输出就一行:Logged in using ChatGPT。评审要走模型,登录没打通后面全白搭,两秒钟的事。

检查点 4(最容易翻车的一步):先自己 git status 看一眼

回到 --uncommitted 的定义:已暂存 + 未暂存 + 未跟踪。未跟踪那部分是坑的来源。

本地随手生成的临时文件、构建产物、日志、临时数据集,只要没进 .gitignore,在 git 眼里就是未跟踪文件。所以跑评审之前先 git status 扫一眼,确认列出来的东西确实是你这次要改的内容。这一步花五秒,能省掉一次”它怎么在跟我聊一个我根本没动过的文件”的困惑。

顺便说一个实测出来的边界:--strict-config 的说明是”config.toml 里出现本版本不认识的字段时直接报错退出”,但本机执行 codex -c model_reasoning_effortt=high --strict-config exec --help(注意 key 被故意拼错了)时,help 正常打印,没有报未知字段错误。说明这个校验发生在真正加载配置去跑会话的时候,--help 这类不进入会话的路径不触发。别指望用 --help 来验证你的配置拼写对不对。

沙箱这边也有一条本机观测:用 codex sandbox 在默认沙箱状态下执行一条往仓库路径写文件的命令,命令返回后目标文件并不存在codex sandbox 的位置参数官方说明是 “Full command args to run under Windows restricted token sandbox”,Windows 侧走的是受限令牌这一套。它跟 -s read-only 不是同一个东西,但可以作为一个便宜的验证手段:你想确认某条命令在受限环境下的行为,可以先在 codex sandbox 底下跑一次无害命令试试。

最后补上第二节埋的那个伏笔:-s 的值写错了会怎样。本机实测执行 codex -s bogus-mode,输出逐字如下:

error: invalid value 'bogus-mode' for '--sandbox <SANDBOX_MODE>'
  [possible values: read-only, workspace-write, danger-full-access]

For more information, try '--help'.

这条报错是”好”的那一类——直接退出,并且把三个合法取值原地列给你,不用去翻文档。值得注意的是它和上面 --strict-config 那条形成了鲜明对比:选项名/选项值这一层的错误,命令行解析阶段就会当场拦下;而 config.toml 内部的错误,只会让配置静悄悄地不生效。 所以你写自查脚本时,命令行选项写错基本不会漏,反倒是配置文件那侧需要靠 doctor 主动去看。

五、什么情况别走这条路

改动已经提交了。 --uncommitted 只看工作树。已经 commit 的用 --commit <SHA>,要跟基线分支比用 --base <BRANCH>,各有各的入口,别在 --uncommitted 上较劲。

项目不在 Git 仓库里。 0.147.0 上 --skip-git-repo-check(允许在非 Git 仓库里运行)是 codex exec 的专有选项,codex review 自己的选项列表里没有这一项。既然 --uncommitted 的定义完全建立在 git 的暂存/未暂存/未跟踪三态上,没有仓库这条路本身就不成立。

一次性大重构。 几十个文件同时动的时候,把整个工作树扔进去评审,得到的东西大概率是泛泛而谈。这种情况更应该做的是先把改动拆开分批提交,每批跑一次。

你指望它把问题顺手改掉。 review 的定位是”跑一次代码评审”,不是改代码。顶层确实有个 apply 子命令(官方说明是把 Codex agent 产出的最新 diff 以 git apply 打到本地工作树),但那是另一条链路,别在自查流程里顺手连起来——自查的价值就在于人还在回路里。

代码本身敏感。 评审要把改动内容送给模型。仓库涉密、有合规约束的,先按你们团队的规定判断能不能用,这不是命令行选项能解决的问题。顺便一提,--search(开启实时联网搜索,启用后原生 Responses web_search 工具对模型可用,且无逐次调用审批)在提交前自查这个场景基本没有必要开——评审看的是你自己的 diff,不需要联网,而它是没有逐次审批的。

你想把它当发布闸门。 我不会说”跑过评审就没问题了”。它是提交前多加的一道低成本筛子,测试、CI、人工 review 该有的一样都不能少。


最后归拢一下这条流程:git status 确认范围 → codex doctor --summary 确认配置真的加载了 → codex -s read-only -a never review --uncommitted --title "<这次改动>" → 需要留档再去核对 codex exec review --help 的机读选项。四步里前两步都是只读命令,几乎不花时间,却挡掉了绝大多数”跑了个寂寞”的情况。

相关阅读


本文依据 Codex 官方文档(learn.chatgpt.com/docs/ 的《Code review》《Non-interactive mode》《Command line options / Slash commands in Codex CLI》《Sandbox》《Configuration Reference》页面)整理,核对日 2026-08-09;文中标注「本机实测」的部分基于 codex-cli 0.147.0 / Windows 11 环境下的只读命令输出。产品功能、模型与价格以官方最新说明为准。

想系统学会用 AI?报名体系课或加入会员,照着学、照着用。