在这里插入图片描述

最近读《敏捷史话》时,书里提到了 Robert C. Martin。他是《敏捷软件开发宣言》的 17 位签署者之一,也是《代码整洁之道》的作者。

看到这里,我想到自己用 AI Coding 时反复遇到的一类问题:生成结果能够运行,却容易留下重复逻辑、多余封装和含混命名;该解释的地方没有注释,有些注释又只是在复述代码。局部看似完成,代码的可读性、修改成本和错误边界却没有得到稳定控制。

我最初只想借用《代码整洁之道》中的思想,做一个约束代码生成与审查的 Skill。真正动手后,问题很快超出了“把规则写进一个 Markdown 文件”:Skill 应该采用什么结构,哪些字段属于开放规范,同一个包怎样被不同平台发现和加载,description 怎样参与触发,工具权限由谁控制,这些都需要先弄清楚。

调研各个平台的 Skill 实现后,我又受到 Superpowers 的启发,继续研究多个 Skill 怎样组合、交接和串联。原本针对代码整洁的一项实践,逐渐展开成了一条完整链路。于是有了这篇文章:从一个 SKILL.md 目录开始,依次拆开规范、跨平台实现、触发、调用和自动串联背后的机制。

一、Skill 从一个目录开始

一个 Skill 包至少由一个目录和其中的 SKILL.md 组成:

example-skill/
└── SKILL.md

SKILL.md 的开头必须是 YAML frontmatter,正文随后写给 Agent 的工作说明。开放标准要求 namedescription,其余标准字段是可选项。资源目录不是最低要求,但规范建议用相对路径组织 scripts/references/assets/。[1]

一个可使用的 Skill 至少应声明适用范围与非目标、输入范围与禁止访问对象、判断和行动顺序、输出契约、授权点、停止条件以及命令或测试验证方法。这些声明属于正文契约,不会自动转化为宿主权限或确定性调度规则。

Skill 不等于以下对象:

对象 主要职责 与 Skill 的关系
Skill 按任务加载的方法、约束和资源 这里讨论的包格式
插件 分发多个能力、配置或工具 可以携带 Skill,但范围更大
MCP 连接实时数据、外部工具和受控动作 可被 Skill 调用,不是 Skill 本体
AGENTS.md 项目或目录范围的持久规则 约束宿主工作环境,不是按任务加载的能力包
GEMINI.md Gemini 系列宿主的项目指令 宿主指令文件,不是开放 Skill 格式

把这些对象统称为“技能”会掩盖权限、发现和生命周期差异。

目录结构

最小布局

适合一次性方法、没有脚本和外部参考资料的 Skill:

example-skill/
└── SKILL.md

只要 SKILL.md 能独立说明触发条件、步骤、输出和停止条件,就不必为了形式增加空目录。

扩展布局

适合需要确定性检查、长篇参考资料或模板资产的 Skill:

example-skill/
├── SKILL.md
├── LICENSE.txt
├── scripts/
│   ├── prepare-input.py
│   └── validate-output.py
├── references/
│   ├── output-schema.md
│   └── domain-guidance.md
└── assets/
    └── output-template.md

扩展布局的原则是按需加载。SKILL.md 先告诉 Agent 何时读取哪个资源,不要把所有参考资料复制进主体。目录名采用小写 ASCII kebab-case,例如 example-skill,这是跨文件系统、搜索工具和宿主解析器的稳妥建议,不是说标准必然拒绝 Unicode 名称。参考实现实际上接受 Unicode 字母数字名称,也接受小写 skill.md,但这些属于实现宽松行为,不应作为可移植包的依赖。[2]

文件职责

路径 必需性 职责 不应承担的职责
SKILL.md 必需 名称、描述、工作流程、输入输出、边界 承诺宿主一定会授予权限
scripts/ 可选 可重复的机械检查或数据转换 绕过用户授权执行高风险动作
references/ 可选 长篇规范、术语、示例和背景材料 作为自动发现入口
assets/ 可选 模板、样例、静态资源 存放凭据或隐含的运行时配置
LICENSE.txt 工程建议 说明包的许可条件 代替 frontmatter 的 license 字段
agents/openai.yaml Codex 扩展 Codex 的界面、默认提示或调用配置 伪装成开放标准字段

