Han Plugin Development
This skill provides comprehensive guidance for developing Han plugins.
Plugin Types
Han supports three plugin types:
- Jutsu (Technique) - Skills and validation hooks for languages/tools
- Do (Discipline) - Specialized agents for specific domains
- Hashi (Bridge) - MCP servers for external integrations
Directory Structure
Every plugin must follow this structure:
my-plugin/
├── .claude-plugin/
│ └── plugin.json # Plugin metadata (required)
├── han-plugin.yml # Hook configuration (optional)
├── skills/ # Skills directory (optional)
│ └── my-skill/
│ └── SKILL.md # Skill definition
├── commands/ # Commands directory (optional)
│ └── my-command.md # Slash command
├── hooks/ # Hook scripts (optional)
│ └── my-hook.sh # Hook implementation
└── README.md # Documentation
plugin.json (Required)
The plugin.json file defines metadata:
{
"name": "my-plugin-name",
"version": "1.0.0",
"description": "What the plugin does",
"author": {
"name": "Author Name",
"url": "https://author-website.com"
},
"license": "MIT",
"keywords": ["keyword1", "keyword2"]
}
Required fields:
name- Must match directory nameversion- Semantic versioning
han-plugin.yml (Hooks)
Define validation hooks that run at lifecycle events:
hooks:
my-validation:
event: Stop # When to run
command: bash "hooks/my-hook.sh"
description: What this hook does
# Optional filters:
if_changed: # Only run if these files changed
- "**/*.ts"
dirs_with: # Only run in dirs containing
- "package.json"
Hook Events
Setup- Plugin installationSessionStart- Session beginsUserPromptSubmit- User sends messagePreToolUse- Before tool executionPostToolUse- After tool executionStop- Work completion (validation)SubagentStop- Subagent completion
Hook Environment Variables
Scripts receive:
CLAUDE_PLUGIN_ROOT- Plugin directory pathHAN_SESSION_ID- Current session IDHAN_PROJECT_DIR- Project directoryHAN_FILES- Changed files (space-separated)
Skills (SKILL.md)
Skills provide domain expertise:
---
name: skill-name
description: When to use this skill
allowed-tools: [Read, Write, Edit, Bash, Glob, Grep]
---
# Skill Title
Skill content with guidance, examples, and best practices.
Required frontmatter:
name- Skill identifierdescription- When Claude should use this skill
Commands (Slash Commands)
Commands provide slash command functionality:
---
description: What the command does
---
Command implementation content...
Invoke with: /plugin-name:command-name
Validation
Before publishing, validate your plugin:
cd my-plugin
han plugin validate
This checks:
- Required files exist
- JSON/YAML syntax is valid
- Frontmatter is correct
- No misplaced files
Best Practices
Hook Scripts
- Use
set -e- Exit on first error - Quote variables -
"${HAN_FILES}"not$HAN_FILES - Clear error messages - Write to stderr on failure
- Exit codes - 0 for success, non-zero for failure
Skills
- Specific descriptions - Help Claude know when to use
- Practical examples - Show real usage patterns
- Progressive detail - Start simple, add complexity
- Troubleshooting - Include common issues
General
- Follow naming conventions - jutsu-, do-, hashi-*
- Include README - Installation and usage docs
- Version properly - Use semantic versioning
- Test locally - Install via path before publishing
Local Installation
Test your plugin locally:
# Install from local path
han plugin install /path/to/my-plugin --scope project
# Or add to .claude/settings.json manually
Publishing
Share your plugin:
- Push to a git repository
- Add to the Han marketplace (optional)
- Users install via:
han plugin install github:user/repo
Troubleshooting
Hook Not Running
- Check
eventmatches lifecycle point - Verify
commandpath is correct - Check
if_changed/dirs_withfilters
Validation Fails
- Run
han plugin validatefor specific errors - Check plugin.json syntax
- Verify skill frontmatter
Skill Not Found
- Check SKILL.md path and naming
- Verify frontmatter has required fields
- Skill name should match directory name