Claude Code中英文系列教程22:通过Skills扩展 Claude 的功能【重要】

5 阅读26分钟

Create, manage, and share skills to extend Claude’s capabilities in Claude Code. Includes custom slash commands. 通过在 Claude Code 中创建、管理和共享技能,以扩展 Claude 的功能。包含自定义斜杠命令。

Skills extend what Claude can do. Create a SKILL.md file with instructions, and Claude adds it to its toolkit. Claude uses skills when relevant, or you can invoke one directly with /skill-name. 技能扩展了 Claude 的功能。创建一个 SKILL.md 文件,包含说明,Claude 将其添加到其工具包中。Claude 在相关情况下使用技能,或者您可以直接使用 /skill-name 调用其中一个技能。

Custom slash commands have been merged into skills. A file at .claude/commands/review.md and a skill at .claude/skills/review/SKILL.md both create /review and work the same way. Your existing .claude/commands/ files keep working. Skills add optional features: a directory for supporting files, frontmatter to control whether you or Claude invokes them, and the ability for Claude to load them automatically when relevant. 自定义斜杠命令现在已经合并到技能中。位于 .claude/commands/review.md 的文件和位于 .claude/skills/review/SKILL.md 的技能都会创建 /review 并以相同方式工作。 您现有的 .claude/commands/ 文件仍然可以正常使用。技能增加了更多可选功能:支持文件的目录、用于控制由您或 Claude 调用的 frontmatter,以及 Claude 在相关的情况下自动加载它们的能力。

Claude Code skills follow the Agent Skills (agentskills.io/ )open standard, which works across multiple AI tools. Claude Code extends the standard with additional features like invocation control, subagent execution, and dynamic context injection. Claude Code 技能遵循 Agent Skills 开放标准,该标准可在多种 AI 工具中工作。Claude Code 通过增加调用控制、子代理执行和动态上下文注入等附加功能扩展了该标准。

一,Getting started 入门指南

1.1 Create your first skill 创建你的第一个技能

This example creates a skill that teaches Claude to explain code using visual diagrams and analogies. Since it uses default frontmatter, Claude can load it automatically when you ask how something works, or you can invoke it directly with /explain-code. 以下示例创建了一个技能,教 Claude 使用视觉图表和类比来解释代码。由于它使用了默认的frontmatter前置文本,当您询问某个事物的工作原理时,Claude 可以自动加载它,或者您可以直接使用 /explain-code 手动调用它。

1, Create the skill directory 创建技能目录

Create a directory for the skill in your personal skills folder. Personal skills are available across all your projects. 在您的个人技能文件夹中为技能创建一个目录。个人技能可以在所有您的项目中使用。

mkdir -p ~/.claude/skills/explain-code

2,Write SKILL.md 编写 SKILL.md

Every skill needs a SKILL.md file with two parts: YAML frontmatter (between --- markers) that tells Claude when to use the skill, and markdown content with instructions Claude follows when the skill is invoked. The name field becomes the /slash-command, and the description helps Claude decide when to load it automatically. 每个技能需要一个 SKILL.md 文件,包含两部分:YAML 前置部分(位于 --- 标记之间),用于告诉 Claude 何时使用该技能,以及包含 Claude 在调用技能时遵循的 指令的 markdown 内容。 name 字段成为 /slash-command ,而 description 帮助 Claude 自动决定何时加载它。

Create ~/.claude/skills/explain-code/SKILL.md: #创建 ~/.claude/skills/explain-code/SKILL.md

内容如下:

---
name: explain-code
description: Explains code with visual diagrams and analogies. Use when explaining how code works, teaching about a codebase, or when the user asks "how does this work?" #使用视觉图表和类比来解释代码。在解释代码如何工作、仓库教学或当用户问“这是如何工作的?”时使用。
---

When explaining code, always include: #在解释代码时,始终包含:

1. **Start with an analogy**: Compare the code to something from everyday life   #**从一个类比开始**: 将代码与日常生活中的某物进行比较
2. **Draw a diagram**: Use ASCII art to show the flow, structure, or relationships #**绘制一个图表**: 使用ASCII展示流程、结构或关系
3. **Walk through the code**: Explain step-by-step what happens  #**逐步解释代码**: 解释每一步发生了什么
4. **Highlight a gotcha**: What's a common mistake or misconception? # **突出一个常见陷阱**: 什么是常见的错误或误解?

Keep explanations conversational. For complex concepts, use multiple analogies. #保持解释简洁易懂。对于复杂的概念,使用多个类比。

上面这个就是一个skills

3, Test the skill 测试技能

You can test it two ways: 你可以通过两种方式测试它:

1,Let Claude invoke it automatically by asking something that matches the description: 通过询问符合描述的内容来自动调用它,如:

How does this code work?

2,Or invoke it directly with the skill name: 直接使用技能名称调用它:

/explain-code src/auth/login.ts

Either way, Claude should include an analogy and ASCII diagram in its explanation. 无论使用哪种方式,Claude 都应该在解释中包含类比和 ASCII 图。

1.2 Where skills live 技能存放位置

Where you store a skill determines who can use it: 你存储技能的位置决定了谁可以使用它:

