最近 Claude 更新了一个让我挺兴奋的能力——Skills。简单说,它把 Anthropic Claude 从一个"对话助手"变成了"可以装软件的工作系统",就像手机装 App、电脑装软件一样,你可以在 Claude 里挂载一个"技能包",让它干特定活时自动使用特定的流程、规则和工具。我试用了一段时间,今天把理解到的原理、手写技能包的方法、踩过的坑一次性整理出来。
这篇内容适合两类人:一类是觉得 Claude 虽然聪明但干活不够稳定的普通用户,另一类是正在用 Claude 或类似模型做自动化流程、想把它真正产品化的开发者。无论你是只想抄作业,还是想搞清楚背后机制,这篇都覆盖了。
1. 为什么 Claude 突然需要"技能包":从对话助手到工作系统的转变
1.1 一个让人抓狂的日常场景:让 AI 做同一件事,每次结果都不一样
在 Skills 出现之前,我使用 Claude 的方式基本是人肉操作:每次要它生成一份周报,都要重新粘贴一大段背景说明;要它做代码审查,每次都要强调"你先看目录结构、再找潜在问题、最后给修改建议"。最烦的是,就算你费劲写了一大段提示词,下一次换个窗口它就全忘了。
这种"每次从零开始教"的体验,本质上是因为 Claude 是一个通用模型,它可以理解和生成任何内容,但它本身没有"长期记忆",也没有预设的"工作方式"。你对它说"帮我写一份报告",它能写,但格式可能这次用表格、下次用列表;你对它说"审查这段代码",它能审,但这次盯着缓冲区溢出、下次只看代码风格——取决于它当时怎么理解你的话。
很多人的解法是保存"提示词模板",但这只是把问题从"每次打字"变成"每次粘贴",模板本身不会根据任务类型自动加载,也不会绑定特定的工具。
1.2 Skills 解决的不只是"提示词过长",而是工作流程标准化
Skills 的核心思想和上面完全不一样:它把"如何完成一类任务"打包成一个文件(实际上是一组文件),放在 Claude 能读取的目录里。当你的任务匹配到某个技能时,Claude 会自动读取这个技能的定义,然后严格按照里面的步骤、规则和工具调用来干活。
我用一个生活中的类比解释一下:提示词像你给临时工口述今天要做什么,说得再详细,明天换个人他又不知道了;Skills 像一个标准作业流程图(SOP),挂在墙上,谁来都能按流程操作。它不是一次性的对话指令,而是一个可存储、可复用、可分享的"岗位说明书"。
从产品形态上讲,Claude Skills 引入了项目级的\.skills\目录约定。你可以把不同的技能文件放在这个目录下,每个技能对应一个独立的.md文件。Claude 在对话中会先扫描这些文件,当用户请求涉及某个技能描述的场景时,自动加载对应技能的完整指令。整个过程对用户来说是透明的,只需要在配置中把技能目录关联到 Claude,后续对话就不需要再手动提示"请按照 XXX 流程执行"。
1.3 和传统提示词、记忆、MCP 的定位差异
很多人刚接触时会问:Skills 和系统提示词、和 Claude 的 Memory、和 MCP(模型上下文协议)到底有什么区别?会不会重复了?我自己梳理过一遍,它们其实是三个完全不同的层次:
| 机制 | 本质 | 解决的问题 | 局限 |
|---|---|---|---|
| 系统提示词 / 自定义指令 | 一段始终生效的全局文字 | 设定角色和通用偏好 | 不分场景强制生效,占上下文,无法绑定工具 |
| Memory / 记忆 | 模型对信息的持久化存储 | 记住用户身份、偏好、历史事实 | 存储的是"事实",不是"做事方法" |
| MCP / 外部工具 | 把外部 API、数据库、本地文件暴露给模型 | 让模型能"触达"外部世界 | 只解决"能做什么",不解决"该怎么做" |
| Skills / 技能包 | 指令、流程、工具绑定的整体封装 | 让模型"知道怎么完成一类任务" | 需要提前编写和配置,有版本维护成本 |
可以这样理解:MCP 是给 AI 装了"手"(能操作外部工具),Skills 是给 AI 装了"大脑皮层里的程序"(面对特定任务时知道怎么一步步做)。提示词是口头嘱咐,Skills 是书面的、可存档的作业指导书。
这个定位差异很关键,很多人把技能包单纯理解成"更长的提示词",那就错过它真正的价值了——Skills 支持绑定工具列表,一个技能可以声明"我会用到代码执行器、文件编辑器、网页搜索",Claude 在加载技能时就会自动把相关工具准备好,不需要你在对话里反复交代。
2. Skills 的底层文件结构:一个 SKILL.md 到底写了什么
2.1 .skills\ 目录:一种新的项目级"技能仓库"约定
先用一个最简例子让你建立直观印象。假设你在某个工作目录下使用 Claude,那么你可以在目录根下创建一个\.skills\文件夹,结构大概是这样的:
your_project/ │ ├── .skills/ │ ├── create-report/ │ │ ├── SKILL.md │ │ └── templates/ │ │ └── report_template.md │ │ │ └── code-review/ │ ├── SKILL.md │ └── rules/ │ └── security_checklist.md │ ├── documents/ └── README.mdSKILL.md是每个技能的灵魂文件,它用 Markdown 格式编写,Claude 通过读取这个文件了解技能的名称、作用、使用条件、具体操作步骤、需要绑定的工具以及参考资源。旁边的附属文件(模板、规则、代码片段)是可选的支持材料,技能激活时可以按需引用。
我一开始以为这个目录类似于一个"插件市场",要把别人的技能下载下来放进去。上手后发现,其实你没有必要去找现成的技能包——因为一个技能的核心就是一份写清楚"怎么做"的 Markdown 文档,你自己完全可以写出来。反而"自己写"才是这个功能最大的价值:你可以把团队内部的工作规范、行业经验沉淀成 AI 能读懂的文档。
2.2 SKILL.md 的核心字段逐项拆解
一个SKILL.md文件通常包含 YAML 格式的 frontmatter(元信息区)和 Markdown 正文(指令区)。下面是一个实用的结构示例:
--- name: create-report description: 根据原始数据生成结构化月度报告。当用户提到"写月报""生成报告""汇总本月数据"时使用。 version: 1.0.0 allowed-tools: - bash - read_file - write_file - web_search metadata: author: team-data updated: 2025-06-01 --- # 月度报告生成技能 ## 目标 将输入的散乱数据整理为三部分:摘要、明细、趋势分析。 ## 执行步骤 1. 读取用户提供的数据文件或粘贴文本。 2. 用 bash 过滤并统计数据(若数据为 CSV/JSON)。 3. 按模板结构生成 Markdown 报告。 4. 如有需要,用 web_search 补充行业背景。 ## 输出要求 - 摘要部分不超过 3 段,每段不超过 5 行。 - 明细使用表格呈现,行数不得超过 30。 - 趋势分析必须给出至少一个明确的结论,不能只说"需关注"。 ## 参考模板 见 `templates/report_template.md`,输出时必须加载该模板。我从实际体验中总结一下每个字段的作用:
- name:技能的唯一标识。建议用 kebab-case(小写加连字符),不要用中文或空格,否则某些环节匹配容易出问题。
- description:这是最关键的一个字段。Claude 会先用它来判断"当前这个任务该不该加载这个技能"。你写得太泛(比如"处理数据"),它可能在任何涉及数字的对话里都触发;写得太窄,又可能该触发时不触发。最佳实践是:用一两句话描述适用场景,再列出两三个具体的触发短语。
- allowed-tools:允许技能调用的工具白名单。这份声明非常重要——它告诉 Claude 这个技能的"工作边界"。不需要联网的技能你就不要写 web_search;不需要执行代码的技能就别放 bash。工具声明越克制,技能行为越可控。
- 指令区(正文):真正的"工作方法论"。这里值得注意,Claude 对指令性文字的服从度并不是简单的"越长越听话"。过长、过于空泛的指令反而会在执行中自我矛盾。我的建议是:每一步指令都对应一个可验证的结果,比如"读取文件""生成数据表""输出结论",让模型每做完一步就知道下一步做什么。
2.3 Progressive Disclosure 机制:为什么不会撑爆上下文窗口
我第一次看到技能文件时有个疑问:如果技能定义好几千字,那不是每次对话都把上下文塞满?后来仔细研究了一下,才发现这部分设计很巧妙。
Claude Skills 采用的机制是渐进式披露(progressive disclosure)。在对话开始时,Claude 只会读取每个技能description字段的那几句话——相当于浏览一本书的目录。只有当判断某个技能适用于当前任务时,它才把对应技能的完整指令加载进上下文;不相关的技能始终只保留一个标题级别的存在感。
这个设计和人类翻手册的路径非常像:遇到"内存泄漏"问题,你不会去读整本系统运维手册,而是先看目录索引,翻到对应章节,再按步骤操作。Claude 也是这样,几百个技能同时挂载也不会让上下文爆炸,因为绝大多数技能在一个会话中根本不会被激活。
不过这个机制也带来一个副作用——description 写得好不好,直接决定了技能的"召回率"(就是该用到时能不能被找到)。后面第五部分我会专门讲这个问题。
3. 手写第一个 Skill:从需求拆解到功能上线
3.1 场景选择:为什么从"报告生成"入手最合适
说一百遍原理不如动手写一个。我第一次尝试写的技能是"月度销售报告生成"。选这个场景有三个理由:
第一,任务边界足够清晰——输入是几段散乱的数据和文字,输出是一篇固定格式的报告,不容易出现"这个技能到底该不该管这件事"的歧义; 第二,它在实际工作中足够通用,写完就能用,不是只能在演示环境里跑的玩具; 第三,它的执行过程包含"读取数据—处理数据—按模板输出"三个基本环节,正好覆盖技能文件里最核心的编写模式。
我不推荐一上来就写那种要联动十几个工具、跨多个系统的复杂技能——技能包调试时,问题往往不是单个环节错,而是环节之间的衔接出问题。从简单的开始,快速拿到正反馈,再逐渐往上加复杂度,这条路走得最稳。
3.2 创建步骤:从新建文件夹到绑定工具
整个创建过程分为四步,这里按我实际操作的顺序来写:
第一步:建立技能目录结构。
mkdir -p .skills/create-report/templatestemplates文件夹用来放输出模板,这样技能指令里不用写死几百行的模板内容,只需要在SKILL.md里引用模板文件的路径。
第二步:编写 SKILL.md 主文件。按照上一节的结构,把 name、description、allowed-tools、指令区逐项填好。这里给一段我当时用的完整示例(做了脱敏处理,你替换成自己的业务即可):
--- name: monthly-report description: 生成结构化月度报告。当用户要求"写月度总结""整理月报""汇总本月营收/销量/指标"时使用。 version: 1.0.0 allowed-tools: - bash - read_file - write_file --- # 月度报告生成 ## 输入 用户提供的数据文本、表格或 CSV 文件路径。 ## 执行流程 1. 用 read_file 读取数据(若是 CSV,使用 bash 中的相关命令解析)。 2. 将数据拆分为三个维度:总量、环比变化、异常值。 3. 使用模板文件 `.skills/monthly-report/templates/report_template.md` 生成最终报告。 4. 将结果用 write_file 保存到 `output/` 目录,文件名格式:`YYYY-MM_report.md`。 ## 输出规范 - 每段总结必须写具体数字,禁止出现"有所增长""大概不错"这类模糊表述。 - 如数据存在缺口,在报告末尾单独列"待补充数据",不能自行编造。第三步:编写模板文件。templates/report_template.md可以写成一个带占位符的 Markdown 模板:
# {{月份}} 月度报告 ## 一、核心指标 | 指标 | 本期数值 | 上期数值 | 环比 | |------|---------|---------|------| | {{指标名}} | {{本期}} | {{上期}} | {{环比}} | ## 二、要点总结 {{总结内容,必须引用具体数字}} ## 三、异常说明 {{异常项,无则写"无"}}模板的作用不是给 Claude 一个"好看的格式",而是给它一个"不可省略的结构"。它知道里面每一项都要填,填不出来的地方就要标记为"待补充数据"或写"无"——这大大减少了 AI 常见的"虚写""空话"问题。
第四步:在 Claude 中启用技能。在 Claude 的设置里找到 Skills 相关选项(不同客户端位置略有差异),把项目的根目录挂载上去。挂载完成后,新开一个对话窗口,直接说"帮我生成月度报告",然后丢几段数据给它。
提示:首次挂载目录后,需要在新的对话会话中才会生效。已经开着的窗口不会自动重新扫描技能目录,这是很多人遇到的"怎么没反应"的原因。
3.3 验证技能是否被正确加载
验证技巧比较隐蔽:你可以在对话里直接问 Claude "你当前加载了哪些技能?"如果它准确说出monthly-report的名称和作用,说明挂载成功;如果它一脸茫然,基本可以确定是目录路径没对、或者没有新开对话窗口。
还有一种更细的验证方式:故意用一个与技能无关的任务试探(比如"帮我写一首诗"),如果 Claude 完全没有提到报告相关的内容,说明 description 的过滤作用是正常的,没有"无差别加载"。能做到"该用时出现、不该用时隐形",就是一个合格技能包的标准。
4. 实测几个应用场景:Skills 在不同任务里的真实表现
4.1 场景一:报告生成——输出一致性大幅提升
我拿同一份 6 月份的销售数据分别测了两次:一次用普通对话(给它详细提示词),一次用挂载好的monthly-report技能,各跑 5 遍,对比输出结构。
结果差异非常大。普通对话模式下,5 次输出里只有 2 次使用了表格汇总,3 次用列表;段落结构每次都不一样;最要命的是,有 2 次它在"异常说明"部分凭空写了"库存环比下降 12%"——但原始数据里根本没提库存。这种"看起来合理但完全不存在的数据",在 AI 对话里极难察觉,却是实际业务中的大坑。
技能模式下,5 次输出结构完全一致,模板字段一个不落,所有数字都能在原始数据里找到对应位置,没有出现任何编造数据。虽然没有一次是"惊艳"的,但每一次都是"可靠"的。
这个对比让我意识到 Skills 真正的价值不在于让 AI 变聪明,而在于让 AI 变稳定。在企业场景里,"稳定"往往比"聪明"重要得多——一个每 5 次就有 2 次输出格式错乱的 AI 助手,很难被业务部门真正用起来。
4.2 场景二:代码审查——工具绑定带来的行为变化
第二个实测场景是代码审查。我给一个代码审查类技能配置了allowed-tools:bash(运行静态检查工具)、read_file(读源码)。技能指令里规定了审查的固定顺序:先看变更文件列表,再逐文件读取,然后运行基础静态检查,最后按"安全隐患—性能问题—可读性问题"三层输出。
绑定工具后的变化在于:以前让 Claude 审查代码,它只能"读你贴给它的代码片段",碰上跨文件的调用关系就只能靠猜。绑定了文件读写工具后,它能自己去读相邻文件、去查被调用函数的实现;绑定了 bash 后,它可以直接跑一些命令行检查命令。技能的流程加上工具的边界,就构成了一条完整的"自动化审查流水线"。
需要注意的一点是:技能文件里自己写的检查规则再长,也比不上专门的静态分析工具。所以我的用法是让 Claude 跑完工具之后,再基于工具的输出来做语义层面的判断。AI 的价值在于理解上下文,而不在于替代专业工具。
4.3 场景三:领域知识注入——把行业经验写进技能包
第三个场景没有用到任何外部工具,纯粹靠技能文件注入领域知识。我当时模拟了一个"房屋租赁合同审查"技能:审查清单里包含十几条常见风险点,比如"押金条款是否明确退还条件""维修责任是否写清""违约金是否过高""租金支付方式是否存在二房东转租漏洞"等等。
实测效果很明显:没有技能时,让 Claude 审一份合同,它只能给出非常通用的"合同应当明确双方权利义务"这类废话,重话里带不了几点有用的东西。挂载技能后,它会严格按照清单逐条比对原文,发现"第 3.2 条未约定押金退还期限"会直接指出来,并给出修改建议。
这种"领域经验注入"才是 Skills 最有想象力的用法——它让你可以把一个老师傅十几年的审核经验、几十条需要注意的细节,完完整整地翻译成 AI 能遵循的规则。任何一个行业、任何一类重复性判断任务,理论上都可以沉淀成技能包。我甚至觉得,未来"写好一个技能包"本身就能成为一种职业能力,就像现在会写提示词、会做表格一样普通。
5. 我踩过的坑与优化心得:版本管理、增量加载、多技能协作
5.1 描述写太泛:技能该来不来
先说最影响体验的一个坑:description 写得太泛,导致技能"召不回"。
我第一次给报告技能写的描述是"生成报告"。听起来没错,但这个描述太宽泛了。实际测试中,用户说"把这几行数据整理一下",Claude 就完全不触发报告技能——因为它觉得"整理数据"不等于"生成报告"。明明技能里规定了输出模板和保存格式,但因为没被加载,所有规则全部失效,输出又回到自由发挥的状态。
后来我改成描述里明确列出触发短语:"生成月度报告""写工作总结""整理本月数据"以及"按模板输出报告"。改完之后,触发命中率明显提高。用了几次之后我总结出一个原则:description 里的触发词,应该来自用户可能说出口的话,而不是来自你心里给这个技能起的名字。你想着它叫"报告生成",但用户说的是"把这堆数弄整齐点"——这两个说法之间的鸿沟,就是技能会不会被触发的原因所在。
5.2 指令写得太重:频繁反问反而拖慢效率
第二个坑是指令覆盖过度。一开始我担心 Claude 不按要求做,所以把技能里的每一步都写得非常细,细到"第 3 步第 2 小步里如果销售额超过 100 万就输出红色标记"。结果实际运行起来,模型反而频繁"卡住"——因为指令太复杂了,它会为了确认某个边界条件而停下来反问用户:"这里销售额超过 100 万是否要标记?"
这种"谨慎"看起来不是大问题,但在批量处理几十份报告时,每份多一次反问就是几十倍的效率损失。后来我调整了策略:对于有明确规则的内容写成硬性指令(比如"必须引用具体数字");对于无法事前穷举的边界情况,只给一个默认行为(比如"无法判断时按不标记处理")。
深层次的原因在于:模型对指令的解释受限于上下文理解,指令写得越复杂,反而越容易产生歧义。可验证、可执行、有默认行为的指令,远比"鞭策式"的详细规定可靠。
5.3 多个技能同时挂载时的优先级冲突
第三个坑出现在技能数量多了之后。我同时挂载了报告生成技能和数据分析技能,两个技能都声明了"用户给出数据时可以使用"。结果在一次会话中,Claude 把两个技能都加载了,然后一边按报告模板输出,一边又想执行数据统计的流程,最后生成的内容结构混杂、前后矛盾。
后来我才注意到,技能描述里不光要写"何时启用",还要写"何时不要启用"。比如报告技能的描述里加一句"如果用户只要求统计数值、不要求生成文档,则不应使用本技能";数据分析技能描述里加一句"如果用户明确要求生成结构化报告,则仅供数据参考、不覆盖输出格式"。添加排除条件之后,冲突大幅减少。
如果你有多个技能存在潜在边界重叠,可以建立一个优先级规则,直接写在各技能的开头:"当与数据分析技能冲突时,本技能拥有最终输出格式控制权。"模型对这类显式声明非常敏感,写不写效果差异很大。
5.4 用版本管理维护技能包:这不仅仅是文本文件的事
使用一段时间后,技能的迭代是不可避免的:规则要改、模板要换、新的触发场景要加。一开始我是直接修改 SKILL.md,后来发现出了问题没法回退——一个改了 5 处描述文件的技能,如果对话中出了奇怪的行为,你很难快速定位是哪一处改动引起的。
我的方案是给技能包加上版本管理:用 git 管理整个.skills目录,每个技能文件头部维护版本号;每次修改提交信息里写明改了什么。同时在技能内部增加一个CHANGELOG段落,记录每个版本的重大调整:
## 变更记录 - v1.1.0:增加"异常值"输出维度,修改模板路径。 - v1.0.1:修复 description 过长导致的匹配歧义。 - v1.0.0:初版,支持基础月度报告生成。这看起来是个不起眼的习惯,但实际排查问题时帮了我大忙。有一次技能行为突然异常,我直接把 SKILL.md 回退到上一个版本,问题立刻消失——这就是版本管理的价值,不需要懂什么高深理论,用 git 就行。
5.5 给技能"减肥":从大而全到小而专
最后一个心得是关于技能规模的。我第一次写的技能包试图覆盖所有场景:既要能生成月报,又要能分析销售趋势,还要能生成图表建议,甚至还想让它顺便处理市场竞品信息。结果就是 SKILL.md 长达 300 多行,Claude 加载后反而"不知道该听哪句"——因为技能内部的指令优先级不明确,指令之间还会互相打架。
后来我把一个"全能技能"拆成了三个小技能:一个管报告生成、一个管数据分析、一个管图表建议。每个技能只负责一件事,里面只写清楚这一件事怎么做。拆完之后各技能的表现都有提升:加载更快,行为更准,调试也容易多了。
这让我想起软件开发里的单一职责原则。技能包本质上就是一段逻辑代码,它同样遵循"小而专优于大而全"的规律。
最后补一个我觉得很实用的小细节:给每个技能写一个简单的"测试用例"清单,也就是你预期用户可能会提出的 3-5 个问题,每次修改完技能后把这几个问题都跑一遍。我发现这比任何复杂的验证工具都实用——一个技能只要在这 5 个问题上表现稳定,那它在实际工作中出错的概率就低很多。技能包的维护没有终点,你写它的时候要想着它还会被改很多次,所以干净的描述、清晰的脚步、完整的变更记录,比一次性的"完美指令"重要得多。