Codex Headless 模式与 CI/CD——Codex 进入自动化流水线
Windows 10/11 · Codex CLI v0.130.0 · GitHub Actions · DeepSeek V4 Pro · dsv4-cc-proxy-tray · 2026-06-02 · 🟡 中度时效
一、这篇教程解决什么问题
一句话定位:单次对话是玩具,嵌入流水线才是生产力。Codex 的exec模式和管道输入让你把 AI 嵌入 GitHub Actions——自动审查 PR、自动修 bug、自动生成 CHANGELOG。这篇给你三个完整的 CI/CD YAML 和五个自动化脚本。
跳读指南:只想抄 GitHub Actions 的直接跳到 第五节 CI/CD 实战。想学 exec 参数的直接跳到 第二节 exec 模式完全指南。想把 Claude Code 也放进 CI 的跳到 第六节 与 Claude Code -p 对比。遇到 exec 报错的跳到 Debug 章节。
阅读前提:
- Codex CLI 已安装(
codex --version有输出) - 了解
codex exec基础(详见 [(九)exec 模式概述](新手上路(九):Codex 代码审查——用 Codex 做你的第一读者.md)) - 有 GitHub 账号并了解 Actions 基础(知道
.github/workflows/目录) - dsv4-cc-proxy-tray 已启动
读完能得到什么:
codex exec全部参数详解——-p/--json/--model/--allowedTools/--ephemeral- 三个可复制的 GitHub Actions YAML:PR 自动审查、Push 自动测试、定时安全扫描
- CI 环境 API Key 安全存储方案 + DeepSeek 代理在 CI 中的配置
- 五个自动化脚本:批量代码迁移、自动 CHANGELOG、依赖更新审查、lint 自动修复、README 同步
- Codex exec vs Claude Code
-p模式完整对比
二、codex exec完全指南
2.1 exec vs 交互模式
| 维度 | 交互式codex | codex exec |
|---|---|---|
| 对话方式 | 多轮,可以追问 | 单次,一问一答 |
| 输入 | 对话中逐步输入 | 一次性 prompt + 管道数据 |
| 输出 | 对话流 | 文本输出,可-o保存 |
| 工具调用 | 完整 | 取决于--allowedTools |
| 会话持久 | 有状态 | --ephemeral不保存 |
| 适用 | 开发、调试 | 审查、CI/CD、脚本化 |
2.2 参数速查
| 参数 | 作用 | 示例 |
|---|---|---|
-p "<prompt>" | 执行 prompt(必填) | codex exec -p "fix lint errors" |
--json | 输出 NDJSON(CI 可解析) | codex exec --json -p "review" |
--model <name> | 指定模型 | --model deepseek-v4-flash |
-o <file> | 最后一条消息写入文件 | -o report.md |
--ephemeral | 不保存会话记录 | --ephemeral |
--allowedTools <list> | 工具白名单 | --allowedTools "read,write" |
--disallowedTools <list> | 工具黑名单 | --disallowedTools "bash,delete" |
--skip-git-repo-check | 跳过 Git 检查 | CI 中不在 Git 目录下时用 |
注意:Codex没有
--max-turns或--max-budget-usd参数。这是已知功能空白(GitHub #5085/#5099)。CI 中靠 prompt 设计 +--allowedTools+ Shell 超时兜底。见 Debug #5。
2.3 管道输入——CI/CD 的核心模式
# 管道输入:echoecho"把以下 Python 代码改成 async/await"|codex exec-p"重构代码"# 管道输入:git diff(最常用)gitdiffHEAD~1|codex exec-p"审查这些改动,列出安全问题"# 管道输入:文件内容catold_code.py|codex exec-p"迁移到 Python 3.12 语法"# 管道输入:多文件内容拼接Get-ChildItemsrc-Recurse-Filter*.py|Get-Content-Raw|codex exec-p"分析所有源文件"三、安全控制——CI 环境不能给完整权限
3.1 工具白名单 / 黑名单
# ✅ PR 审查:只需要读gitdiffmain|codex exec-p"审查"--allowedTools"read"--ephemeral# ✅ 自动修 lint:读+写,不给 shellcodex exec-p"修复 src/ 下所有 ruff 错误"\--allowedTools"read,write"--disallowedTools"bash"--ephemeral# ❌ 危险:CI 中给完整 bash 权限# codex exec -p "..." --allowedTools "bash,write,delete"3.2 Shell 超时兜底(Codex 没有 --max-turns 的替代方案)
# GitHub Actions 中-name:Codex reviewrun:git diff origin/main|codex exec-p "审查"--allowedTools "read"timeout-minutes:5# PowerShell 中$job=Start-Job{gitdiffmain|codex exec-p"审查"}Wait-Job$job-Timeout 300if($job.State-eq'Running'){Stop-Job$job;throw"Timeout"}四、CI 环境 API Key 安全
4.1 原则
❌ 永远不要:写到 YAML 里、commit 到代码仓库 ✅ 正确做法:GitHub Secrets → workflow 环境变量 → codex 读取4.2 Secrets 配置
# Settings → Secrets and variables → Actions → New repository secretDEEPSEEK_API_KEY# sk-你的Key4.3 CI 环境 config.toml
CI runner 没有本地~\.codex\config.toml。从 Secrets 动态生成,且直连DeepSeek API(不用本地代理):
-name:Configure Codexrun:|mkdir -p ~/.codex cat > ~/.codex/config.toml << 'TOML' model = "deepseek-v4-flash" model_provider = "deepseek" model_reasoning_effort = "medium" model_max_output_tokens = 8000 [model_providers.deepseek] name = "DeepSeek" base_url = "https://api.deepseek.com/v1" env_key = "DEEPSEEK_API_KEY" wire_api = "responses" TOMLenv:DEEPSEEK_API_KEY:${{secrets.DEEPSEEK_API_KEY}}五、三个 GitHub Actions 实战
5.1 PR 自动审查
# .github/workflows/codex-pr-review.ymlname:Codex PR Reviewon:pull_request:types:[opened,synchronize]jobs:review:runs-on:ubuntu-latesttimeout-minutes:10steps:-uses:actions/checkout@v4with:fetch-depth:0-name:Setup Codexrun:npm install-g @openai/codex-name:Configure Codexrun:|mkdir -p ~/.codex cat > ~/.codex/config.toml << 'TOML' model = "deepseek-v4-flash" model_provider = "deepseek" model_reasoning_effort = "medium" model_max_output_tokens = 8000 [model_providers.deepseek] name = "DeepSeek" base_url = "https://api.deepseek.com/v1" env_key = "DEEPSEEK_API_KEY" wire_api = "responses" TOMLenv:DEEPSEEK_API_KEY:${{secrets.DEEPSEEK_API_KEY}}-name:Review PRrun:|git diff origin/${{ github.base_ref }} | \ codex exec --json -p "审查 PR 改动。维度:安全性、正确性、性能。输出格式:文件:行号 | severity | 描述 | 修复建议" \ --allowedTools "read" --ephemeral -o codex-review.json-name:Post review commentuses:actions/github-script@v7with:script:|const fs = require('fs'); const review = fs.readFileSync('codex-review.json', 'utf8'); github.rest.issues.createComment({ ...context.repo, issue_number: context.issue.number, body: `## Codex Review\n\`\`\`\n${review.slice(0, 60000)}\n\`\`\`` });5.2 Push 自动测试 + 修复
# .github/workflows/codex-push-fix.ymlname:Codex Auto Fixon:push:branches:[main,develop]jobs:auto-fix:runs-on:ubuntu-latesttimeout-minutes:15steps:-uses:actions/checkout@v4-name:Setup Codexrun:npm install-g @openai/codex-name:Configure Codexrun:|mkdir -p ~/.codex cat > ~/.codex/config.toml << 'TOML' model = "deepseek-v4-flash" model_provider = "deepseek" model_reasoning_effort = "medium" [model_providers.deepseek] name = "DeepSeek" base_url = "https://api.deepseek.com/v1" env_key = "DEEPSEEK_API_KEY" wire_api = "responses" TOMLenv:DEEPSEEK_API_KEY:${{secrets.DEEPSEEK_API_KEY}}-name:Run testsrun:pytest--tb=short 2>&1|tee test-output.txtcontinue-on-error:true-name:Fix failing tests with Codexif:failure()run:|cat test-output.txt | codex exec \ -p "分析以上测试失败原因并修复代码。只修改源代码,不改测试文件。" \ --allowedTools "read,write" --ephemeral-name:Create fix PRif:failure()uses:peter-evans/create-pull-request@v6with:title:"fix: Codex auto-fix for failing tests"body:"Codex 自动修复了 push 后失败的测试。请人工审查后合并。"branch:codex/fix-tests5.3 定时安全扫描
# .github/workflows/codex-security-scan.ymlname:Codex Security Scanon:schedule:-cron:'0 8 * * 1'workflow_dispatch:jobs:security-scan:runs-on:ubuntu-latesttimeout-minutes:20steps:-uses:actions/checkout@v4with:fetch-depth:0-name:Setup Codexrun:npm install-g @openai/codex-name:Configure Codexrun:|mkdir -p ~/.codex cat > ~/.codex/config.toml << 'TOML' model = "deepseek-v4-pro" model_provider = "deepseek" model_reasoning_effort = "max" model_max_output_tokens = 32000 [model_providers.deepseek] name = "DeepSeek" base_url = "https://api.deepseek.com/v1" env_key = "DEEPSEEK_API_KEY" wire_api = "responses" TOMLenv:DEEPSEEK_API_KEY:${{secrets.DEEPSEEK_API_KEY}}-name:Security scanrun:|git diff HEAD~7 | codex exec -p "深度安全审计。检查SQL注入、XSS、认证绕过、敏感数据泄露、路径遍历。" \ --model deepseek-v4-pro --allowedTools "read" --ephemeral -o security-report.md-name:Create issue if vulnerabilities foundif:success()uses:actions/github-script@v7with:script:|const fs = require('fs'); const report = fs.readFileSync('security-report.md', 'utf8'); if (!report.includes('审查通过')) { github.rest.issues.create({ ...context.repo, title: 'Security: Codex weekly scan findings', body: report.slice(0, 60000), labels: ['security', 'codex-auto'] }); }六、Codex exec vs Claude Code-p模式
6.1 功能矩阵
| 维度 | Codex exec | Claude Code-p |
|---|---|---|
| 基本用法 | codex exec -p "prompt" | claude -p "prompt" |
| 管道输入 | ✅ | ✅ |
--max-turns | ❌不支持 | ✅--max-turns 10 |
--max-budget-usd | ❌ 不支持 | ✅--max-budget-usd 1.00 |
| 工具白名单 | ✅--allowedTools | ✅--allowedTools |
| JSON 输出 | ✅--json | ✅--json |
| 不保存会话 | ✅--ephemeral | ✅--no-save-session |
| 输出到文件 | ✅-o file.md | Shell 重定向 |
| token 效率 | 高 3-4× | 较低 |
6.2 各自最佳场景
| 场景 | 推荐 | 理由 |
|---|---|---|
| PR 自动审查 | Codex exec | 更快更省 |
| CI 自动修 bug | Codex exec | token 效率高 |
| 定时安全扫描 | Claude Code-p | /security-review更全面 |
| 有预算上限的 CI | Claude Code-p | 有--max-budget-usd |
| 批量代码迁移 | Codex exec | 管道 +--json适合脚本化 |
6.3 混用——一个 CI 两个工具
-name:Quick scan (Codex)run:git diff origin/main|codex exec-p "快速安全检查"--model deepseek-v4-flash-name:Deep review (Claude Code)run:git diff origin/main|claude-p "深度审查"--max-turns 5env:ANTHROPIC_BASE_URL:"https://api.deepseek.com/anthropic"ANTHROPIC_AUTH_TOKEN:${{secrets.DEEPSEEK_API_KEY}}七、五个自动化脚本
7.1 批量代码迁移
# migrate-to-py312.ps1Get-ChildItemsrc-Recurse-Filter*.py|ForEach-Object{Get-Content$_.FullName-Raw|codex exec-p"迁移到 Python 3.12 语法。不改变逻辑。"--allowedTools"write"--ephemeral}7.2 自动 CHANGELOG
# gen-changelog.ps1git log--oneline--no-merges v1.0..HEAD|codex exec-p"根据以上 git log 生成 CHANGELOG(Keep a Changelog 格式)。分类 Added/Changed/Fixed。"-o CHANGELOG.md7.3 依赖更新审查
npm outdated--json|codex exec-p"审查过时的 npm 依赖。每个 major 升级是否有 breaking change 和安全风险?"-o dep-audit.md7.4 Lint 自动修复
ruff check src/ 2>&1|codex exec-p"修复所有 lint 错误。只改源代码,不改测试。"--allowedTools"read,write"--ephemeral7.5 README 同步
Get-ChildItemsrc-Recurse-Filter*.py|Get-Content|codex exec-p"根据源代码更新 README.md 的 API 文档。"-o README.md八、Debug——五个最常见 CI/CD 问题
Debug #1:exec 在 CI 中超时
现象:GitHub Actions 日志显示 exec 运行 10 分钟后被 kill。
根因:diff 太大(> 2000 行)或 DeepSeek API 高峰期响应慢。
修复:
# job + step 双层 timeoutjobs:review:timeout-minutes:10steps:-name:Codex reviewtimeout-minutes:5run:git diff origin/main|codex exec-p "审查"# 分片审大 diffgitdiffmain--src/api.py|codex exec-p"审查"gitdiffmain--src/models.py|codex exec-p"审查"Debug #2:--allowedTools语法不生效
现象:设了--allowedTools "read",Codex 仍尝试写文件。
根因:工具名大小写敏感,且不能有空格。
修复:
# ✅--allowedTools"read,glob,grep"--allowedTools"read,write,edit"# ❌--allowedTools"Read"# 大小写--allowedTools"read, write"# 多余空格Debug #3:管道编码问题——中文乱码
现象:GitHub Actions 中管道传入的中文内容变成乱码。
根因:Ubuntu runner 默认 locale 是POSIX(ASCII)。
修复:
-name:Run Codexrun:git diff origin/main|codex exec-p "审查"env:LANG:zh_CN.UTF-8LC_ALL:zh_CN.UTF-8Debug #4:CI 中 429 更频繁
现象:本地很少 429,但 CI 中频繁触发限流。
根因:CI runner 出口 IP 共享 + 每次全新会话无缓存命中,更深消耗服务器资源。
修复:
-name:Codex with retryrun:|for i in 1 2 3; do git diff origin/main | codex exec -p "审查" && break echo "Attempt $i failed, retrying in $((2**i))s..." sleep $((2**i)) doneDebug #5:没有--max-turns——如何限制执行范围
现象:你想限制 exec 的最大步数,发现没有这个参数。
根因:Codex 确实没有--max-turns或--max-budget-usd(GitHub #5085/#5099)。
修复——四层组合防线:
# 1. Shell timeouttimeout-minutes:5# 2. Prompt 中限制"只审查不改代码,一轮完成,不要多步操作。"# 3. 工具白名单--allowedTools "read"# 4. 混用 Claude Code(如必须 --max-turns)claude-p "..."--max-turns 5--max-budget-usd 1.00九、速查卡
9.1 exec 参数
| 参数 | 用途 |
|---|---|
-p "<prompt>" | 执行 prompt |
--json | NDJSON 输出 |
--model <name> | 指定模型 |
-o <file> | 输出到文件 |
--ephemeral | 不保存会话 |
--allowedTools "read,write" | 工具白名单 |
9.2 三个 workflow
| Workflow | 触发 | 模型 |
|---|---|---|
| PR Review | pull_request | Flash |
| Auto Fix | push | Flash |
| Security Scan | schedule(周一) | Pro |
十、扩展阅读
- 新手上路(九):代码审查
- 新手上路(七):双轨并行
- 新手上路(六):成本优化
- 新手上路(一):config.toml 深度配置
十一、参考文献
- Codex CLI Exec Mode (OpenAI Docs)
- GitHub Actions Documentation
- Codex Cost Tracking RFC (#5085)
- Claude Code Headless Mode