有以下4种位置 1,Enterprise 企业

See managed settings 参见管理设置

哪些人可以用:All users in your organization 您组织中的所有用户

2,Personal 个人

存放在 ~/.claude/skills//SKILL.md

All your projects 所有你的项目都能用

3,Project 项目级

存放在 .claude/skills//SKILL.md

This project only 仅此项目可用

4,Plugin 插件里面的

位置在 /skills//SKILL.md

Where plugin is enabled 在插件启用的地方才能用。

When skills share the same name across levels, higher-priority locations win: enterprise > personal > project. Plugin skills use a plugin-name:skill-name namespace, so they cannot conflict with other levels. If you have files in .claude/commands/, those work the same way, but if a skill and a command share the same name, the skill takes precedence. 当技能在不同级别共享相同名称时,高优先级位置会生效:企业 > 个人 > 项目。 插件技能使用 plugin-name:skill-name 命名空间,因此它们不会与其他级别冲突。 如果你在 .claude/commands/ 中有文件,它们的工作方式相同,但如果一个技能和一个命令有相同名称,技能会优先于command。

1.2.1 Automatic discovery from nested directories 从嵌套目录自动发现技能

When you work with files in subdirectories, Claude Code automatically discovers skills from nested .claude/skills/ directories. For example, if you’re editing a file in packages/frontend/, Claude Code also looks for skills in packages/frontend/.claude/skills/. This supports monorepo setups where packages have their own skills. 当你处理子目录中的文件时,Claude Code 会自动从嵌套的 .claude/skills/ 目录中发现技能。 例如,如果你正在编辑 packages/frontend/ 中的文件,Claude Code 也会在 packages/frontend/.claude/skills/ 中查找技能。这支持单一代码库设置,其中每个packages都有自己的技能。

Each skill is a directory with SKILL.md as the entrypoint: 每个技能都是一个目录,以 SKILL.md 作为入口点:

my-skill/
├── SKILL.md           # Main instructions (required) 主要指令
├── template.md        # Template for Claude to fill in 供Claude填充的模板
├── examples/
│   └── sample.md      # Example output showing expected format
└── scripts/
    └── validate.sh    # Script Claude can execute Claude可以执行的脚本

The SKILL.md contains the main instructions and is required. Other files are optional and let you build more powerful skills: templates for Claude to fill in, example outputs showing the expected format, scripts Claude can execute, or detailed reference documentation. Reference these files from your SKILL.md so Claude knows what they contain and when to load them. SKILL.md 包含主要指令,是必需的。其他文件是可选的,它们让你构建更强大的技能: Claude 可以填写的模板、展示预期格式的示例输出、Claude 可以执行的脚本或详细的参考文档。 从你的 SKILL.md 文件里面引用这些文件,以便 Claude 知道它们包含的内容以及何时加载它们。

Files in .claude/commands/ still work and support the same frontmatter. Skills are recommended since they support additional features like supporting files. .claude/commands/ 中的文件仍然有效,并支持相同的 frontmatter。但建议使用技能,因为它们支持额外的功能,如支持文件。

二,Configure skills 配置技能

Skills are configured through YAML frontmatter at the top of SKILL.md and the markdown content that follows. 技能通过 SKILL.md 顶部附近的 YAML 前置文本和随后的 markdown 内容进行配置。

2.1 Types of skill content 技能内容类型

Skill files can contain any instructions, but thinking about how you want to invoke them helps guide what to include: 技能文件可以包含任何指令,思考如何调用它们将有助于指导你将要包含的内容:

Reference content adds knowledge Claude applies to your current work. Conventions, patterns, style guides, domain knowledge. This content runs inline so Claude can use it alongside your conversation context. Reference参考内容为 Claude 提供 应用于当前工作的知识。 约定、模式、风格指南、领域知识。此内容以行内方式运行,因此 Claude 可以在您的对话上下文中使用它。

---
name: api-conventions
description: API design patterns for this codebase #这个代码库的API设计模式
---

When writing API endpoints: #编写 API 端点时
- Use RESTful naming conventions #使用 RESTful 命名规范
- Return consistent error formats #返回一致的错误格式
- Include request validation #包含请求验证

Task content gives Claude step-by-step instructions for a specific action, like deployments, commits, or code generation. These are often actions you want to invoke directly with /skill-name rather than letting Claude decide when to run them. Add disable-model-invocation: true to prevent Claude from triggering it automatically. Task任务内容为 Claude 提供针对特定操作的逐步指令,例如部署、提交或代码生成。这些操作通常是你希望直接使用 /skill-name 调用,而不是让 Claude 决定何时执行。 添加 disable-model-invocation: true 以防止 Claude 自动触发它。

---
name: deploy
description: Deploy the application to production #将应用程序部署到生产环境
context: fork
disable-model-invocation: true
---

Deploy the application: #部署应用程序
1. Run the test suite #运行测试套件
2. Build the application #构建应用程序
3. Push to the deployment target #推送到部署目标

