连载

阶段小结|Plugin:把你打磨好的 Claude Code 配置打包分享

AI Coding 系列第 07 篇 · 第一阶段终点站


前言:学了一圈,怎么让这些东西长腿跑起来

前面 01 到 05 篇,我们从 Prompt 的基本写法,一路走到了 CLI 命令、CLAUDE.md 规则、Skill 模板、Hooks 自动化。每一篇解决一个独立问题,但横向看,它们其实在回答同一个问题:"怎么让 Claude Code 越来越像你的搭档?"

篇目 解决的场景 承载形式
01 开篇 建立全局认知:Claude Code 是什么、能做什么 ---
02 Prompt 单次对话的质量控制 一条 prompt
03 Commands 把重复操作固化为 /命令 commands/*.md
04 CLAUDE.md 持久的行为规则,跨会话生效 CLAUDE.md 文件
05 Skill 复杂任务的 SOP 模板 skills/*.md
06 Hooks 确定性自动化(写文件后跑 lint、切换分支前提示) hooks/hooks.json

现在你手里攒了一堆好用的东西------一个精心维护的 CLAUDE.md、几套验证过的 Skill、一组靠谱的 Hooks。但这些东西困在了你的机器里。团队里另一个同事问你:你的 Claude Code 怎么比我的好用那么多?

你发给他几个文件,他一个个手动复制,发现有的路径不对,有的配置缺了依赖,折腾了半小时还没跑起来。

Plugin 解决的就是这个问题:把你打磨好的整套配置打包成一个可安装的单元,一条命令即可在任何机器上复现你的 Claude Code 环境。

回顾:前五篇的产物,天然就是 Plugin 的零件

Plugin 不是什么新奇东西。把前面几篇文章产出的文件放进同一个目录,你就已经拥有了一个 Plugin 的雏形------以社区最成熟的 Superpowers 插件为例,它的完整结构:

bash 复制代码
superpowers/                            # Git 仓库根目录 = Plugin 根目录
├── .claude-plugin/                     # ★ Claude Code 插件定义
│   ├── plugin.json                     #    插件清单(必须)
│   └── marketplace.json               #    市场定义(给安装者发现用)
├── .codex-plugin/                      #    同时支持 Codex CLI
│   └── plugin.json
├── .cursor-plugin/                     #    同时支持 Cursor
│   └── plugin.json
├── skills/                             # ← 第05篇:14 个 Skill(每个一个子目录)
│   ├── brainstorming/
│   │   ├── SKILL.md                    #    核心 Skill 定义(frontmatter + 执行步骤)
│   │   ├── visual-companion.md         #    辅助文档
│   │   └── scripts/                    #    Skill 自带的脚本资源
│   ├── test-driven-development/
│   │   └── SKILL.md
│   ├── dispatching-parallel-agents/
│   │   └── SKILL.md
│   └── ...  (共 14 个)
├── hooks/                              # ← 第06篇:自动化钩子
│   ├── hooks.json                      #    SessionStart 钩子配置
│   ├── run-hook.cmd                    #    跨平台启动脚本
│   └── session-start/                  #    会话启动时注入上下文
├── CLAUDE.md                           #    本项目的 contributor 指南(给维护者看)
├── AGENTS.md                           #    → 指向 CLAUDE.md
├── README.md                           #    项目说明 + 安装指南
├── docs/                               #    设计文档、计划
├── tests/                              #    测试套件(7 个)
├── assets/                             #    图标、SVG
├── .github/                            #    Issue/PR 模板
│   ├── PULL_REQUEST_TEMPLATE.md
│   └── ISSUE_TEMPLATE/
├── package.json
└── LICENSE

对比一下各篇的产物是怎么装进 Plugin 的:

前文产物 在 Plugin 中的位置
04 CLAUDE.md 规则 重构成 Skill:行为规则写在 SKILL.md 正文中,触发条件和权限声明在 frontmatter
03 Commands 可放在 commands/ 目录,或在 plugin.jsoncommands 字段声明
05 Skill 模板 skills/<name>/SKILL.md,每个 Skill 一个子目录
06 Hooks 配置 hooks/hooks.json,使用 ${CLAUDE_PLUGIN_ROOT} 引用插件内路径

Plugin 不创造新能力,它是一种分发机制------把你的 Skills、Hooks、Commands 打包进一个 Git 仓库,通过 marketplace 让团队一键安装。安装后,这些内容按层级合并到用户的配置中,不会覆盖用户自己的设置。

明白了这一点,下面逐个看 Plugin 的每一个组成部分。


一、Plugin 的组成:plugin.json + marketplace.json

Claude Code 的 Plugin 系统由两层组成:

第一层:plugin.json(插件清单) ------定义插件本身提供什么。每个 Plugin 必须有一个 plugin.json,放在 .claude-plugin/ 目录下:

json 复制代码
{
  "name": "team-review-plugin",
  "description": "团队代码 Review 标准化配置",
  "version": "1.0.0",
  "author": {
    "name": "Your Team"
  },
  "homepage": "https://github.com/your-team/claude-plugins",
  "repository": "https://github.com/your-team/claude-plugins",
  "license": "MIT",
  "keywords": ["code-review", "team-standards"]
}

第二层:marketplace.json(市场定义)------告诉 Claude Code 去哪里找这个插件,以及有哪些版本可用:

json 复制代码
{
  "name": "my-team",
  "owner": { "name": "Your Team" },
  "plugins": [
    {
      "name": "team-review-plugin",
      "description": "团队代码 Review 标准化配置",
      "version": "1.0.0",
      "source": "./"
    }
  ]
}

source: "./" 表示插件目录就是仓库根目录。两个 JSON 文件 + 你的 skills/ 和 hooks/ 目录 → 一个完整的 Plugin。

安装后,Plugin 的 Skills、Hooks、Commands 按层级合并到用户配置里,不会互相覆盖。冲突时用户优先级更高(详见第五章)。


二、什么时候需要打一个 Plugin

判断标准很简单:这套配置是否有人会重复安装?

个人使用,不需要 Plugin。 你自己电脑上的 CLAUDE.md 和 Skills,直接放在对应目录就行,没有分发需求。

以下场景值得打成 Plugin:

团队新人入职,需要快速获得和老员工一致的 Claude Code 环境。与其发一份"配置说明文档"让人手动操作,不如给一个 Plugin,让新人 /plugin install onboarding-plugin@team-marketplace 一行搞定。

你做了一套针对某类项目的完整配置(比如专门为 React + TypeScript 项目优化的 Skills 和 Hooks),想开源出去给社区用。

公司有统一的安全合规要求,需要确保所有工程师的 Claude Code 都安装了同一套红线规则,不依赖个人自觉。


三、从零打一个 Plugin

以"团队代码 Review 标准化"为例,走一遍完整流程。

第一步:创建仓库结构

bash 复制代码
mkdir team-review-plugin
cd team-review-plugin
mkdir -p .claude-plugin skills/code-review hooks
git init

第二步:写 plugin.json(插件清单)

这是 Plugin 的唯一身份文件 ------告诉 Claude Code 这个插件叫什么、谁做的、版本是多少。注意:是 plugin.json,不是 SKILL.mdSKILL.md 是单个 Skill 的入口,Plugin 可以有多个 Skill。

json 复制代码
// .claude-plugin/plugin.json
{
  "name": "team-review-plugin",
  "description": "帮助团队成员用一致的标准做代码 Review",
  "version": "1.0.0",
  "author": { "name": "Your Team" },
  "homepage": "https://github.com/your-team/team-review-plugin",
  "repository": "https://github.com/your-team/team-review-plugin",
  "license": "MIT",
  "keywords": ["code-review", "team-standards"]
}

plugin.json 的关键字段:

字段 必须 说明
name 唯一标识,kebab-case,不能有空格。安装后完整 ID 为 name@marketplace
description 简介,给用户看的
version semver(如 1.0.0
author { name, email, url }
dependencies 依赖的其他 Plugin,格式 dep-name@marketplace

第三步:放入 Skills

每个 Skill 是一个子目录 ,里面放一个 SKILL.md,用 YAML frontmatter 声明触发条件和权限(第 05 篇讲过):

markdown 复制代码
# skills/code-review/SKILL.md
---
name: code-review
description: 按团队标准执行代码审查
when_to_use: 需要 Review 代码时
allowed-tools:
  - Bash(git diff *)
  - Read
---

## 执行步骤
1. 用 `git diff` 获取当前变更
2. 按三个维度逐一检查:
   - 安全性:注入漏洞、越权访问、敏感数据泄露
   - 性能:不必要的循环、N+1 查询、内存泄漏风险
   - 可读性:命名清晰度、函数长度、注释必要性
3. 每个问题标注严重级别(high / medium / low)
4. 给出修改建议,不直接改代码

你的 CLAUDE.md 里的行为规则,重构成 Skill:规则正文放在 SKILL.md 的 Markdown 部分,触发条件(when_to_use)和权限限制(allowed-tools)声明在 frontmatter。Plugin 系统没有单独的"CLAUDE.md 注入"机制------行为规则以 Skill 为载体进入 Claude 的上下文。

第四步:放入 Hooks 配置

json 复制代码
// hooks/hooks.json
{
  "hooks": {
    "PostToolUse": [
      {
        "matcher": "Write",
        "hooks": [
          {
            "type": "command",
            "command": "npx eslint --fix ${CLAUDE_PLUGIN_ROOT}/../.. 2>/dev/null || true"
          }
        ]
      }
    ]
  }
}

注意:Hook 里可以用 ${CLAUDE_PLUGIN_ROOT} 引用插件根目录,避免硬编码路径。模板变量语法在不同版本的 Claude Code 间可能有差异,建议对着你当前版本验证。

第五步:写 marketplace.json

这是"分发层"的配置------Claude Code 通过 marketplace 发现和安装插件。一个 marketplace 可以包含多个插件。

json 复制代码
// .claude-plugin/marketplace.json
{
  "name": "my-team",
  "owner": { "name": "Your Team" },
  "plugins": [
    {
      "name": "team-review-plugin",
      "description": "团队代码 Review 标准化配置",
      "version": "1.0.0",
      "source": "./"
    }
  ]
}

source: "./" 表示插件就在仓库根目录。如果 monorepo 里有多个插件,可以用 source: "./plugins/code-review" 指向子目录。

第六步:推送到 Git(真正的"打包")

Plugin 不打包成 zip。直接 push 到 Git 仓库即可:

bash 复制代码
git add -A
git commit -m "init: team-review-plugin v1.0.0"
git remote add origin https://github.com/your-team/team-review-plugin.git
git push -u origin main

完成------你的 Plugin 已经在 GitHub 上了,可以分发了。


四、安装和使用 Plugin

方式一:添加你的 marketplace 后安装(推荐)

团队成员只需要两步:

bash 复制代码
# 1. 注册你的 marketplace(只需做一次)
claude plugin marketplace add your-team/team-review-plugin

# 或通过 slash command
/plugin marketplace add your-team/team-review-plugin
bash 复制代码
# 2. 安装插件
claude plugin install team-review-plugin@my-team

# 或
/plugin install team-review-plugin@my-team

marketplace 系统会自动从 Git 仓库拉取 marketplace.json,定位插件并安装。

方式二:本地目录测试(开发阶段)

在推送到 Git 之前,可以用本地目录验证:

bash 复制代码
# 直接指向插件目录
claude --plugin-dir ./team-review-plugin

查看已安装的 Plugin:

bash 复制代码
claude plugin list
# 或
/plugin list

启用 / 禁用:

bash 复制代码
claude plugin enable team-review-plugin@my-team
claude plugin disable team-review-plugin@my-team

卸载:

bash 复制代码
claude plugin uninstall team-review-plugin@my-team

安装后,Plugin 里的 Skills、Hooks 立即生效,不需要重启。


源码视角:Claude Code 是怎么挂载 Plugin 的

理解了"怎么做一个 Plugin",再往下一层看 Claude Code 内部是怎么加载它的。整个流程从三个来源汇集:

三路汇入:marketplace + session + builtin

scss 复制代码
assemblePluginLoadResult()                        // pluginLoader.ts:3155
  ├── loadPluginsFromMarketplaces()               // 从 settings.json 里注册的 marketplace 拉取
  ├── loadSessionOnlyPlugins()                    // 从 --plugin-dir 传入的本地目录加载
  └── getBuiltinPlugins()                         // CLI 内置的可开关 Plugin(name@builtin)
         ↓
  mergePluginSources()                            // 三路合并,session 覆盖 marketplace
         ↓
  PluginLoadResult { enabled[], disabled[], errors[] }

合并优先级:session(--plugin-dir)> marketplace(已安装)> builtin。但企业的 managed settings 可以锁死某些 Plugin 不被 session 覆盖。

单个 Plugin 的加载:从 plugin.json 到 LoadedPlugin

typescript 复制代码
// pluginLoader.ts:1348 --- createPluginFromPath()
export async function createPluginFromPath(pluginPath, source, enabled, fallbackName) {
  // Step 1: 读 .claude-plugin/plugin.json,用 Zod schema 校验
  const manifest = await loadPluginManifest(manifestPath, fallbackName, source)

  // Step 2: 并行探测 4 个可选目录是否存在
  const [commandsDirExists, agentsDirExists, skillsDirExists, outputStylesDirExists] =
    await Promise.all([
      pathExists(join(pluginPath, 'commands')),
      pathExists(join(pluginPath, 'agents')),
      pathExists(join(pluginPath, 'skills')),
      pathExists(join(pluginPath, 'output-styles')),
    ])

  // Step 3: 组装 LoadedPlugin 对象
  const plugin: LoadedPlugin = {
    name: manifest.name,
    manifest,
    path: pluginPath,      // 插件根目录的绝对路径
    source,                // 来源标识(如 "github:repo")
    enabled,
    commandsPath,          // 探测到的 commands/ 目录路径
    skillsPaths,           // 探测到的 skills/ 目录路径
    hooksConfig,           // hooks/hooks.json 解析后的配置
    mcpServers,            // MCP 服务器配置
    lspServers,            // LSP 服务器配置
  }
}

关键点:Plugin 不要求所有目录都存在 ------createPluginFromPath() 只挂载实际存在的目录。你的 Plugin 可以只有 skills/,没有 commands/hooks/,它照常工作。

manifest 校验:JSON → Zod Schema

typescript 复制代码
// pluginLoader.ts:1147 --- loadPluginManifest()
export async function loadPluginManifest(manifestPath, pluginName, source) {
  if (!(await pathExists(manifestPath))) {
    // plugin.json 缺失时,用最小兜底 manifest
    return { name: pluginName, description: `Plugin from ${source}` }
  }

  const content = await readFile(manifestPath, 'utf-8')
  const parsedJson = jsonParse(content)

  // Zod 校验 --- 不通过直接抛异常
  const result = PluginManifestSchema().safeParse(parsedJson)
  if (result.success) {
    // 注意:Zod 默认 strip 未知字段,所以 plugin.json 里多写字段不会报错
    return result.data
  }
  // 校验失败:name 带空格、非法字段类型等 → 阻止加载
  throw new Error(`Plugin ${pluginName} has an invalid manifest file`)
}

PluginManifestSchema (schemas.ts:884) 定义了 plugin.json 的完整 Zod schema,核心约束:

  • name 不能为空、不能包含空格、必须 kebab-case
  • version 可选,semver
  • dependencies 数组,格式 dep-name@marketplace
  • commands / agents / skills / hooks / mcpServers / lspServers / outputStyles / userConfig / settings 等可选扩展字段

Command 提取:扫描 commands/ 和 skills/

typescript 复制代码
// loadPluginCommands.ts --- 核心逻辑
// 1. walkPluginMarkdown() 遍历 commands/ + commandsPaths,收集所有 .md 文件
// 2. 对每个 .md 文件:
//    - 解析 YAML frontmatter(parseFrontmatter)
//    - skills/ 目录下的 SKILL.md 用父目录名作为 skill 名
//    - 提取 name, description, allowedTools, whenToUse, model, hooks 等字段
//    - 替换变量(${CLAUDE_SKILL_DIR}, ${CLAUDE_SESSION_ID}, 用户参数)
// 3. 返回 Command[] 数组,注入到 Claude 的可用工具列表中

Skill 的命名规则(loadPluginCommands.ts:60):

ini 复制代码
skills/brainstorming/SKILL.md  →  Command.name = "brainstorming"
skills/tdd/SKILL.md            →  Command.name = "tdd"
commands/review.md             →  Command.name = "review"(文件名去 .md)

Hook 挂载:注册 + 热更新

typescript 复制代码
// loadPluginHooks.ts:28 --- convertPluginHooksToMatchers()
// 读取 plugin.hooksConfig(来自 hooks/hooks.json 或 manifest.hooks 内联)
// 遍历 25 种 Hook 事件(SessionStart / PostToolUse / PreToolUse / ...)
// 为每个 matcher 注入 Plugin 上下文:

pluginMatchers[hookEvent].push({
  matcher: matcher.matcher,      // "startup" / "Write" / "*"
  hooks: matcher.hooks,           // 实际要执行的命令
  pluginRoot: plugin.path,        // → ${CLAUDE_PLUGIN_ROOT} 的值
  pluginName: plugin.name,
  pluginId: plugin.source,
})

Hook 还支持热更新:当 enabledPlugins 在 settings.json 中变化时,自动注销旧 Hook、注册新 Hook,不需要重启。

一句话总结

Claude Code 的 Plugin 挂载本质上是一个 三路 merge + 目录探测 + frontmatter 解析 的流程。没有魔法------plugin.json 是 Zod 校验的 JSON,Skills 是带 frontmatter 的 Markdown,Hooks 是 JSON 配置。理解这三样,你就完全理解了 Plugin 系统的内核。


五、Plugin 的优先级和冲突处理

Plugin 的配置和你自己的配置共存时,有明确的优先级:

markdown 复制代码
用户配置(个人 CLAUDE.md + Skills)
    ↓ 优先级更高
Plugin 配置(Plugin 的 Skills + Hooks)
    ↓
默认配置

用户自己的规则始终优先于 Plugin 的规则,所以安装一个 Plugin 不会覆盖掉你的个人设置。如果你的规则和 Plugin 规则有冲突,以你的为准。

这个设计的好处:团队统一安装公司 Plugin,个人仍然可以有自己的偏好配置,两者互不干扰。


六、从"用别人的 Plugin"到"做自己的 Plugin"

大多数人的路径应该是这样的:

第一阶段:用社区现成的 Plugin。 Anthropic 官方和社区有一些公开的 Plugin,覆盖常见语言和框架。先安装来用,观察它做了什么、效果怎样。

第二阶段:基于现有 Plugin 修改。 克隆别人的 Plugin 仓库(就是 Git 仓库),看看 .claude-plugin/plugin.jsonskills/hooks/ 的结构,提取对你有用的部分,删掉不适合你项目的,改好 plugin.json 后推到你自己的仓库。

第三阶段:从零沉淀自己的 Plugin。 等你积累了足够多的 Skills 和 Hooks,发现某些组合在你们团队反复使用,这时候打成 Plugin 才有意义------不是为了打包而打包,是因为真的有分发需求。


本篇实践任务

任务一(了解结构): 克隆 Superpowers 仓库,查看 .claude-plugin/plugin.jsonmarketplace.jsonskills/hooks/ 的完整结构,对照本篇理解每个文件的作用。

任务二(从头做一个): 把你在第 05 篇提炼的 Skill 和第 06 篇配好的 Hooks 组合成一个 Plugin。建仓库 → 写 plugin.json + marketplace.json → 放 Skills 和 Hooks → 推送到 Git → 用 --plugin-dir 本地测试验证。

任务三(团队推广预演): 让同事用 claude plugin marketplace add 添加你的仓库,然后 claude plugin install 安装。观察他能否在 5 分钟内跑起来,记录遇到的问题,改进文档。


总结

这篇文章是第一阶段(01 ~ 07)的收尾。

回头看一下我们走过的路:

markdown 复制代码
02 Prompt          → 怎么和 Claude 说话
03 Commands        → 怎么把常用操作固化为 /命令
04 CLAUDE.md       → 怎么给 Claude 持久的规则和记忆
05 Skill           → 怎么把复杂任务封装成可复用的 SOP
06 Hooks           → 怎么让 Claude 在关键节点自动做检查
                                                        ↓
07 Plugin          → 怎么把上面这些打包,一键分发

Plugin 是配置旅程的最后一步:你把好用的东西固化下来,让别人不需要重走你走过的路。

单独用 Claude Code 时,Plugin 不是必须的。但一旦涉及团队协作------统一标准、快速 onboarding、分发最佳实践------Plugin 是目前最干净的解法。

打包的时机不要太早。先用 CLAUDE.md、Skills 和 Hooks 把效果验证清楚,真正到了"这套东西值得让五个人以上用"的时候,再花时间打包成 Plugin,回报才值得。


展望:下一阶段,从"配置"到"编排"

前面 01 ~ 07 篇,我们把 Claude Code 单会话的体验打磨到了极致。但从第 08 篇开始,问题变了:

  • 单个 Claude 完成不了的任务怎么办?→ Sub-agents(第 09 篇)
  • 多个 Agent 怎么分工合作?→ Multi-agent 与 Agent Teams(第 10 篇)
  • 怎么把外部工具接进来?→ MCP 与工具系统(第 11 篇)
  • 怎么设计可持续的日常 AI Coding 工作流?→ 工作流设计(第 12 篇)

如果你已经把自己的配置打成了 Plugin,恭喜------你已经有了一个标准化的"Agent 起点"。 接下来要做的是让这个 Agent 能调动更多 Agent,去完成一个人做不完的任务。


AI Coding 系列持续更新。如果你做了有意思的 Plugin,欢迎开源出来。

相关推荐
deli00700714 分钟前
Markdown 实时预览器:左边写右边看,排版效率翻倍
前端·ai编程
全栈弄潮儿18 分钟前
用 AI 写 README 和接口文档:让项目更容易交接
aigc·openai·ai编程
郑州光合科技余经理19 分钟前
海外版外卖系统架构:订单怎么流转、权限怎么分
java·开发语言·前端·系统架构·uni-app·php·ai编程
pengyu33 分钟前
【Kotlin 协程修仙录 · 炼虚境 · 初阶】 | 虚空造物:Channel 基础与协程间通信的管道艺术
android·前端·kotlin
提线木偶35 分钟前
CORS 到底谁说了算?一份跨域配置的避坑指南
前端·后端
浩风祭月38 分钟前
Agent Plugins 1.0怎么把一套技能同时带进VS Code和Copilot CLI?
ai编程·vs code·github copilot·mcp·copilot cli·agent plugins
Csvn1 小时前
没有评测,你就不敢改任何东西——AI 应用评测第一课(E01)
aigc·agent·ai编程
黑科技iOS上架1 小时前
新手程序员如何入行
经验分享·aigc·ai编程
网安蟹佬霸2 小时前
区块链与智能合约安全实战:从Solidity审计到DeFi漏洞深度剖析
运维·前端·网络·安全·自动化·区块链·智能合约
卷无止境2 小时前
Python的contextlib与 FastAPI 中的上下文管理
后端·python·fastapi