跳转到正文
莫尔索随笔
返回

使用 Skills 加速开源项目维护

预计 20 分钟

第一时间捕获有价值的信号

本文译自 OpenAI 官方发布的 使用 Skills 加速开源项目维护使用 Skills 和 GitHub Actions 优化 OpenAI Agents SDK 仓库中的 Codex 工作流。

我们使用 Codex 来改变维护 OpenAI Agents SDK 仓库的方式。仓库本地的 Skills、AGENTS.md 和 GitHub Actions 让我们能够将重复性的工程工作,如验证、发布准备、示例集成测试和 PR 审查,转化为可重复的工作流。即使设置相当简单,这也帮助我们在这些活跃的仓库中提高了开发吞吐量。在 2025 年 12 月 1 日至 2026 年 2 月 28 日期间,两个仓库合并了 457 个 PR,而此前三个月(2025 年 9 月 1 日至 2025 年 11 月 30 日)仅为 316 个(Python:182 -> 226,TypeScript:134 -> 231)。

简单介绍一下背景,该 SDK 有 PythonTypeScript 两个版本。它提供了构建智能体应用的核心组件,也是在 Realtime API 之上构建语音智能体的简洁方式,支持多智能体、工具和人工在环控制。它的使用规模相当大:截至 2026 年 3 月 6 日的最近 30 天窗口中,Python 包在 PyPI 上有约 1470 万次下载,TypeScript 包在 npm 上有约 150 万次下载。

设置很简单:

  • AGENTS.md 中的仓库策略
  • .agents/skills/ 中的仓库本地 Skills
  • 这些 Skills 中的可选脚本和引用
  • 当相同工作流需要在 CI 中运行时,使用 Codex GitHub Action

这种设置为 Codex 提供了关于仓库如何工作的稳定上下文,从而提高了重复性工程工作的速度和准确性。

如果你维护一个公共开源项目,请参阅 Codex for Open Source。符合条件的维护者可以申请带有 Codex 的 ChatGPT Pro、API 积分,以及 Codex Security 的条件访问权限。

将工作流保存在仓库中

在这些仓库中,我们使用 Skills 来捕获仓库特定的工作流。Skill 是一小部分操作知识:一个 SKILL.md 清单,加上可选的 scripts/references/assets/Codex 自定义文档 解释了为什么这种方式效果很好:Skills 非常适合可重复的工作流,因为它们可以携带更丰富的指令、脚本和引用,而不会在前期使智能体的上下文膨胀。

这与 Skills 使用的渐进式披露模型相匹配:

  • 它首先看到 namedescription 等元数据
  • 仅当选择 Skill 时才加载 SKILL.md
  • 仅在需要时才读取引用或运行脚本

两个 SDK 仓库都将这些工作流保存在代码附近:

Python 仓库是更简单的基准:

  • code-change-verification 在代码或构建行为发生变化时运行所需的格式化、lint、类型检查和测试栈。
  • docs-sync 根据代码库审计文档,查找缺失、不正确或过时的文档。
  • examples-auto-run 在自动模式下运行示例,带有日志和重运行助手。
  • final-release-review 比较上一个发布标签与当前发布候选版本,并检查发布就绪状态。
  • implementation-strategy 在编辑运行时或 API 更改之前决定兼容性边界和实现方法。
  • openai-knowledge 通过官方 Docs MCP 工作流获取当前的 OpenAI API 和平台文档。
  • pr-draft-summary 在交接时准备分支名称建议、PR 标题和草稿描述。
  • test-coverage-improver 运行覆盖率,找到最大的缺口,并提出高影响力的测试。

JavaScript 仓库遵循相同的通用模式,然后为其 npm 单仓库和发布流程添加了一些仓库特定的 Skills:

  • changeset-validation 检查 changeset 和版本提升级别是否实际与包差异匹配。
  • integration-tests 将包发布到本地 Verdaccio 注册表,并在支持的运行时中验证安装和运行行为。
  • pnpm-upgrade 以协调的方式更新 pnpm 工具链和 CI 固定版本。