Your SKILL.md can contain anything, but thinking through how you want the skill invoked (by you, by Claude, or both) and where you want it to run (inline or in a subagent) helps guide what to include. For complex skills, you can also add supporting files to keep the main skill focused. 你的 SKILL.md 可以包含任何内容,但思考一下你希望技能如何被调用(被你、被 Claude 或两者)以及你希望它在何处运行(内联或在一个子代理中)有助于指导你应包含哪些内容。 对于复杂的技能,你也可以添加支持文件以保持主技能更专注。

2.2 Frontmatter reference # Frontmatter参考

Beyond the markdown content, you can configure skill behavior using YAML frontmatter fields between --- markers at the top of your SKILL.md file: 除了 Markdown 内容之外,还可以使用 YAML frontmatter字段在 SKILL.md 文件顶部的2个 --- 标记之间配置技能的行为:

---
name: my-skill
description: What this skill does
disable-model-invocation: true
allowed-tools: Read, Grep
---

Your skill instructions here...

All fields are optional. Only description is recommended so Claude knows when to use the skill. 所有字段都是可选的。建议使用 description ,以便 Claude 知道何时使用该技能。

下面介绍一下这些字段的含义

name:Display name for the skill. If omitted, uses the directory name. Lowercase letters, numbers, and hyphens only (max 64 characters). 技能的显示名称。如果省略,则使用目录名称。仅限小写字母、数字和连字符(最多 64 个字符)。

description:What the skill does and when to use it. Claude uses this to decide when to apply the skill. If omitted, uses the first paragraph of markdown content. 这个技能是干什么的以及何时使用它。Claude 使用此信息来决定何时应用该技能。如果省略,则使用 markdown 内容的第一段。 最好填这个字段

argument-hint:Hint shown during autocomplete to indicate expected arguments. Example: [issue-number] or [filename] [format]. 在自动补全期间显示的提示,用于指示预期的参数。例如: [issue-number] 或 [filename] [format] 。

disable-model-invocation:Set to true to prevent Claude from automatically loading this skill. Use for workflows you want to trigger manually with /name. Default: false. 设置为 true 以防止 Claude 自动加载此技能。用于您希望手动使用 /name 触发的流程。默认: false 。

user-invocable:Set to false to hide from the / menu. Use for background knowledge users shouldn’t invoke directly. Default: true. 设置为 false ,就会隐藏于 / 菜单里面。用于背景知识,用户不应直接调用。默认: true 。

allowed-tools:Tools Claude can use without asking permission when this skill is active. 无需请求权限即可使用的工具。

model:Model to use when this skill is active. 使用的模型。

context:Set to fork to run in a forked subagent context. 设置为 fork 以在forked的subagent子代理上下文中运行。

agent:Which subagent type to use when context: fork is set. 当 context: fork 被设置时,使用哪种subagent子代理类型

hooks:Hooks scoped to this skill’s lifecycle. 与此技能生命周期相关的钩子。

2.2.1 Available string substitutions 可用的字符串替换

Skills support string substitution for dynamic values in the skill content: 技能支持对技能内容中的动态值进行字符串替换:

有下面2个变量:

1,ARGUMENTSAllargumentspassedwheninvokingtheskill.IfARGUMENTS:All arguments passed when invoking the skill. If ARGUMENTS is not present in the content, arguments are appended as ARGUMENTS: . 调用技能时传递的所有参数。如果内容中不存在 $ARGUMENTS ,参数将作为 ARGUMENTS: 附加。

2,${CLAUDE_SESSION_ID} :The current session ID. Useful for logging, creating session-specific files, or correlating skill output with sessions. 当前会话 ID。用于日志记录、创建会话特定文件,或将技能输出与会话相关联。

Example using substitutions: 使用替换的示例:

---
name: session-logger
description: Log activity for this session #记录本次会话的日志活动
---

Log the following to logs/${CLAUDE_SESSION_ID}.log: #将以下内容记录到 logs/${CLAUDE_SESSION_ID}.log 中:

$ARGUMENTS

2.3 Add supporting files

Skills can include multiple files in their directory. This keeps SKILL.md focused on the essentials while letting Claude access detailed reference material only when needed. Large reference docs, API specifications, or example collections don’t need to load into context every time the skill runs. 技能可以包含其目录中的多个文件。这使 SKILL.md 聚焦于核心内容,同时允许 Claude 仅在需要时访问详细的参考材料。 大型参考文档、API 规范或示例集合 无需每次技能运行时都加载到上下文中。

my-skill/
├── SKILL.md (required - overview and navigation) #概述和导航
├── reference.md (detailed API docs - loaded when needed) #按需加载
├── examples.md (usage examples - loaded when needed) #按需加载
└── scripts/
    └── helper.py (utility script - executed, not loaded) #实用脚本 ,不会加载

Reference supporting files from SKILL.md so Claude knows what each file contains and when to load it: 从 SKILL.md 引用支持文件,以便 Claude 知道每个文件的内容以及何时加载它:

## Additional resources #附加资源

- For complete API details, see [reference.md](reference.md) #请参考reference.md以获取完整的API详细信息
- For usage examples, see [examples.md](examples.md) #使用示例

Keep SKILL.md under 500 lines. Move detailed reference material to separate files. 保持 SKILL.md 在 500 行以内。将详细的参考材料移动到单独的文件中。

2.4 Control who invokes a skill 控制谁调用技能