脚本应使用相对路径访问包内资源,避免假定当前工作目录。脚本需要的依赖、输入、输出和失败码应写在 SKILL.md 中。是否允许执行脚本,仍由宿主的工具、沙箱和授权策略决定。

Frontmatter 与元数据字段

标准字段

推荐的跨平台核心写法如下:

---
name: example-skill
description: Process a bounded task with the documented workflow and return a validated structured result.
license: MIT
compatibility: Requires a host that can read package resources and run the declared validation command.
metadata:
  version: "0.1.0"
  author: example
---
字段 标准地位 约束或用途
name 必需 Skill 名称。建议小写 ASCII kebab-case,并与目录名一致。
description 必需 说明做什么和何时使用。应足够帮助宿主发现和路由。
license 可选 包的许可说明,可以是标识符或文件名。
compatibility 可选 环境要求,例如工具、网络或运行时约束。
metadata 可选 宿主或发布方的额外键值。具体键不由开放标准统一解释。
allowed-tools 实验性 某些实现尝试声明允许工具,不应作为跨平台安全边界。

标准没有规定 version、依赖、签名、注册表、锁文件或更新协议。若把版本放在 metadata.version,它只是包作者的可读信息,不能假设宿主会比较或阻止旧版本。

宿主扩展
宿主 可观察扩展 处理方式
Claude 产品级调用控制、工具和模型控制,以及不同产品表面的加载与共享能力 放在适配文档,不写入便携核心。Claude 的安全建议也要求审计整个目录。[3]
Codex agents/openai.yaml 等 Codex 专属配置,项目或用户目录的发现与显式调用 作为可选适配层。固定提交中的官方 Skill Creator 文件和协议文档支持这些形状,不推出当前产品的额外承诺。[4]
Gemini CLI activate_skill、激活前同意、允许路径、启用和禁用命令 这些是 Gemini CLI 行为,不是 SKILL.md 的标准字段。 [5]
Antigravity Google 公告确认保留 Skill 开放规范方向,但不承诺立即与 Gemini CLI 一对一平等 目前不写解析器规则,等待独立文档或实测证据。 [6]
OpenCode 支持核心字段,忽略未知顶层字段,并由原生 skill 工具按需加载 不能据此推断其他宿主也会忽略未知字段。 [7]
Hermes Agent 兼容核心包结构,并增加 versionplatformsprerequisitesrequired_environment_variablesmetadata.hermes 这些字段属于 Hermes 扩展。便携核心仍只使用标准字段,平台、工具、环境变量和 Blueprint 配置进入 Hermes 适配层。[9]

skills-ref是 Agent Skills 仓库提供的参考解析器和校验器,用于检查 Skill 包的基本结构是否符合规范。它会读取 SKILL.md,解析 YAML frontmatter,并检查必需字段、字段类型、名称规则和允许出现的顶层字段。如果出现未知顶层字段,它会直接报错。需要注意的是,它只能检查 Skill 的“文件外形”,不能判断正文是否有用,也不会验证引用资源是否存在、脚本是否能够执行,或模型是否会遵守其中的指令。

在字段处理上,skills-ref 使用固定允许列表,而 OpenCode 会忽略未知顶层字段。这是两种实现之间的直接差异。为了提高可移植性,Skill 顶层应只使用标准字段;额外信息放入 metadata,宿主专属配置则放入对应的适配文件。。

二、从安装到生命周期的一条运行链

Skill 从安装或注册到生命周期记录,经过十个连续阶段。下面用 example-skill 表示其中的具体包;表格中的“保证”只描述执行主体自身能够观察和控制的范围。