比确切列表更重要的是模式。每个 Skill 都有一个狭窄的契约、清晰的触发器和具体的输出。

一些最有用的 Skills 不是硬性门槛。docs-synctest-coverage-improver 是报告优先的工作流:它们检查当前的差异或覆盖率工件,优先处理重要事项,并在进行编辑之前请求批准。在 Python 仓库中,docs-sync 还将源文档字符串和注释视为生成参考文档的真实来源,而不是手动修补生成的输出。仅 JavaScript 有的 pnpm-upgrade Skill 是狭窄维护工作流的另一个好例子:它一起更新本地 pnpm 版本、packageManager 和工作流固定版本,而不是退回到广泛的搜索替换。

使工作流成为强制性的

当仓库在正确的时间需要 Skills 时,Skills 会变得更有用。这就是 AGENTS.md 发挥作用的地方。

AGENTS.md 指南 将这些文件描述为仓库级别的指令,它们随代码库一起传播,并在智能体开始工作之前应用。它还建议保持它们简短。在 Agents SDK 仓库中,我们使用该空间存放 Codex 每次都应遵循的规则,并将最高价值的规则放在顶部。

实际上,两个仓库都对强制性 Skill 使用使用简短的 if/then 规则。在编辑运行时或 API 更改之前,调用 $implementation-strategy 来首先决定兼容性边界和实现方法。如果更改影响 SDK 代码、测试、示例或构建行为,则调用 $code-change-verification。如果 JavaScript 包更改影响发布元数据,则调用 $changeset-validation。如果工作涉及 OpenAI API 或平台集成,则调用 $openai-knowledge。当工作完成并准备好交接时,调用 $pr-draft-summary

该结构也与 agents.md 建议一致:将项目概述、构建和测试命令、代码风格、测试指南、安全考虑和其他仓库特定规则保存在一个地方。Agents SDK 仓库遵循该形状,但它们以日常工作中最重要的操作触发器开头。一个精简版本如下所示:

# AGENTS.md

## 项目概述

- 核心 SDK 代码位于 `src/agents/``packages/*/src/` 下。
- 测试位于 `tests/``packages/*/test/` 下。
- 示例应用和集成界面位于 `examples/` 下。

## 强制性 Skill 使用

- 在编辑可能影响兼容性边界的运行时或 API 更改之前,使用 `$implementation-strategy`
- 当运行时代码、测试、示例或构建/测试行为发生更改时,运行 `$code-change-verification`
- 对于 OpenAI API 或平台工作,使用 `$openai-knowledge`
- 当实质性代码工作准备好进行审查时,使用 `$pr-draft-summary`

## 构建和测试命令

- Python:`make format``make lint``make typecheck``make tests`
- TypeScript:`pnpm i``pnpm build``pnpm -r build-check``pnpm lint``pnpm test`

## 兼容性规则

- 保留公共构造函数和数据类字段的位置兼容性。

然后,真实文件在该基准之上添加了仓库特定的细节,例如 JavaScript 仓库中的 $changeset-validation 以及两个文件中更详细的运行时、文档和发布指南。如果你想要完整示例,请参阅 openai-agents-python 中的 AGENTS.mdopenai-agents-js 中的 AGENTS.md

AGENTS.md 不仅用于 Skill 触发器。Python 仓库还在那里记录了一个公共 API 兼容性规则:保留导出的构造函数参数和数据类字段的位置含义,尽可能在末尾追加新的可选参数,如果无法避免重新排序则添加兼容性测试。这是另一个好模式:将发布关键的兼容性规则与 Skill 触发器保存在同一个地方。

验证规则

一个清晰的例子是 $code-change-verification

在两个仓库中,规则不是”总是运行长验证栈”。规则是”当运行时代码、测试、示例或构建/测试行为发生更改时运行它,并且在通过之前不要将工作标记为完成。”