By default, both you and Claude can invoke any skill. You can type /skill-name to invoke it directly, and Claude can load it automatically when relevant to your conversation. Two frontmatter fields let you restrict this: 默认情况下,你和 Claude 都可以调用任何技能。你可以输入 /skill-name 直接调用,Claude 会在对话相关时自动加载它。有两个 frontmatter 字段可以限制这一点:

1,disable-model-invocation: true: Only you can invoke the skill. Use this for workflows with side effects or that you want to control timing, like /commit, /deploy, or /send-slack-message. You don’t want Claude deciding to deploy because your code looks ready. disable-model-invocation: true : 只有你可以调用该技能。适用于有副作用或需要你来控制时机的流程,如 /commit 、 /deploy 或 /send-slack-message 。你不希望 Claude 因为你的代码看起来准备好了就自行决定部署。

2,user-invocable: false: Only Claude can invoke the skill. Use this for background knowledge that isn’t actionable as a command. A legacy-system-context skill explains how an old system works. Claude should know this when relevant, but /legacy-system-context isn’t a meaningful action for users to take. user-invocable: false : 只有 Claude 可以调用该技能。适用于不可作为命令执行的后台知识。一个 legacy-system-context 技能解释了旧系统的工作原理。 Claude 在相关时应知道这一点,但 /legacy-system-context 对用户来说并不是一个有意义的操作。

This example creates a deploy skill that only you can trigger. The disable-model-invocation: true field prevents Claude from running it automatically: 下面这个示例创建了一个只有你能触发的部署技能。 disable-model-invocation: true 字段防止 Claude 自动运行它:

---
name: deploy
description: Deploy the application to production #将应用程序部署到生产环境
disable-model-invocation: true
---

Deploy $ARGUMENTS to production:

1. Run the test suite #运行测试套件
2. Build the application #构建应用程序
3. Push to the deployment target #推送到部署目标
4. Verify the deployment succeeded #验证部署是否成功

Here’s how the two fields affect invocation and context loading: 以下是这两个字段如何影响调用和上下文加载:

1,默认情况下,你和claude code都可以调用,Description always in context, full skill loads when invoked 描述始终在上下文中,调用时才加载完整技能

2,disable-model-invocation: true 时,你可以手动调用,但cc不能调用,此时 Description not in context, full skill loads when you invoke 描述不在上下文里面,调用时才加载完整技能

3,user-invocable: false 时,cc可以调用,但不能手动调用,此时 Description always in context, full skill loads when invoked 描述始终在上下文中,调用时才加载完整技能

In a regular session, skill descriptions are loaded into context so Claude knows what’s available, but full skill content only loads when invoked. Subagents with preloaded skills work differently: the full skill content is injected at startup. 在常规会话中,技能描述被加载到上下文中,以便 Claude 知道有哪些可用技能,但完整技能内容仅在调用时加载。 预加载技能的Subagents子代理工作方式不同:完整技能内容在启动时注入。

2.5 Restrict tool access 限制工具访问

Use the allowed-tools field to limit which tools Claude can use when a skill is active. This skill creates a read-only mode where Claude can explore files but not modify them: 使用 allowed-tools 字段来限制当技能激活时 Claude 可以使用哪些工具。下面这个技能创建了一个只读模式,Claude 可以探索文件但不能修改它们:

---
name: safe-reader
description: Read files without making changes #在不修改文件的情况下读取文件
allowed-tools: Read, Grep, Glob
---

2.6 Pass arguments to skills 向技能传递参数

Both you and Claude can pass arguments when invoking a skill. Arguments are available via the ARGUMENTSplaceholder.你和Claude在调用技能时都可以传递参数。参数可以通过ARGUMENTS placeholder. 你和 Claude 在调用技能时都可以传递参数。参数可以通过 ARGUMENTS 占位符访问。

This skill fixes a GitHub issue by number. The ARGUMENTSplaceholdergetsreplacedwithwhateverfollowstheskillname:下面这个技能通过编号修复GitHubissueARGUMENTS placeholder gets replaced with whatever follows the skill name: 下面这个技能通过编号修复 GitHub issue。 ARGUMENTS 占位符会被技能名称后面的内容替换:

---
name: fix-issue
description: Fix a GitHub issue
disable-model-invocation: true
---

Fix GitHub issue $ARGUMENTS following our coding standards. #按照我们的编码标准修复 GitHub 问题 $ARGUMENTS。

1. Read the issue description #阅读问题描述
2. Understand the requirements #理解需求
3. Implement the fix #实现修复
4. Write tests #编写测试
5. Create a commit #创建提交

When you run /fix-issue 123, Claude receives “Fix GitHub issue 123 following our coding standards…” 当你运行 /fix-issue 123 时,Claude 会收到“修复 GitHub 问题 123,遵循我们的编码标准……”

If you invoke a skill with arguments but the skill doesn’t include ARGUMENTS,ClaudeCodeappendsARGUMENTS:<yourinput>totheendoftheskillcontentsoClaudestillseeswhatyoutyped.如果你调用一个带参数的技能,但该技能不包含ARGUMENTS, Claude Code appends ARGUMENTS: <your input> to the end of the skill content so Claude still sees what you typed. 如果你调用一个带参数的技能,但该技能不包含 ARGUMENTS ,Claude Code 会在技能内容的末尾追加 ARGUMENTS: ,这样 Claude 仍然能看到你输入的内容。