阶段 执行主体 Skill 输入或对象 动作 可观察输出 能保证什么 不能保证什么
安装/注册 发布系统、插件或宿主配置 example-skill/ 注册路径及提交 将包放入项目、用户或外部 Skill 路径 磁盘目录和注册配置 文件和路径可被读取 宿主一定扫描该路径
发现 宿主扫描器 注册路径、example-skill/SKILL.md 查找包并解析文件入口 候选包 扫描范围内发现符合外形的包 同名优先级和模型采用结果
索引 宿主索引器 frontmatter 中的 name: example-skilldescription 建立低成本候选清单 example-skill 名称、描述索引 元数据可被列出 description 变成确定性语义规则
环境过滤 宿主索引器 compatibility、工具集、命令和环境变量 检查当前环境并显示或隐藏包 过滤后的可见性 宿主声明的过滤规则生效 过滤器理解用户任务或授予权限
激活 用户、宿主或模型 example-skill 索引、用户任务、名称或显式参数 选择、请求同意或发起加载 激活请求、同意提示或工具调用 显式入口可被解析 模型每次都正确选择
主体加载 宿主 Skill 工具 example-skill/SKILL.md 读取 frontmatter 后的正文 方法说明进入上下文 指定主体被读取 正文被完整遵循或不会被压缩
资源加载 模型和宿主读取器 example-skill/references/output-schema.md 按正文要求用包内相对路径读取 schema 输出字段和资源内容 指定资源可被加载 资源内容可信、存在或可执行
工具与授权执行 宿主权限层、工具注册器、操作系统 report-only 意图、目标 diff、只读命令 拒绝写入或允许已授权的读取和检查 工具结果、拒绝结果或授权记录 宿主权限门禁能够限制动作 Markdown 自行成为权限边界
输出与评估 模型、测试夹具、人工审查 结构化结果、命令输出、transcript、fixture 生成结果并区分发现、选择、合规、权限和验证状态 结果、状态、未知项和评估记录 已覆盖夹具的行为可复现 一次通过证明所有会话都正确
版本与生命周期 仓库、发布系统、宿主 tag、提交、.usage.json 或生命周期记录 固定版本、升级、归档或回滚 可追踪版本状态 仓库和宿主能记录其管理范围 开放规范自动锁定、更新或回滚

Hermes 的项目发现顺序是 <project-root>/.hermes/skills/<project-root>/.agents/skills/~/.hermes/skills/ 和配置外部目录,按 first-wins 处理同名包;项目包还需通过 hermes skills trust 建立信任。该发现、覆盖和信任行为属于 Hermes 固定提交 27562ad5f80e90f7d552f92dbd4af7f1f511c3c8 的宿主证据。[9] 同一提交记录了本地 Skill 的 active → stale → archived 生命周期和 .usage.json 活动记录;这不能扩展为开放规范的统一生命周期。[9]

三、触发与调用

Skill 的触发与调用按因果顺序分为四种机制:自动发现产生候选,环境过滤改变可见性,模型依据元数据作语义选择,用户或模型再通过显式入口加载主体和资源。下面继续使用 example-skill 表示被处理的具体包。

机制 执行主体 具体输入 宿主动作 输出 确定性 失败边界
自动发现 宿主扫描器 注册路径、example-skill/SKILL.md 扫描目录并解析入口文件 候选 Skill 扫描范围内较确定 路径未扫描、同名覆盖、信任未建立
环境过滤 宿主索引器 metadata.hermes.requires_toolsetsrequires_toolsfallback_for_toolsetsfallback_for_tools 检查工具集和环境,显示或隐藏候选 过滤后的 example-skill 可见性 规则执行可确定 字段不识别、显式路径绕过;过滤不等于授权
模型介导选择 模型与宿主工具 name: example-skilldescription、用户任务和上下文 模型判断是否适用并决定是否加载 Skill 调用决定 概率性 漏选、误选、重复;description 不是确定性语义触发器
显式调用/渐进加载 用户、模型和宿主接口 Gemini activate_skill、OpenCode skill、Hermes /skill-nameskill_view(name);Codex 固定协议中的名称和路径证据 解析入口,读取主体,再按需读取资源 SKILL.md 和需要时的 references/output-schema.md 指定解析和读取通常确定 名称错误、宿主不支持、权限拒绝、压缩或资源缺失

example-skill 为例,它的 namedescription 先进入索引;过滤字段决定它是否可见;用户或模型选择后,宿主读取主体;只有生成结构化结果时才读取 references/output-schema.md。Hermes 的渐进接口是 skills_list()skill_view(name)skill_view(name, file_path),分别对应低成本索引、完整主体和包内资源。[9]