条件部分使仅文档工作保持轻量。强制性部分确保 SDK 代码更改经过仓库的标准验证步骤。

实际的验证栈编码在 Skills 本身中。

在 Python 仓库中,它要求:

make format
make lint
make typecheck
make tests

在 JavaScript 仓库中,Skill 要求这个确切的顺序:

pnpm i
pnpm build
pnpm -r build-check
pnpm -r -F "@openai/*" dist:check
pnpm lint
pnpm test

Skill 编码了仓库对”已验证”的定义,而 AGENTS.md 使该定义可强制执行。

Changeset 验证

JavaScript 仓库对包更改还有一个额外的强制性步骤:$changeset-validation,围绕 Changesets 构建。

packages/ 下的任何内容发生更改,或者当 .changeset/ 发生更改时,模型不仅需要运行测试。它必须创建或更新正确的 changeset,验证版本提升级别,并确认 changeset 实际与差异匹配。

这个 Skill 不仅仅检查文件是否存在。它要求 Codex 判断 git diff,并且它将验证规则保存在共享提示中,以便本地运行和 GitHub Actions 使用相同的逻辑。它还编码了仓库特定的策略,例如:

  • 当已经存在一个时,使用现有分支 changeset 而不是创建另一个
  • 将摘要保持为 Conventional Commit 风格的一行,以便它可以兼作提交标题
  • 在 1.0 之前,避免为正常功能工作进行主要版本提升,并且如果明确标记为仅预览的添加不更改现有行为,则将其视为补丁更改
  • 针对实际的包更改验证所需的版本提升级别

这使 Codex 负责在它可以说工作完成之前验证它创建的发布元数据。

使用当前文档

当工作涉及 OpenAI API 或平台集成时,两个仓库也需要 $openai-knowledge

该 Skill 是官方 OpenAI Docs MCP 的薄包装。它不让模型从内存中回答,而是告诉 Codex 使用 OpenAI 开发者文档 MCP 服务器来查找 Responses API、工具、流式传输、Realtime 和 MCP 等界面的当前文档。

如果 MCP 服务器尚未在本地 Codex 环境中配置,该 Skill 会将维护者指向 Docs MCP 快速入门官方 MCP 服务器端点

准备 PR 交接

在实质性工作结束时,两个仓库都使用 $pr-draft-summary

该 Skill 仅在任务实际完成或准备好进行审查并且更改触及了有意义的代码、测试、示例、有行为影响的文档或构建/测试配置时才触发。然后它自动收集分支名称、工作树状态、更改的文件、差异统计和最近提交,并生成:

  • 分支名称建议
  • PR 标题
  • PR 草稿描述

输出格式是故意刚性的。一个典型的结果如下所示:

# Pull Request Draft

## 分支名称建议

git checkout -b fix/tracing-lazy-init-fork-safety

## 标题

fix: #2489 延迟初始化跟踪全局变量以避免导入时的分叉危险

## 描述

此拉取请求通过将跟踪引导移至延迟的首次使用初始化来修复可能破坏基于分叉的进程模型的导入时跟踪副作用。

它更新跟踪设置,以便初始化在首次访问时发生一次,同时保留现有的公共跟踪 API。

它还添加了针对导入时行为、一次性引导和自定义提供程序处理的回归测试。

此拉取请求解决了 #2489。

一旦你信任模型来验证和总结它自己的工作,要求它生成 PR 草稿是自然的最后一步。它保持交接一致,并在编码工作已经完成后减少重复性写作。

编写更好的描述

Skill 的 SKILL.md 前置元数据中的 description 字段是路由契约的一部分。

这是结构性的,而不是风格上的。Agent Skills 规范 使 namedescription 成为必需的 SKILL.md 前置元数据字段,并且它的渐进式披露模型说这些字段是在启动时为所有 Skills 加载的。完整的 SKILL.md 正文和任何 scripts/references/assets/ 仅在稍后,当 Skill 实际被激活时才加载。