三,Advanced patterns 高级模式

3.1 Inject dynamic context 注入动态上下文

The !command syntax runs shell commands before the skill content is sent to Claude. The command output replaces the placeholder, so Claude receives actual data, not the command itself. ! 命令语法在skill内容发送给 Claude 之前先运行 shell 命令。命令输出会替换占位符,因此 Claude 接收的是实际数据,而不是命令本身。

This skill summarizes a pull request by fetching live PR data with the GitHub CLI. The !gh pr diff and other commands run first, and their output gets inserted into the prompt: 下面这个技能通过使用 GitHub CLI 获取实时 PR 数据来总结 pull 请求。 ! gh pr diff和其他命令会首先运行,它们的输出会被插入到提示中:

---
name: pr-summary
description: Summarize changes in a pull request #总结一个PR的变更
context: fork
agent: Explore
allowed-tools: Bash(gh:*)
---

## Pull request context #拉取请求上下文
- PR diff: !`gh pr diff`
- PR comments: !`gh pr view --comments`
- Changed files: !`gh pr diff --name-only`

## Your task
Summarize this pull request...

When this skill runs: 当这个技能运行时:

Each !command executes immediately (before Claude sees anything) 每个 ! 命令“会立即执行(在 Claude 看到任何内容之前)

The output replaces the placeholder in the skill content 输出替换了技能内容中的占位符

Claude receives the fully-rendered prompt with actual PR data Claude 接收到包含实际 PR 数据的完整渲染提示

This is preprocessing, not something Claude executes. Claude only sees the final result. 这是预处理,不是 Claude 执行的操作。Claude 只看到最终结果。

To enable extended thinking in a skill, include the word “ultrathink” anywhere in your skill content. 要在技能中启用扩展思考,请在技能内容中的任何位置包含单词“ultrathink”。

3.2 Run skills in a subagent 在子代理中运行技能

Add context: fork to your frontmatter when you want a skill to run in isolation. The skill content becomes the prompt that drives the subagent. It won’t have access to your conversation history. 当你希望一个技能独立运行时,在 frontmatter 中添加 context: fork 。技能内容将成为驱动子代理的提示。它将无法访问你的对话历史。

context: fork only makes sense for skills with explicit instructions. If your skill contains guidelines like “use these API conventions” without a task, the subagent receives the guidelines but no actionable prompt, and returns without meaningful output. context: fork 仅适用于具有明确指令的技能。如果你的技能包含如“使用这些 API 规范”之类的指南但没有任务,子代理将接收指南但没有可操作的提示,并返回无意义的输出。

Skills and subagents work together in two directions: 技能和子代理在两个方向上协同工作:

1, Skill with context: fork 此时系统提示来自 From agent type (Explore, Plan, etc.)

任务:SKILL.md content

会加载 CLAUDE.md

2,Subagent with skills field 系统提示词来自 Subagent’s markdown body #子代理的 markdown 正文

任务来自 Claude’s delegation message #Claude 的委派消息

会加载 Preloaded skills + CLAUDE.md

With context: fork, you write the task in your skill and pick an agent type to execute it. For the inverse (defining a custom subagent that uses skills as reference material), see Subagents. 使用 context: fork ,你在技能中编写任务并选择一个代理类型来执行它。对于反向操作(定义一个使用技能作为参考材料的自定义子代理),请参考子代理。

3.2.1 Example: Research skill using Explore agent #示例:使用探索agent的研究skill技能

This skill runs research in a forked Explore agent. The skill content becomes the task, and the agent provides read-only tools optimized for codebase exploration: 下面这个技能在一个forked的 Explore 代理中运行研究。技能内容成为任务,代理提供针对仓库探索优化的只读工具:

---
name: deep-research
description: Research a topic thoroughly #彻底研究一个主题
context: fork
agent: Explore
---

Research $ARGUMENTS thoroughly: #彻底研究 $ARGUMENTS

1. Find relevant files using Glob and Grep #使用 Glob 和 Grep 查找相关文件
2. Read and analyze the code #读取并分析代码
3. Summarize findings with specific file references #总结发现并附上具体文件引用

When this skill runs: 当此技能运行时:

1, A new isolated context is created 创建了一个新的隔离上下文

2, The subagent receives the skill content as its prompt (“Research ARGUMENTSthoroughly)subagent子代理将技能内容作为其提示(“彻底研究ARGUMENTS thoroughly…”) subagent子代理将技能内容作为其提示(“彻底研究ARGUMENTS…”)

3, The agent field determines the execution environment (model, tools, and permissions) agent 字段确定执行环境(模型、工具和权限)

4, Results are summarized and returned to your main conversation 结果被总结并返回到您的主对话中

The agent field specifies which subagent configuration to use. Options include built-in agents (Explore, Plan, general-purpose) or any custom subagent from .claude/agents/. If omitted, uses general-purpose. agent 字段指定使用哪个子代理配置。选项包括内置代理( Explore 、 Plan 、 general-purpose )或来自 .claude/agents/ 的任何自定义子代理。如果省略,则使用 general-purpose 。

