Claude-Code-操作模型-一-
Claude Code 操作模型(一)
原文:The Claude Code Operating Model
译者:飞龙
贡献者
关于作者
Jia Huang 是新加坡 A*STAR 的 AI 研究员,也是一位技术作者,撰写关于 AI 智能体如何被工程化的内容。他是 Designing AI Agents 和 RAG from First Principles 的作者。
他提出了智能体设计模式的双轴框架,该框架按认知功能和执行拓扑对模式进行分类,以及模式选择卡(Pattern Selection Card),一种在真实成本和延迟约束下选择模式的实用方法。他的工作聚焦于模型周围的工程,而非模型本身:上下文、工具、执行环境和治理。他用中文和英文写作。
感谢 Lucy Wan,她连接了我的中文和英文市场,并将我带入 Packt 团队,这一联系开启了一段非凡的合作时期。我也感谢 Kinnari Chohan,她的专业编辑使这个英文版比我独自完成的更加清晰和有力。
我在人民邮电出版社的中国出版团队全程支持了这项工作。
Jikang Chen 和 Sha Li 在每一步都支持我,并帮助塑造了我的写作方式;
Jian Qin 编辑了中文版;Chenyu Yuan 创作了插图。
我也感谢极客时间团队,特别是编辑 Yuxin Zhao 和 Dongqing Wang,以及我的 Claude Code 课程中的众多学习者。他们深思熟虑的问题、实用的反馈和宝贵的建议帮助我完善了本书中的想法,并使其对实践者更有用。
我感谢 ADPS 社区——智能体设计模式学会(Agent Design Patterns Society)——的同事们:Bingsheng Ru、Ning Jiang、Bo Liang、Haofen Wang 教授、Huisheng Yin、Haili Zhang 和 Pingping Bai,感谢他们与我共同建设这个社区。
最后,我最深切地感谢我的父母,感谢他们无条件的爱与支持。
关于审阅者
Wei Wei 是一位 AI 工程实践者和技术作者,拥有英国阿伯丁大学人工智能硕士学位。他专攻 LLM 系统、智能体 AI 架构和 Harness Engineering。他著有五本以上技术书籍,涵盖 Python 系统、Web 架构和应用机器学习,曾在同程数科领导大数据平台开发,并作为高级 ML 科学家构建了多模态智能系统。作为独立顾问,他曾为花旗银行、中国银行和平安人寿等机构提供企业 AI 培训和咨询,并在十多所大学讲授 LLM 工程课程。
Yury Vashchylau 以制作软件和自动化系统为生,并将两者视为同一件事。早在智能体 AI 成为一个类别之前,他就已经在自托管服务栈之上开展工程工作。他相信,塑造优秀代码的原则同样塑造围绕代码构建的 AI 工具。他的工作涵盖银行基础设施、开源贡献、DIGITALBY 的消费级应用以及开发者工具。他在 yuryv.info 上写作,并对动画、电影制作、业务流程以及自动化系统如何随时间演变感兴趣。
前言
两年来,业界最关心的问题始终是:哪个模型最强?在当时,这是个正确的问题。但到了 2025 年的某个时候,格局发生了转变。前沿模型变得如此强大,彼此之间又如此接近,以至于原始模型质量不再是区分一个运转良好的系统和一个令人沮丧的系统之关键。真正区分它们的是模型周围的一切:你喂给它的上下文、你赋予它的工具、你运行它的环境,以及你施加于它的护栏。这种围绕模型的结构在本书中有一个名字:Harness(驾驭框架)。这些篇章的核心论点说起来简单,实践起来却要求极高——智能体等于模型加 Harness,而一旦模型被商品化,Harness 才是工程所在之处。
Claude Code 是当今这一理念最清晰的化身。从表面看,它是一个命令行编码助手。在底层,它是一个完整、可检视的 Harness:CLAUDE.md 注入上下文,Skills 和子智能体扩展能力,Hooks 和权限强制实施控制,而无头模式、Agent SDK 和插件将这一切带入真实的执行环境。本书逐一拆解 Claude Code 的各个机制,不是为了赞叹它,而是为了传授底层的方法论,这样你所学到的东西就能迁移到你构建的任何智能体、任何框架中——即便在具体工具早已更迭之后依然如此。
这是一本动手实践的工程书,而非综述。每一个机制都通过一个具体问题引入,用真实代码实践,并一路推进,直到它要么站得住脚,要么暴露出自身的局限。各章层层递进:前面的章节建立 Harness 的四个层次——上下文、工具、执行和治理——后面的章节将它们组合成无头流水线、自定义 SDK 智能体、可共享的插件,最后是让整个组织能够以这种方式工作而不陷入混乱的团队实践。
关于书中的人物,有一点说明。贯穿全书,你会在简短对话中遇到三位反复出现的角色。小冰是一位将 Claude Code 应用于真实项目的工程师;小雪带来数据分析的视角,提出实践者真正会遇到的问题;Kage 则是资深技术导师,帮助他们推理架构决策。他们不是装饰——每一段对话都铺陈出你自己将会面临的一种设计张力,而随后的章节会用代码来解决它。
这个领域的工具发展迅速,本书中的一些具体细节将会过时。但机制不会。注入仍然是注入,上下文窗口仍然会被填满,而在智能体可以感知什么和可以做什么之间划定一条清晰的边界,仍然是一个你可以信任的系统和一个你无法信任的系统之间的区别。我的目标是,当你读完本书时,你不仅能知道如何操作 Claude Code,还能知道如何思考任何智能体底层的 Harness,以及如何构建一个值得信任的 Harness。
本书的读者对象
本书面向软件工程师、技术架构师和工程负责人,他们使用过 AI 编码助手,现在想要认真、可靠、大规模地、以团队的方式用 AI 进行构建。如果你运行过 Claude Code 或类似的工具,既感受到了它的强大,也感受到了它的粗糙之处,并且想要足够深入地理解这套机制,从而去塑造它而非与之抗争,那么这本书就是为你而写的。书中假定你熟悉命令行、Git 和至少一种编程语言(示例主要使用 Python、JavaScript/TypeScript 和 shell)。你不需要有智能体框架或 LLM 内部原理方面的经验;本书会从头开始逐步构建这些概念。
本书涵盖的内容
第 1 章,Claude Code 作为智能体框架:技术架构概览,确立了本书的核心视角——智能体等于模型加 Harness——并勾勒出本书其余部分将要填充的四个层次(上下文、工具、执行和治理)。
第 2 章,以史为鉴:记忆系统的工程实践,考察 Claude Code 如何通过 CLAUDE.md 层级结构及其记忆作用域来管理上下文,以及如何保持上下文精简、分层并以正确的顺序加载。
第 3 章,授人以渔:可复用 Skills 的工程化,介绍 Skills——在 SKILL.md 中定义的声明式能力包——并展示如何设计、界定作用域和触发它们,使 Claude 在正确的时刻调用正确的能力。
第 4 章,分而治之:子智能体与任务委派的艺术,涵盖子智能体和上下文隔离:如何分解工作、将其委派给专注的智能体,并确定性地聚合结果。
第 5 章,从准则到护栏:用 Hooks 实现自动化控制,使用事件驱动的 Hooks 机制将软性准则转化为强制执行的护栏,包括钩子如何在危险操作运行之前将其阻止。
第 6 章,连接一切:用 MCP 集成外部工具,通过模型上下文协议(Model Context Protocol)将 Claude Code 向外部世界开放,安全地连接外部工具、数据源和凭据。
第 7 章,无头模式与 CI/CD 集成,将 Claude Code 从交互式终端带入自动化:无头调用、预算和轮次限制,以及在 GitHub Actions、GitLab 和 Jenkins 上的完整 CI/CD 流水线。
第 8 章,以 Claude 为引擎构建:Agent SDK 智能体开发工具包,从通过参数驱动 Claude 转向在代码中编排它——使用 @tool 装饰器自定义工具、结构化输出、权限层,以及一个完整的基于 SDK 的服务。
第 9 章,从个人技艺到共享资产:插件生态,将 Skills、子智能体、Hooks 和 MCP 打包成可分发的插件,并展示私有市场如何将一位工程师的配置变成团队标准。
第 10 章,从个人到团队:Claude Code 的工程实践,在组织规模上处理治理层——成本、调试、安全、扩展、指令和协作——使整个团队能够以这种方式工作而不陷入混乱。
后记,刀之道,回到本书的指导隐喻和 Harness 论题,并指向本书所连接更广泛的方法论和设计模式工作。
如何充分利用本书
要跟随书中的示例,你需要一个可用的 Claude Code 安装和对 Claude 的访问权限(一个 Anthropic API 密钥或等效的 Claude 订阅)。需要较新的 Node.js 运行时,因为 Claude Code 运行在 Node 上;示例中贯穿使用了 Python 3.10+ 和 Git。本书假定你熟悉命令行和代码编辑器。其他一切——Skills、子智能体、Hooks、MCP 服务器、Agent SDK——都会在需要时引入和搭建,因此你可以从一个干净的安装开始,逐步构建。
请将官方 Claude Code 文档与本书一起打开。机制是稳定的,但确切的标志、模型名称和定价会演变;当某个具体细节自出版以来已经发生变化时,文档是真相的来源。
下载示例代码文件
本书包含一个完整的可下载代码包,其中包含各章节中使用的所有示例项目和文件。我们建议下载该代码包,以便你能够顺利地跟随学习并对示例进行实验。
将代码包作为实用的起点。修改它、扩展它,并在阅读各章的过程中通过创建自己的变体来应用所学内容。
获取代码包
如果你直接从 Packt 购买了本书:
-
前往 packtpub.com
-
点击你的头像并选择你的订单
-
找到这本书并点击 Download Code
如果你是从 Amazon 或任何其他渠道购买的这本书:
-
访问 packtpub.com/unlock 或扫描以下二维码:
-
搜索这本书
-
注册或登录你的免费 Packt 账户
-
上传你的购买凭证并在本地下载代码包
使用说明: 你可以自由使用和修改这些代码,用于个人学习和非商业项目。
下载彩色图片
你的购买包含这本书的彩色、无 DRM 的 PDF 副本,非常适合查看彩色图片、截图和图表。请参阅 Preface 末尾的 Free benefits with your book section 来解锁你的 PDF 副本。
使用的约定
本书中使用了若干文本约定。
CodeInText:表示文本中的代码词、命令名、文件和目录名以及环境变量。例如:“CLAUDE.md 文件在每次会话开始时自动加载。”
代码块设置如下:
{
"hooks": {
"PreToolUse": [
{ "matcher": "Bash", "hooks": [ { "type": "command",
"command": "./check-bash.sh" } ] }
]
}
}
任何命令行输入或输出都写成如下形式:
claude -p "Review the code changes in this MR" --output-format json --max-turns 10
粗体:表示一个新术语、一个重要词或你在屏幕上看到的词。终端标签、斜杠命令和键组合会像这样出现在文本中。例如:“首先,进入你的 GitHub 仓库,然后点击 Settings | Secrets | Actions。”
警告或重要提示会像这样出现。
提示和技巧会像这样出现。
联系我们
读者的反馈始终欢迎。
一般反馈:如果你对本书的任何方面有疑问,或有任何一般性反馈,请发送电子邮件至 customercare@packt.com 并在邮件主题中提及书名。
勘误:尽管我们已尽一切努力确保内容的准确性,但错误仍会发生。如果你在本书中发现错误,我们将非常感谢你向我们报告。请访问 www.packt.com/submit-errata,点击 Submit Errata,并填写表格。
盗版:如果你在互联网上以任何形式遇到我们作品的非法副本,我们将非常感谢你提供位置地址或网站名称。请通过 copyright@packt.com 联系我们,并附上该材料的链接。
如果你有兴趣成为作者:如果你在某个主题上有专业知识,并且有兴趣撰写或参与一本书,请访问 authors.packt.com/。
本书的免费权益
本书包含旨在支持你的学习并帮助你有效应用所学内容的免费权益。立即激活它们以获得即时访问权限(请参阅 How to unlock 部分获取说明)。
以下是你可以通过购买立即解锁内容的快速概览:
如何解锁
扫描二维码(或访问 packtpub.com/unlock)。按名称搜索这本书,确认版本,然后按照页面上的步骤操作。
注意:请准备好你的发票。直接从 Packt 网站进行的购买不需要发票。
分享你的想法
一旦你阅读了 The Claude Code Operating Model,我们很想听听你的想法!扫描下方的二维码,直接前往这本书的 Amazon 评论页面并分享你的反馈。
你的评论对我们和科技社区都很重要,并将帮助我们确保我们提供高质量的内容。
1
第一章:Claude Code 作为 Agent 框架:技术架构概览
“我们塑造工具,此后工具塑造我们。”
—— Marshall McLuhan
最近,Xiaobing 领导了一个 AI Agent 项目,并选择 Claude Code 作为核心开发工具。起初,它的表现令人惊叹:只要需求表述清楚,代码就能快速生成,效率远超手动编码。然而,两周后,一系列问题突然爆发:每次新会话开始时,Claude 似乎都无法记住项目的技术栈(例如 FastAPI + SQLAlchemy),迫使开发者反复重述背景信息;生成的代码缺乏风格一致性,Black 格式标准应用不一致,导致三个 pull requests(PRs)在审查中被拒绝。更关键的是,在执行一个涉及六个文件的重构任务时,受上下文窗口容量限制,Claude 到第四个文件时已经“忘记”了前面的逻辑,导致输出代码不一致且不连贯。
“感觉就像每天都在管理一个失忆的实习生,”Xiaobing 向 Xiaoxue 和 Kage 抱怨道,“能力极强,但对项目上下文毫无记忆。”
Kage 没有急于安慰她,而是连续抛出三个问题:
第一,你在项目根目录中配置了 CLAUDE.md 吗?
第二,对于那个涉及六个文件的重构任务,你为什么不把它拆解给子代理协作处理?
第三,既然代码规范如此重要,为什么只依赖口头说明,而不把它们打包成一个 Skill,让模型自动加载?
Xiaobing 哑口无言,一个问题也答不上来。
“问题的根源不是 Claude 模型不够聪明,”Kage 指出,“而是你只使用了它的基本对话能力,因此只触及了它潜力的表面。事实上,Claude Code 本身就是一个完整的 Agent 框架,内置记忆系统、技能模块、子代理委派机制、事件钩子和外部工具协议。你遇到的每一个痛点,在框架层面都有相应的解决方案——只是你还不知道而已。”
这场对话持续了整整两个小时。接近尾声时,Xiaobing 感叹道:“我以为自己在驾驭一个 AI 助手,但实际上,我只是在使用一个花哨的聊天窗口。”
从命令行助手到代理框架
Xiaobing 遇到的问题:记忆丢失、风格漂移,以及长任务中的上下文溢出,几乎是每个将 Claude Code 应用于真实工程开发的人都会面临的瓶颈。这些现象表面上看起来是三个独立缺陷,但实际上,它们都指向同一个根本原因:把一个 Agent 框架误认为是一个简单的聊天工具。
Claude Code 的本质是:它是一个可编程、可扩展、可组合的 Agent 框架。
这不仅仅是营销噱头。这三个关键词对应着核心工程能力。
-
可编程:这意味着你可以直接用 Python 或 TypeScript 代码驱动它,将其无缝嵌入 CI/CD 流水线或自动化脚本中,完全解放人力资源,而无需人工终端监督
-
可扩展:这意味着你可以通过配置文件注入记忆模块、技能库和事件钩子等能力,而无需接触或修改核心代码
-
可组合:这意味着这些扩展模块可以像乐高积木一样灵活编排、自由组装,从而构建复杂而高效的工作流
综合起来,这三个方面勾勒出的不是一个单一工具,而是一个健壮的基础设施框架,是开发者构建自己的 AI 工作系统的基石。
Kage 生动地将 Claude Code 比作一座冰山,并画在了白板上,如图 1.1所示。
图 1.1:Claude Code 与冰山类比
图 1.1 Claude Code 就像一座冰山,许多核心功能隐藏在水面之下。水面之上只是冰山一角,对应着小冰的日常使用场景:终端对话、代码生成和命令执行。隐藏在水面之下的庞大基座,则是一系列精准解决小冰所遇挑战的关键技术架构。
-
CLAUDE.md:治愈“健忘症”问题,将项目规范一次性写入配置文件,之后每次会话自动加载,无需反复重述 -
Skills:终结风格漂移,将代码审查标准可配置化、制度化,彻底取代口头提醒的不确定性
-
Sub-agents:解决上下文溢出,将六文件重构任务拆分为六个独立的上下文单元,实现并行处理与逻辑隔离
-
Hooks:在工具调用时自动触发安全检查或日志记录,构建防御性编程机制
-
MCP(模型上下文协议):打破数据孤岛,赋予 Claude 调用外部数据库和 API 的能力
-
Headless 模式:支持在 CI/CD 流水线中无人值守运行,实现真正的自动化交付
-
Agent SDK:允许通过代码编排复杂的多步骤 Agent 工作流,增强任务执行的灵活性
-
Plugins 生态:将上述能力打包,便于团队内部高效分发和复用
“你遇到的每一个痛点,”Kage 指着冰山下方的庞大基座说,“这里都有对应的机制来解决它。问题不在于工具本身不够强大,而在于你还没有解锁它真正的潜力。现在,我希望你能退后一步,从全局视角审视 Claude Code,掌握它的全貌,释放它的真正力量。”
小冰听后反思道:“我之前的使用方式本质上就是低效的‘手动脚本’,反复给 Claude 喂同样的信息,手动拆解任务,靠肉眼检查风格;而框架化的方法则将这一切变为可配置、自动化的流程。”
Kage 点头确认:“正是如此。每次开始新对话,你都要重述技术栈;每次代码审查,你都要手动描述标准;每次代码提交都靠个人记忆来检查——所有这些都是低效的‘手动脚本’操作。框架化的方法是:将技术栈一劳永逸地固化在 CLAUDE.md 中;将审查标准打包成 Skill 自动加载;将提交检查配置为 Hooks 确保万无一失。”
这种从“逐步指令”到“系统配置”的范式转变,不仅极大提升了效率,更深刻重塑了人机协作的质量。配置一旦建立,就永远不会被遗忘,永远不会被忽视,永远不会因深夜加班而打折扣。这就是工程化的本质:将个人智慧提炼为制度标准。
接下来,我们将深入剖析这个框架的内部结构。
四层架构模型
在真正理解任何复杂系统之前,都需要一张清晰的“地图”。正如建筑师在施工前绘制蓝图,软件工程师在编码前确立架构,Claude Code 的完整技术栈也可以抽象为一个四层架构模型,如图 1.2所示。从下到上,这四层分别是:记忆层、扩展层、集成层和编程层。深入理解这四层的含义与边界,是掌握整个 Claude Code 系统的第一步。
图 1.2:Claude Code 的四层架构模型
Kage 生动地将这四层比作一栋摩天大楼。
-
记忆层的记忆系统是深埋地下的地基。没有这个地基,上面建造的一切都将随时面临坍塌的风险。
-
扩展层的四大扩展组件构成了建筑的主体楼层,承载着日常运行的核心功能,代表了用户最直接感知到的价值。
-
集成层的集成能力就像隐藏但至关重要的水电网络,将建筑与广阔的外部基础设施紧密连接,确保能量和信息的持续流动。
-
编程层的 Agent SDK 是顶楼的建筑师工作室。在这里,你不再只是住户,而是拥有设计新建筑和重构空间逻辑的最高权限。
“从下往上看是建造者的视角,关注地基和支撑;从上往下看是用户的视角,关注功能和体验,”Kage 强调。“这是一个值得记住的原则。”
记忆层:CLAUDE.md 系统
建筑的地基决定了整个结构的承载能力。Claude Code 的记忆层同样如此:它直接定义了 Claude 对项目“理解”的深度。
本质上,Claude 是一个无状态模型。每次新对话开始时,它对项目背景、技术栈选择、代码规范或团队约定一无所知。如果不做任何配置,开发者就必须反复重述“用 TypeScript 而不是 JavaScript”、“优先用 pnpm 而不是 npm”或“将 Vitest 设为测试框架”等基本设置。这种模式好比每天都要重新做一次自我介绍,显然极其低效。
记忆系统通过 CLAUDE.md 文件彻底解决了这一痛点。本质上,它是一份“AI 的员工手册”,在每次对话开始时自动加载到 Claude 的上下文中。更巧妙的是,这种记忆机制并非铁板一块,而是构建了一个五级记忆层次结构(见图 1.3),每一级对应不同的适用范围。
图 1.3:Claude Code 的五级记忆系统
这种分层设计背后的工程哲学与 CSS 中的层叠优先级机制,或软件配置中的四级覆盖模型——“全局–用户–项目–本地”非常相似:每一级都可以覆盖上一级的设置,层级越具体(如本地),优先级越高。
一个典型的项目级 CLAUDE.md 文件如下:
# Project Memory CLAUDE.md
## Tech Stack
- Language: TypeScript 5.x (strict mode enabled)
- Framework: Fastify + Prisma
- Testing: Vitest (all public functions must include unit tests)
- Package Management: pnpm (npm or yarn are prohibited)
## Code Standards
- Component Style: Prefer functional components; class components are forbidden
- Error Handling: Always return using the Result type; throwing exceptions directly is strictly prohibited
- Commit Convention: Follow the <type>(<scope>): <description> format
## Common Commands
- pnpm dev — Start the development server
- pnpm test — Run the test suite
- pnpm lint — Run code linting
有了 CLAUDE.md 文件,Claude 每次对话开始都会自动“研读说明书”,从而杜绝技术栈误用和代码风格靠猜。正如小雪所说:“自从我们创建了 CLAUDE.md 文件,我再也不用在每次对话时反复提醒 Claude‘我们用的是 pnpm,不是 npm’了。”
这个看似简单的机制,实际上是整个框架的基石。所有上层配置和行为——无论是 Skills、Commands 还是 Hooks——都建立在 Claude 对项目上下文的精确理解之上。正如建筑的地基可能不如外观装饰那样引人注目,但没有了地基,一切装饰都将无所依附。第 2 章将深入剖析这个看似平淡却至关重要的记忆系统。
扩展层:四大扩展组件
如果说记忆层是地基,那么扩展层就是建筑的主体结构——它赋予了 Claude 在日常使用中最丰富的能力。这一层由四大组件构成:Commands(斜杠命令)、Skills、SubAgents 和 Hooks。它们各自独立运作,又能灵活组合。
其中,Commands 是最直观的扩展方式。当你在终端输入 /review、/commit 或 /deploy 这样的命令时,Claude 会按照预定义的模板执行标准化的工作流程。本质上,这是将高频、固定步骤的操作封装成“一键式”快捷方式——就像智能手机上的快捷指令,轻点一下便能触发一系列预设动作。
从设计模式的角度看,Commands 是命令模式(Command Pattern)的教科书级应用:它将请求封装为对象,使得客户端可以用参数化的方式处理不同的请求。命令定义文件存放在 .claude/commands/ 目录下,每个 Markdown 文件代表一个独立命令。例如,一个名为 review.md 的文件里可能写着代码审查的检查清单和输出格式要求,输入 /review 就能让 Claude 严格按照清单逐项审查当前代码。
Kage 的笔记
在当前的 Claude Code 中,自定义命令通过 Skills 系统实现。本章仍将 Commands 单独命名,作为一种概念上的触发模式:手动调用的斜杠工作流,与语义触发的 Skills 相对。
Skills 则走着一条完全不同的设计路线。Skills 位于 .claude/skills/<skill‑name>/SKILL.md(旧版的 .claude/commands/ 位置仍然可用);子代理定义位于 .claude/agents/<agent‑name>.md. 它们不需要用户手动触发,而是由 Claude 根据当前任务的语义上下文自动判断并加载相关技能。每个 Skill 本质上是一个包含 SKILL.md 文件的目录。在这个文件中,通过 YAML Frontmatter(顶部的元数据)声明技能的名称、描述和允许使用的工具列表。Claude 根据 description 字段的内容来动态决定“当前任务是否需要激活这个 Skill”。这种隐式触发机制使 Skills 成为领域知识的理想载体——无论是财务分析方法、API 设计规范,还是某个特定框架的最佳实践,都可以封装其中。
例如,当你和 Claude 讨论财务指标时,它会自动加载“财务 Skill”;而一旦话题转向代码架构,那个 Skill 就会悄然退场。这种“按需加载、闲时沉默”的机制,极大提升了交互的流畅性和智能感。
下面是一个典型的 SKILL.md 示例。
---
name: code-reviewing
description: >
Review code for best practices and potential issues.
Use when the user asks for code review or mentions
reviewing changes.
allowed-tools:
- Read
- Grep
- Glob
---
# Code Review Guidelines
You are a professional code reviewer...
Sub-agent 的设计则针对一个更深层的瓶颈:上下文窗口的限制。
Claude 的上下文窗口就像一张固定大小的桌面:工作空间有限,文件堆得越多就越杂乱。当一个任务涉及海量文件时(例如审查整个 PR 的所有代码变更),把所有细节都塞进主对话的上下文中,很快就会出现“桌面溢出”,导致 Claude 顾此失彼,甚至遗漏关键信息。
Sub-agent 的解决思路是为特定任务开辟一个独立的上下文空间——这相当于在主桌旁边新开一张工作台,派一位专员在那里处理子任务。任务完成后,只需把结论(一份简洁的报告)带回主桌,而不必把所有工作草稿都搬过来。这很像管理者向下属委派任务:管理者无需逐行查看代码,只需审阅审查结论和改进建议。
Sub-agent 定义文件位于 .claude/agents/ 目录下,每个 Markdown 文件详细描述一个子代理的角色、权限范围和行事准则。更重要的是,你可以为子代理设置严格的工具权限——例如规定“代码审查员”只拥有读取文件的权限,严禁进行任何修改操作。这种设计有力地体现了 AI Agent 架构中“最小权限原则”(Principle of Least Privilege)的核心思想。
Hooks 是四大模块中唯一具备“拦截”能力的组件。如果说 Commands 定义了 Claude“做什么”,Skills 指导 Claude“怎么做”,那么 Hooks 则决定 Claude“能不能做”。
它们在特定的事件节点自动触发,最常用的 hook 包括工具调用前(PreToolUse)、工具调用后(PostToolUse)以及响应生成结束前(Stop)。完整的事件列表记录在 Claude Code hooks 参考文档中。开发者可以在这些关键时刻插入检查、拦截或增强逻辑。这种机制与 Web 框架中的中间件(middleware)概念如出一辙。
例如,通过在 .claude/settings.json 中配置一个 Hook,可以实现这样的效果:每当 Claude 尝试执行 git commit 时,自动运行一次 lint 检查;如果检查不通过,则直接阻止这次提交操作。这种“隐形守护者”的角色,使 Hooks 成为保障代码质量和安全合规的利器。
下面是一个典型的配置示例。
{
"hooks": {
"PreToolUse": [
{
"matcher": "Bash",
"hooks": [
{
"type": "command",
"command": "python .claude/hooks/safety_check.py"
}
]
}
]
}
}
上述配置的含义是这样的:每当 Claude 即将调用 Bash 工具时,safety_check.py 脚本会先行运行。注意这个条目的结构——一个 matcher 搭配一个 hooks 数组,每个元素声明自己的 type 和 command。这里没有“blocking”字段;hook 通过以退出码 2 退出来阻止工具调用,而它写入 stderr 的内容会作为原因反馈给 Claude。第 5 章将完整介绍这一约定。
这种事件驱动的守护机制在软件工程中有成熟的对应物——无论是 Git Hooks、数据库触发器,还是消息队列的消费者,它们的本质都遵循同一个模式:当特定事件发生时,自动执行预设逻辑。
这四大组件共同构成了 Claude Code 可扩展性的核心基础。需要强调的是,它们是正交的:既支持独立学习和单独使用,也能灵活组合,构建出更强大的工作流。
Claude Code 的四层架构
这种正交设计紧密遵循软件工程中的单一职责原则(SRP):每个组件专注于解决某一类特定问题(“做好一件事”),但通过有机组合,便能释放出看似无穷能力的系统。
Kage 的笔记
在初学阶段,不要急于一次性掌握全部四个组件。建议遵循以下循序渐进的学习路径:首先,编写一份扎实的 CLAUDE.md 文件;接着,学习 Commands,这是扩展功能最直观的方式;然后,掌握 Skills,体验语义自动触发的魔力;之后,引入 Hooks,建立安全与质量保障机制;最后,挑战子代理,去应对大规模复杂任务。每掌握一个组件,务必在真实项目中实践两周,再进入下一阶段。毕竟,“贪多嚼不烂”这句话在这里同样适用。
集成层:连接外部世界
在四层架构这座摩天大楼中,集成层就像维持其运转的水网与电网——它将 Claude Code 的核心能力延伸到外部系统,使其真正融入开发生态。
其中,Headless 是关键。它使 Claude Code 能够在无人值守环境中自动运行,摆脱交互式终端。通过 ‑p 参数传入任务描述,并用 ‑‑output‑format json 指定输出格式,Claude Code 可以无缝嵌入任何 CI/CD 流水线,例如 GitHub Actions、Jenkins 或 GitLab CI。
一个典型用例是自动化 PR 审查:每当开发者提交 Pull Request 时,CI 流水线会自动调用 Claude Code 进行代码审查,并将结果直接写回 PR 页面作为评论。整个过程无需人工干预,真正实现了“无人值守”的智能协作。
下面是在 CI/CD 流水线中调用 Claude Code 的示例命令。
# Invoke Claude Code in a CI/CD pipeline
claude -p "Review the most recent code changes, focusing on security risks and performance issues" \
--output-format json \
--max-turns 10 \
--allowedTools Read,Grep,Glob
上述命令中的每个参数都带有明确的工程意图:‑p 激活 Headless 模式以实现非交互式运行;‑‑output‑format json 确保输出可被脚本自动解析;‑‑max‑turns 通过限制最大交互轮数来精确控制成本;‑‑allowedTools 则使用白名单机制严格限制 Claude 可调用的工具范围,从而建立强大的安全屏障。
而 MCP 则解锁了另一个集成维度——它让 Claude 能够与外部工具和数据源深度交互。如果说 Headless 让 Claude 能够“走出去”并融入流水线,那么 MCP 就是让外部能力“走进来”并为模型赋能。
你只需在项目根目录的 .mcp.json 文件中配置 MCP 服务器,就能轻松扩展 Claude 的能力边界:无论是访问数据库、调用第三方 API、操作 GitHub Issues,还是查询 Jira 工单,都可以通过一次配置无缝连接。Anthropic 将 MCP 生动地描述为“AI 时代的 USB-C”——一种标准化接口协议,使任何工具或数据源都能以统一、规范的方式集成到 Claude Code 生态中。
下面是一个 GitHub MCP 服务器的示例配置。
{
"mcpServers": {
"github": {
"command": "npx",
"args": ["-y", "@modelcontextprotocol/server-github"],
"env": {
"GITHUB_TOKEN": "your-token-here"
}
}
}
}
MCP 背后的设计理念值得深入思考。在传统的 AI 工具集成中,接入每一个新的外部系统往往都需要编写大量定制适配代码。而 MCP 则通过定义一套标准化协议(涵盖 Tools、Resources 和 Prompts 三项核心能力),实现了工具提供方与 AI 使用方之间的“接口统一”。这让人联想到 REST API 在 Web 时代对前后端通信统一所产生的变革性影响——标准化并不会带来限制,反而会催生繁荣的生态。
Headless 与 MCP 共同构成了集成层的两大支柱。
-
Headless 面向自动化流水线,使 Claude Code 能够无缝嵌入现有 CI/CD 系统
-
MCP 面向工具生态,将外部数据和服务纳入 Claude Code 的能力工具箱
二者共同推动 Claude Code 从独立的终端工具,演进为可灵活集成到任何技术栈中的基础组件。如果说扩展层是在“内部”强化 Claude Code 的核心功能,那么集成层就是“外部”构建连接网络——二者相辅相成,缺一不可。
编程层:Agent SDK
摩天大楼的顶层是建筑师的工作室——在这里,你不再只是住户,而是设计新蓝图的人。
Agent SDK 位于 Claude Code 技术栈的顶端,也是一个关键的“分水岭”。在下面三层(记忆、扩展和集成)中,开发者主要通过配置文件和命令行操作来扩展 Claude 的行为边界,本质上仍是使用者。但一旦跨过 Agent SDK 的门槛,你就正式进入了构建者的领域:开发者可以使用 Python 或 TypeScript 编写代码,直接调用 Claude Code 的核心能力,从零构建全新的 AI Agent。
下面是使用 Agent SDK 构建代码健康检查 Agent 的示例。
import asyncio
from claude_agent_sdk import query, ClaudeAgentOptions,
AssistantMessage, ResultMessage
async def main():
options = ClaudeAgentOptions(
allowed_tools=["Read", "Grep", "Glob"],
max_turns=15,
)
async for message in query(
prompt="Analyze the code quality of all Python files
under src/ and provide a health score.",
options=options,
):
if isinstance(message, AssistantMessage):
for block in message.content:
if hasattr(block, "text"):
print(block.text)
elif isinstance(message, ResultMessage):
print(f"\n[done] cost=${message.total_cost_usd}")
asyncio.run(main())
上述代码更深层的意义在于:开发者不再局限于 Claude Code 的终端界面,而是可以在自己的应用中直接驱动 Claude 执行任务。这意味着 Claude 的分析与推理能力可以无缝嵌入任何场景——定时任务、Web 服务、数据处理流水线——只要你的代码能够到达,Claude 的能力就能延伸过去。
对绝大多数开发者而言,前三层(记忆、扩展、集成)已足以轻松应对日常开发场景。然而,如果你的愿景是构建团队级 AI 开发平台,或设计多代理协作自动化系统,那么 Agent SDK 就是必经之路。
借助 Agent SDK,你可以构建批量代码审查工具、项目健康仪表盘、自动化测试报告生成器,甚至将多个 Claude Agent 编排成高效协作团队。例如,第一个 Agent 专门负责读代码,第二个专门负责写测试,第三个专门负责审查,共同组成一条全自动的智能流水线。
Agent SDK 的存在还揭示了一个有趣的事实:Claude Code 和 Agent SDK 运行着相同的智能体循环、工具和上下文管理。SDK 将这套运行时打包为库,使开发者能够将驱动 Claude Code 的同一套 harness 嵌入到自己的应用中。 你在终端中看到的一切——读取文件、编写代码、执行命令——本质上都是 Agent SDK 层面的一次工具调用。一旦理解了这一点,你对 Claude Code 的认知将从“一个产品”提升为“一种架构模式的具体实现”。
在后续章节中,我们将深入探讨 Agent SDK 的实际应用。现在,建立一个核心认知至关重要:Agent SDK 是这座架构大厦的顶峰,也标志着从“配置驱动”到“代码驱动”开发方式飞跃的起点。
底层视角:harness 与智能体循环
理解了四层架构的“外部视角”后,让我们深入探讨一个更基础的概念:Harness。
Anthropic 的官方文档给出了一个简洁的定义:“Claude Code 是围绕 Claude 的智能体 harness:它提供了工具、上下文管理和执行环境,将语言模型转变为有能力的编码智能体。”
简而言之,Claude Code 是包裹在 Claude 模型外层的智能编排框架。原生模型只能生成文本。是 Harness 赋予了它读取文件、编写代码、检索代码库和在终端中执行命令的“手脚”。没有 Harness,Claude 只是一个有智能但无法行动的“大脑”。
“harness”的原意是套在马身上的挽具和缰绳。马虽然有力量,但没有挽具的引导,就无法拉动车辆。挽具并不改变马本身的力量,而是改变了力量的传递和控制方式。
用公式表示:Agent = Model + Harness。
如果模型是引擎,那么 Harness 就是围绕它构建的所有基础设施:工具系统、权限控制、上下文管理、会话持久化、事件钩子,以及驱动这一切的核心循环:智能体循环。
图 1.4:智能体循环——Harness 的核心
这种循环机制深刻揭示了 Claude Code 核心能力的来源。当你提交一个 bug 时,它不会简单地“看一眼就猜答案”。相反,它会经历一个观察、假设和验证的反复过程:先查阅错误日志,然后搜索相关代码,深入理解上下文,然后才着手修复问题。
循环何时终止?取决于两个条件:第一,模型主动停止(即判断任务完成,不再发起工具调用);第二,达到最大轮次(由 --max-turns 参数设置以防止无限循环)。
最近的基准测试结果使这一点更加具体:即使底层模型保持不变,改变 harness 也能显著改变智能体的性能(www.langchain.com/blog/improving-deep-agents-with-harness-engineering)。
在 TerminalBench 基准测试中,仅仅优化 Harness 就使同一模型在 Terminal-Bench 2.0 上从第 30 名跃升至前 5 名(52.8% → 66.5%,提升了 13.7 个百分点)。换句话说,Harness 比模型本身更重要。你所学到的四层架构中的每一个环节——无论是编写 CLAUDE.md、设置工具权限、集成 hooks,还是连接 MCP——本质上都是对 Harness 的精心打磨。
听到这里,小冰恍然大悟:“我以前以为 Claude Code 只是 Claude 模型的一个外壳。原来,这个‘外壳’才是它真正价值所在。”
组件关系与协作
深入理解四层架构中每个组件之后,更关键的问题是:它们如何协同工作?在不同场景下应该如何选择?一个真实的任务是如何流经这个系统的?
触发机制对比
四大扩展组件中最容易混淆的是它们的触发机制。表 1.1 从五个维度对它们进行了比较。
| 触发方式 || 命令 || 技能 || 人工或 AI || 钩子 |
| --- | --- | --- | --- | --- |
| 是否需要记忆? || 是(需要知道命令名称) || 金融分析、API 设计 || 是(需要知道智能体名称) || 否(配置后即生效) |
| 典型场景 || CLI 命令 || AI || 代码审查、日志分析 || 提交前检查、保存后格式化 |
| 工程类比 || Claude 根据语义自动匹配 || 策略模式(自动选择算法) || 线程池(隔离执行) || 中间件/Git Hooks |
| 用户手动输入 || /review、/deploy || 子智能体 || 系统事件自动触发 || 应用场景 |
| 人工 || 否(自动发现) || 用户指定或 Claude 主动委托 || 系统 || 推荐组件 |
表 1.1:四大扩展组件对比
一个直观的记忆口诀如下:
-
命令:“你告诉它做什么”(响应用户指令)
-
技能:“它自己知道做什么”(自主判断并执行)
-
子智能体:“它把任务委托给别人”(协调子智能体完成任务)
-
钩子:“无论谁做,这一步都执行检查”(在特定工作流节点自动拦截或处理)
读完上述总结,小学颇有见地地指出:“命令和钩子都是确定性触发——前者由用户命令显式触发,后者由特定事件自动触发;而技能和子智能体则涉及 AI 的自主判断——前者在 AI 认为必要时启用,后者在 AI 决定委托任务时启用。”
Kage 赞赏地点了点头:“这种‘确定性 vs. AI 判断’的二分法确实是理解四大扩展组件差异的另一个关键视角。在工程实践中,对于安全性要求极高的场景(如敏感信息拦截),应优先使用确定性的钩子;对于需要更大灵活性的场景(如领域知识匹配),由 AI 判断触发的技能更为合适。”
数据流:一个请求的旅程
为了更直观地理解各组件的协作机制,让我们追踪一个请求在 Claude Code 系统中的完整旅程。
假设开发者在终端中输入命令:“帮我审查 src/payment/ 目录中最近的代码变更,确保没有安全风险。”
Claude Code 的处理流程如图 1.5所示。
图 1.5:Claude Code 的处理流程
在图 1.5所示的过程中,记忆层和扩展层中的每个组件都发挥着各自的作用:记忆层(CLAUDE.md)构建项目上下文,技能注入领域知识,子智能体提供隔离的执行环境,钩子严格把守质量检查关口。整个过程无需用户额外干预——一切都在用户输入那条自然语言命令后自动编排完成。
这正是“可组合性”的精髓所在。每个组件都像一个独立的积木,组合起来便形成了一条完整的自动化流水线。这与软件工程中经典的“关注点分离”原则完美契合:每个模块专注于单一职责,通过清晰的接口协作。Claude Code 的组件设计正是这一原则的典范。
-
CLAUDE.md专注于“知道做什么” -
Skills 专注于“知道怎么做”
-
Sub-agents 专注于“谁来做”
-
Hooks 专注于“安全护栏”
正是因为这些清晰的职责边界,这些组件才能自由组合而不互相干扰。
值得注意的是,上面的示例展示的是一个“全家桶”式的协作场景。在实际工程实践中,大多数任务并不需要所有组件:简单的代码生成可能只需要 memory 和 Skills 的配合,而日常的 commit 操作可能只涉及 Hooks。组件的核心价值不在于“全部用上”,而在于“按需调用,随时可用”。
Plugins:组合的打包与分发
“小冰,你曾经问我:‘Skills 和 Plugins 到底是什么关系?’” Kage 在白板上画了一个大盒子,然后揭晓了答案:“很简单——Plugins 不是一种新能力,而是一种打包机制。”
想象一下,你花了三周时间为团队精心打造了一套 Claude Code 扩展体系:包含两个 Skills(代码审查、API 设计)、一个 sub-agent(安全审计员)、三个 Hooks(提交前 lint 检查、保存后格式化、敏感信息拦截)。现在,一位新同事加入,急需复用这套配置。如果靠手动复制文件,光搞清楚“哪些文件放哪个目录”就得花上半天。
Plugins 机制优雅地解决了这个问题。它本质上是一种标准化的打包格式:通过一个 plugin.json 清单文件,将 Skills、Commands、sub-agents、Hooks 和 MCP 配置统一封装在一起。打包完成后,一条安装命令即可自动将所有配置部署到位。
这就好比 npm 之于 Node.js、Docker 镜像之于容器——Plugins 的核心价值在于分发和复用,而非创造新的能力维度。
厘清这个概念至关重要。初学者常误以为 Plugins 是某种“更高级的 Skills”,但实际上两者处于完全不同的维度:Skills 定义的是能力类型,而 Plugins 定义的是分发形式。
Plugin 就像一个容器,能够将 Skills、Commands、Hooks、sub-agents 等组件封装在一起。它的核心关注点不是“执行什么任务”,而是“如何打包和分享”。
对于个人开发者而言,可能无需刻意创建 Plugins,在项目中本地配置组件即可。
但对于团队负责人来说,Plugins 则是标准化最佳实践、实现新成员一键配置的强大工具。
技术选型指南
面对多种多样的组件,一个核心问题随之而来:针对你的具体需求,应该选择哪一个?
为了帮助你快速判断,这里提供了 Claude Code 组件选型决策树(见图 1.6)和应用场景对照表(见表 1.2)。
图 1.6:Claude Code 组件选型决策树
| 核心原因 || 每次发布执行固定的检查清单 || 步骤清晰且固定,适合通过手动命令一键触发 |
| --- | --- | --- |
| 讨论财务问题时自动获得专业指导 || Commands || 基于语义自动匹配领域知识并按需加载;用户无需手动指定或记忆命令 |
| --- | --- | --- |
| 审查大型 PR 以避免上下文溢出 || Skills || Sub-agent |
| 使用独立的 sub-agent 隔离上下文,仅向主会话返回简洁结论,有效管理 token 消耗 || 在代码提交前自动拦截敏感信息泄露 || 事件驱动机制确保在特定操作(如工具调用)前强制执行拦截和检查,无一遗漏 |
| PR 提交后自动触发代码审查 || Hooks(PreToolUse) || 适合无人值守环境,可嵌入 CI/CD 流水线,通过命令自动执行审查任务 |
| 让 Claude 操作 GitHub Issues || Headless Commands || 通过标准协议无缝连接外部系统(如 GitHub API),扩展模型的工具边界 |
| 文件类型 || MCP || 路径 |
表 1.2:Claude Code 组件选型应用场景对照表
对于决策树,请按照以下自问路径进行。首先,问自己:“这个任务是如何触发的?”如果需要人工发起,继续问:“逻辑有多复杂?”如果步骤固定,选择 Commands;如果需要 Claude 进行判断,选择 Skills。如果由 Claude 自动触发,则问:“是在特定事件节点触发,还是在 CI/CD 流水线中触发?”如果是事件节点,选择 Hooks;如果在 CI/CD 流水线中,选择 Headless 模式。接下来,问自己:“运行环境是什么?”如果任务负载较重或需要上下文隔离,加入 sub-agents。如果需要访问外部系统(如工具或数据),加入 MCP。如果需要代码级的编程控制,使用 Agent SDK。
需要注意的是,这些组件通常是组合使用,而非互斥选择。
一个成熟的团队配置通常会协调所有组件,构建一个稳健的自动化体系。
-
CLAUDE.md文件奠定基础上下文 -
Skills 注入领域专业知识
-
Commands 为手动操作提供标准化入口
-
Hooks 构建自动化安全防线
-
Sub-agents 分解并处理高度复杂的任务
-
MCP 打破与外部系统的数据壁垒
-
Headless 模式将能力无缝集成到 CI/CD 流水线中
这就像一家高效的企业:每个角色(组件)都有清晰的职责和边界,但它们紧密协作以实现最终目标。
Kage 的笔记
技术选型的核心原则始终是“用最简单的方案解决当前的问题”。不要陷入“手里有锤子,看什么都是钉子”的陷阱:不要因为学会了 sub-agents 就把每个任务都委托出去,也不要因为掌握了 Hooks 就给每个细微操作都加上护栏。过度工程和工程不足同样有害。优秀的架构师懂得平衡的艺术:知道何时引入抽象层以增强可扩展性,也知道何时一个简单的 CLAUDE.md 文件就是完美的解决方案。
小结
本章从一个关键的视角转变开始:Claude Code 不是 ChatGPT 的命令行版本,而是一个可编程、可扩展、可组合的 Agent 框架。对于 Claude Code 而言,水线之上的对话界面只是入口;真正的技术深度隐藏在水面之下——在记忆系统、四大扩展组件、集成机制和 Agent SDK 中。理解这一点,是从“被动使用”迈向“主动编排”的第一步。
四层架构为整个系统提供了一张清晰的蓝图。记忆层是地基,让 Claude Code 能够理解项目上下文;扩展层是主体,提供 Commands、Skills、sub-agents 和 Hooks 四种正交的扩展方式;集成层是管道,通过 Headless 和 MCP 连接外部世界;编程层是顶层,让开发者从使用者走向构建者。这四层既层层递进,也可以独立学习——你不需要一次性掌握所有内容才能开始实践。
理清组件之间的关系,是本章要内化的核心知识。Commands 是显式指令,Skills 是隐式知识,sub-agents 是隔离委派,Hooks 是自动守护。这四种触发机制覆盖了从手动干预到自动执行、从显式调用到隐式响应的完整光谱。它们既可以独立运作,也可以组合编排。而 Plugins 作为标准化封装机制,让这些组合能够被高效分发和复用。
在第 2 章中,我们将深入四层架构的基石——记忆系统(CLAUDE.md 文件)。它既是整栋建筑的地基,也是实践 Claude Code 框架能力的最佳起点。一份精心编写的 CLAUDE.md 文件,胜过十次冗余的口头解释。
思考题
-
回顾你目前使用 Claude Code(或其他 AI 编程工具)的习惯:哪些操作还停留在"冰山之上"的被动交互层?如果引入本章描述的组件,哪些步骤可以被自动化或结构化重构?
-
在你团队的日常开发流程中,哪些步骤最适合通过 Hooks 实现自动守护(如代码规范检查、敏感信息拦截)?哪些步骤更适合固化为 Commands 以供显式调用?列出 3–5 个具体场景,并为每个场景匹配最合适的组件。
-
本章指出 Claude Code 的四大扩展组件遵循"单一职责原则"。深入思考:如果将 Skills 和 Commands 合并为一个组件(同时支持手动触发和自动响应),会带来哪些便利?又可能产生哪些潜在问题?这一设计体现了软件设计中"简单性"与"正交性"之间的经典权衡。
第二章:以史为鉴:记忆系统的工程实践
"那些不能记住过去的人,注定要重蹈覆辙。"
—— 乔治·桑塔亚那
上次技术讨论结束后,小冰迫不及待地在她负责的订单服务项目中尝试 Claude Code。她兴致勃勃地输入了第一个请求:"帮我写一个用户登录 API。"几秒钟后,Claude 生成了一段看起来十分完美的代码:基于 Express 框架,使用 JavaScript 语法,甚至还附带了 npm install 命令,一气呵成。小冰盯着屏幕看了三秒,才慢慢打出下一行字:"我们项目用的是 Fastify 和 TypeScript……"她随后耐心地纠正了模型的约束条件,重新陈述了需求,最终才得到了符合预期的代码。
第二天,小冰关掉终端,开启了一个全新的会话,让 Claude 编写一个订单创建 API。这一次,Claude 更加热情,事无巨细地生成了一整套路由、控制器和数据模型。然而,框架依然是 Express,包管理器依然是 npm,甚至目录结构都与团队规范大相径庭。盯着屏幕上那行熟悉的 const express = require('express'),小冰感到一种深深的无力感在心底涌起。
这种"AI 失忆症"并非源于 Claude 能力的欠缺。恰恰相反,它在每一个独立会话中都展现出卓越的编程能力。然而,它所做的每一个看似"合理"的选择——选择 Express 而非 Fastify,选择 npm 而非 pnpm,选择 JavaScript 而非 TypeScript——都无一例外地触碰了团队的标准。
为什么 AI 需要"记忆"
沮丧的小冰去找 Kage。听完她的经历后,Kage 并没有急于给出解决方案。
"小冰,你还记得第一天上班时的感受吗?"Kage 问道。
小冰想了想。"当然记得。我什么都不懂——代码仓库在哪、分支策略是什么、CI 流程怎么走……什么都得问同事。"
"没错。现在想象一下,如果你每天早上醒来,都忘记了前一天在公司学到的一切,每一天都像是 ' 入职第一天'。 你会怎么办?"
小冰打了个寒颤。"这不就是现在使用 Claude Code 的感觉吗?"
"正是如此,"Kage 解释道。"对 Claude 来说,每一次对话都是它的'入职第一天'(见图 2.1)。它就像一个技术过硬的新员工,第一天上班时对公司的技术栈一无所知,只能根据个人经验和行业惯例来猜测。猜测或许合乎逻辑,但未必准确。*"
图 2.1:每一次对话都是 Claude 的"入职第一天"。
这是大模型的一个根本特征:会话之间缺乏持久状态。每次你关闭 Claude Code 会话并开启一个新的会话,Claude 模型面对的都是完全空白的白板。它不记得你的项目使用什么框架、团队偏好的代码风格,甚至不记得你五分钟前纠正过的错误。这不是某个特定模型的缺陷,而是当前所有大模型的共同特征——每一次对话都必须从零开始构建上下文。
从软件工程的角度来看,这与"约定优于配置"原则恰好相反。Ruby on Rails 之所以能赋予开发者高效能,正是因为其一套合理的默认约定:数据库表名用复数、模型名用单数、控制器放在 app/controllers 目录下,开发者只需关注约定之外的例外情况。
然而,Claude 默认的"约定"并非来自项目规范,而是来自它的训练数据——互联网上所有公开代码的统计规律。在这个分布中,Express 的出现频率高于 Fastify,npm 比 pnpm 更常见,JavaScript 样本数量远超 TypeScript。因此,在缺乏具体项目上下文时,Claude 会自然地倾向于最"主流"的方案。这些选择在通用场景下或许合理,但未必契合你团队的具体规范。
换句话说,Claude 缺的不是能力,而是上下文。
鉴于此,解决方案显而易见:既然每次对话都是 Claude 的“入职第一天”,何不为它准备一份专属的“入职手册”,让它在每次启动时自动研读?这份手册就是 CLAUDE.md 文件。作为一个纯 Markdown 文本文件,你只需将其放入指定的项目目录,Claude Code 便会在启动时自动扫描并加载其内容,将其作为高优先级的用户消息注入到系统提示词之后(而非嵌入系统提示词内部)。这也解释了为什么 CLAUDE.md 表现为一种指导性建议而非强制性配置。从此,Claude 无需再从零开始猜测你的项目长什么样——每一个规范和细节都明明白白地写在了手册里。
这种设计哲学在软件工程中早已司空见惯。我们用 .editorconfig 统一编辑器行为,用 .eslintrc 规范代码风格,用 tsconfig.json 约束 TypeScript 编译选项,用 .prettierrc 固化格式规则。这些配置文件的本质,都是将隐性的“团队约定”从人的大脑中外化为机器可读的声明式规则。
CLAUDE.md 遵循的也是同样的逻辑,唯一的区别在于它的“读者”:不再是编译器或格式化工具,而是一个具备自然语言理解能力的大模型。这正是“配置驱动”思维在 AI 时代的自然延伸与进化。
Kage 的笔记
有人可能会问:“Claude Code 不是有读取项目文件的能力吗?让它看看 package.json 不就能推断出技术栈了?”话虽如此,但“主动探测”不仅会消耗宝贵的工具调用配额和上下文窗口空间,更重要的是,package.json 只记录了依赖列表,无法捕捉到架构决策和团队约定等更深层的信息。CLAUDE.md 的核心价值在于将零散的隐性知识固化为一份显性的指导文档,确保 Claude 在开始编码之前就能建立起对项目的准确心智模型。
五层记忆架构
“原理我懂了,但 CLAUDE.md 到底应该放在哪里?”小冰追问道。
Kage 微微一笑。“好问题。答案是:它不只存在于一个地方。”
Claude Code 的记忆系统采用了一套精妙的分层架构,从全局到局部共分为五个层级。这种设计让人联想到操作系统中的配置加载机制:正如 Linux 通过扫描 /etc/ 中的全局设置、家目录中的用户专属设置以及当前目录中的项目专属设置来读取配置——逐层递进而愈发具体——Claude Code 的五层记忆系统遵循的也是同样的设计哲学。
本章使用的五层模型是本书自身对记忆工作机制的组织方式。Claude Code 的官方文档定义了四种记忆作用域——托管策略、用户、项目和本地。这里单独列出的“规则目录”层(.claude/rules/)在该分类法中并非独立作用域;它是项目作用域内的一种模块化、按路径限定范围的功能。我们将其单独列为一个层级,是为了突出条件规则机制。
我们可以用一个通俗的类比来说明这套体系:公司制度文件的层级。
-
第一层是总部下发的“集团行为准则”,是所有子公司都必须遵守且不可修改的铁律。它确立了公司的核心价值观和底线。
-
第二层是各部门的“部门操作手册”,适用于部门内所有项目,确保同一业务线内的规范性。
-
第三层是各项目团队的“项目开发规范”,将规则细化到单个产品,明确技术选型和编码风格等核心约定。
-
第四层是特定场景的“专项操作指南”。例如“数据库迁移操作规范”,仅在涉及特定任务时才被引用,具有高度的场景针对性。
-
第五层是每个员工工位上的个人便利贴——完全个性化的知识,只有自己可见,用于记录临时的调试技巧或个人偏好。
自上而下,适用范围逐层收窄,内容粒度逐层增加,管理灵活度也随之上升。
图 2.2 展示了 Claude Code 的五层记忆系统。
图 2.2:Claude Code 的五层记忆系统
接下来,我们逐层分析每个层级的职责与典型用途。
企业策略层构成了整个体系的“天花板”,通常是开发者无法触及的。这一层由公司的 IT 管理员通过系统级配置文件(macOS /Library/Application Support/ClaudeCode/CLAUDE.md;Linux/WSL /etc/claude‑code/CLAUDE.md;Windows C:\Program Files\ClaudeCode\CLAUDE.md)或 Anthropic 企业管理控制台统一设定。典型策略包括:禁止代码发送至外部 API、要求所有数据库操作必须经过 ORM、严禁在代码中硬编码密钥等安全红线。这一层确立了企业合规的基线:无论开发者如何配置下面四层,这些强制性约束都无法被绕过。对于个人开发者和小团队而言,这一层通常为空,无需特别关注。
用户层本质上是用户的“个人偏好档案”。该配置文件位于用户家目录下的 ~/.claude/CLAUDE.md,对本机打开的所有项目生效。它最适合存放与具体业务逻辑无关、但体现个人工作习惯的通用偏好,例如沟通语言的选择(中文还是英文)、Git 提交信息的格式约定,或将常用的个人快捷命令映射到具体的执行命令。这些偏好高度稳定,不随项目切换而变化。
<!-- ~/.claude/CLAUDE.md -->
# Personal Coding Preferences
- Communication language: Replies in Chinese, code comments in English
- Commit conventions: Git commit messages follow the format "type(scope): description in Chinese"
- Programming paradigm: Prefer functional programming style
- Shortcut command mappings:
- When I say "run tests," automatically execute pnpm test
- When I say "start service," automatically execute pnpm dev
**项目层**是日常开发中最常用的层,也是本章的重点。它由项目根目录下的 `CLAUDE.md` 文件表示,必须提交到 Git 仓库,成为项目代码资产的一部分。
这意味着当新同事克隆项目时,Claude Code 会自动读取该文件。无需额外配置——Claude 即刻获得完整的项目上下文。这就像在新工作入职第一天,欢迎礼包中就收到一份专属的“项目开发手册”——打开一看,技术栈选型、目录结构、编码规范、常用命令一目了然。
规则目录层是一项精妙的高级设计,旨在解决“单个 CLAUDE.md 文件无法容纳所有复杂规则”的痛点。你可以在 .claude/rules/ 目录下部署多个独立的 Markdown 文件,每个文件聚焦于一个特定主题(如数据库约定、API 设计风格或测试策略)。更重要的是,该层支持条件触发机制——只有当操作特定文件或进入特定上下文时,规则文件才会被动态加载,从而避免无关信息干扰上下文。我们将在条件规则系统一节中深入探讨这一机制及其实际用法。
本地层是开发者的“个人备忘录”,对应 CLAUDE.local.md 文件。该文件不提交到 Git 仓库(Claude Code 仅在你运行 /init 并选择个人选项时才将 CLAUDE.local.md 添加到 .gitignore;如果你是手动创建该文件,请自行将其加入 .gitignore),用于记录对个人极具价值但不适合共享的信息,例如测试服务器的地址和端口、个人调试过程中积累的独特见解,或临时工作笔记。
例如,如果你知道开发环境的数据库会在特定时间进行维护,这类信息只需记录在本地层,无需通知整个团队,从而避免信息噪音。
<!-- ./CLAUDE.local.md (automatically added to .gitignore) -->
# Local Development Notes
- Database connection: postgresql://dev:dev123@10.0.1.50:5432/orders_dev
- Maintenance window: Database maintenance every Wednesday from 22:00 to 23:00; strictly forbidden to perform migration operations during this period
- Troubleshooting: If a CORS error occurs, first check the Nginx configuration (/usr/local/etc/nginx/nginx.conf)
- Integration configuration: The frontend service runs on port 5173; manual proxy forwarding configuration is required
至此,小冰敏锐地提出了一个关键问题:“如果这五层之间出现了冲突怎么办?比如我在用户层设置了‘4 空格缩进’,但项目层规定的是‘2 空格缩进’?”
“问得好,”Kage 赞许地回应,“这些文件遵循的是‘累加而非覆盖’的原则。Claude Code 会读取所有层的内容,将它们合并成一个完整的上下文。当出现冲突时,Claude 模型会根据它的判断来做决策,核心逻辑是 具体性优先。在缩进的例子里,项目层的‘2 空格’规则对当前项目更具体,因此会优先于用户层通用的‘4 空格’偏好。但企业策略层是个例外,它拥有绝对权威——无论下层如何配置,它的约束都无法被绕过。这就像公司的法律或安全红线,任何项目经理或个人偏好都无法凌驾其上。”
值得一提的是,CLAUDE.md 还拥有强大的文件引用机制。在任意层的记忆文件中,你都可以通过 @path/to/file 语法来引入其他文件的内容,实现配置的模块化组织。
例如,在项目层的 CLAUDE.md 中写入 @docs/api‑conventions.md,Claude 就会自动加载并解析 API 约定文档的内容。该机制最多支持五层嵌套引用,对于大多数复杂项目的组织需求来说已经足够。
这为大型项目提供了一种优雅的文档治理方案:CLAUDE.md 不再需要独自承担全部细节,而是作为一个“总索引”,灵活地指向各类专项文档。这种设计成功规避了海量信息堆积在单一巨型文件中的弊端,使配置结构更清晰、更易维护。
CLAUDE.md 的写作范式
理解了记忆文件的存放位置与层级职责后,一个更根本的问题浮出水面:它们究竟应该怎么写?
Kage 在白板上郑重写下三个词:少即是多。
“CLAUDE.md 的内容具有全局持久性,”Kage 解释道,“它会在每次对话开始时被完整注入上下文窗口。这意味着,你写的每一行,都在消耗每一次交互中宝贵的 token 配额。”
他打了个形象的比方:“你可以把上下文窗口想象成一张面积有限的办公桌。桌面大小是固定的。如果在 Claude Code 开始实际工作之前,你就把厚厚的参考资料(也就是冗长的规则文件)堆满了桌面,那么留给真正需要处理的代码、文件和临时草稿的空间就所剩无几了。一旦桌面被塞满,Claude Code 就不得不‘扔掉’一些早期的关键信息来腾出空间,这往往会导致它‘忘记’重要指令或上下文细节。”
根据 Anthropic 官方指导,用户应尽量将每个 CLAUDE.md 文件控制在 200 行以内;更长的文件会消耗更多上下文并降低遵循度。其底层逻辑是:指令密度与遵循概率成反比。指令越冗长复杂,每条规则被模型“深度关注”并“严格执行”的可能性就越低。
这与管理学中的“信息过载”原理高度吻合:当一本员工手册厚到没人能读完时,它的实际效力往往还不如一页提炼了核心要点的 A4 摘要。在 AI 协作中,简洁不仅是节省 token 的方式,更是确保指令被有效执行的关键策略。
那么,哪些内容值得写入 CLAUDE.md?Kage 给出了一套高效的“三问框架”作为筛选标准。
第一问:WHY(为什么这样做?)
核心价值:赋予 Claude 模型“举一反三”的能力。
这类信息旨在揭示决策背后的底层逻辑,帮助 Claude 理解项目的核心关切。一旦掌握了“为什么”,即使遇到未明确规定的边缘情况,模型也能基于原则做出正确推断。
示例:“我们选择 Fastify 而非 Express,是因为 Fastify 基于 schema 的验证方式与本项目‘类型安全优先’的策略相契合。”
效果:当 Claude 理解“类型安全”是最高优先级后,即便你在某处未指定库,它也会主动倾向类型定义更完善的方案,而非机械匹配关键词。
第二问:WHAT(做什么,不做什么?)
核心价值:界定不可逾越的“行为边界”。
这是最直接、最刚性的行为指令,明确划定了允许与禁止的界限。这类规则通常无需解释,要求绝对遵循与执行。绝大多数项目规范都属于此类。
示例:“必须使用 pnpm 作为包管理器;禁止使用 npm 或 yarn。”
效果:建立清晰“红线”,消除工具选择的不确定性,确保技术栈的一致性。
第三问:HOW(如何按步骤做?)
核心价值:规范“标准操作流程”。
这类内容适用于常用命令、固定流程或特定操作范式。模型无需理解命令背后的复杂原理,只需准确执行既定步骤。
示例:“执行数据库迁移,运行 pnpm db:migrate;填充测试数据,运行 pnpm db:seed。”
效果:将团队最佳实践转化为模型的肌肉记忆,减少因命令拼写错误或参数遗漏导致的低级错误,提升执行效率。
并非所有信息都需要同时回答这三个问题。大多数规则只需在 WHAT 层面用一句话清晰界定即可。只有那些容易被误解,或模型容易“好心办坏事”的关键决策,才值得在 WHY 层面补充深入解释。
如果你发现 CLAUDE.md 中每条规则后面都跟着冗长的背景解释或情感表达,那通常意味着内容已经过载。简洁,才是高效协作的关键。
接下来,让我们通过一个反面例子与随后的正面例子对比,快速建立直觉。
先看一个反面例子:含糊其辞的“正确废话”。
# Project Description
This is a backend service for an e-commerce platform. Our team has 5 members, and the project started development in March 2024.
It is written in Node.js and is a RESTful API service.
The code should be written well, with attention to performance.
Testing should be comprehensive.
Please follow best practices.
CLAUDE.md中充满了人类社交语境中常见的礼貌用语和模糊指令,这些对 AI 来说几乎等同于无用信息。
-
Written well:好到什么程度?是指符合
Prettier格式化,还是使用设计模式? -
“Comprehensive”:应该覆盖哪些场景?是单元测试、集成测试还是 E2E 测试?覆盖率要求是 80% 还是 100%?
-
“Best practices”:谁的最佳实践?
读完这些,Claude 几乎获取不到任何可执行的信息。
最致命的问题是“follow best practices”这条指令。它看起来正确,实际上却是空洞的,因为 Claude 默认就会尝试遵循它所认为的“最佳实践”(基于海量互联网数据的统计模式)。核心问题在于,模型通用的“最佳实践”往往与你们团队特定的“技术约定”不同。
此外,像“团队有 5 个人”或“开发始于 2024 年 3 月”这样的元数据,对代码生成逻辑没有任何指导意义,却占用了宝贵的上下文空间。
现在,让我们看一个正面例子:一份精确的“操作手册”。
# Order Service API
## Technology Stack
- Node.js 20 + TypeScript 5.3 (strict mode)
- Fastify 4 framework (do not use Express)
- Prisma ORM + PostgreSQL 15
- pnpm 8 package management (do not use npm/yarn)
## Project Structure
- src/routes/ — Route definitions, only for parameter parsing and response construction
- src/services/ — Business logic layer, all core logic resides here
- src/repositories/ — Data access layer, encapsulates Prisma calls
- src/schemas/ — Zod validation schemas, one-to-one correspondence with routes
## Key Conventions
- Unified API response format: { success: boolean, data?: T, error?: { code: string, message: string } }
- Error codes use UPPER_SNAKE_CASE, e.g., ORDER_NOT_FOUND
- Database table names use snake_case plural form, primary key is UUID, must include created_at and updated_at
## Common Commands
pnpm dev # Start development server, port 3000
pnpm test # Run all tests (vitest)
pnpm build # TypeScript compilation + type checking
pnpm db:migrate # Run Prisma database migration
两份文档的差距一目了然。优秀的版本简洁、具体、可执行——每一条规则都直接锚定 Claude 的行为逻辑。
-
技术栈锁定:看到“Fastify 4 框架(不要用 Express)”,Claude 会立即排除 Express 相关的方案,基于 Fastify 生成代码
-
架构规范化:读到目录结构后,Claude 能准确判断新增路由文件应放在
src/routes/目录下,而不是随意散落 -
零错误执行:有了常用命令及其注释,Claude 能准确执行构建和测试任务,省去了在
npm run build和yarn build之间的猜测
除了手动编辑,Claude Code 还提供了两个便捷工具来帮助管理记忆文件。
首先是 /init 命令。在项目根目录下执行后,Claude Code 会自动扫描项目的目录结构、依赖配置文件(如 package.json、pyproject.toml、Cargo.toml 等)以及其他关键配置,然后生成一份 CLAUDE.md 草稿。这份草稿通常涵盖技术栈识别、目录结构概览和常用脚本命令,是一个很好的起点。
然而,对于 /init 无法自动推断的内容,仍需要人工审查和补充,例如分层架构的具体约束、统一的 API 响应格式,以及团队特有的命名约定。
这些“隐性知识”只存在于团队成员的大脑中,无法仅从配置文件中提取。必须通过人工干预将其显式化,以确保 AI 的行为完全符合团队预期。
其次是 /memory 命令,用于在对话过程中动态更新记忆。执行该命令后,Claude Code 会弹出一个文件选择器,列出当前所有可用的记忆文件供你选择和编辑。这些文件覆盖了不同的作用范围,如表 2.1所示。
| 作用范围 | 项目记忆 | ./CLAUDE.md 或 ./.claude/CLAUDE.md |
| --- | --- | --- |
| 团队共享:可纳入版本控制,适合统一团队规范 | 用户记忆 | 个人全局:个人偏好配置,对当前用户的所有项目生效 |
| 项目本地记忆 | ~/.claude/CLAUDE.md | 个人本地:仅针对当前项目的个人偏好,通常被 .gitignore 自动排除,避免提交到代码仓库 |
| 系统文件 | ./CLAUDE.local.md | 承载内容 |
表 2.1:项目记忆的作用范围
选择文件后,系统会直接在编辑器中打开该文件,供你立即修改。
假设你在交互过程中发现 Claude Code 又使用了 moment.js,而项目规范明确要求使用 date-fns。此时,你无需退出对话或手动查找文件,只需按以下步骤操作。
-
输入
/memory命令 -
选择项目级的
CLAUDE.md -
添加规则:日期处理一律使用
date-fns,禁止使用moment.js -
保存并关闭
下一次对话启动时,这条新规则会立即生效。如果这个偏好只是个人习惯,不希望影响团队,可以选择写入 CLAUDE.local.md——该文件默认通过 .gitignore 排除,不会被提交到代码仓库。
这种机制形成了一个“犯错 → 纠正 → 更新记忆 → 避免再犯”的正反馈循环。久而久之,你的记忆文件会越来越精准,Claude Code 在项目中的表现也会持续提升。
条件规则系统
随着项目不断演进,单一的 CLAUDE.md 文件终将面临容量瓶颈。
当一个项目涵盖前端组件规范、后端 API 设计、数据库迁移流程、测试策略(覆盖率/模拟)以及基础设施(Docker 和 CI/CD)的所有规则时,将所有内容堆砌到一个文件中会导致两个核心问题。
-
维护噩梦:文件变得极其冗长,难以查找和更新特定规则。
-
注意力稀释:例如,当 Claude 编写一个简单的前端组件时,其上下文被迫加载数据库迁移规范和 CI 配置要求等无关信息。这些噪音稀释了模型的注意力,降低了其处理当前任务的效率,甚至可能导致幻觉或关键前端约束被忽略。
这正是 .claude/rules/ 目录的核心价值所在。它将记忆系统从“一本厚重、包罗万象的单一手册”进化为“一个可按需访问的模块化知识库”。
这种机制有两个核心优势。
-
领域分割:允许将庞大的规则集拆分为多个主题特定的文件,每个文件聚焦于一个特定领域,极大地提升了可维护性。
-
智能激活:通过在每个文件开头添加 YAML Frontmatter,并使用
paths字段声明 Glob 模式,只有当 Claude Code 操作的文件路径匹配该模式时,对应的规则才会被激活并注入上下文。在无匹配的场景下,这些规则文件静静地存储在磁盘上,不消耗任何 token 或上下文空间。
来看一个示例。如果你需要规范测试文件的编写,可以创建如下规则文件。
<!-- .claude/rules/testing.md -->
---
paths:
- "**/*.test.ts"
- "**/*.spec.ts"
- "tests/**"
---
# Testing Guidelines
- Use vitest as the testing framework; jest is prohibited.
- Every test file must contain a describe block, and its name must match the module under test.
- Module mocking must be done uniformly with vi.mock(); manual mocking is strictly forbidden.
- All asynchronous tests must use async/await syntax; the use of done callbacks is prohibited.
- Test data must be generated through factory functions; hardcoding data in tests is strictly forbidden.
有了这个配置,当 Claude 编辑 src/services/order-service.ts 时,这些测试指南不会被加载;然而,一旦编写 tests/order-service.test.ts,这些规则就会自动生效。这种“按需加载”的设计理念与编程语言中的懒加载概念高度一致:无需在启动时预加载所有潜在资源——只在真正需要时动态调用。
同样的方法可以扩展到开发的其他领域。例如,数据库指南只在处理 Prisma 文件或数据访问层时加载,而 API 设计指南只在编辑路由或 schema 文件时生效。
<!-- .claude/rules/database.md -->
---
paths:
- "prisma/**"
- "src/repositories/**"
---
# Database Guidelines
- Once a migration file is committed to the main branch, it is strictly forbidden to modify it; only create new migrations as needed.
- All queries must go through the repository layer; the service layer is prohibited from directly invoking the Prisma client.
- Batch operations must be wrapped in a transaction. When writing more than 100 records at a time, batch processing is mandatory.
<!-- .claude/rules/api-design.md -->
---
paths:
- "src/routes/**"
- "src/schemas/**"
---
# API Design Guidelines
- Every route must be configured with a corresponding Zod schema for input parameter validation.
- List endpoints must uniformly support pagination parameters: page (starting from 1) and limit (default 20, maximum 100).
- 错误响应结构必须包含机器可读的
code字段和人类可读的message字段。
小雪听后,精辟地总结道:“这就好比为公司里不同岗位的员工量身定制专属操作手册——前台遵循前台流程,仓库员工遵守仓库规范,没人需要背下整个公司的规章制度。只有当你踏入仓库作业时,才需要翻开‘仓库管理手册’。”
Kage 点头补充道:“这种模块化的规则组织方式还有另一个重要的实践优势:在协作场景中,领域专家可以独立维护自己的规则文件,大大降低了 Git 合并冲突的可能性。前端工程师负责 frontend.md,后端工程师维护 api‑design.md,DBA 管理 database.md——各管一摊,互不干扰。随着团队规模增长,这种‘分而治之’策略的价值会越来越明显。”
Kage 的笔记
如果某个规则文件没有配置 paths 前置元数据,系统会将其视为全局无条件规则,在每个会话中强制加载——效果等同于直接写入主 CLAUDE.md 文件。因此,务必为每个规则文件设置精确的 paths 限制,才能真正发挥记忆系统“按需加载”的核心优势。
实践:三种典型项目配置
理论讲完了,让我们通过三个典型项目的 CLAUDE.md 实战示例来融会贯通。请特别留意它们各自不同的侧重点。
-
前端项目:聚焦组件约定与状态管理策略
-
后端项目:围绕分层架构设计与 API 规范
-
数据项目:强调数据处理流程的严谨性与实验可复现标准
这些差异绝非偶然,它们恰恰反映了不同技术领域中“最高频出错点”的分布。一份优秀的 CLAUDE.md 应当像精确制导武器一样,将火力集中在那些最容易出问题的关键区域。
React 前端项目配置
在 React 前端项目中,组件粒度、状态归属和样式方案选型往往是分歧的高发地带,也是 Claude 最容易“自作主张”导致代码风格碎片化的地方。如果不明确指定状态管理策略,Claude 极有可能在同一个项目中混用 Redux、Context API 和局部状态,造成架构混乱。
以下是一个电商平台前端项目的 CLAUDE.md 实战示例。
# 电商平台前端项目规范
## 技术栈
- 核心:React 18 + TypeScript(严格模式)
- 构建/包管理:Vite 5 + pnpm
- 状态管理:
- 服务端状态:TanStack Query (React Query)
- 全局客户端状态:Zustand
- 样式方案:Tailwind CSS(严禁使用 CSS Modules 或 styled-components)
## 组件规范
- 范式:仅使用函数组件 + Hooks;禁止使用类组件。
- 命名:
- 文件使用 PascalCase(如 ProductCard.tsx)
- Props 类型命名为 ComponentName + Props(如 ProductCardProps)
- 目录结构:
- 通用 UI 原子组件 → src/components/ui/
- 业务领域组件 → src/components/features/
## 状态管理决策树
- 服务端数据(API 响应、缓存、同步)→ TanStack Query
- 全局客户端状态(主题切换、用户登录状态、临时购物车状态)→ Zustand
- 组件局部状态(表单输入值、下拉展开/收起、弹窗显示)→ useState
## 常用命令
```bash
pnpm dev # 在 5173 端口启动开发服务器
pnpm build # 生产环境构建
pnpm test # 运行 vitest 单元测试
pnpm lint # 运行 ESLint 代码检查
```
请注意“状态管理决策树”这一节。它不仅仅是一份技术栈名称清单,而是构建了一套“从场景到工具”的映射逻辑。这种“决策指引”远比简单的工具罗列有效得多——它直接告诉 Claude 在面对具体问题时“该选哪把钥匙”,从而从根本上杜绝了架构风格的漂移。
Node.js 后端项目配置
Node.js 后端项目的命脉在于分层架构中清晰的职责边界和数据格式的统一。后端代码的“正确性”往往取决于每一层是否严格遵守依赖规则——如果路由层绕过服务层和仓储层直接调用 Prisma,业务逻辑就会泄漏到基础设施层,导致后期维护的泥潭。
以下是一个订单微服务的 CLAUDE.md 实战示例。
# 订单微服务后端规范
## 技术栈
- 运行时:Node.js 20 + TypeScript 5.3
- 框架:Fastify 4(严禁使用 Express)
- 数据库:Prisma ORM + PostgreSQL 15
- 工具链:pnpm(包管理)、Zod(数据校验)
## 分层架构(严格单向依赖)
- routes/ → 解析请求参数、校验输入、调用控制器、构造 HTTP 响应
- controllers/ → 编排服务调用、处理 HTTP 语义、捕获和转换异常
- services/ → 实现核心业务规则、管理事务、协调多个仓储
- repositories/ → 封装 Prisma 查询、数据映射(严禁其他层直接调用 Prisma)
## API 响应规范
所有端点必须返回统一格式:{ success: boolean, data?: T, error?: { code: string, message: string } }
分页规范:page(从 1 开始)、limit(默认 20,最大 100)
错误码:必须使用 UPPER_SNAKE_CASE 格式
## 常用命令
```bash
pnpm dev # 在 3000 端口启动开发服务器
pnpm test # 运行 vitest 测试套件
pnpm build # 使用 tsc 编译
pnpm db:migrate # 执行 Prisma 数据库迁移
pnpm db:studio # 启动 Prisma Studio 可视化界面
```
在这份配置中,最关键的一条规则是“严禁其他层直接调用 Prisma”。这不仅仅是一个编码风格偏好问题,而是一条不可违背的架构原则,直接决定了项目的可维护性和生命周期。
Python 数据项目配置
Python 数据项目呈现出与 Web 开发截然不同的面貌。如果 Claude 不熟悉数据科学领域的工程惯例,很容易生成违反最佳实践的代码——例如滥用 inplace=True 原地修改 DataFrame,破坏数据流的可追溯性,或混用 None 和 pd.NA,导致缺失值处理逻辑混乱。
以下是一个用户行为分析系统的 CLAUDE.md 规范实战示例。
# 用户行为分析系统规范
## 技术栈
- 环境:Python 3.11 + uv(依赖与虚拟环境管理)
- 核心库:
- 数据处理:pandas 2.x
- 机器学习:scikit-learn
- 可视化:matplotlib + seaborn
- 代码标准:
- 类型注解:严格使用 typing 模块
- 文档字符串:强制使用 Google Style
## 项目结构
- notebooks/:探索性数据分析(Jupyter),命名格式为“编号-描述.ipynb”,如 01-data-exploration.ipynb
- src/data/:数据加载、清洗与管道构建
- src/features/:特征工程逻辑
-
src/models/:模型定义、训练工作流和评估指标 -
tests/:pytest单元测试套件
数据处理约定
-
缺失值:仅使用
pd.NA;不要使用None或裸np.nan -
日期列:始终转换为
datetime64类型;输出/存储格式必须为YYYY-MM-DD -
内存优化:低基数分类变量必须显式转换为
category类型 -
DataFrame:不要使用inplace=True;所有转换操作必须返回一个新的DataFrame副本
常用命令
uv sync # 安装/同步依赖环境
uv run pytest # 运行测试套件
uv run jupyter lab # 启动 Jupyter Lab
uv run python -m src.train # 执行模型训练脚本
Kage 指着那三个配置文件,给出了他的最终总结和点评:
“你注意到了吗?这三个文件,每一个都只保持在二三十行,但每一行都是精华——每一条都是干货。它们放弃了 Claude 已经烂熟于心的通用知识——你不需要解释什么是 React,也不需要重申 Python 的缩进规则——而是精准聚焦于特定领域和这个项目独有的约定与决策。”
这就是编写 CLAUDE.md 的核心法则:只记录 Claude 必须知道、但无法自行推断的关键信息。请始终记住这个黄金测试:如果删除某条规则后 Claude 依然能正确行事,那这条规则就不属于 CLAUDE.md。
小结
回到本章开头的场景:每次小冰开启新会话,Claude 都习惯性地使用 Express 而非 Fastify,使用 npm 而非 pnpm。现在我们明白了,这不是 Claude 模型能力的局限,而是因为它缺少一份至关重要的“入职手册”。
CLAUDE.md 正是解决这一痛点的关键机制。它将团队的技术选型、编码规范、项目结构和常用命令固化为一份机器可读的配置文档。每当会话启动,Claude Code 便自动加载这些信息,彻底免除反复纠正的繁琐,直接进入高效协作状态。
五层记忆架构的设计,深刻体现了“关注点分离”这一经典软件工程原则。
-
企业策略层:严守安全底线,由组织统一管理
-
用户层:捕捉个人偏好,尊重个体差异
-
项目层:承载团队共识,确保协作一致
-
规则目录层:实现模块化与条件化加载
-
本地层:存放私人笔记,提供灵活的临时上下文
每一层都有清晰的职责边界和管理方式,在有力支撑团队协作的同时,充分尊重个人习惯。
其中,条件化规则系统是一项尤为精妙的工程设计。它利用 Glob 模式精确定义规则的生效范围,实现了“在恰当的时刻将恰当的信息送入上下文”的智能机制。这种设计彻底摒弃了将所有规则一股脑堆在 Claude 面前的粗暴做法,确保了上下文的清爽高效。
至于编写范式,“少即是多”绝非一句空洞的口号——它背后有着严肃的技术逻辑。上下文窗口是大模型最宝贵的战略资源,每一个 token 都承载着高昂的机会成本。强行将无关信息塞入 CLAUDE.md,就好比在早高峰时段往地铁车厢里硬塞非乘客——不仅占用了宝贵的空间,还将真正需要上车的“关键信息”挤在门外,无法进入模型的视野。
一份优秀的 CLAUDE.md 应当如同一份简洁的作战备忘录,严格遵循以下三条铁律。
-
必要性:每一条都是 Claude 必须知道且无法自行推断的信息
-
可操作性:每一条都是具体、明确、可执行的指令
-
脆弱性测试:删除任何一条,都会直接导致 Claude 犯错或偏离预期
在第 3 章中,我们将正式踏入 Skills 的广阔世界。如果说 CLAUDE.md 是让 Claude 建立基础认知的“入职手册”,那么 Skills 就是为它量身定制的“专业培训教材”。当你的“入职手册”变得越来越臃肿,试图将所有领域知识都塞进去时,不仅浪费了上下文资源,还降低了核心规则的响应效率。此时,你需要一种更优雅、更智能的按需加载机制——这正是 Skills 系统的核心价值所在:在真正需要之时,将专业知识精准注入对话上下文。
思考题
-
请识别你当前项目中 Claude 必须知道的核心信息。尝试用“三问框架”(WHY、WHAT、HOW)进行拆解,并起草一份不超过 30 行的
CLAUDE.md。起草完毕后,逐行审视:如果删除这一行,Claude 会犯什么错误?如果你无法回答这个问题,那一行或许就是多余的。 -
在团队协作中,如果开发者对
CLAUDE.md中的规则存在分歧(例如缩进使用 2 个还是 4 个空格),你如何利用“五层记忆架构”来化解?请具体说明:哪些规则必须放在项目层以强制执行统一标准,哪些偏好适合放在用户层或本地层以保留个人选择自由? -
在你的项目中运行
/init命令自动生成CLAUDE.md,然后将其与你手动编写的版本进行深度对比:哪些显性信息机器能够准确推断?而哪些“隐性知识”必须依赖人工补充?
3
第三章:授人以渔:打造可复用的技能
我们重复做什么,就会成为什么样的人。因此,卓越不是一种行为,而是一种习惯。
——威尔·杜兰特
周二早上,小冰开启了一个全新的 Claude Code 会话,准备处理本周的第一项任务:为支付模块生成 API 文档。她先花了三分钟厘清背景:团队遵循 RESTful 约定,文档必须使用 OpenAPI 3.0 格式,错误码要与企业内部标准对齐,示例数据必须真实有效,输出需包含中英双语。直到把上周同事写的参考文档也喂给模型之后,她才正式下达开工指令。
昨天如此,上周五如此,上上周五亦如此。每一次新对话开始,这些前置知识都要重新“喂”给 Claude。更让人沮丧的是,即便在同一个会话内,当任务从“生成 API 文档”切换到“审查代码质量”时,Claude 也无法自动适应新的工作模式——她不得不又花一轮对话重新说明审查重点、输出格式和严重程度分级。这哪里是在用智能助手,分明是在日复一日地给一个“失忆”的临时工做入职培训。
小雪的体会如出一辙。在与公司数据分析团队协作时,每次让 Claude 执行财务分析,她都要重新解释毛利率公式、行业基准数据和报告模板格式。这些核心知识从未改变,但 Claude 每次都像第一次听说。
“有没有一种办法,”她问 Kage,“能让 Claude 永久记住某些领域专属的工作范式?不只是 CLAUDE.md 那样的项目级通用记忆,而是更精准的上下文感知——比如我一提到‘API 文档’,它自动就知道执行标准;一提到‘财务分析’,它自动就加载相关的行业基准和报告模板。”
Kage 微微点头,转身在白板上写下一个词:Skills。
从 CLAUDE.md 到 Skills:知识的两维
“在深入 Skills 之前,”Kage 开口道,“我想先厘清一个根本问题:为什么 CLAUDE.md 不再够用了?”
说着,他在白板上画出了一个知识类型与加载策略的坐标系(见图 3.1)。
图 3.1:知识类型与加载策略:CLAUDE.md 与 Skills
“CLAUDE.md 就像公司的‘文化手册’,”Kage 解释道。“它规定了项目的基本规则:* 是用 TypeScript 还是 Python,是用 tab 还是空格缩进,PR 标题应该遵循什么格式。这些规则必须在每一次对话的每一个时刻都生效,所以它必须始终驻留在上下文中,每次全量加载。但代价也很明显:‘始终驻留’意味着无论你是否在做相关任务,这些 token 都在被持续消耗。”
他顿了顿,看向小冰:“再想想你的 API 文档知识。OpenAPI 3.0 标准、错误码约定、双语格式。这些信息只有在你生成 API 文档时才需要。如果你硬把它塞进 CLAUDE.md,那么当你调试 bug、运行测试、编写配置文件时,这几千 token 的文档标准依然占据着上下文,白白浪费了宝贵空间,也稀释了真正关键信息的权重。”
“所以,这就是 Skills 要解决的核心痛点?”小冰问,开始理解。
“正是。Skills 解决的是 按需知识投递 的问题。”Kage 说着,在白板上画出了一个完整的对比表(见表 3.1)。
| 维度 | | CLAUDE.md | | Skills |
| --- | --- | --- | --- | --- |
| 承载内容 | | 项目通用规范 | | 专业工作流、领域知识 |
| 作用范围 | | 当前项目 | | 跨项目、跨会话 |
| 触发方式 | | 始终生效 | | 按需激活 |
| 加载策略 | | 每次全量加载 | | 渐进式按需加载 |
| 典型用途 | | 使用 TypeScript | | “如何执行代码审查” |
| 与 Agent 的关系 | | 所有 agent 共享 | | 可绑定到特定 Agent |
| Token 消耗 | | 固定开销 | | 按需付费,用时才花 |
| 企业本体 | | 企业文化手册 | | SOP(标准作业程序)操作手册 |
表 3.1:CLAUDE.md 与 Skills 的全维度对比
表 3.1 最后一行,企业 本体,引起了小雪的注意。“这是什么意思?”她问。
Kage 解释道:“一个成熟的企业,其实拥有两种截然不同的知识资产。第一种是所有人都必须遵守的通用规则——比如考勤制度、安全红线、沟通协议。这些就像贴在办公室墙上的标语:人人可见,时刻生效。对应的就是 CLAUDE.md。第二种是特定角色的 标准作业程序 (SOP),比如财务每月如何结账、运维如何处理故障、客服如何应对投诉。这些不会贴在墙上给所有人看,而是整齐地存放在部门的文件柜里,只有特定角色在执行特定任务时才会去查阅。那就是 Skills。 CLAUDE.md 是墙,Skills 是文件柜。你不需要在写代码时翻阅财务手册,也不需要在做报表时查阅安全规程。只有在‘需要’的那一刻,相应的知识才会被精确调取(见图 3.2)。”
图 3.2:Skills 可以按需调用
这个类比精准地锚定了 Skills 在 Claude Code 架构中的核心地位。Claude Code 对 Skill 的定义既直白又深刻:Skill 是一个包含指令的文件夹,被封装成简单的目录结构,用来“教”Claude 如何处理特定任务或工作流。在这段定义中,有两个关键词值得深究。
第一个是“文件夹”,从“字符串”到“工程化”。Skill 远不止是一个 prompt 或一个简单配置项,它是一个工程化的完整目录,可以容纳复杂的代码库、详尽的领域文档、多样化的模板,甚至可执行的脚本。
第二个是“教”,从“约束”到“内化”。定义中用的是“教”,而不是“命令”或“约束”。这隐隐揭示了其运作机制的根本转变。“教”是能力的传授与内化。通过 Skills,Claude 真正理解了某个领域的运作逻辑。它不再是一台被动执行指令的机器,而是成为了该领域的“熟练从业者”。
解剖一个 Skill:骨架与血肉
“中国有个古老的故事,讲的是庖丁解牛,那位大师级屠夫之所以能游刃有余,不是靠蛮力,而是因为他完全内化了牛的自然结构——关节在哪里,空隙如何走,”Kage 引用道。“理解一个 Skill 的结构,也需要同样的智慧:先看到它的‘骨架’,理解知识如何被放置和组织,然后才能谈如何巧妙运用。”
目录结构
他转向坐标系旁的白板,列出了一个典型的 Skill 目录结构。
“把这个想象成刀本身是如何被构造的,”Kage 说,指着他刚在白板上画出的目录结构。“就像庖丁解牛那样,大师顺着牛的自然间隙和空隙引导刀刃,而不是强行切割,技巧在于读懂结构——而不在于刀。”然后他将目录逐一拆解。
api-doc-generator/ ← 技能名称(kebab-case,以连字符分隔,像文件名一样清晰)
├── SKILL.md ← [核心骨架] 必需的主技能文件(注意:大小写必须完全匹配)
├── scripts/ ← [手脚] 可选的可执行脚本,使技能能够主动“做”事情
│ └── detect-routes.py ← 例如,自动扫描代码库以发现路由
├── reference/ ← [记忆库] 可选的按需加载参考文档,不占用常驻内存
│ ├── openapi-patterns.md ← 仅在生成文档时读取的标准
│ └── error-codes.md ← 仅在处理错误时查阅的代码表
└── templates/ ← [模具] 可选的输出模板,以确保输出格式一致
└── endpoint-doc.md ← 定义 API 文档应该是什么样子
“这些看似繁琐的‘规章制度’,其实是用惨痛的工程经验换来的防错机制。”Kage 拿起一支红色记号笔,在白板上目录结构旁边重重地圈出了几个关键点,神情变得严肃起来。
**文件名**:`SKILL.md`:唯一的“触发器”。文件名必须全部大写;`skill.md`、`Skill.md`、`SKILL.MD` 全部无效。Claude 的加载器在扫描文件时执行的是精确字符串匹配,而非模糊搜索。
**目录名**:`kebab-case`:跨平台的“通用语言”。目录名使用全小写字母和连字符(例如 `api‑doc‑generator`),最长 64 个字符,字符集限制为 `[a‑z0‑9‑]`。不允许有空格、下划线、大写字母、开头或结尾的连字符,也不允许连续连字符。这是为了消除操作系统之间的差异。Windows 不区分大小写,而 Linux 区分大小写。`kebab-case` 是互联网时代的“世界语”,确保你的技能能够在任何环境或工具链中被无损识别。
保持技能目录为纯粹的指令空间。Anthropic 建议不要在技能目录中放置 `README.md`,面向人类的文档最好放在父目录中。原因是卫生,而非硬性规则。当一个技能激活时,只有 `SKILL.md` 的主体进入上下文窗口;支持文件——包括任何 `README.md`——只有在 `SKILL.md` 明确指向它们时才会被加载,因此未被引用的 `README.md` 完全不消耗上下文。保持文件夹中没有面向人类的文档,只是消除了引用它们的诱惑,并保持指令表面的清洁。
**命名中立性**:避免使用“claude”和“anthropic”。将无品牌命名视为一种约定,而非强制验证规则。Claude Code 实际上对技能标识符的强制要求是:小写字母、数字和连字符,在长度限制内,并且与文件夹名称匹配。技能是一种通用的知识封装格式,其生命力在于保持跨 harness 的可移植性——这就是为什么即使没有验证器要求,也值得采用品牌中立的名称。
## YAML Frontmatter:技能的“身份证”
`SKILL.md` 文件顶部的 YAML Frontmatter 定义了技能的身份和行为边界。完整字段说明如下:
name: api-doc-generator
[唯一标识符] 最多 64 个字符
如果省略,默认使用目录名
description: >
Generate API documentation from source code. Use when
the user asks to "write API docs", "document endpoints", or
"create OpenAPI specs".
Supports Express, FastAPI, and Spring Boot.
[触发描述] 最多 1024 个字符
如果省略,默认使用 SKILL.md 正文的第一段
argument-hint: "[source directory] [output format]"
[参数提示] 显示在“/”菜单中
帮助用户了解此技能接受的输入格式
disable-model-invocation: true
[禁用模型自动调用] 设置为 true 时,禁止 Claude 自动调用
用户必须通过“/skill-name”手动触发
默认值:false
user-invocable: false
[用户可调用性] 设置为 false 时,从“/”菜单中隐藏
但 Claude 仍可自动调用
默认值:true
allowed-tools:
-
Read
-
Grep
-
Glob
-
Write
-
Bash(python:*)
[工具白名单] 精确控制技能执行期间可以使用哪些工具和权限范围
model: haiku
[指定模型] 指定此技能使用的模型
对于简单任务,推荐使用 haiku 以提高响应速度并降低成本
context: fork
[执行上下文] 设置为“fork”时,在隔离的子代理中执行
确保主对话上下文不被污染
agent: Explore
[子代理类型] 当 context 设置为“fork”时生效
可选值:Explore、Plan、general-purpose 或自定义 Agent
hooks:
PreToolUse:
- matcher: Bash
hooks:
- command: echo "$TOOL_INPUT" >> audit.log
[生命周期钩子] 定义技能激活期间的事件处理逻辑
仅在技能处于激活状态时生效
这些字段可以分为三个逻辑分组,每个分组对应 Skill 设计的三个核心维度之一:触发机制、权限控制和运行时环境。
* **身份字段(触发机制)**:包括 `name`、`description` 和 `argument-hint`。这些字段定义了“Skill 是什么”,向 Claude 和用户清晰地传达 Skill 的功能定位和调用方式。它们构成了触发逻辑的基础。
* **调用与工具字段**:`disable-model-invocation`、`user-invocable`、`allowed-tools`、`disallowed-tools` 和 `model`。请仔细阅读这些字段,因为它们的名称所承诺的比实际提供的更多。`disable-model-invocation: true` 阻止 Claude 自动调用 Skill,使其由用户触发。`user-invocable: false` 将 Skill 从斜杠命令菜单中隐藏——这是一个可见性开关,而非安全边界。`allowed-tools` 在 Skill 激活期间授予并自动批准工具权限;它并不限制工具。真正将工具从 Claude 的访问范围中移除的字段是 `disallowed-tools`。而 `model` 会在当前回合剩余时间内覆盖模型,这是一个路由决策而非权限控制。真正的边界来自你的权限设置和 Hooks(*第 5 章*)。
* **执行字段(运行时环境)**:包括 `context`、`agent` 和 `hooks`。这些字段决定了“在哪里执行”和“执行过程中发生什么”,配置隔离环境、子代理类型和生命周期钩子,以确保任务在预期的上下文中运行。
掌握这三个维度,就掌握了 Skill 架构设计的完整框架。
**Kage 的笔记**
`disable-model-invocation` 和 `user-invocable` 容易混淆,但实际上它们控制的是两个正交的调用方向。`disable-model-invocation: true` 意味着“Claude 不能自动触发此 Skill,必须由用户通过 `/skill-name` 手动执行。”这适用于具有副作用或高风险的操作,例如代码提交(`/commit`)、服务部署(`/deploy`)等,以确保用户明确确认。默认值为 `false`。`user-invocable: false` 意味着“此 Skill 不会出现在 `/` 菜单中,用户无法手动触发它,但 Claude 仍可在内部逻辑中自动调用它。”这适用于纯信息性或辅助参考类 Skill;隐藏它们可以避免菜单杂乱,同时保留 Claude 在适当时自动加载和使用它们的能力。默认值为 `true`。在默认配置下(两者都设为“允许”),Skill 对 Claude 和用户都是开放的。
# 渐进式披露:知识的投资回报
“*好吧,我理解了 Skill 的结构*,”小冰问道,“*但如果我有 20 个 Skill,每个包含数千个 token,Claude Code 是否每次对话都必须加载全部内容?这和把所有东西塞进* `CLAUDE.md` *有什么区别?*”
这是一个非常切中要害的问题,它恰恰揭示了 Skills 系统最精巧的核心:**渐进式披露**。
## 图书馆模型
Kage 回答道:“*这里可以用图书馆来类比。想象你走进一座图书馆查找信息。你绝不会一次性读完所有的书;相反,你会遵循一个高效的检索流程:先浏览目录定位分类,再取出目标书籍查阅其章节,最后只精读你需要的部分。Skills 系统采用了同样的三层渐进式披露模型*(见 *图 3.3*)*,以最小的 token 成本实现按需获取海量知识。*”
<https://github.com/OpenDocCN/freelearn-dl-zh/tree/master/docs/the-claude-code-operating-model/img/B39394_3_3.png>
图 3.3:三层渐进式披露模型
三层模型在实际应用中带来的性能提升是显著的。以一个完整的财务分析 Skill(总计 5,300 个 token)为例,其文件组成如 *表 3.2* 所示。
| **文件** | **Token 数** | **说明** |
| --- | --- | --- |
| `SKILL.md` | 800 | 主逻辑与路由指南 |
| `reference/revenue.md` | 1500 | 收入数据参考 |
| `reference/costs.md` | 1200 | 成本结构参考 |
| `reference/profitability.md` | 1000 | 利润率公式参考 |
| `templates/report.md` | 800 | 报告模板 |
| 合计 | 5300 | — |
表 3.2:一个完整财务分析 Skill 的文件组成
不同加载方式的 token 消耗对比如 *表 3.3* 所示。
| **场景** | **传统全量加载** | **渐进式披露** | **节省比例** |
| --- | --- | --- | --- |
| Skill 未激活 | 0 | 0 | — |
| 扫描阶段(仅判断相关性) | 5300 | 约 100 | 98% |
| 简单请求(仅主文件) | 5300 | 800 | 85% |
| 中等请求(需要一个参考文件) | 5300 | 2300 | 57% |
| 复杂请求(需要全部资源) | 5300 | 5300 | 0% |
表 3.3:不同加载方式的 token 消耗对比
数据表明,绝大多数请求只需要一部分资源。当用户问“毛利率如何计算?”时,Claude Code 只需加载 `SKILL.md`(用于路由)和 `profitability.md`(获取公式),总计约 1,800 个 token。其余三个文件(约 3,500 个 token)完全留在磁盘上,成本为零。这就是“按需知识交付”的核心经济优势:以最小的上下文成本实现最大的知识覆盖。
## description 的预算机制
渐进式披露的第一层,即所有 Skill 的 description,以常驻方式注入 Claude 的上下文。这意味着它们必须共享有限的 token 预算,形成系统的“入口瓶颈”。
Claude Code 通过一个字符预算来确定此列表的规模,该预算随模型的上下文窗口缩放——默认约为 1%。独立于预算之外,每个条目的合计文本上限为 1,536 个字符。由于这些数值在不同版本之间有所变动,请将其视为数量级参考,并对照你所部署的 Claude Code 版本进行验证。
预算并非在所有已安装的 Skill 之间平均分配。Skill 名称始终会被列出。当合并的 description 超出预算时,Claude Code 会从你调用最少的 Skill 开始缩短、然后丢弃其 description,因此你实际使用的 Skill 会保留完整文本。该机制按使用频率降级,而非按每个 Skill 均等的配额。
*每个 Skill 可用字符数 = 总预算 / Skill 总数*
这意味着一个 Skill 绝不会仅仅因为你安装了很多 Skill 而消失。在预算压力下降级的是你使用最少的 Skill 的 description 文本,而所有 Skill 的名称仍然可见。从第一天起就编写简洁的 description 是良好的实践——不是因为有一个配额在你们之间分配,而是因为简短的 description 能在预算压力下完好存活。
<https://github.com/OpenDocCN/freelearn-dl-zh/tree/master/docs/the-claude-code-operating-model/img/B39394_3_4.png>
图 3.4:Claude Code 的 description 预算池
一个 Skill 绝不会因为其 description 过长而被悄悄排除在列表之外。它的名称始终存在;只有在预算紧张时,description 文本才会被缩短或丢弃。因此,Claude 似乎“看不到”某个 Skill 是 description 质量问题,而非隐藏的字符上限。
**Kage 的笔记**
技巧 3:要提高预算,可设置 `skillListingBudgetFraction` 配置项(例如 `0.02` 表示 2%)。`SLASH_COMMAND_TOOL_CHAR_BUDGET` 环境变量仍可作为固定字符数的覆盖方式使用。
这一预算机制揭示了一个核心工程哲学:不要盲目创建 Skill,而应追求“少而精”的架构。
当你发现自己需要安装超过 20 个 Skill 时,这通常是一个信号,表明你需要重新审视你的架构策略。
* **合并同类项**:将多个碎片化的 Skill 合并为一个综合性 Skill。
* **隐藏内部工具**:将纯内部子任务标记为 `disable-model-invocation: true` 以减少预算占用。
* **采用“token 投资”回报思维**:将 description 中的每一个字符都视为一笔昂贵的“token 投资”——精准投资,以换取高效检索和准确执行;浪费投资,不仅浪费了自己的预算配额,还挤占了其他 Skill 的生存空间。
# 触发机制:Claude Code 如何决定调用哪个 Skill
Skill 的触发机制是整个系统中最关键、最需要深入理解的部分。它直接决定了 Skill 能否在恰当的时刻被激活——这甚至比 Skill 内容本身的质量更为重要。毕竟,如果无法成功触发,再精彩的内容也无用武之地。
## 双通道激活机制
每个 Skill 支持两条激活路径。
* **显式调用:** 当用户在对话中输入 `/skill-name` 时,Claude Code 立即加载并执行相应的 Skill。这种方式类似于终端命令——清晰、直接、明确。如果 Skill 定义了 `argument-hint`,用户还可以提供参数,例如 `/commit fix login bug` 或 `/review src/auth/login.ts`。
* **语义匹配**:在深入理解用户意图后,Claude 自主判断哪个 Skill 最契合当前任务并自动加载。在日常使用中,这正是 Skills 的核心价值所在——用户只需描述自己的需求,Claude 会在幕后智能地决定是否以及如何调用最合适的 Skill。整个过程对用户完全透明,实现无缝的“所想即所得”体验。
*图 3.5* 展示了显式调用和语义匹配的执行流程。
<https://github.com/OpenDocCN/freelearn-dl-zh/tree/master/docs/the-claude-code-operating-model/img/B39394_3_5.png>
图 3.5:显式调用(左)和语义匹配(右)的执行流程
## Description:Skills 的灵魂
语义匹配机制完全依赖于 `description` 字段。该字段不是写给人类读者看的说明性文字,而是 Claude 在决定是否调用某个 Skill 时所依据的**唯一信号**。
Claude Code 推荐使用以下公式来组织 `description`:
*\[功能定义\](做什么)+ \[触发场景\](何时使用)+ \[核心能力\](能做什么)*
理解这个公式的最佳方式是对比“无效”和“有效”的示例。以下是两种方式的示例。
# 描述字段的编写要点
## 常见问题示例
### 过于模糊,无法判断何时使用
```yaml
description: Helps with projects.
过于技术化,缺乏面向用户的触发关键词
description: Implements the Project entity model with hierarchical relationships.
仅描述功能,未说明触发场景
description: Generates API documentation.
正确示例:表述清晰、覆盖具体触发场景、说明核心能力
description: Generate API documentation from Express, FastAPI, or Spring Boot source code. Use when user asks to "write API docs", "document endpoints", "create OpenAPI specs", or mentions "Swagger". Supports route detection, request/response schema extraction, and authentication requirement marking.
description字段的限制是 1,024 个字符。空间不大,每个词都必须仔细斟酌。
一个高效实用的写作策略可以拆解为三步:
- 定义核心能力(What):用一句话概括该 Skill 能做什么,确立其基本功能定位
- 说明触发场景(When):用“Use when user...”句式详细列出可能触发该 Skill 的各种用户指令、短语或关键词,提高语义匹配的命中率
- 定义排除项(Not For):(可选但推荐)如果该 Skill 容易被错误触发,务必加上“Not for...”子句,明确说明不应使用的场景,优化决策准确性
Kage 的备注
你描述的读者主要是 Claude,而不是人类读者。人类阅读文档时倾向于扫标题、浏览结构以快速掌握大意;Claude 阅读description字段时执行的是深层语义匹配。它需要捕捉用户意图中的细微差别。为了提高触发准确性,必须在描述中详尽地包含用户可能的各种表达。例如,对于“生成 API 文档”这一需求,用户可能会说“generate API docs”“write interface documentation”“output OpenAPI specs”或“help me write a Swagger”。所有这些不同说法都应明确写入描述。同义词集越丰富,语义匹配覆盖面越广,触发准确性越高。
防止过度触发与触发不足
在实践中,Skill 触发机制常常面临两种典型失败模式。理解并修复这些问题,是优化 Claude 表现的关键。
1. 触发不足
- 现象:应该调用 Skill 时却没有调用。
- 数据警示:在 Vercel 的 Next.js 16 评估中,当 agent 未获得明确指导时,被测的单个 Skill 有 56% 的情况未被调用(Vercel Engineering,“
AGENTS.mdoutperforms skills in our agent evals”)。该结果只针对那次评估中的一个 Skill;应将其理解为关于可发现性的警示,而非普适概率。 - 根本原因:描述写得过于技术化或学术化,与用户自然、口语化的表达之间存在显著的语义鸿沟。
- 修复策略:“翻译”用户语言。在描述中加入大量用户常用表达,覆盖领域术语的同义词、口语短语,甚至常见但不准确的表达(例如,很多用户会混淆“Swagger”和“OpenAPI”——两者都应包含)。
2. 过度触发
- 现象:在本不应调用的情况下错误激活 Skill。
- 根本原因:描述定义得过于宽泛,包含太多高频通用词,导致匹配阈值过低。
- 修复策略:引入否定约束。用“Not for...”句式明确划定边界,排除无关场景。
- 示例:“Not for general code questions or debugging. Only for structured documentation generation.”
要测试一个 Skill 是否能准确触发,可以构建一个包含 10–20 个测试用例的验证集,同时覆盖“应触发”和“不应触发”两种场景。
下面是一个实用的测试模板示例。
应触发的测试用例:
- "Help me generate interface documentation for src/api/" → Should trigger
- "Write an OpenAPI specification" → Should trigger
- "Document the REST endpoints" → Should trigger
- "Help me write Swagger" → Should trigger
不应触发的测试用例:
- "Help me debug this API call" → Should not trigger
- "Why does this endpoint return 500?" → Should not trigger
- "Optimize the performance of this API" → Should not trigger
验收标准:对于相关任务,触发率需达到 90% 或更高;对于无关任务,误触发率需控制在 5% 以下。
参考技能与任务技能:两种技能哲学
在 Skill 设计理念中,disable-model-invocation 字段不仅仅是一个简单的开关;它定义了两种根本不同的 Skill 交互模式:参考型和任务型。
- 参考技能:
- 配置:默认行为。
- 核心逻辑:“按需知识库”。Claude 根据对话上下文自动判断是否需要该 Skill。description 作为触发条件,直接注入 Claude 的上下文进行语义匹配。
- 使用场景:提供知识、指南、框架或标准。用户无需意识到 Skill 的存在;Claude 会自动在适当的时候“打开手册”。
- 示例:API 设计指南、代码审查清单、行业标准文档。
- 任务技能:
- 配置:显式设置
disable-model-invocation: true。 - 核心逻辑:“受控执行工具”。Claude 无法自动触发这些技能;必须由用户通过
/skill-name命令手动调用。description 不会注入 Claude 的上下文,仅作为用户在命令行中选择 Skill 时的标识符。 - 使用场景:具有副作用、需要用户明确授权才能执行的操作。
- 示例:
/commit(提交代码)、/deploy(部署应用)、/notify(发送通知)。
- 配置:显式设置
参考技能与任务技能的对比见 表 3.4。
| 维度 | 参考技能 | 任务技能 |
|---|---|---|
| Claude 自动触发 | 是(语义匹配) | 否(必须手动) |
| 用户/名称触发 | 是 | 是 |
| Description 功能 | 触发条件(注入 Claude 上下文) | 仅用于用户识别(不注入 Claude 上下文) |
| Token 预算消耗 | 是(自动加载消耗) | 否(仅手动调用时消耗) |
| 典型场景 | 知识提供、标准查询 | 动作执行、副作用操作 |
| 经典案例 | API 标准、审查清单 | /commit、/deploy |
表 3.4:参考技能与任务技能对比
Kage 的注释
这里提到的“副作用”不是吃药的副作用。在软件工程中,副作用是指不仅返回结果,还改变系统外部状态的操作。例如,提交代码会修改 Git 仓库历史,部署应用会改变线上服务的状态,发送通知会实际向某人传递消息。这些操作一旦执行,就会产生现实世界的影响,并且通常是不可逆的。因此,这类 Skill 通常被设计为需要用户明确发起,而不是允许模型自行决定何时执行。
小冰问:“一个任务应该设计为参考技能还是任务技能?”
Kage 回答:请使用一个简单的“最坏情况测试”来决定:“如果 Claude 自动执行这个任务,最坏会发生什么?”
如果答案让你感到紧张,例如自动提交未测试的代码、自动部署有缺陷的版本、自动删除生产数据,或自动发送错误通知——那么你必须选择任务技能。务必添加 disable-model-invocation: true。将控制权牢牢掌握在用户手中,只有在用户明确输入 /skill-name 时才执行操作。
如果答案无关紧要,例如多显示一份参考文档、多提供一条建议,或稍微增加 token 消耗,那么你可以选择参考技能。让 Claude 根据上下文智能判断并按需自动加载,为用户提供无缝的知识辅助。
核心原则:副作用越大,控制必须越严格。对于任何可能改变系统状态或造成不可逆后果的操作,绝不要信任 Claude 的自动判断。
SKILL.md 主体内容:路由器,而非仓库
了解了 Frontmatter 中的触发机制和权限控制后,我们现在进入 SKILL.md 内容设计的核心。这是 Skill 真正发挥作用的地方。
路由器思维
一个常见的误区是将 SKILL.md 视为“知识仓库”,试图将所有相关信息都塞进去。正确的设计方法是将其定位为路由器(见 图 3.6):文件本身只包含核心流程和路由表,而详细的知识内容则分布在引用的文件中。
图 3.6:SKILL.md 的角色是路由器
路由设计的核心技巧是构建一个快速参考表。该表只需很少的 token(3 行约 50 个 token),就能清晰地引导 Claude 从五个关键维度进行路由判断。
## Quick Reference
| Analysis Type | Trigger Keywords | Reference Resource |
|-----------------------------------|---------------------------------|-----------------------------------|
| Revenue Analysis (Revenue) | revenue, sales, turnover | reference/revenue.md |
| Cost Analysis (Cost) | cost, expense, expenditure | reference/costs.md |
| Profitability Analysis (Profitability) | profit, gross margin, net margin | reference/profitability.md |
与让 Claude 逐行扫描整个 SKILL.md 文件来推断“遇到收入问题时参考 revenue.md”相比,这种结构化表格的效率显著更高,信息密度是前者的 10 倍。
契约式引用
在 SKILL.md 中引用辅助文件时,绝不要简单地列出路径。你应该建立一个清晰的“契约”,确保 Claude 清楚理解三个核心要素:触发时机(何时加载)、资源位置(在哪里查找)以及预期输出(获得什么)。
以下示例说明了“弱引用”与“契约式引用”的区别。
# Weak Reference: Lacks context (Claude cannot determine when to load this file, and lacks action instructions)
See `reference/revenue.md` for more details.
# Contractual Reference: Explicit condition + path + expected content
## Revenue Analysis
When the user asks about revenue growth, ARPU, or revenue composition:
→ Load `reference/revenue.md` for calculation formulas and industry benchmarks.
这一设计理念与子代理流水线中的“交接契约”一致:下游消费者不仅需要知道上游的位置,还必须清楚理解上游能够提供什么。
500 行规则
Claude Code 建议将 SKILL.md 的长度控制在 500 行以内。
“为什么设定为 500 行?”小冰问道。
Kage 回答说:“这是因为 500 行大约等于 2,000 到 3,000 个 token,对于激活单个 Skill 来说是一个合理的上下文成本。结合 Claude 的系统提示词和当前对话历史,可以确保总 token 数保持在可控范围内。如果超过 500 行,通常意味着你把‘参考资料’和‘路由指令’混淆了——此时解决方案不是继续扩充内容,而是立即重构。”
表 3.5 列出了 Skill 内容过载时的重构信号和策略。
| 重构信号 | 应对策略 |
|---|---|
| 大量公式或标准解释 | 移至 reference/ 目录 |
| 多个完整示例(单个超过 30 行) | 移至 examples/ 目录 |
| 多种输出模板 | 移至 templates/ 目录 |
| 可独立执行的逻辑 | 封装为 scripts/ 脚本 |
| 多个并行功能模块 | 考虑拆分为多个独立 Skill |
表 3.5:Skill 内容过载的重构信号与策略
allowed-tools:知识约束行为
allowed-tools 是 Skill 安全架构中的核心字段。它不仅仅是一份权限列表,更体现了一个深层设计原则:知识应当约束行为。
具体的权限配置应基于 Skill 对业务逻辑的理解。
- 代码审查 Skill:审查过程仅需读取代码,严禁修改,因此仅授予只读工具。
- 文档生成 Skill:需要创建新文件但绝不能改动已有文件,因此仅授予写入权限,并明确禁止编辑权限。
- 测试执行 Skill:只需运行特定测试命令,因此可执行的 Bash 命令被精确限制,以防止任意命令注入。
权限设计模板
以下是不同 Skill 类型的 allowed-tools 配置最佳实践。这些配置体现了最小权限原则,确保每个 Skill 仅拥有完成其特定任务所需的最小工具权限。
# Audit-type Skill: Strictly read-only
allowed-tools:
- Read
- Grep
- Glob
# Generation-type Skill: Writable but not editable
allowed-tools:
- Read
- Grep
- Glob
- Write
# Analysis-type Skill: Read-only + specific scripts
allowed-tools:
- Read
- Grep
- Glob
- Bash(python:*)
# Execution-type Skill: Controlled command whitelist
allowed-tools:
- Read
- Bash(git status:*)
- Bash(git add:*)
- Bash(git commit:*)
- Bash(npm test:*)
细粒度 Bash 控制语法
Bash 工具通过前缀匹配机制支持对可执行命令的细粒度控制。核心语法为 Bash(prefix:*),其中 prefix 指定允许的命令前缀,* 作为后续参数的通配符。
权限控制示例如下:
Bash(git:*) # Allows all subcommands starting with git
Bash(git log:*) # Only allows git log and its parameters, prohibiting dangerous operations like git push
Bash(npm test:*) # Only allows running test commands, preventing accidental execution of npm install or npm publish
Bash(python:*) # Allows execution of all Python scripts
Bash(./scripts/*:*) # Allows execution of specific scripts in the scripts/ directory
当 Claude 尝试执行 Bash 命令时,系统会执行预执行检查。
- 提取前缀:获取用户请求的完整命令字符串
- 匹配规则:检查命令是否以配置的前缀开头
- 执行决策:若匹配成功则允许执行;若不匹配则直接拒绝并返回权限错误。
遵循最小权限原则是构建安全 Skill 的基石。以下是 allowed-tools 配置的正反示例对比。
# Precise Authorization: Only explicitly list the specific subset of commands required for the task
# Scenario: Code commit Skill
# Strategy: Only allow the three specific subcommands: status, add, commit
allowed-tools:
- Bash(git status:*)
- Bash(git add:*)
- Bash(git commit:*)
# Over-authorization: Using a global wildcard is equivalent to abandoning all defenses
# Scenario: Incorrect generic configuration
# Risk: Allows execution of any shell command
allowed-tools:
- Bash(*)
Bash(*) 在安全性上几乎等同于完全没有设置 allowed-tools。这意味着 Claude Code 获得了对宿主机的完整 shell 访问权限。对于 /deploy 这类高风险的任务型 Skill,这样的配置是致命的。一旦模型遭受提示注入攻击,攻击者便可利用该权限窃取密钥、删除生产数据或植入后门。
参数传递与动态注入
Skill 不仅仅是静态指令;它还支持运行时参数传递和上下文预注入,使其行为能够根据调用场景动态调整。
$ARGUMENTS 与位置参数
当用户通过 /skill-name arg1 arg2 调用 Skill 时,可以在 SKILL.md 正文中引用 表 3.6 所示的变量。
| 变量 | 描述 |
|---|---|
$ARGUMENTS |
所有参数的完整字符串 |
$ARGUMENTS[0] |
第一个参数(索引从 0 开始) |
$ARGUMENTS[1] |
第二个参数 |
$0、$1、$2 |
位置参数的简写形式 |
表 3.6:可在 SKILL.md 正文中引用的变量
此类引用的示例如下:
---
name: migrate-component
description: Migrate a component between frameworks
argument-hint: "[component] [from] [to]"
disable-model-invocation: true
---
Migrate the $0 component from $1 to $2.
Preserve all existing behavior and tests.
当调用 /migrate-component SearchBar React Vue 时,Claude 实际接收到的指令是:“将 SearchBar 组件从 React 迁移到 Vue。保留所有现有行为和测试。”
动态上下文注入
这是 Skills 系统中最强大且独特的特性。!`command` 语法允许你在将 SKILL.md 文件发送给 Claude 之前,在 Shell 环境中执行指定命令,并将命令输出直接内联到提示词中。
示例如下。
## Current Context (Auto-detected)
Current branch:
!`git branch --show-current`
Recent commits:
!`git log origin/main..HEAD --oneline 2>/dev/null || echo "No commits"`
Files changed:
!`git diff --stat origin/main 2>/dev/null || git diff --stat HEAD~3`
当你运行 /pr-create "Add auth" 时,shell 命令已经执行完毕,其输出已被内联。Claude 实际接收到的提示词如下所示:
## Current Context (Auto-detected)
Current branch:
feature/auth
Recent commits:
a1b2c3d Add JWT middleware
d4e5f6g Add login endpoint
Files changed:
src/auth/middleware.ts | 45 +++
src/auth/login.ts | 82 +++
2 files changed, 127 insertions(+)
这一设计带来了巨大的工程价值。有无 !`command` 功能的对比如表 3.6所示。
| 维度 | 无 `!command****`** | 有 !****`command` |
|---|---|---|
| Claude 启动上下文 | 空白,需要多轮探索 | 关键信息预先注入 |
| 首次响应中的工具调用次数 | 3–5 次(用于信息收集) | 0–1 次(直接行动) |
| Token 消耗 | 高 | 低 |
| 响应速度 | 慢 | 快 |
| 结果一致性 | 低(存在遗漏信息的风险) | 高(固定注入相同信息) |
表 3.7:有无 !`command` 功能对比
Kage 的笔记
严格定义执行边界。在执行 !`command` 时,Claude 遵循严格的顺序:先替换 $ARGUMENTS 变量,再执行 Shell 命令。这意味着用户的输入会被直接拼接进 Shell 命令中,若缺乏适当控制,极易导致 Shell 注入攻击。因此,任何使用 !`command` 语法的 Skill 都必须通过 allowed‑tools 配置项严格限制可执行命令的范围,以建立必要的安全边界。
作用范围与优先级
Skills 文件可以部署在不同层级,每个层级对应特定的作用范围和适用场景,详见表 3.8。
| 存储位置 | 作用范围 | 典型用途 |
|---|---|---|
| 企业配置中心 | 对所有成员生效 | 强制性的企业级开发规范与安全策略 |
~/.claude/skills/<name>/ |
个人所有项目 | 个人编码习惯、通用工具集以及跨项目辅助脚本 |
<project>/.claude/skills/<name>/ |
仅当前项目 | 项目专属工作流、业务逻辑定制以及团队协作规范 |
| 插件内置资源 | 插件启用时 | 社区共享能力包、特定框架的专用指令集 |
表 3.8:Skills 的作用范围与适用场景
当多个来源包含同名 Skills 时,系统会按照优先级从高到低的顺序解析并加载它们。
企业策略 > 个人配置(~/.claude/) > 项目配置(.claude/) > 插件内置
这一优先级顺序背后的逻辑严格遵循企业治理架构,确保从“强制基线”到“个性化偏好”的有序过渡。
企业策略(不可突破的基线):企业级配置拥有最高权威,用于强制执行全局安全与合规策略。例如,安全审查 Skill 必须强制检查 OWASP Top 10 漏洞。此类关键规则绝不能被项目级或个人配置覆盖,从而确保组织安全红线不被突破。
个人配置(个性化效率工具):个人目录中的配置旨在满足个人开发者习惯。例如,用户可以定义 /commit 命令,按照 conventional commit 规范自动生成提交信息。此类偏好仅适用于个人环境,不影响他人。
项目配置(业务场景定制):项目根目录中的配置是为特定代码库量身定制的。例如,前端项目可以定制专属的组件文档生成 Skill,以适配其独特的技术栈和文档结构。
将 Skill 目录(.claude/skills/)纳入项目的 Git 版本控制,是实现零成本团队知识共享的最优方案。
即插即用:当新团队成员克隆代码库时,相关 Skills 会自动激活,无需手动安装或配置。
同步演进:随着项目迭代,Skill 库可以随代码一同更新,确保团队始终使用最新的工作流标准。
实践:从零构建 3 个 Skills
理论框架至此已经完整,接下来将进入核心工程实践部分。
在本节中,我们将通过三个完整且复杂度递增的案例,逐步演示如何构建高价值 Skills。这三个案例并非随意选择,而是恰好对应前文描述的三种典型应用场景。
- 参考 Skill:代码审查。
- 小冰团队每天需要进行大量代码审查。为此,团队建立了以下内部约定。
- 优先级原则:安全问题最高优先,其次是性能问题,最后是代码风格。
- 反馈要求:必须提供具体修改建议;严禁只指出问题而不提供解决方案。
- 严重程度标注:每个问题都必须标注严重程度。
- 由于相关指南分散在不同文档中,新人难以一次性掌握全部内容,因此将核心指南与目录结构整理如下:
目录结构如下:
code-reviewing/
├── SKILL.md # 核心审查流程与标准
└── reference/
└── severity-guide.md # 严重程度详细分级标准
SKILL.md 的核心内容如下。
---
name: code-reviewing
description: Performs structured code reviews following team standards.
Checks security vulnerabilities, performance issues, and code quality
in priority order. Use when user asks to "review code", "do a code
review", "check this PR", "audit this function", or provides code
and asks for feedback.
allowed-tools:
- Read
- Grep
- Glob
---
# Code Review Process
You are a senior code reviewer. When conducting reviews, strictly follow the priority order below:
## Top Priority: Security Checks
Immediately report the following security issues:
- SQL injection risks: such as direct concatenation of SQL strings or not using parameterized queries
- XSS vulnerabilities: unescaped user input directly output to HTML
- Hardcoded sensitive information: including passwords, keys, tokens, database connection strings, etc.
- Authorization validation flaws: such as missing authentication middleware or logic that allows privilege escalation
## Second Priority: Performance Issues
- N+1 queries: frequent database calls inside loops
- Missing indexes: high-frequency query fields without indexes
- Redundant computation: invariant calculations inside loops that could be moved outside
- Memory leak risks: such as unclosed connections or continuously growing caches
## Third Priority: Code Quality
- Overly long functions: exceeding 50 lines without reasonable justification
- Non-standard naming: unclear variable or function names
- Missing error handling: such as empty catch blocks or silently swallowed exceptions
- Code duplication: violating the DRY principle
## Output Format Specification
Each identified issue must include the following four elements:
- Severity: Critical / Major / Minor
- Issue Description: specific explanation of the problem
- File Location: file_path:line_number
- Recommendation: provide a concrete code fix or solution strategy
If no issues are found, clearly reply "Review Passed" and briefly summarize the main aspects checked.
Note: For detailed severity classification standards, refer to `reference/severity-guide.md`.
本 Skill 围绕三个核心原则设计。
- 只读权限保障:仅启用 Read、Grep 和 Glob 工具,从根本上消除评审过程中意外修改代码的风险
- 优先级排序策略:严格遵循 安全 > 性能 > 质量 的评审顺序,确保关键风险优先处理、不被遗漏
- 结构化输出规范:统一采用 严重级别 + 问题描述 + 文件位置 + 修改建议 的输出格式,保证每次评审结果的一致性与可追溯性
任务型 Skill:智能提交
小冰每天需要频繁提交代码(每天十余次)。手动编写提交信息既耗时又往往不一致。为此,我们设计了以下任务型 Skill。考虑到该操作具有副作用(会直接修改 Git 历史),系统被配置为需要用户显式发起,并严格禁止自动执行。
---
name: committing
description: Quickly perform a git commit with an auto-generated or user-specified message
argument-hint: "[optional: commit message]"
disable-model-invocation: true
allowed-tools:
- Bash(git status:*)
- Bash(git add:*)
- Bash(git commit:*)
- Bash(git diff:*)
model: haiku
---
# Task: Create a git commit
## Input Handling
If a message is provided: $ARGUMENTS
- Use that as the commit message
If no message is provided:
- Analyze the changes with `git diff --staged` (or `git diff` if nothing is staged)
- Generate a concise, meaningful commit message
## Current State (Auto-detected)
Git status:
!`git status --short 2>/dev/null || echo "Not a git repository"`
Staged changes:
!`git diff --staged --stat 2>/dev/null || echo "Nothing staged"`
## Steps
1. Check `git status` to view the current state
2. If nothing is staged, run `git add .` to stage all changes
3. Review the changes to be committed with `git diff --staged`
4. Create a commit with an appropriate message
5. Display a brief confirmation
## Commit Message Format
- Start with type: `feat:`, `fix:`, `docs:`, `refactor:`, `test:`, `chore:`
- Be concise but descriptive (maximum 72 characters for the first line)
- Example: `feat: add user authentication with JWT`
## Output
Show a brief confirmation:
✓ Committed: [commit message]
[number] files changed
上述 Skill 展示了多项高级特性的深度集成。
-
安全控制(
disable‑model‑invocation: true):强制禁用模型调用,确保执行仅依赖预设脚本,防止非预期的 AI 推理介入。 -
动态参数(
$ARGUMENTS):支持灵活的参数传递机制,允许用户直接指定提交信息,或留空以触发自动生成 -
上下文预注入(
!`command`):利用 Shell 命令在执行前即时捕获并注入当前 Git 状态。这使 Claude 在启动时即拥有完整上下文信息,无需额外工具调用即可感知变化,显著提升响应速度。!`command`中的反引号是语法的一部分,而非 Markdown 格式:你需要在SKILL.md中按原样逐字输入它们。 -
成本与性能优化(
model: haiku):指定使用轻量级模型(Haiku)。由于提交操作主要依赖规则匹配而非复杂推理,该配置在保证准确性的同时,有效降低延迟与资源消耗。
一个示例用法如下:
# Automatically generate commit message
/committing
# Specify commit message
/committing fix: resolve login validation bug
复合型 Skill:财务分析(渐进式披露完整案例)
本案例展示了一种高度模块化的渐进式披露架构。通过分层解耦,该设计能够高效管理复杂任务。
- 控制层:主文件负责意图识别与流程路由。
- 知识层:参考文件提供深入的领域知识与基准。
- 规范层:模板确保输出格式高度一致。
- 执行层:脚本封装确定性计算逻辑,消除幻觉风险。
目录结构如下:
financial-analyzing/
├── SKILL.md # [Control Layer] Core entry point: responsible for intent recognition and process routing
├── reference/ # [Knowledge Layer] Domain knowledge base
│ ├── revenue.md # Revenue analysis: formula definitions, industry benchmarks, and key indicators
│ ├── costs.md # Cost analysis: cost structure, allocation logic, and benchmarks
│ └── profitability.md # Profitability analysis: profit margin calculation models and evaluation standards
├── templates/ # [Specification Layer] Output standardization
│ └── analysis_report.md # Analysis report: structured template to ensure uniform deliverable format
└── scripts/ # [Execution Layer] Deterministic computation
└── calculate_ratios.py # Calculation engine: performs precise financial ratio computations, eliminating hallucination risk
SKILL.md 的核心内容如下。
---
name: financial-analyzing
description: Analyze financial data, calculate financial ratios, and generate analysis reports. Use when the user asks about revenue, costs, profits, margins, ROI, financial metrics, or needs financial analysis of a company or project.
allowed-tools:
- Read
- Grep
- Glob
- Bash(python:*)
---
# Financial Analysis Skill
You are a financial analyst. Help users analyze financial data,
calculate key metrics, and generate insightful reports.
## Quick Reference
| Analysis Type | When to Use | Reference |
|-------------------------|---------------------------------|-------------------------------------------|
| Revenue Analysis | Revenue, sales, turnover | `reference/revenue.md` |
| Cost Analysis | Cost, expenses, expenditure | `reference/costs.md` |
| Profitability | Profit, gross margin, net margin | `reference/profitability.md` |
## Analysis Process
### Step 1: Understand the Question
- What financial aspect is the user asking about?
- What data do they have available?
### Step 2: Gather Data
- Request the necessary financial data from the user
- Or read from the provided files/sources
### Step 3: Calculate Metrics
For specific formulas and calculations:
- Revenue metrics → see `reference/revenue.md`
- Cost metrics → see `reference/costs.md`
- Profitability metrics → see `reference/profitability.md`
To run calculations programmatically:
```bash
python scripts/calculate_ratios.py <data_file>
```
### Step 4: Generate Report
Use the template in `templates/analysis_report.md` for structured output.
## Output Guidelines
1. Always show your calculations
2. Explain what each metric means in plain language
3. Provide context (industry benchmarks when available)
4. Give actionable recommendations
5. Never make up financial data — ask for clarification if incomplete
SKILL.md 文件只有约 200 行,完全符合“500 行规则”。快速参考表充当路由器:当 Claude 识别到“毛利率”时,可以直接定位到 reference/profitability.md 中的公式,而无需加载与收入和成本相关的冗余文件。此外,calculate_ratios.py 脚本封装了确定性的计算逻辑,因此 Claude 无需自己执行容易出错的浮点运算——只需调用脚本即可获得精确结果。
这是“渐进式披露”理念的完整体现:以最小的 token 投入实现最大的任务质量。
四种 Skill 设计模式
从工程实践中,我们提炼出四种经过验证的 Skill 设计模式(见 图 3.7)。这些模式并不互斥;成熟的 Skill 系统通常会结合多种模式。
图 3.7:Skill 设计模式组合决策树
- 模板驱动模式:使用预定义模板严格约束输出格式。该模式适用于需要标准化输出的场景,例如周报、事故报告和评审报告。在这种模式下,Claude 的输出将严格遵循模板结构,确保结果可预测、可比较,并支持自动化后处理。
- 脚本增强模式:将确定性的计算逻辑封装到脚本中,由 Claude 调用和执行,而不是自行推导。该模式适用于财务计算、正则表达式匹配和数据转换等场景。与大模型推理相比,脚本执行更精确、更节省 token,也更具可复现性。一个经验法则:如果你发现自己在
SKILL.md中编写公式让 Claude 计算,请立即停止——该逻辑应移入脚本中。 - 知识分层模式:根据使用频率对知识进行分层组织。遵循“80/20 法则”(即 80% 的请求只需要 20% 的核心内容),高频知识内联到
SKILL.md中,而低频知识则放在参考文件中并按需加载。这是对“渐进式披露”理念的模式化总结。 - 工具隔离模式:通过
allowed-tools机制严格定义 Skill 的能力边界。这属于安全设计范畴,而不仅仅是功能设计。其核心价值在于,清晰定义“禁止什么”往往比定义“允许什么”更关键。例如,评审型 Skill 不授予写权限,生成型 Skill 不授予修改权限,测试型 Skill 严禁修改源代码。
小冰问:“Skill 写完了就结束了吗?”
Kage 回答:“当然不是。Skill 是一份活文档,需要持续打磨。”
Claude Code 官网推荐了三种核心测试方法,以确保 Skill 的稳健性。
- 触发测试:准备 10 个应触发该 Skill 的问题和 10 个不应触发的问题,以验证 Claude 的判断准确性。目标是相关任务触发率超过 90%,而不相关任务的误触发率低于 5%。
- 功能测试:验证 Skill 加载后的执行质量。检查点包括输出格式是否符合预期、是否覆盖所有检查清单项,以及边界情况是否得到妥善处理。
- 性能对比:对于同一任务,分别在“有 Skill”和“无 Skill”条件下各执行五次,比较 token 消耗、用户纠正次数和最终输出质量。
如果你发现自己反复手动纠正 Claude 的输出(例如,总是不得不提醒它“记得标注认证要求”),这就是一个明确信号:SKILL.md 正文需要更新。将纠正逻辑直接写入 SKILL.md,下次就不会再出现同样的错误。
这个迭代过程与传统软件修 bug 循环完全相同:发现问题 → 定位原因(描述不精确?步骤缺失?格式定义含糊?)→ 修复文档 → 验证效果。
Claude Code 还提供了一个名为 skill-creator 的专用 Skill,可以帮助你从自然语言描述生成 SKILL.md 的初始版本。示例指令:

浙公网安备 33010602011771号