Codex Skills 文档自定义文档 从 Codex 方面描述了相同的行为:Codex 从每个 Skill 的元数据开始进行发现,仅在选择 Skill 时加载 SKILL.md,并仅在需要时读取引用或运行脚本。OpenAI API 中的 Skills 烹饪书 同样明确地描述了托管 shell 方面:OpenAI 首先读取每个 Skill 的 namedescription 和路径,模型使用该信息来决定何时读取完整的 SKILL.md。它的 SKILL.md 前置元数据部分 更直接地提出了相同的观点:namedescription 对于发现和路由很重要。

在 Agents SDK 仓库中,这使 description 成为 Codex 读取 Skill 其余部分之前的主要路由信号之一。

这是来自 code-change-verification 的一个具体例子。

太模糊:

description: 在 OpenAI Agents JS 单仓库中运行强制性验证栈。

更好(实际描述):

description: 当更改影响 OpenAI Agents JS 单仓库中的运行时代码、测试或构建/测试行为时,运行强制性验证栈。

较短的版本已经告诉 Codex Skill 做什么,但它仍然没有说明 Skill 何时适用、什么样的更改应该触发它,或者检查是否是可选的。更具体的版本告诉模型这三者。

相同的模式出现在 pr-draft-summary 中。

太模糊:

description: 为拉取请求创建 PR 标题和草稿描述。

更好(实际描述):

description: 在实质性代码更改完成后创建 PR 标题和草稿描述。在完成中等或更大的更改(运行时代码、测试、构建配置、有行为影响的文档)并且你需要带有更改摘要加上 PR 草稿文本的 PR 就绪摘要块时触发。

同样,真实描述是路由元数据。它告诉 Codex:

  • 这是任务结束时的 Skill
  • 它用于实质性更改,而不是每个聊天轮次
  • 输出是 PR 就绪块,而不仅仅是散文摘要

从这些仓库中得到的一个实际教训是花时间在 description 上。如果路由感觉不可靠,请在添加更多代码之前修复元数据。

将机制放在脚本中

在那之后,下一个问题是什么属于模型,什么应该推送到脚本中。

一个可靠的划分是:

  • 解释、比较和报告留在模型中
  • 确定性的、重复的 shell 工作进入 scripts/

这与公共指南一致。Codex 自定义文档 将 Skills 描述为一种为 Codex 提供更丰富的指令、脚本和引用以用于可重复工作流而不会在前期使上下文膨胀的方式。这适合模型优先的设置:让 Codex 处理工作的上下文相关部分,并仅在需要时引入脚本用于确定性部分。OpenAI API 中的 Skills 烹饪书 还建议将 Skill 脚本设计为微型 CLI:从命令行运行的脚本、打印确定性标准输出、大声失败并显示使用或错误消息,并在需要时将输出写入已知文件路径。

在 Agents SDK 仓库中,我们尝试在模型的智能实际有用的地方使用模型,例如:

  • 阅读源代码以推断预期行为
  • 将日志与该预期行为进行比较
  • 决定发布差异是否包含真正的兼容性风险
  • 生成维护者可以采取行动的解释

然后脚本处理围绕该工作的机制,例如:

  • 以固定顺序运行仓库所需的验证命令
  • 启动示例运行,收集每个示例的日志,并为失败写入重运行文件
  • 在发布就绪审查之前获取上一个发布标签
  • 公开辅助命令,例如 startstopstatuslogstailcollectrerun,以便相同的工作流易于重复运行

如果模型每次都必须重新发现相同的 shell 配方,这通常是该配方应该成为脚本的标志。如果任务依赖于上下文、权衡或解释,则该部分应该留在模型中。

自动化集成测试

两个仓库中最有用的工作流领域之一是自动化集成测试。这里有两个相关层:在两个仓库中自动验证仓库内示例,以及在 JavaScript 仓库中单独验证已发布的包在以用户消费方式安装时仍然有效。