3.3 Restrict Claude’s skill access 限制 Claude 的技能访问

By default, Claude can invoke any skill that doesn’t have disable-model-invocation: true set. Built-in commands like /compact and /init are not available through the Skill tool. 默认情况下,Claude 可以调用任何未设置 disable-model-invocation: true 的技能。 内置命令 /compact 和 /init 无法通过技能工具访问。

Three ways to control which skills Claude can invoke: 控制 Claude 可以调用哪些技能有三个方法:

1,Disable all skills by denying the Skill tool in /permissions: 禁用所有技能,通过在 /permissions 中拒绝技能工具:

# Add to deny rules:
Skill

2,Allow or deny specific skills using permission rules: 使用权限规则允许或拒绝特定技能:

# Allow only specific skills
Skill(commit)
Skill(review-pr:*)

# Deny specific skills
Skill(deploy:*)

Permission syntax: Skill(name) for exact match, Skill(name:) for prefix match with any arguments. 权限语法: Skill(name) 用于精确匹配, Skill(name:) 用于带任何参数的前缀匹配。

3,Hide individual skills by adding disable-model-invocation: true to their frontmatter. This removes the skill from Claude’s context entirely. 通过在它们的 frontmatter 前添加 disable-model-invocation: true 隐藏单个技能。这将技能完全从 Claude 的上下文中移除。

The user-invocable field only controls menu visibility, not Skill tool access. Use disable-model-invocation: true to block programmatic invocation. user-invocable 字段仅控制菜单可见性,不控制技能工具访问。使用 disable-model-invocation: true 来阻止程序化调用。

四,Share skills 分享技能

Skills can be distributed at different scopes depending on your audience: 技能可以根据你的受众在不同的范围内分发:

1,Project skills: Commit .claude/skills/ to version control 项目技能:将 .claude/skills/ 提交到版本控制

2, Plugins: Create a skills/ directory in your plugin 插件:在你的插件中创建一个 skills/ 目录

3,Managed: Deploy organization-wide through managed settings 管理:通过管理设置进行全组织部署

4.1 Generate visual output 生成可视化输出

Skills can bundle and run scripts in any language, giving Claude capabilities beyond what’s possible in a single prompt. One powerful pattern is generating visual output: interactive HTML files that open in your browser for exploring data, debugging, or creating reports. 技能可以打包并运行任何语言的脚本,使 Claude 的能力超越单个提示所能实现的范围。一种强大的模式是生成可视化输出:在浏览器中打开交互式 的HTML 文件,用于探索数据、调试或创建报告。

This example creates a codebase explorer: an interactive tree view where you can expand and collapse directories, see file sizes at a glance, and identify file types by color. 下面这个示例创建了一个代码库浏览器:一个交互式树形视图,你可以展开和折叠目录,一眼就能看到文件大小,并通过颜色识别文件类型。

Create the Skill directory: 创建 Skill 目录:

mkdir -p ~/.claude/skills/codebase-visualizer/scripts

Create ~/.claude/skills/codebase-visualizer/SKILL.md. The description tells Claude when to activate this Skill, and the instructions tell Claude to run the bundled script: 创建 ~/.claude/skills/codebase-visualizer/SKILL.md 。通过描述告诉 Claude 何时激活这个技能,并通过指令告诉 Claude 运行捆绑的脚本:

---
name: codebase-visualizer
description: Generate an interactive collapsible tree visualization of your codebase. Use when exploring a new repo, understanding project structure, or identifying large files. #生成一个交互式可折叠的代码库树形可视化。用于探索新仓库、理解项目结构或识别大文件。
allowed-tools: Bash(python:*)
---

# Codebase Visualizer #代码库可视化工具

Generate an interactive HTML tree view that shows your project's file structure with collapsible directories. #生成一个交互式的HTML树形视图,显示您的项目文件结构,并具有可折叠的目录。

## Usage

Run the visualization script from your project root: #从你的项目根目录运行可视化脚本

```bash
python ~/.claude/skills/codebase-visualizer/scripts/visualize.py .

This creates codebase-map.html in the current directory and opens it in your default browser. #这会在当前目录下创建 codebase-map.html 并用你的默认浏览器打开它。

What the visualization shows

  • Collapsible directories: Click folders to expand/collapse #可折叠目录:点击文件夹进行展开/折叠
  • File sizes: Displayed next to each file #文件大小:显示在每个文件旁边
  • Colors: Different colors for different file types #颜色:不同文件类型使用不同颜色
  • Directory totals: Shows aggregate size of each folder #目录总计:显示每个文件夹的总大小

Create ~/.claude/skills/codebase-visualizer/scripts/visualize.py. This script scans a directory tree and generates a self-contained HTML file with:
创建 ~/.claude/skills/codebase-visualizer/scripts/visualize.py 。这个脚本扫描目录树并生成一个自包含的 HTML 文件,包含:

A summary sidebar showing file count, directory count, total size, and number of file types
一个显示文件数量、目录数量、总大小和文件类型数量的摘要侧边栏

A bar chart breaking down the codebase by file type (top 8 by size)
按文件类型分解代码库的条形图(前 8 个按大小排序)

A collapsible tree where you can expand and collapse directories, with color-coded file type indicators
一个可折叠的树形结构,可以展开和折叠目录,并带有颜色编码的文件类型指示器

The script requires Python but uses only built-in libraries, so there are no packages to install:
该脚本需要 Python,但仅使用内置库,因此无需安装任何包:

```python
#!/usr/bin/env python3
"""Generate an interactive collapsible tree visualization of a codebase."""