Gemini CLI 的 activate_skill 和激活前同意、OpenCode 的原生 skill 工具属于宿主行为。[5][7] Hermes 支持 /skill-nameskill_view(name);固定提交还记录最多五个连续 Slash Skill。Codex 固定协议和 Skill Creator 样本支持名称及 SKILL.md 路径形状,但不足以断言所有当前产品行为。[4][9]

四、跨平台实现

检查维度 Claude Codex Gemini CLI OpenCode Hermes Antigravity
核心包与证据状态 官方文档支持 Skill;具体调用和工具/模型控制随产品表面变化。[3] 固定提交 186b449bc218ced20399bc950e23ca16cc3f9be3 的固定文件支持核心包和 agents/openai.yaml;仅由固定文件支持,不作当前产品保证。[4] 官方文档支持 Skill;以下行为限于 Gemini CLI 文档。[5] 官方文档支持核心字段和原生 Skill 工具。[7] 固定提交 27562ad5f80e90f7d552f92dbd4af7f1f511c3c8 的文档和源码证据。[9] Google 公告只确认方向,独立解析器行为未确认。[6]
发现/入口 产品表面决定,未据此指定通用路径;需以具体 Claude 表面验证入口。[3] 项目/用户发现及显式协议形状有固定文件支持;当前产品行为未被这些文件确认。[4] 分层发现;入口和允许路径由官方 CLI 文档定义。[5] 文档列出多个发现位置;原生 skill 工具是入口。[7] <project-root>/.hermes/skills/.agents/skills/~/.hermes/skills/、外部目录,first-wins;项目入口需 hermes skills trust。[9] 解析路径未确认。[6]
显式调用 调用、工具和模型控制按产品表面变化,未外推统一命令。[3] 固定协议包含 Skill 名称和 SKILL.md 路径形状;这是协议文件事实,不等于当前产品承诺。[4] activate_skill,激活前可请求同意。[5] 原生 skill 工具。[7] /skill-nameskill_view(name);固定提交记录最多五个连续 Slash Skill。[9] 未确认。[6]
主体与资源加载 产品表面决定;需实测 example-skill/SKILL.md 和资源读取。[3] 固定文件支持 Skill 文件路径;资源加载没有统一协议。[4] 宿主行为由 CLI 文档定义,资源加载需实测。[5] 原生 Skill 工具按需加载主体;资源读取需逐包验证。[7] skills_list()skill_view(name)skill_view(name, file_path),可验证主体和 references/output-schema.md 按需读取。[9] 未确认。[6]
权限/同意边界 工具和模型控制随产品表面变化,不能从 Skill 文本推导权限。[3] 由运行时决定;固定协议文件不提供跨产品权限保证。[4] 激活前同意、启用/禁用和允许路径由 CLI 配置控制。[5] 权限系统可询问;未知字段处理不等于权限授予。[7] 项目 trust、profile、toolset、工具注册和运行时共同决定;allowed-tools 不能据此写成强制沙箱。[9] 未确认。[6]
可执行验证 具体产品表面和版本必须单独记录;矩阵不把格式支持当作行为证明。[3] 标记为 repository-evidence-only;需实测当前版本。[4] 可按官方入口、同意和允许路径做 CLI 夹具。[5] 可按发现位置、skill 工具和权限规则做宿主夹具。[7] 可按 trust、first-wins、三段加载、Slash 和生命周期记录做固定提交夹具。[9] 只能记录未确认,不从 Gemini CLI 外推。[6]

同一个 example-skill 包应在每个宿主分别记录最终解析路径和版本提交,执行该宿主支持的显式入口,确认 SKILL.mdreferences/output-schema.md 的读取结果,尝试未授权写入并记录拒绝或放行,再检查结果是否符合预定输出 schema。这样能把格式发现、入口调用、资源访问、权限边界和输出行为分开归因;未确认单元不能用其他宿主的通过结果填补。

五、Skill 怎样组合与串联

一项复杂任务通常无法由一份 Skill 完成。范围确认、实现约束、代码审查、有限修改和结果验证承担的是不同职责。把这些职责全部写进一份巨大的 SKILL.md,会让触发条件变得模糊,也会让每次调用都加载与当前阶段无关的规则。拆成多份 Skill 后,系统还需要解决两个问题:哪些 Skill 应同时生效,以及前一阶段结束后怎样进入下一阶段。