在此设置之前,验证示例部分是手动的。你可以运行示例,但最后一英里通常依赖于视觉检查日志或通过检查决定输出是否看起来正确。这对于一个示例是可管理的。它在不断增长的 SDK 仓库中不能很好地扩展。

第一层是 examples-auto-run,但 Skill 出现在运行器之后。为了完全自动化示例验证,我们首先必须在两个仓库中构建对非交互式示例执行的底层支持。这意味着使在自动模式下运行示例脚本成为可能,包括通常涉及提示或批准的示例。

该基础工作包括:

  • 自动回答常见的交互式提示
  • 在运行器支持的地方自动批准 HITL、MCP、apply_patch 和 shell 操作
  • 将仍然不适合自动化的示例保留在自动跳过列表上,例如需要额外运行时设置的 realtime 或 Next.js 应用示例
  • 为每个示例运行编写结构化日志
  • 生成重运行文件,以便可以重试失败而无需重新运行所有内容

一旦该基础到位,我们将其组织为一个 Skill,以便工作流变得可重用且易于调用。在 Python 仓库中,examples-auto-run 包装了 uv run examples/run_examples.py --auto-mode --write-rerun --main-log ... --logs-dir ...。在 JavaScript 仓库中,它包装了构建检查,然后在自动模式下运行 pnpm examples:start-all,带有每个示例的日志记录和重运行支持。

为了提高验证质量,运行器的工作是执行示例并将它们的 stdout 和 stderr 保留在每个示例的日志中。然后 Skill 让 Codex 逐一查看这些日志并将它们与源代码进行比较:

  • 阅读示例源代码和注释
  • 推断预期流程
  • 打开匹配的日志
  • 将预期行为与实际 stdout 和 stderr 进行比较
  • 对每个成功的示例都这样做,而不仅仅是一个样本

这比尝试将正确性编码为固定的脚本级断言更准确且更灵活。成功的退出代码很有用,但对于与真实 API 对话、使用工具或生成结构化输出的示例来说是不够的。通过首先记录实际输出,然后根据源代码仔细检查它,我们可以根据每个示例的真实意图来验证它。

在 JavaScript 仓库中,然后有第二层:单独的 integration-tests Skill。该工作流超越了就地运行源示例。它将包发布到本地 Verdaccio 注册表并测试在多个环境中安装和运行它们,包括 Node.js、Bun、Deno、Cloudflare Workers 和 Vite React 应用。这捕获了不同类别的问题:不是”示例在仓库中运行吗?“而是”包在发布、安装和运行时集成后仍然表现正确吗?”

综合起来,这些工作流展示了为什么结合 Skills、脚本和模型判断很有用。脚本使运行可重复,捕获证据,并覆盖手动检查乏味的安装路径。然后 Codex 使用该证据进行比简单的脚本通过/失败检查更仔细的比较。

添加发布检查

发布准备是这种模式有帮助的另一个领域。

两个仓库中的发布审查工作流都从找到上一个发布标签开始,将其与最新的 main 进行差异比较,然后要求 Codex 检查该差异以寻找:

  • 公共 API 和面向用户的 SDK 行为中的向后兼容性问题
  • 回归,包括预期行为的较小更改
  • 需要它们的更改缺少迁移说明或发布说明更新

基于这些发现,Skill 做出整体发布就绪决定。

一个具体的例子是 openai/openai-agents-python#2480,其中发布审查总体保持绿色,同时仍然指出 Python 3.9 的放弃和它需要的发布说明后续工作:

发布就绪审查(节选)

发布决定:
🟢 可以发布。次版本提升包含预期的破坏性更改
(放弃 Python 3.9),未发现具体回归。

范围摘要:

- 38 个文件更改(+1450/-789);触及的关键领域:`src/agents/tool.py`
  `src/agents/extensions/``src/agents/realtime/``tests/`
  `pyproject.toml``uv.lock`

已删除 Python 3.9 支持

- 风险:🟡 中等。固定在 Python 3.9 的用户将无法安装
  0.9.0 版本。