import json
import sys
import webbrowser
from pathlib import Path
from collections import Counter

IGNORE = {'.git', 'node_modules', '__pycache__', '.venv', 'venv', 'dist', 'build'}

def scan(path: Path, stats: dict) -> dict:
    result = {"name": path.name, "children": [], "size": 0}
    try:
        for item in sorted(path.iterdir()):
            if item.name in IGNORE or item.name.startswith('.'):
                continue
            if item.is_file():
                size = item.stat().st_size
                ext = item.suffix.lower() or '(no ext)'
                result["children"].append({"name": item.name, "size": size, "ext": ext})
                result["size"] += size
                stats["files"] += 1
                stats["extensions"][ext] += 1
                stats["ext_sizes"][ext] += size
            elif item.is_dir():
                stats["dirs"] += 1
                child = scan(item, stats)
                if child["children"]:
                    result["children"].append(child)
                    result["size"] += child["size"]
    except PermissionError:
        pass
    return result

def generate_html(data: dict, stats: dict, output: Path) -> None:
    ext_sizes = stats["ext_sizes"]
    total_size = sum(ext_sizes.values()) or 1
    sorted_exts = sorted(ext_sizes.items(), key=lambda x: -x[1])[:8]
    colors = {
        '.js': '#f7df1e', '.ts': '#3178c6', '.py': '#3776ab', '.go': '#00add8',
        '.rs': '#dea584', '.rb': '#cc342d', '.css': '#264de4', '.html': '#e34c26',
        '.json': '#6b7280', '.md': '#083fa1', '.yaml': '#cb171e', '.yml': '#cb171e',
        '.mdx': '#083fa1', '.tsx': '#3178c6', '.jsx': '#61dafb', '.sh': '#4eaa25',
    }
    lang_bars = "".join(
        f'<div class="bar-row"><span class="bar-label">{ext}</span>'
        f'<div class="bar" style="width:{(size/total_size)*100}%;background:{colors.get(ext,"#6b7280")}"></div>'
        f'<span class="bar-pct">{(size/total_size)*100:.1f}%</span></div>'
        for ext, size in sorted_exts
    )
    def fmt(b):
        if b < 1024: return f"{b} B"
        if b < 1048576: return f"{b/1024:.1f} KB"
        return f"{b/1048576:.1f} MB"

    html = f'''<!DOCTYPE html>
<html><head>
  <meta charset="utf-8"><title>Codebase Explorer</title>
  <style>
    body {{ font: 14px/1.5 system-ui, sans-serif; margin: 0; background: #1a1a2e; color: #eee; }}
    .container {{ display: flex; height: 100vh; }}
    .sidebar {{ width: 280px; background: #252542; padding: 20px; border-right: 1px solid #3d3d5c; overflow-y: auto; flex-shrink: 0; }}
    .main {{ flex: 1; padding: 20px; overflow-y: auto; }}
    h1 {{ margin: 0 0 10px 0; font-size: 18px; }}
    h2 {{ margin: 20px 0 10px 0; font-size: 14px; color: #888; text-transform: uppercase; }}
    .stat {{ display: flex; justify-content: space-between; padding: 8px 0; border-bottom: 1px solid #3d3d5c; }}
    .stat-value {{ font-weight: bold; }}
    .bar-row {{ display: flex; align-items: center; margin: 6px 0; }}
    .bar-label {{ width: 55px; font-size: 12px; color: #aaa; }}
    .bar {{ height: 18px; border-radius: 3px; }}
    .bar-pct {{ margin-left: 8px; font-size: 12px; color: #666; }}
    .tree {{ list-style: none; padding-left: 20px; }}
    details {{ cursor: pointer; }}
    summary {{ padding: 4px 8px; border-radius: 4px; }}
    summary:hover {{ background: #2d2d44; }}
    .folder {{ color: #ffd700; }}
    .file {{ display: flex; align-items: center; padding: 4px 8px; border-radius: 4px; }}
    .file:hover {{ background: #2d2d44; }}
    .size {{ color: #888; margin-left: auto; font-size: 12px; }}
    .dot {{ width: 8px; height: 8px; border-radius: 50%; margin-right: 8px; }}
  </style>
</head><body>
  <div class="container">
    <div class="sidebar">
      <h1>📊 Summary</h1>
      <div class="stat"><span>Files</span><span class="stat-value">{stats["files"]:,}</span></div>
      <div class="stat"><span>Directories</span><span class="stat-value">{stats["dirs"]:,}</span></div>
      <div class="stat"><span>Total size</span><span class="stat-value">{fmt(data["size"])}</span></div>
      <div class="stat"><span>File types</span><span class="stat-value">{len(stats["extensions"])}</span></div>
      <h2>By file type</h2>
      {lang_bars}
    </div>
    <div class="main">
      <h1>📁 {data["name"]}</h1>
      <ul class="tree" id="root"></ul>
    </div>
  </div>
  <script>
    const data = {json.dumps(data)};
    const colors = {json.dumps(colors)};
    function fmt(b) {{ if (b < 1024) return b + ' B'; if (b < 1048576) return (b/1024).toFixed(1) + ' KB'; return (b/1048576).toFixed(1) + ' MB'; }}
    function render(node, parent) {{
      if (node.children) {{
        const det = document.createElement('details');
        det.open = parent === document.getElementById('root');
        det.innerHTML = `<summary><span class="folder">📁 ${{node.name}}</span><span class="size">${{fmt(node.size)}}</span></summary>`;
        const ul = document.createElement('ul'); ul.className = 'tree';
        node.children.sort((a,b) => (b.children?1:0)-(a.children?1:0) || a.name.localeCompare(b.name));
        node.children.forEach(c => render(c, ul));
        det.appendChild(ul);
        const li = document.createElement('li'); li.appendChild(det); parent.appendChild(li);
      }} else {{
        const li = document.createElement('li'); li.className = 'file';
        li.innerHTML = `<span class="dot" style="background:${{colors[node.ext]||'#6b7280'}}"></span>${{node.name}}<span class="size">${{fmt(node.size)}}</span>`;
        parent.appendChild(li);
      }}
    }}
    data.children.forEach(c => render(c, document.getElementById('root')));
  </script>
</body></html>'''
    output.write_text(html)