组合解决共同约束

组合是让多份 Skill 在同一阶段共同进入上下文。它们没有天然的先后顺序,也不自动传递阶段状态。例如,代码审查时可以同时加载 reviewing-code-quality 和对应的语言配置:前者规定审查范围、finding 结构和只读边界,后者补充 Python、TypeScript、Go 或 Rust 的具体检查方式。两份材料共同约束一次审查,但不会因为同时加载就产生“先审查、再修改、后验证”的流程。

同时加载还需要处理职责重叠。若一份 Skill 要求只读,另一份 Skill 允许修改;一份要求先报告,另一份要求立即修复,模型只能在自然语言中解释冲突。可组合的 Skill 因此需要明确自己的责任、默认副作用和优先级,避免两份 Skill 同时控制同一个动作。

组合方式 进入上下文的内容 适合解决的问题 不会自动获得的能力
同时加载 多份 SKILL.md 共同约束同一阶段 阶段顺序和状态转移
Skill 加语言配置 通用方法与语言细节 保留跨语言核心,同时应用项目惯例 自动选择正确工具和命令
名称清单或 Bundle 一组 Skill 名称及可选补充说明 预先声明需要共同使用的能力 结构化交接、失败恢复和授权继承
宿主预加载 入口 Skill 或固定 Skill 集合 降低模型发现入口的成本 模型必然遵守每条规则

部分宿主允许在一条消息中列出多份 Skill,或通过 Bundle 加载一组 Skill。这证明宿主可以确定地完成“把哪些文件放进上下文”,不能证明模型会按预期协调这些文件。[9]

串联解决阶段交接

串联要求前一份 Skill 的结果影响下一份 Skill 的选择。以代码整洁流程为例,可以拆成下面几段:

code-craft-foundations
  确认范围、基线、风险和授权
  输出:scope、risk、authorization、next_stage
        ↓
writing-maintainable-code
  在实现前固定接口、错误、日志、性能和测试约束
  输出:实现契约
        ↓
reviewing-code-quality
  读取实现或 diff,只报告有证据的 findings
  输出:findings、unknowns、verification
        ↓ 人工选择 findings 并授权
simplifying-code-safely
  只修改获批文件和 finding
  输出:最小 diff、保留的语义假设
        ↓
verifying-code-changes
  分别运行格式化、静态检查、类型或编译、测试和场景验证
  输出:结果、未覆盖风险、最终状态

这条链不是因为文件名排成一列就成立。每次交接至少需要前一阶段的状态、输出、下一跳、授权和停止条件。缺少其中任何一项,后一份 Skill 都可能不知道该读取什么,也可能把“报告问题”误解成“已经允许修改”。

一个可检查的交接对象可以写成:

task_id: code-review-001
stage: review
status: complete
scope_checked:
  - src/cache.ts
findings:
  - CQ-2026-0001
authorization:
  mode: report_only
next_stage: needs_human
unknowns:
  - 真实依赖服务尚未验证

next_stage 只表达建议去向。authorization.mode: report_only 明确说明当前结果不能直接进入写入阶段。只有用户或宿主更新授权状态,后续修改 Skill 才具备合法输入。这样,串联传递的不是一句含糊的“继续”,而是一组能够被下一阶段检查的条件。

文本路由把下一跳写进 Skill

没有工作流引擎时,Skill 可以直接在正文中声明交接规则。完整的文本路由通常包含以下内容:

路由内容 作用 代码整洁流程中的例子
触发条件 确定当前 Skill 何时适用 收到限定范围的代码审查任务
入口动作 指定要加载的 Skill 或工具 加载 reviewing-code-quality
输入契约 规定开始前必须具备的材料 base revision、目标 diff、项目规则
输出契约 规定交接给下一阶段的内容 findings、evidence、unknowns
下一跳 指出可能进入的阶段 授权后进入 simplifying-code-safely
停止条件 阻止流程在证据不足时继续 范围不清或工具失败时停止
否定路由 明确不能自动进入的路径 未授权时不得修改代码
用户优先级 处理默认流程与用户选择的冲突 用户拒绝修改时停在报告阶段

