
1. 从一次发票去重翻车说起为什么需要 SKILL.md先说结论Agent Skills 的核心价值是把「你脑子里那套正确做法」固化成一份可被多个 AI 编程工具直接读取的 SKILL.md一次编写Claude Code、Codex、Antigravity 等工具都能加载运行。它适合谁适合那些反复给 AI 解释同一套流程、被临场提示词不稳定折磨过的开发者以及想把业务方法论沉淀成可复用资产的人。我遇到过一个很典型的需求用户上传一批发票截图里面有重复的需要筛出来。听起来机械交给 AI 就行。我先让某个 CLI 工具直接做结果它搞了个视觉相似度算法把背景板一样的图片全匹配上了——交易号完全不同根本不是重复发票。多模态再强也不该在「精确去重」这种任务上过度自信视觉匹配。问题不在于模型笨而在于我没把正确路径写死。正确做法应该是OCR 提取文本 → 正则抓 20-30 位交易号 → 模糊匹配处理 OCR 误差 → 分组输出。这套流程每次临场说一遍既费口舌又不稳定。于是我把它固化成一个 skill之后同类需求直接触发AI 就按标准流程走抓到了两组真正的重复发票。这就是 Agent Skills 的意义它不是「又多了一种提示词写法」而是把「正确路径写死、错误路径封死」变成可复用文件。而 SKILL.md 就是这份文件的统一载体。下面我把目录骨架、各工具识别路径、配置片段和跨工具验证步骤完整走一遍你可以直接跟着做。2. TaoToken 前置给跨工具调用准备一个统一入口在验证「一次编写、多工具通用」之前得先解决一个现实问题Claude Code、Codex 这类工具各自要配 API Key、各自要设 base_url切换工具时配置散落各处。我的做法是用 TaoToken 作为统一接入层官网是 https://taotoken.net/?utm_sourcetaotoken_aicg_blog_endutm_mediumcsdnutm_campaignrewriteutm_content API 端点是 https://taotoken.net/api 这个地址不加 UTM。它在这里扮演的角色很单纯提供一个兼容的 API 入口让不同工具指向同一个 base_url省去每个工具单独折腾接入的麻烦。注意它是接入层不是编辑器替代品你的代码还是在 Claude Code 或 Codex 里写。操作路径大致是这样先到控制台创建密钥控制台地址是 https://taotoken.net/console?utm_sourcetaotoken_aicg_blog_endutm_contentconsoleutm_campaignrewrite 密钥管理页在 https://taotoken.net/api-keys?utm_sourcetaotoken_aicg_blog_endutm_contentapi-keysutm_campaignrewrite 。拿到 Key 之后各工具的环境变量都指向同一个 base_url这样后面验证 SKILL.md 跨工具加载时变量就只剩「工具本身对 Skills 的支持差异」而不是「接入配置差异」。如果你只是想先验证模型对话能不能通可以用模型对话页 https://taotoken.net/models?utm_sourcetaotoken_aicg_blog_endutm_contentmodelsutm_campaignrewrite 快速试一条请求。接入文档在 https://taotoken.net/doc?utm_sourcetaotoken_aicg_blog_endutm_contentdocutm_campaignrewrite 遇到参数问题先查这里。3. SKILL.md 目录骨架与可复制配置3.1 最小可用目录结构一个 skill 就是一个文件夹加一个 SKILL.md需要的话再放脚本和参考文件。项目级结构长这样my-project/ └── .agent/ └── skills/ └── invoice-dedup/ ├── SKILL.md ├── scripts/ │ └── extract_txn.py └── references/ └── txn-rules.md全局级则放在用户目录下所有项目共享。不同工具的全局路径不一样这是后面要重点验证的差异点。3.2 SKILL.md 的 YAML frontmatter文件开头是 YAML 元数据name 是技能名description 写清楚「什么场景下调用、能做什么」。这段描述直接决定 Agent 能不能正确触发别写得太模糊。--- name: invoice-dedup description: 通过 OCR 提取交易号识别重复发票。当用户上传多张发票截图并需要去重时调用。 --- ## 怎么用 1. 对每张发票图片执行 OCR提取全部文本 2. 用正则匹配 20-30 位连续数字作为交易号候选 3. 对候选交易号做模糊匹配容忍 OCR 常见误差如 0/O、1/l 混淆 4. 按交易号分组输出重复组及对应文件名 ## 注意事项 - 不要用视觉相似度判断重复背景板相同不代表发票重复 - 交易号缺失时标记为「无法判定」不要强行归组3.3 各工具识别路径对照这是跨工具通用性的关键。同一份 SKILL.md放到不同工具认的目录里才能被加载。下面是我实测整理的对照表工具项目级路径全局路径Claude Code项目/.claude/skills/skill/~/.claude/skills/skill/Codex项目/.codex/skills/skill/~/.codex/skills/skill/Antigravity项目/.agent/skills/skill/~/.gemini/antigravity/skills/skill/注意路径里的工具名目录是各工具自己约定的SKILL.md 内容本身不用改。这就是「一次编写」的含义——文件内容通用落位路径按工具放。3.4 环境变量配置片段把各工具的 base_url 统一指向 TaoTokenKey 用同一个export TAOTOKEN_API_KEY你的密钥 export ANTHROPIC_BASE_URLhttps://taotoken.net/api export OPENAI_BASE_URLhttps://taotoken.net/apiClaude Code 走 Anthropic 兼容协议Codex 走 OpenAI 兼容协议两者都指向同一个入口。配置完记得新开终端让环境变量生效。4. 验证请求同一技能包跨工具调用4.1 准备测试技能先建一个最小技能 hello-skill只做一件事被触发时输出固定字符串。用它验证「识别 触发」这条链路。--- name: hello-skill description: 测试技能是否被正确识别和触发。当用户说「测试技能」时调用。 --- ## 怎么用 1. 输出字符串SKILL_LOADED_OK 2. 不要输出任何其他解释文字把它分别复制到三个工具的项目级路径下然后依次启动。4.2 Claude Code 验证在项目根目录启动 Claude Code输入「测试技能」。预期它识别到 hello-skill 并输出SKILL_LOADED_OK。如果没触发先确认.claude/skills/hello-skill/SKILL.md路径拼写再检查 frontmatter 的---是否顶格。4.3 Codex 验证同样在项目里启动 Codex输入相同指令。Codex 认的是.codex/skills/目录。实测下来只要 SKILL.md 的 YAML 合法触发行为和 Claude Code 基本一致。4.4 复杂格式与落盘验证基础触发通过后再上强度。我设计了三个进阶测试技能format-boundary-trapfrontmatter 里塞复杂 YAML嵌套、多行字符串看解析是否出错strict-json-trap要求输出纯 JSON不能有 markdown 代码块和解释文字验证能否直接JSON.parse()file-generation-trap要求真实创建文件验证ls能找到、cat能打开# 验证 file-generation-trap 是否真的落盘 ls -la ./output/ cat ./output/result.txt三个工具跑下来基础链路「技能识别、格式解析、结构输出、真实落盘」表现相当一致。这说明至少在基础标准层面SKILL.md 的通用性是真的。5. 本篇常见错排查5.1 技能不触发最常见的原因是 description 写得太泛比如只写「处理文件」。Agent 匹配不到具体场景就不会加载。改成「当用户上传多张发票截图并需要去重时调用」这种带触发条件的描述。另一个原因是路径放错Claude Code 的技能放到.agent/下当然不认。5.2 YAML 解析失败frontmatter 必须以---开头、以---结束中间不能有 tab 缩进多行字符串用|或。如果 description 里有冒号记得加引号否则 YAML 会把它当键值对解析。5.3 输出带了多余解释strict-json 类技能最容易翻车。在 SKILL.md 正文里明确写「只输出 JSON不要任何前后缀文字」必要时给出输出示例。光靠 description 约束不够正文指令要硬。5.4 全局技能不生效检查全局路径是否写对。Antigravity 的全局路径是~/.gemini/antigravity/skills/不是~/.agent/。另外确认工具版本是否支持全局技能老版本可能只认项目级。5.5 跨工具行为不一致如果某个工具触发正常、另一个不触发先对比两边 SKILL.md 是否完全一致有人复制时改了内容再确认工具版本。基础链路一致不代表所有高级特性都一致复杂脚本调用、多文件依赖这类场景各工具支持程度仍有差异这也是通用性的边界所在。6. 把技能沉淀成长期资产验证完基础链路下一步是把真正有价值的技能固化下来。如果你要长期做编码类任务、跑 Agent 工作流建议了解一下 Coding Planhttps://taotoken.net/coding-plan?utm_sourcetaotoken_aicg_blog_endutm_contentcoding-planutm_campaignrewrite 它更适合高频、持续的编码场景。Claude Code 相关的接入细节可以看 https://taotoken.net/claude-code?utm_sourcetaotoken_aicg_blog_endutm_contentclaude-codeutm_campaignrewrite 。我的建议是先从你每周都要重复解释的那件事开始写 skill别一上来就追求大而全。一个文件夹、一个 SKILL.md把正确路径写死错误路径封死然后放到各工具认的目录里跑一遍。跑通了你就拥有了一份跨工具通用的经验资产。跑不通的地方往往就是当前通用性的真实边界——这比任何宣传都值得记录。