if __name__ == '__main__':
    target = Path(sys.argv[1] if len(sys.argv) > 1 else '.').resolve()
    stats = {"files": 0, "dirs": 0, "extensions": Counter(), "ext_sizes": Counter()}
    data = scan(target, stats)
    out = Path('codebase-map.html')
    generate_html(data, stats, out)
    print(f'Generated {out.absolute()}')
    webbrowser.open(f'file://{out.absolute()}')

To test, open Claude Code in any project and ask “Visualize this codebase.” Claude runs the script, generates codebase-map.html, and opens it in your browser. 要测试,在任何项目中打开 Claude Code,并询问“可视化这个代码库。”Claude 运行脚本,生成 codebase-map.html ,并在您的浏览器中打开它。

This pattern works for any visual output: dependency graphs, test coverage reports, API documentation, or database schema visualizations. The bundled script does the heavy lifting while Claude handles orchestration. 这种模式适用于任何可视化输出:依赖关系图、测试覆盖率报告、API 文档或数据库结构可视化。捆绑的脚本负责繁重的工作,而 Claude 负责协调。

五, Troubleshooting 故障排除

5.1 Skill not triggering 技能未触发

If Claude doesn’t use your skill when expected: 如果 Claude 未按预期使用您的技能:

Check the description includes keywords users would naturally say 检查描述中是否包 含用户会自然使用 的关键词

Verify the skill appears in What skills are available? 确认技能是否出现在 What skills are available?

Try rephrasing your request to match the description more closely 尝试重新表述您的请求,使其更符合描述

Invoke it directly with /skill-name if the skill is user-invocable 如果技能是用户可调用的,可以直接使用 /skill-name 调用

5.2 Skill triggers too often 技能触发过于频繁

If Claude uses your skill when you don’t want it: 如果 Claude 在你不想使用它的时候调用你的技能:

Make the description more specific 使描述更具体

Add disable-model-invocation: true if you only want manual invocation 如果你只想手动调用,请添加 disable-model-invocation: true

5.3 Claude doesn’t see all my skills # Claude 无法识别所有技能

Skill descriptions are loaded into context so Claude knows what’s available. If you have many skills, they may exceed the character budget (default 15,000 characters). Run /context to check for a warning about excluded skills. 技能描述被加载到上下文中,所以 Claude 知道有哪些可用。如果你有很多技能,它们可能会超过字符预算(默认 15,000 个字符)。运行 /context 来检查是否有关于排除技能的警告。

To increase the limit, set the SLASH_COMMAND_TOOL_CHAR_BUDGET environment variable. 要增加限制,请设置 SLASH_COMMAND_TOOL_CHAR_BUDGET 环境变量。

小结 每个技能都是一个目录,里面有一个SKILL.md 文件,使用 /skill-name 调用

description 要写清楚,方便cluade决定什么时候调用skills

自动从嵌套的 .claude/skills/ 目录中发现技能

保持 SKILL.md 在 500 行以内。

技能描述被加载到上下文中,以便 Claude 知道有哪些可用技能,但完整技能内容仅在调用时加载。

预加载技能的Subagents子代理工作方式不同:完整技能内容在启动时注入。

示例了一个fix-issue skills, 技能里面有操作的数字步骤

!命令可以先运行一些预处理命令,将它们的输出内容集成到上下文中。

要在技能中启用扩展思考,请在技能内容中的任何位置包含单词“ultrathink”。

可以使用skills指导subagent干活

可以捆绑脚本

可生成测试覆盖率报告

技能太多,会超限(默认 15,000 个字符)