- 证据:`pyproject.toml` 现在设置 `requires-python = ">=3.10"` 并删除了
  Python 3.9 分类器;删除了 3.9 的 CI 跳过逻辑。
- 操作:确保发布说明清楚地说明放弃 Python 3.9,并且
  打包元数据保持 `>=3.10`

Skill 还定义了如何做出门槛决定。审查从”可以安全发布”开始,仅当差异显示真实问题的具体证据时才切换到阻止决定。每个阻止决定都必须附带具体的解除阻止清单。这使输出更易于使用:绿色结果意味着在差异中未发现阻止发布的问题,而阻止结果意味着存在真实问题并带有明确的下一步。

这比通用的”请审查发布”更有用。它迫使模型对具体差异进行推理并用操作术语解释结果。如果发布是安全的,就这么说。如果不是,指出确切的证据和所需的确切后续工作。

在 CI 中运行工作流

一旦 Skill 在本地有用,Codex GitHub Action 使得在 CI 中自动化相同工作流变得容易。当本地工作流已经稳定时,这效果最好,因为手动使用是你调试指令、完善脚本并找到真实边缘情况的地方。

对于公共仓库,触发器设计与 Skill 同样重要。GitHub Action 安全清单 建议限制谁可以启动工作流,优先考虑受信任的事件或明确批准,清理来自 PR、提交、问题或注释的提示输入,使用 drop-sudo 或非特权用户保护 OPENAI_API_KEY,并将 Codex 作为作业的最后一步运行。

如果工作流是可写的并接受不受信任的公共输入,风险通常在于 Skill 周围的触发器设计、输入处理和运行时权限。

在 PR 审查中使用 Codex

Skills 是这些仓库中生产力故事的一部分。Codex GitHub PR 自动审查 是另一部分。

自从 Codex GitHub PR 自动审查可用以来,Codex 一直是这些仓库中大多数代码更改的有用审查者。我们将其用作审查的常规部分,而不是作为特殊情况工具。

对于直接的程序错误、回归和缺失测试,依赖 Codex 作为必需的审查路径现在在实践中足够安全。它在反复检查相同的正确性模式方面是一致的,并且它为小修复和例行改进消除了主要瓶颈。

同行审查仍然很重要,但用于不同类别的更改。

当主要问题不是”这段代码正确吗?“而是”我们应该选择几个有效选项中的哪一个,以及我们应该如何发布它?“时,人工审查仍然必不可少。这包括:

  • API 或架构更改,其中有多个合理的设计,维护者需要做出明确选择
  • 影响产品期望、向后兼容性承诺或推出策略的行为更改
  • 命名、迁移和发布沟通决策,其中困难的部分是选择对用户和贡献者最清楚的内容
  • 需要维护者或团队之间对齐的更改,例如确定工作范围、排序它或决定现在应该发布什么与以后发布什么

Codex 仍然可以在所有这些情况下做出有用的贡献,但它们仍然受益于人工决策者和直接讨论。

AGENTS.md 也可以编码该划分:仓库可以告诉 Codex 什么对正确性审查很重要,并且 Codex 可以一致地应用该指导。

这也对吞吐量做出了重大贡献。重复性审查和验证工作不再等待每个低风险更改的稀缺审查者时间,而维护者可以专注于他们的判断最重要的更高上下文审查。这种转变帮助我们更快地处理积压错误和较小的功能改进。

总结

在 OpenAI Agents SDK 仓库中,当 Skills 成为仓库正常工作设置的一部分时,它们效果最好。

AGENTS.md 告诉 Codex 哪些工作流是必需的。description 告诉它何时路由到这些工作流中。scripts/ 处理确定性部分。模型处理上下文部分。一旦工作流在本地稳定,Codex GitHub Action 可以将相同的流程带入 CI。

这使得这些仓库中的日常工程工作更加明确和可靠。它还使得更快地发布小改进变得更容易,因为验证、发布审查和 PR 交接现在遵循相同的可重复流程。

资源