byanthropics· 237 skills
This skill should be used when the user asks to "create a plugin", "scaffold a plugin", "understand plugin structure", "organize plugin components", "set up plugin.json", "use ${CLAUDE_PLUGIN_ROOT}", "add commands/agents/skills/hooks", "configure auto-discovery", or needs guidance on plugin directory layout, manifest configuration, component organization, file naming conventions, or Claude Code plugin architecture best practices.
$npx -y skills add anthropics/claude-code --skill plugin-structureInstalls into the current project.
Run `npx skills use "https://github.com/anthropics/claude-code" --skill "anthropics/claude-code/plugin-structure"` and follow the generated skill instructions now. Read its complete output, redirecting it to a temporary file first if necessary. Resolve relative paths from the supporting-files directory it provides.
Use the skills in "https://github.com/anthropics/claude-code" that are relevant to the current task. Run `npx skills add "https://github.com/anthropics/claude-code"` and select the relevant skills, then follow their instructions.
| 1 | # Plugin Structure for Claude Code |
| 2 | |
| 3 | ## Overview |
| 4 | |
| 5 | Claude Code plugins follow a standardized directory structure with automatic component discovery. Understanding this structure enables creating well-organized, maintainable plugins that integrate seamlessly with Claude Code. |
| 6 | |
| 7 | **Key concepts:** |
| 8 | - Conventional directory layout for automatic discovery |
| 9 | - Manifest-driven configuration in `.claude-plugin/plugin.json` |
| 10 | - Component-based organization (commands, agents, skills, hooks) |
| 11 | - Portable path references using `${CLAUDE_PLUGIN_ROOT}` |
| 12 | - Explicit vs. auto-discovered component loading |
| 13 | |
| 14 | ## Directory Structure |
| 15 | |
| 16 | Every Claude Code plugin follows this organizational pattern: |
| 17 | |
| 18 | ``` |
| 19 | plugin-name/ |
| 20 | ├── .claude-plugin/ |
| 21 | │ └── plugin.json # Required: Plugin manifest |
| 22 | ├── commands/ # Slash commands (.md files) |
| 23 | ├── agents/ # Subagent definitions (.md files) |
| 24 | ├── skills/ # Agent skills (subdirectories) |
| 25 | │ └── skill-name/ |
| 26 | │ └── SKILL.md # Required for each skill |
| 27 | ├── hooks/ |
| 28 | │ └── hooks.json # Event handler configuration |
| 29 | ├── .mcp.json # MCP server definitions |
| 30 | └── scripts/ # Helper scripts and utilities |
| 31 | ``` |
| 32 | |
| 33 | **Critical rules:** |
| 34 | |
| 35 | 1. **Manifest location**: The `plugin.json` manifest MUST be in `.claude-plugin/` directory |
| 36 | 2. **Component locations**: All component directories (commands, agents, skills, hooks) MUST be at plugin root level, NOT nested inside `.claude-plugin/` |
| 37 | 3. **Optional components**: Only create directories for components the plugin actually uses |
| 38 | 4. **Naming convention**: Use kebab-case for all directory and file names |
| 39 | |
| 40 | ## Plugin Manifest (plugin.json) |
| 41 | |
| 42 | The manifest defines plugin metadata and configuration. Located at `.claude-plugin/plugin.json`: |
| 43 | |
| 44 | ### Required Fields |
| 45 | |
| 46 | ```json |
| 47 | { |
| 48 | "name": "plugin-name" |
| 49 | } |
| 50 | ``` |
| 51 | |
| 52 | **Name requirements:** |
| 53 | - Use kebab-case format (lowercase with hyphens) |
| 54 | - Must be unique across installed plugins |
| 55 | - No spaces or special characters |
| 56 | - Example: `code-review-assistant`, `test-runner`, `api-docs` |
| 57 | |
| 58 | ### Recommended Metadata |
| 59 | |
| 60 | ```json |
| 61 | { |
| 62 | "name": "plugin-name", |
| 63 | "version": "1.0.0", |
| 64 | "description": "Brief explanation of plugin purpose", |
| 65 | "author": { |
| 66 | "name": "Author Name", |
| 67 | "email": "author@example.com", |
| 68 | "url": "https://example.com" |
| 69 | }, |
| 70 | "homepage": "https://docs.example.com", |
| 71 | "repository": "https://github.com/user/plugin-name", |
| 72 | "license": "MIT", |
| 73 | "keywords": ["testing", "automation", "ci-cd"] |
| 74 | } |
| 75 | ``` |
| 76 | |
| 77 | **Version format**: Follow semantic versioning (MAJOR.MINOR.PATCH) |
| 78 | **Keywords**: Use for plugin discovery and categorization |
| 79 | |
| 80 | ### Component Path Configuration |
| 81 | |
| 82 | Specify custom paths for components (supplements default directories): |
| 83 | |
| 84 | ```json |
| 85 | { |
| 86 | "name": "plugin-name", |
| 87 | "commands": "./custom-commands", |
| 88 | "agents": ["./agents", "./specialized-agents"], |
| 89 | "hooks": "./config/hooks.json", |
| 90 | "mcpServers": "./.mcp.json" |
| 91 | } |
| 92 | ``` |
| 93 | |
| 94 | **Important**: Custom paths supplement defaults—they don't replace them. Components in both default directories and custom paths will load. |
| 95 | |
| 96 | **Path rules:** |
| 97 | - Must be relative to plugin root |
| 98 | - Must start with `./` |
| 99 | - Cannot use absolute paths |
| 100 | - Support arrays for multiple locations |
| 101 | |
| 102 | ## Component Organization |
| 103 | |
| 104 | ### Commands |
| 105 | |
| 106 | **Location**: `commands/` directory |
| 107 | **Format**: Markdown files with YAML frontmatter |
| 108 | **Auto-discovery**: All `.md` files in `commands/` load automatically |
| 109 | |
| 110 | **Example structure**: |
| 111 | ``` |
| 112 | commands/ |
| 113 | ├── review.md # /review command |
| 114 | ├── test.md # /test command |
| 115 | └── deploy.md # /deploy command |
| 116 | ``` |
| 117 | |
| 118 | **File format**: |
| 119 | ```markdown |
| 120 | --- |
| 121 | name: command-name |
| 122 | description: Command description |
| 123 | --- |
| 124 | |
| 125 | Command implementation instructions... |
| 126 | ``` |
| 127 | |
| 128 | **Usage**: Commands integrate as native slash commands in Claude Code |
| 129 | |
| 130 | ### Agents |
| 131 | |
| 132 | **Location**: `agents/` directory |
| 133 | **Format**: Markdown files with YAML frontmatter |
| 134 | **Auto-discovery**: All `.md` files in `agents/` load automatically |
| 135 | |
| 136 | **Example structure**: |
| 137 | ``` |
| 138 | agents/ |
| 139 | ├── code-reviewer.md |
| 140 | ├── test-generator.md |
| 141 | └── refactorer.md |
| 142 | ``` |
| 143 | |
| 144 | **File format**: |
| 145 | ```markdown |
| 146 | --- |
| 147 | description: Agent role and expertise |
| 148 | capabilities: |
| 149 | - Specific task 1 |
| 150 | - Specific task 2 |
| 151 | --- |
| 152 | |
| 153 | Detailed agent instructions and knowledge... |
| 154 | ``` |
| 155 | |
| 156 | **Usage**: Users can invoke agents manually, or Claude Code selects them automatically based on task context |
| 157 | |
| 158 | ### Skills |
| 159 | |
| 160 | **Location**: `skills/` directory with subdirectories per skill |
| 161 | **Format**: Each skill in its own directory with `SKILL.md` file |
| 162 | **Auto-discovery**: All `SKILL.md` files in skill subdirectories load automatically |
| 163 | |
| 164 | **Example structure**: |
| 165 | ``` |
| 166 | skills/ |
| 167 | ├── api-testing/ |
| 168 | │ ├── SKILL.md |
| 169 | │ ├── scripts/ |
| 170 | │ │ └── test-runner.py |
| 171 | │ └── references/ |
| 172 | │ └── api-spec.md |
| 173 | └── database-migrations/ |
| 174 | ├── SKILL.md |
| 175 | └── examples/ |
| 176 | └── migration-template.sql |
| 177 | ``` |
| 178 | |
| 179 | **SKILL.md format**: |
| 180 | ```markdown |
| 181 | --- |
| 182 | name: Skill Name |
| 183 | description: When to use this skill |
| 184 | version: 1.0.0 |
| 185 | --- |
| 186 | |
| 187 | Skill instructions and guidance... |
| 188 | ``` |
| 189 | |
| 190 | **Supporting files**: Skills can include scripts, references, examples, or assets in subdirectories |
| 191 | |
| 192 | **Usage**: Claude Code autonomously activates skills based on task context matching the description |
| 193 | |
| 194 | ### Hooks |
| 195 | |
| 196 | **Location**: `hooks/hooks.json` or inline in `plugin.json` |
| 197 | **Format**: JSON configuration defining event handlers |
| 198 | **Registration**: Hooks register automatically when plugin enables |
| 199 | |
| 200 | **Example structure**: |
| 201 | ``` |
| 202 | hooks/ |
| 203 | ├── hooks.json # Hook configuration |
| 204 | └── scripts/ |
| 205 | ├── validate.sh # Hook script |
| 206 | └── check-style.sh # Hook script |
| 207 | ``` |
| 208 | |
| 209 | **Configuration format**: |
| 210 | ```json |
| 211 | { |
| 212 | "PreToolUse": [{ |
| 213 | "matcher": "Write|Edit", |
| 214 | "hooks": [{ |
| 215 | "type": "command", |
| 216 | "command": "bash ${CLAUDE_PLUGIN_ROOT}/hooks/scripts/validate.sh", |
| 217 | "timeout": 30 |
| 218 | }] |
| 219 | }] |
| 220 | } |
| 221 | ``` |
| 222 | |
| 223 | **Available events**: PreToolUse, PostToolUse, Stop, SubagentStop, SessionStart, SessionEnd, UserPromptSubmit, PreCompact, Notification |
| 224 | |
| 225 | **Usage**: Hooks execute automatically in response to Claude Code events |
| 226 | |
| 227 | ### MCP Servers |
| 228 | |
| 229 | **Location**: `.mcp.json` at plugin root or inline in `plugin.json` |
| 230 | **Format**: JSON configuration for MCP server definitions |
| 231 | **Auto-start**: Servers start automatically when plugin enables |
| 232 | |
| 233 | **Example format**: |
| 234 | ```json |
| 235 | { |
| 236 | "mcpServers": { |
| 237 | "server-name": { |
| 238 | "command": "node", |
| 239 | "args": ["${CLAUDE_PLUGIN_ROOT}/servers/server.js"], |
| 240 | "env": { |
| 241 | "API_KEY": "${API_KEY}" |
| 242 | } |
| 243 | } |
| 244 | } |
| 245 | } |
| 246 | ``` |
| 247 | |
| 248 | **Usage**: MCP servers integrate seamlessly with Claude Code's tool system |
| 249 | |
| 250 | ## Portable Path References |
| 251 | |
| 252 | ### ${CLAUDE_PLUGIN_ROOT} |
| 253 | |
| 254 | Use `${CLAUDE_PLUGIN_ROOT}` environment variable for all intra-plugin path references: |
| 255 | |
| 256 | ```json |
| 257 | { |
| 258 | "command": "bash ${CLAUDE_PLUGIN_ROOT}/scripts/run.sh" |
| 259 | } |
| 260 | ``` |
| 261 | |
| 262 | **Why it matters**: Plugins install in different locations depending on: |
| 263 | - User installation method (marketplace, local, npm) |
| 264 | - Operating system conventions |
| 265 | - User preferences |
| 266 | |
| 267 | **Where to use it**: |
| 268 | - Hook command paths |
| 269 | - MCP server command arguments |
| 270 | - Script execution references |
| 271 | - Resource file paths |
| 272 | |
| 273 | **Never use**: |
| 274 | - Hardcoded absolute paths (`/Users/name/plugins/...`) |
| 275 | - Relative paths from working directory (`./scripts/...` in commands) |
| 276 | - Home directory shortcuts (`~/plugins/...`) |
| 277 | |
| 278 | ### Path Resolution Rules |
| 279 | |
| 280 | **In manifest JSON fields** (hooks, MCP servers): |
| 281 | ```json |
| 282 | "command": "${CLAUDE_PLUGIN_ROOT}/scripts/tool.sh" |
| 283 | ``` |
| 284 | |
| 285 | **In component files** (commands, agents, skills): |
| 286 | ```markdown |
| 287 | Reference scripts at: ${CLAUDE_PLUGIN_ROOT}/scripts/helper.py |
| 288 | ``` |
| 289 | |
| 290 | **In executed scripts**: |
| 291 | ```bash |
| 292 | #!/bin/bash |
| 293 | # ${CLAUDE_PLUGIN_ROOT} available as environment variable |
| 294 | source "${CLAUDE_PLUGIN_ROOT}/lib/common.sh" |
| 295 | ``` |
| 296 | |
| 297 | ## File Naming Conventions |
| 298 | |
| 299 | ### Component Files |
| 300 | |
| 301 | **Commands**: Use kebab-case `.md` files |
| 302 | - `code-review.md` → `/code-review` |
| 303 | - `run-tests.md` → `/run-tests` |
| 304 | - `api-docs.md` → `/api-docs` |
| 305 | |
| 306 | **Agents**: Use kebab-case `.md` files describing role |
| 307 | - `test-generator.md` |
| 308 | - `code-reviewer.md` |
| 309 | - `performance-analyzer.md` |
| 310 | |
| 311 | **Skills**: Use kebab-case directory names |
| 312 | - `api-testing/` |
| 313 | - `database-migrations/` |
| 314 | - `error-handling/` |
| 315 | |
| 316 | ### Supporting Files |
| 317 | |
| 318 | **Scripts**: Use descriptive kebab-case names with appropriate extensions |
| 319 | - `validate-input.sh` |
| 320 | - `generate-report.py` |
| 321 | - `process-data.js` |
| 322 | |
| 323 | **Documentation**: Use kebab-case markdown files |
| 324 | - `api-reference.md` |
| 325 | - `migration-guide.md` |
| 326 | - `best-practices.md` |
| 327 | |
| 328 | **Configuration**: Use standard names |
| 329 | - `hooks.json` |
| 330 | - `.mcp.json` |
| 331 | - `plugin.json` |
| 332 | |
| 333 | ## Auto-Discovery Mechanism |
| 334 | |
| 335 | Claude Code automatically discovers and loads components: |
| 336 | |
| 337 | 1. **Plugin manifest**: Reads `.claude-plugin/plugin.json` when plugin enables |
| 338 | 2. **Commands**: Scans `commands/` directory for `.md` files |
| 339 | 3. **Agents**: Scans `agents/` directory for `.md` files |
| 340 | 4. **Skills**: Scans `skills/` for subdirectories containing `SKILL.md` |
| 341 | 5. **Hooks**: Loads configuration from `hooks/hooks.json` or manifest |
| 342 | 6. **MCP servers**: Loads configuration from `.mcp.json` or manifest |
| 343 | |
| 344 | **Discovery timing**: |
| 345 | - Plugin installation: Components register with Claude Code |
| 346 | - Plugin enable: Components become available for use |
| 347 | - No restart required: Changes take effect on next Claude Code session |
| 348 | |
| 349 | **Override behavior**: Custom paths in `plugin.json` supplement (not replace) default directories |
| 350 | |
| 351 | ## Best Practices |
| 352 | |
| 353 | ### Organization |
| 354 | |
| 355 | 1. **Logical grouping**: Group related components together |
| 356 | - Put test-related commands, agents, and skills together |
| 357 | - Create subdirectories in `scripts/` for different purposes |
| 358 | |
| 359 | 2. **Minimal manifest**: Keep `plugin.json` lean |
| 360 | - Only specify custom paths when necessary |
| 361 | - Rely on auto-discovery for standard layouts |
| 362 | - Use inline configuration only for simple cases |
| 363 | |
| 364 | 3. **Documentation**: Include README files |
| 365 | - Plugin root: Overall purpose and usage |
| 366 | - Component directories: Specific guidance |
| 367 | - Script directories: Usage and requirements |
| 368 | |
| 369 | ### Naming |
| 370 | |
| 371 | 1. **Consistency**: Use consistent naming across components |
| 372 | - If command is `test-runner`, name related agent `test-runner-agent` |
| 373 | - Match skill directory names to their purpose |
| 374 | |
| 375 | 2. **Clarity**: Use descriptive names that indicate purpose |
| 376 | - Good: `api-integration-testing/`, `code-quality-checker.md` |
| 377 | - Avoid: `utils/`, `misc.md`, `temp.sh` |
| 378 | |
| 379 | 3. **Length**: Balance brevity with clarity |
| 380 | - Commands: 2-3 words (`review-pr`, `run-ci`) |
| 381 | - Agents: Describe role clearly (`code-reviewer`, `test-generator`) |
| 382 | - Skills: Topic-focused (`error-handling`, `api-design`) |
| 383 | |
| 384 | ### Portability |
| 385 | |
| 386 | 1. **Always use ${CLAUDE_PLUGIN_ROOT}**: Never hardcode paths |
| 387 | 2. **Test on multiple systems**: Verify on macOS, Linux, Windows |
| 388 | 3. **Document dependencies**: List required tools and versions |
| 389 | 4. **Avoid system-specific features**: Use portable bash/Python constructs |
| 390 | |
| 391 | ### Maintenance |
| 392 | |
| 393 | 1. **Version consistently**: Update version in plugin.json for releases |
| 394 | 2. **Deprecate gracefully**: Mark old components clearly before removal |
| 395 | 3. **Document breaking changes**: Note changes affecting existing users |
| 396 | 4. **Test thoroughly**: Verify all components work after changes |
| 397 | |
| 398 | ## Common Patterns |
| 399 | |
| 400 | ### Minimal Plugin |
| 401 | |
| 402 | Single command with no dependencies: |
| 403 | ``` |
| 404 | my-plugin/ |
| 405 | ├── .claude-plugin/ |
| 406 | │ └── plugin.json # Just name field |
| 407 | └── commands/ |
| 408 | └── hello.md # Single command |
| 409 | ``` |
| 410 | |
| 411 | ### Full-Featured Plugin |
| 412 | |
| 413 | Complete plugin with all component types: |
| 414 | ``` |
| 415 | my-plugin/ |
| 416 | ├── .claude-plugin/ |
| 417 | │ └── plugin.json |
| 418 | ├── commands/ # User-facing commands |
| 419 | ├── agents/ # Specialized subagents |
| 420 | ├── skills/ # Auto-activating skills |
| 421 | ├── hooks/ # Event handlers |
| 422 | │ ├── hooks.json |
| 423 | │ └── scripts/ |
| 424 | ├── .mcp.json # External integrations |
| 425 | └── scripts/ # Shared utilities |
| 426 | ``` |
| 427 | |
| 428 | ### Skill-Focused Plugin |
| 429 | |
| 430 | Plugin providing only skills: |
| 431 | ``` |
| 432 | my-plugin/ |
| 433 | ├── .claude-plugin/ |
| 434 | │ └── plugin.json |
| 435 | └── skills/ |
| 436 | ├── skill-one/ |
| 437 | │ └── SKILL.md |
| 438 | └── skill-two/ |
| 439 | └── SKILL.md |
| 440 | ``` |
| 441 | |
| 442 | ## Troubleshooting |
| 443 | |
| 444 | **Component not loading**: |
| 445 | - Verify file is in correct directory with correct extension |
| 446 | - Check YAML frontmatter syntax (commands, agents, skills) |
| 447 | - Ensure skill has `SKILL.md` (not `README.md` or other name) |
| 448 | - Confirm plugin is enabled in Claude Code settings |
| 449 | |
| 450 | **Path resolution errors**: |
| 451 | - Replace all hardcoded paths with `${CLAUDE_PLUGIN_ROOT}` |
| 452 | - Verify paths are relative and start with `./` in manifest |
| 453 | - Check that referenced files exist at specified paths |
| 454 | - Test with `echo $CLAUDE_PLUGIN_ROOT` in hook scripts |
| 455 | |
| 456 | **Auto-discovery not working**: |
| 457 | - Confirm directories are at plugin root (not in `.claude-plugin/`) |
| 458 | - Check file naming follows conventions (kebab-case, correct extensions) |
| 459 | - Verify custom paths in manifest are correct |
| 460 | - Restart Claude Code to reload plugin configuration |
| 461 | |
| 462 | **Conflicts between plugins**: |
| 463 | - Use unique, descriptive component names |
| 464 | - Namespace commands with plugin name if needed |
| 465 | - Document potential conflicts in plugin README |
| 466 | - Consider command prefixes for related functionality |
| 467 | |
| 468 | --- |
| 469 | |
| 470 | For detailed examples and advanced patterns, see files in `references/` and `examples/` directories. |