这篇适合谁、读完能做到什么
如果你想让 Codex 在 CI、定时任务或 shell 管道里运行,而不是每次在交互界面里操作,这篇适合你。读完你能用 codex exec 跑一个任务、保存输出、选对沙箱权限、得到机器可读的 JSON,并知道 API key 放在哪里才安全。[1]
codex exec 是什么
非交互模式让 Codex 在脚本里运行,不必打开交互界面,入口是 codex exec。[1] 它适合放进流水线,比如 CI、合并前检查和定时任务;也适合把输出交给其他工具、把命令输出接给 Codex 处理,或者用事先定好的沙箱和审批设置来运行。[1] 每个命令行参数的说明,可以在开发者命令参考里的 codex exec 条目中查到。[1]
第一个命令
把任务描述作为唯一参数传入。下面的命令让 Codex 梳理仓库结构,并列出风险最高的五个区域:[1]
codex exec "summarize the repository structure and list the top 5 risky areas"运行时,进度信息输出到 stderr,stdout 里只有最终回复。所以结果很容易重定向,或者接到下一个命令里。[1]
codex exec "generate release notes for the last 10 commits" | tee release-notes.md不想把会话记录保存到磁盘,就加上 --ephemeral:[1]
codex exec --ephemeral "triage this repository and suggest next steps"用管道把数据交给 Codex
如果同时传了 stdin 和 prompt 参数,Codex 把 prompt 当作指令,把管道里的内容当作补充上下文。记住这个分工,就不会把指令误放进管道里。下面的例子先取一批评论数据,再让 Codex 整理成表格:[1]
curl -s https://jsonplaceholder.typicode.com/comments \
| codex exec "format the top 20 items into a markdown table" \
> table.md还有两种 stdin 用法。第一种是「prompt 加 stdin」:指令自己写,命令的输出作为上下文。比如先跑测试,再让 Codex 总结失败的用例:[1]
npm test 2>&1 \
| codex exec "summarize the failing tests and propose the smallest likely fix" \
| tee test-summary.md第二种是用 codex exec - 让 stdin 成为完整的 prompt,适合由脚本拼出来的提示词:[1]
cat prompt.txt | codex exec -不带 prompt 参数时,Codex 同样从 stdin 读取 prompt;- 只是把这个行为写明确。[1]
权限:先给最少的
codex exec 默认在只读沙箱里运行。需要它改文件时,加上 --sandbox workspace-write。--sandbox danger-full-access 的权限更大,只应在隔离的 CI runner 或容器里使用。[1]
--full-auto 已经不再支持。旧脚本要改成 --sandbox workspace-write,或者改用 --approve-for-me,让审批请求经过自动审查,同时仍然运行在 workspace-write 沙箱中。[1]
需要跳过用户配置时,加 --ignore-user-config,它会跳过 $CODEX_HOME/config.toml。--ignore-rules 则跳过用户和项目的 execpolicy .rules 文件,适合受控的自动化环境。[1]
如果某个启用的 MCP 服务器配置了 required = true,而它初始化失败,codex exec 会报错退出,而不是在缺少它的情况下继续。[1]
输出机器可读的结果
加上 --json 后,stdout 变成 JSON Lines(JSONL)流,Codex 运行时的每个事件都会记一行:[1]
codex exec --json "summarize the repo structure" | jq事件类型包括 thread.started、turn.started、turn.completed、turn.failed、item.* 和 error。条目类型有 agent 消息、推理过程、命令执行、文件改动、MCP 工具调用、网页搜索和计划更新。[1] 一段示例输出如下,每行是一个 JSON 对象:[1]
{"type":"thread.started","thread_id":"0199a213-81c0-7800-8aa1-bbab2a035a53"}
{"type":"turn.started"}
{"type":"item.started","item":{"id":"item_1","type":"command_execution","command":"bash -lc ls","status":"in_progress"}}
{"type":"item.completed","item":{"id":"item_3","type":"agent_message","text":"Repo contains docs, sdk, and examples directories."}}
{"type":"turn.completed","usage":{"input_tokens":24763,"cached_input_tokens":24448,"output_tokens":122,"reasoning_output_tokens":0}}下游脚本可以逐行解析这些事件,看到 turn.failed 就能知道这一轮运行失败了,再决定是否重试或通知。[1]
如果只需要最后一条消息,用 -o <路径> 或 --output-last-message <路径>。消息会写进该文件,同时仍然打印到 stdout。[1]
用 JSON Schema 约束输出
下游步骤要依赖固定的字段名时,用 --output-schema 让最终回复符合一个 JSON Schema。这适合生成任务摘要、风险报告或发布元数据这类自动化流程。[1] schema 文件大致是这样:[1]
{
"type": "object",
"properties": {
"project_name": { "type": "string" },
"programming_languages": {
"type": "array",
"items": { "type": "string" }
}
},
"required": ["project_name", "programming_languages"],
"additionalProperties": false
}然后带上 schema 运行,并把结果写进文件:[1]
codex exec "Extract project metadata" \
--output-schema ./schema.json \
-o ./project-metadata.jsonCI 里的认证
codex exec 默认复用机器上已保存的 CLI 登录状态。自动化任务通常要显式提供凭据。[1] 如果只想为某一次运行换一个 API key,可以在命令前内联设置 CODEX_API_KEY:[1]
CODEX_API_KEY=<api-key> codex exec --json "triage open bug reports"CODEX_API_KEY 可用于 codex exec、codex review、TypeScript SDK,以及 codex exec-server --remote。[1]
安全上要注意:在会检出或运行仓库代码的工作流里,不要把 OPENAI_API_KEY 或 CODEX_API_KEY 设为整个 job 的环境变量。构建脚本、测试、依赖的生命周期钩子,或者被攻破的 action,都可能在同一个 job 里读到它们。[1]
在 GitHub Actions 里,文档建议直接使用官方的 Codex GitHub Action,而不是自己安装并登录 CLI。这个 action 会安装 Codex、启动一个 Responses API 代理,并按可配置的安全策略运行 Codex。[1]
如果确实需要以 Codex 用户账户在 CI/CD 中运行,那是高级用法。~/.codex/auth.json 含有访问令牌,要像对待密码一样保护:不要提交,不要贴进工单,也不要在聊天里分享。公开或开源仓库不要使用这种方式。[1]
续接上一次运行
两阶段的流水线里,可以用 resume 接着上一次的会话:[1]
codex exec "review the change for race conditions"
codex exec resume --last "fix the race conditions you found"也可以用 codex exec resume <SESSION_ID> 指定某个会话。[1] 用 --last 时则指向最近一次的会话,不必记住 ID。[1]
必须在 Git 仓库里运行
Codex 要求命令在 Git 仓库中执行,这样可以防止破坏性修改。这条限制对脚本同样生效,脚本报错时应先检查工作目录是不是仓库。只有在确认环境安全时,才加 --skip-git-repo-check 跳过这项检查。[1] 如果任务不在 Git 仓库里运行,先确认环境确实安全,再决定是否加这个参数。[1]
例子:CI 失败后自动修复
文档里给出了一个模式:主 CI 失败后,触发一个后续工作流;以只读的仓库权限检出失败的提交;在 Codex 之前运行安装等准备步骤,但不把 OpenAI API key 交给这些步骤;运行 Codex GitHub Action;把 Codex 产生的本地改动保存为 patch 产物;最后由单独的 job 应用这个 patch,并开一个 PR。[1]
在这个模式里,生成修复的 job 只有 contents: read 权限;负责开 PR 的 job 有写权限,但拿不到 OPENAI_API_KEY。[1] 写仓库的那一步因此接触不到 key。[1]
常见问题
- 报错说不在 Git 仓库里。 确认当前目录位于 Git 仓库中。只有确认环境安全时,才加
--skip-git-repo-check。[1] - **旧脚本里的
--full-auto不能用了。** 换成--sandbox workspace-write,或者--approve-for-me。[1] - 需要结构化的结果。 用
--output-schema固定字段,再用-o把结果保存到文件。[1] - MCP 服务器没起来,整个命令退出了。 这是
required = true的效果。如果允许缺少这个服务器,就不要把它设为必需。[1]
下一步
命令行参数的完整列表在官方的开发者命令参考里。[1]
来源
- 1Non-interactive modeOpenAI Codex docs
引用本页: Codex 非交互模式:codex exec 写脚本. TellWorld, https://www.tellworld.net/zh/practice/practice-codex-non-interactive. 更新于 2026-11-14