模型读取这些文字后,可以调用宿主的 Skill 工具加载下一份 SKILL.md。这一过程表现得像自动串联,实际包含了不同性质的动作:宿主注册目录和读取文件通常由程序执行;模型根据任务选择 Skill、理解下一跳并发起调用,仍然是概率性的语言行为。

Superpowers 展示了这种文本串联如何落地。宿主先注册 Skill 目录并注入一个短入口,模型再根据任务选择具体 Skill;brainstorming 的正文把 writing-plans 写成设计确认后的下一步,模型读到规则后再次调用 Skill 工具。这里可复用的是“入口、选择、加载、交接”的结构,而不是这些具体 Skill 名称。[10]

宿主注册 Skill 目录
  ↓
入口规则进入上下文
  ↓
模型依据任务选择当前 Skill
  ↓
宿主工具加载 SKILL.md
  ↓
当前 Skill 输出结果、停止条件和下一跳
  ↓
模型或用户决定是否加载下一份 Skill

这条链中,目录注册、入口注入和指定文件读取可以由宿主代码确认;任务匹配、文字规则遵循和下一跳选择不能获得同样的确定性。行为评测需要检查 transcript 中是否真的发生了 Skill 调用,不能仅凭正文出现“必须进入下一阶段”就判定串联成功。[10]

宿主编排提供更强的确定性

宿主还可以在会话开始时预加载入口 Skill、按名称清单同时加载多份 Skill,或在用户接受后建立定时任务。这些机制负责确定“何时把哪份 Skill 放入上下文”。例如,Bundle 表达一组待加载的 Skill;Blueprint 可以形成 SKILL.md → suggestion → user acceptance → cron job → Skill preload 的调度链。[9]

宿主调度仍不等于阶段工作流。真正的工作流引擎需要保存权威状态、校验当前阶段输出、判断转移条件,并把结构化结果作为下一节点输入。它可以强制“没有授权就不能进入修改阶段”,也可以在验证失败后返回指定节点。普通 Skill 的文字下一跳没有这种执行权。

串联方式 谁决定下一步 是否保存权威状态 是否能强制转移条件
文字 handoff 模型根据 Skill 正文判断 通常依赖当前上下文 不能保证
用户确认后调用 用户决定 可由宿主记录 能形成明确授权点,但不等于完整状态机
宿主预加载或定时调度 宿主配置和调度器 保存配置与调度状态 能保证加载时机,不能保证模型遵循正文
工作流引擎 程序状态机 保存结构化状态 可以校验并强制节点转移

因此,Skill 的组合与串联处在三个层次:组合负责把相关方法同时放进上下文;文本交接负责表达下一阶段及其条件;宿主或工作流引擎负责把其中一部分关系变成可执行约束。所谓“自动串联”必须说明自动发生在哪一层,不能把文件加载、模型选择和状态调度合并成一个动作。

六、权限、失败与验证边界

权限与信任边界

example-skill 正文声明只读模式,只输出结构化结果,不修改目标文件。这个声明不是权限实现。宿主必须在工具注册、授权提示、沙箱和操作系统层实际拒绝未授权写入;allowed-tools 即使能被解析或扫描,也没有足够证据构成跨平台强制沙箱。[1][9]

项目 Skill 的 trust、外部目录优先级、脚本解释器和环境变量都由宿主和运行环境决定。prerequisitesrequired_environment_variables 可以描述依赖,不能自行授予读取凭据、联网或运行进程的权限。目录中的 Markdown、脚本、README、issue、注释和外部仓库内容都按不可信数据处理;提示注入和供应链内容不能改变 example-skill 的授权范围。[8]

运行时失败类别

  • 发现失败:注册路径没有扫描到 example-skill,或同名包解析到意外路径。
  • 过滤或选择失败:包进入索引却被环境字段隐藏,或模型看到 namedescription 后没有选择它。
  • 重复 bootstrap:宿主在多个 agent step 注入同一入口,缺少 marker 导致上下文重复。Superpowers v6.3.0 的 OpenCode message transform 需要这类去重边界。[10]
  • 压缩丢失:上下文压缩后丢失 report-only、已完成阶段或下一跳;Superpowers 本地 6.1.1 的压缩后补注入记录不能外推为开放规范保证。[10]
  • 控制者/worker 泄漏:worker 重复执行入口流程,造成重复规划或错误角色边界。
  • 资源或 shell 漂移references/output-schema.md 不存在、相对路径错误、解释器或 shell 不同,导致正文声明的资源或脚本不可用。
  • 权限拒绝:宿主正确拒绝未授权写入,不能被误报为 Skill 执行失败;若实际放行,则是权限边界失败。
  • 虚假完成:报告声称已运行命令、读取资源或通过测试,但 transcript 和工具结果没有对应证据。

验证层次

结构层用 skills-ref 检查 SKILL.md、frontmatter 和允许字段;它不能证明 references/output-schema.md 存在,也不能证明模型遵守正文。[2] 宿主基础设施测试记录最终解析路径、版本、索引、显式调用、主体和资源读取、权限拒绝,以及 Hermes 固定提交 27562ad5f80e90f7d552f92dbd4af7f1f511c3c8 的 trust/生命周期行为。[9]

行为夹具必须分别标记发现失败、选择失败、body-compliance 失败、权限失败和验证失败。example-skill 夹具应检查只读模式是否生效、references/output-schema.md 是否解析、结果是否满足 schema,以及输出是否只建议下一阶段而不伪造后续结果。模型行为评估保存任务、Skill 调用、工具调用、结构化结果和失败原因,不能只保存最终文本。

baseline 与 with-Skill 使用同一模型、宿主、输入、权限和工具;前者不加载 example-skill,后者加载它。两组都保存 transcript、资源访问、写入尝试、命令结果、报告、diff 和耗时。对照结果只能说明固定夹具和版本中的观察,不构成所有会话的调度或语义等价证明。

七、规范、宿主和模型各自决定什么

开放格式保证的是一个可被识别的公共核心:目录中有 SKILL.md,文件有合法 frontmatter,namedescription 表达包的名称与用途,资源可以用相对路径组织。它不保证发现目录、激活时机、工具权限、模型选择、版本锁定、更新回滚或定时调度。[1]

宿主可以保证自己实现的发现、索引、加载、同意、信任、工具和调度行为。Hermes 的三级读取、项目 trust、first-wins、Bundle、Blueprint 和生命周期存在于固定提交;OpenCode 的原生 skill 工具和未知顶层字段处理是另一种宿主行为。Claude、Codex、Gemini CLI 的公开文档支持各自产品能力,不能自动变成跨平台保证。Antigravity 的独立解析规则仍未确认。[4][5][6][7][9]

模型只是在上下文中根据自然语言、任务和工具结果进行概率性选择。它可能正确理解 description,也可能漏掉 Skill、重复调用、跳过授权说明或误读下一跳。Superpowers 的 bootstrap 和文字 handoff 能降低发现成本,却没有把 Markdown 变成程序化状态机。[10]

必须实测的内容包括:同名冲突、信任门槛、资源读取、脚本失败、权限拒绝、提示注入、压缩后规则是否仍在、显式调用是否绕过过滤、Bundle 是否按预期加载、Blueprint 是否等待用户接受、模型是否在正确阶段调用 Skill,以及输出是否通过项目已有验证。能证明的结论应写成“在固定宿主、版本、输入和测试范围内观察到”;不能证明的内容保留为未知,不用“通常”“应该”或产品名称填补空白。

参考文献

  1. Agent Skills Specification.
  2. Agent Skills, pinned skills-ref validator and parser.
  3. Anthropic, Agent Skills and Claude Code Skills.
  4. OpenAI Codex, pinned Skill Creator sample and protocol v1.
  5. Gemini CLI, Skills.
  6. Google Developers Blog, transitioning Gemini CLI to Antigravity CLI.
  7. OpenCode, Skills.
  8. OWASP GenAI, Prompt Injection.
  9. Nous Research, Hermes Agent,固定提交 27562ad5f80e90f7d552f92dbd4af7f1f511c3c8
  10. Superpowers v6.3.0
Logo

汇聚全球AI编程工具,助力开发者即刻编程。

更多推荐