⚙️plugin-settings
- プラグイン
- plugin-dev
- ソース
- GitHub で見る ↗
説明
次のような場合に使用: ユーザーが「プラグイン設定」「プラグイン設定の保存」「ユーザーが設定可能なプラグイン」「`.local.md` ファイル」「プラグインの状態ファイル」「YAML フロントマターの読み取り」「プロジェクトごとのプラグイン設定」について質問している場合、またはプラグインの動作を設定可能にしたい場合。 YAML フロントマターとマークダウンコンテンツを使ってプラグイン固有の設定を保存するための、`.claude/plugin-name.local.md` パターンについて解説します。
原文を表示
This skill should be used when the user asks about "plugin settings", "store plugin configuration", "user-configurable plugin", ".local.md files", "plugin state files", "read YAML frontmatter", "per-project plugin settings", or wants to make plugin behavior configurable. Documents the .claude/plugin-name.local.md pattern for storing plugin-specific configuration with YAML frontmatter and markdown content.
ユースケース
- ✓プラグイン設定について質問するとき
- ✓プラグイン設定を保存したいとき
- ✓プロジェクトごとに設定を変更したいとき
- ✓プラグインの動作を設定可能にしたいとき
- ✓YAMLフロントマターを読み取るとき
本文(日本語訳)
Claude Code プラグイン向け Plugin Settings パターン
概要
プラグインは、プロジェクトディレクトリ内の .claude/plugin-name.local.md ファイルに、ユーザーが設定可能な設定値や状態を保存できます。
このパターンでは、構造化された設定には YAML frontmatter を、プロンプトや追加コンテキストには markdown の本文を使用します。
主な特徴:
- ファイルの場所: プロジェクトルートの
.claude/plugin-name.local.md - 構造: YAML frontmatter + markdown 本文
- 目的: プロジェクトごとのプラグイン設定と状態管理
- 利用場所: hook、コマンド、agent から読み込み
- ライフサイクル: ユーザー管理(git には含めず、
.gitignoreに追加すること)
ファイル構造
基本テンプレート
---
enabled: true
setting1: value1
setting2: value2
numeric_setting: 42
list_setting: ["item1", "item2"]
---
# Additional Context
この markdown 本文には以下を記載できます:
- タスクの説明
- 追加の指示
- Claude にフィードバックするプロンプト
- ドキュメントやメモ
例: プラグイン状態ファイル
.claude/my-plugin.local.md:
---
enabled: true
strict_mode: false
max_retries: 3
notification_level: info
coordinator_session: team-leader
---
# Plugin Configuration
このプラグインは標準バリデーションモードで設定されています。
質問は @team-lead までご連絡ください。
設定ファイルの読み込み
hook から読み込む(Bash スクリプト)
パターン: ファイルの存在確認と frontmatter のパース
#!/bin/bash
set -euo pipefail
# 状態ファイルのパスを定義
STATE_FILE=".claude/my-plugin.local.md"
# ファイルが存在しない場合は即時終了
if [[ ! -f "$STATE_FILE" ]]; then
exit 0 # プラグイン未設定、スキップ
fi
# YAML frontmatter をパース(--- マーカーの間の部分)
FRONTMATTER=$(sed -n '/^---$/,/^---$/{ /^---$/d; p; }' "$STATE_FILE")
# 個々のフィールドを取り出す
ENABLED=$(echo "$FRONTMATTER" | grep '^enabled:' | sed 's/enabled: *//' | sed 's/^"\(.*\)"$/\1/')
STRICT_MODE=$(echo "$FRONTMATTER" | grep '^strict_mode:' | sed 's/strict_mode: *//' | sed 's/^"\(.*\)"$/\1/')
# enabled フラグを確認
if [[ "$ENABLED" != "true" ]]; then
exit 0 # 無効化されている
fi
# hook のロジックで設定を使用
if [[ "$STRICT_MODE" == "true" ]]; then
# 厳格なバリデーションを適用
# ...
fi
完全な動作例は examples/read-settings-hook.sh を参照してください。
コマンドから読み込む
コマンドは設定ファイルを読み込んで動作をカスタマイズできます:
---
description: プラグインでデータを処理する
allowed-tools: ["Read", "Bash"]
---
# Process Command
手順:
1. `.claude/my-plugin.local.md` に設定が存在するか確認
2. Read ツールを使って設定を読み込む
3. YAML frontmatter をパースして設定値を取り出す
4. 設定を処理ロジックに適用する
5. 設定済みの動作で実行する
agent から読み込む
agent は instructions 内で設定を参照できます:
---
name: configured-agent
description: プロジェクト設定に適応する Agent
---
`.claude/my-plugin.local.md` のプラグイン設定を確認してください。
存在する場合は YAML frontmatter をパースし、以下に従って動作を調整します:
- enabled: プラグインが有効かどうか
- mode: 処理モード(strict、standard、lenient)
- その他の設定フィールド
パース技法
frontmatter の抽出
# --- マーカーの間の内容をすべて抽出
FRONTMATTER=$(sed -n '/^---$/,/^---$/{ /^---$/d; p; }' "$FILE")
個々のフィールドの読み込み
文字列フィールド:
VALUE=$(echo "$FRONTMATTER" | grep '^field_name:' | sed 's/field_name: *//' | sed 's/^"\(.*\)"$/\1/')
真偽値フィールド:
ENABLED=$(echo "$FRONTMATTER" | grep '^enabled:' | sed 's/enabled: *//')
# 比較: if [[ "$ENABLED" == "true" ]]; then
数値フィールド:
MAX=$(echo "$FRONTMATTER" | grep '^max_value:' | sed 's/max_value: *//')
# 利用: if [[ $MAX -gt 100 ]]; then
markdown 本文の読み込み
2つ目の --- 以降の内容を抽出:
# --- の閉じタグ以降をすべて取得
BODY=$(awk '/^---$/{i++; next} i>=2' "$FILE")
よくあるパターン
パターン 1: 一時的に有効化する Hook
設定ファイルで hook の有効化を制御する:
#!/bin/bash
STATE_FILE=".claude/security-scan.local.md"
# 未設定であれば即時終了
if [[ ! -f "$STATE_FILE" ]]; then
exit 0
fi
# enabled フラグを読み込む
FRONTMATTER=$(sed -n '/^---$/,/^---$/{ /^---$/d; p; }' "$STATE_FILE")
ENABLED=$(echo "$FRONTMATTER" | grep '^enabled:' | sed 's/enabled: *//')
if [[ "$ENABLED" != "true" ]]; then
exit 0 # 無効化されている
fi
# hook のロジックを実行
# ...
ユースケース: hooks.json を編集せずに hook を有効化・無効化する(変更には再起動が必要)。
パターン 2: Agent の状態管理
agent 固有の状態と設定を保存する:
.claude/multi-agent-swarm.local.md:
---
agent_name: auth-agent
task_number: 3.5
pr_number: 1234
coordinator_session: team-leader
enabled: true
dependencies: ["Task 3.4"]
---
# タスクの割り当て
API に JWT 認証を実装する。
**成功基準:**
- 認証エンドポイントの作成完了
- テストがパス
- PR が作成され CI がグリーン
agent を連携させるために hook から読み込む:
AGENT_NAME=$(echo "$FRONTMATTER" | grep '^agent_name:' | sed 's/agent_name: *//')
COORDINATOR=$(echo "$FRONTMATTER" | grep '^coordinator_session:' | sed 's/coordinator_session: *//')
# コーディネーターに通知を送る
tmux send-keys -t "$COORDINATOR" "Agent $AGENT_NAME completed task" Enter
パターン 3: 設定ドリブンな動作
.claude/my-plugin.local.md:
---
validation_level: strict
max_file_size: 1000000
allowed_extensions: [".js", ".ts", ".tsx"]
enable_logging: true
---
# バリデーション設定
このプロジェクトでは strict モードが有効です。
すべての書き込みはセキュリティポリシーに従って検証されます。
hook またはコマンドで使用する:
LEVEL=$(echo "$FRONTMATTER" | grep '^validation_level:' | sed 's/validation_level: *//')
case "$LEVEL" in
strict)
# 厳格なバリデーションを適用
;;
standard)
# 標準バリデーションを適用
;;
lenient)
# 緩やかなバリデーションを適用
;;
esac
設定ファイルの作成
コマンドから作成する
コマンドで設定ファイルを作成できます:
# Setup Command
手順:
1. ユーザーに設定の好みを確認する
2. YAML frontmatter を含む `.claude/my-plugin.local.md` を作成する
3. ユーザー入力に基づいて適切な値を設定する
4. 設定が保存されたことをユーザーに通知する
5. hook が変更を認識するには Claude Code の再起動が必要であることをユーザーに伝える
テンプレートの生成
プラグインの README にテンプレートを提供する:
## 設定
プロジェクト内に `.claude/my-plugin.local.md` を作成してください:
\`\`\`markdown
---
enabled: true
mode: standard
max_retries: 3
---
# Plugin Configuration
設定が有効になっています。
\`\`\`
作成または編集後、変更を反映させるには Claude Code を再起動してください。
ベストプラクティス
ファイルの命名
✅ 推奨:
.claude/plugin-name.local.md形式を使用する- プラグイン名と完全に一致させる
- ユーザーローカルなファイルには
.local.mdサフィックスを使用する
❌ 非推奨:
- 別のディレクトリを使用する(
.claude/以外) - 命名規則を統一しない
.localなしの.mdを使用する(コミットされる恐れがある)
.gitignore の設定
必ず .gitignore に追加してください:
.claude/*.local.md
.claude/*.local.json
プラグインの README にもこの旨を記載してください。
デフォルト値
設定ファイルが存在しない場合に備えて、適切なデフォルト値を提供してください:
if [[ ! -f "$STATE_FILE" ]]; then
# デフォルト値を使用
ENABLED=true
MODE=standard
else
# ファイルから読み込む
# ...
fi
バリデーション
設定値を検証してください:
MAX=$(echo "$FRONTMATTER" | grep '^max_value:' | sed 's/max_value: *//')
# 数値の範囲を検証
if ! [[ "$MAX" =~ ^[0-9]+$ ]] || [[ $MAX -lt 1 ]] || [[ $MAX -gt 100 ]]; then
echo "⚠️ 設定の max_value が不正です(1〜100 の整数を指定してください)" >&2
MAX=10 # デフォルト値を使用
fi
再起動の必要性
重要: 設定の変更を反映するには Claude Code の再起動が必要です。
README に以下のように記載してください:
## 設定の変更方法
`.claude/my-plugin.local.md` を編集した後:
1. ファイルを保存する
2. Claude Code を終了する
3. 再起動する: `claude` または `cc`
4. 新しい設定が読み込まれます
Hook はセッション中にホットスワップすることはできません。
セキュリティに関する考慮事項
ユーザー入力のサニタイズ
ユーザー入力から設定ファイルを作成する場合:
# ユーザー入力内のクォートをエスケープ
SAFE_VALUE=$(echo "$USER_INPUT" | sed 's/"/\\"/g')
# ファイルに書き込む
cat > "$STATE_FILE" <<EOF
---
user_setting: "$SAFE_VALUE"
---
EOF
ファイルパスのバリデーション
設定にファイルパスが含まれる場合:
FILE_PATH=$(echo "$FRONTMATTER" | grep '^data_file:' | sed 's/data_file: *//')
# パストラバーサルを確認
if [[ "$FILE_PATH" == *".."* ]]; then
echo "⚠️ 設定のパスが不正です(パストラバーサルを検出)" >&2
exit 2
fi
パーミッション
設定ファイルは以下の条件を満たすようにしてください:
- ユーザーのみが読み取り可能(
chmod 600) - git にコミットしない
- ユーザー間で共有しない
実際の使用例
multi-agent-swarm プラグイン
.claude/multi-agent-swarm.local.md:
---
agent_name: auth-implementation
task_number: 3.5
pr_number: 1234
coordinator_session: team-leader
enabled: true
dependencies: ["Task 3.4"]
additional_instructions: セッションではなく JWT トークンを使用すること
---
# タスク: 認証の実装
REST API に JWT ベースの認証を構築する。
共有型については auth-agent と連携すること。
hook での使用(agent-stop-notification.sh):
- ファイルの存在を確認(15〜18行目: 存在しない場合は即時終了)
- frontmatter をパースして
coordinator_session、agent_name、enabledを取得 - enabled が true の場合、コーディネーターに通知を送信
enabled: true/falseで素早く有効化・無効化が可能
ralph-loop プラグイン
.claude/ralph-loop.local.md:
---
iteration: 1
max_iterations: 10
completion_promise: "すべてのテストがパスし、ビルドが成功した状態"
---
プ
原文(English)を表示
Plugin Settings Pattern for Claude Code Plugins
Overview
Plugins can store user-configurable settings and state in .claude/plugin-name.local.md files within the project directory. This pattern uses YAML frontmatter for structured configuration and markdown content for prompts or additional context.
Key characteristics:
- File location:
.claude/plugin-name.local.mdin project root - Structure: YAML frontmatter + markdown body
- Purpose: Per-project plugin configuration and state
- Usage: Read from hooks, commands, and agents
- Lifecycle: User-managed (not in git, should be in
.gitignore)
File Structure
Basic Template
---
enabled: true
setting1: value1
setting2: value2
numeric_setting: 42
list_setting: ["item1", "item2"]
---
# Additional Context
This markdown body can contain:
- Task descriptions
- Additional instructions
- Prompts to feed back to Claude
- Documentation or notes
Example: Plugin State File
.claude/my-plugin.local.md:
---
enabled: true
strict_mode: false
max_retries: 3
notification_level: info
coordinator_session: team-leader
---
# Plugin Configuration
This plugin is configured for standard validation mode.
Contact @team-lead with questions.
Reading Settings Files
From Hooks (Bash Scripts)
Pattern: Check existence and parse frontmatter
#!/bin/bash
set -euo pipefail
# Define state file path
STATE_FILE=".claude/my-plugin.local.md"
# Quick exit if file doesn't exist
if [[ ! -f "$STATE_FILE" ]]; then
exit 0 # Plugin not configured, skip
fi
# Parse YAML frontmatter (between --- markers)
FRONTMATTER=$(sed -n '/^---$/,/^---$/{ /^---$/d; p; }' "$STATE_FILE")
# Extract individual fields
ENABLED=$(echo "$FRONTMATTER" | grep '^enabled:' | sed 's/enabled: *//' | sed 's/^"\(.*\)"$/\1/')
STRICT_MODE=$(echo "$FRONTMATTER" | grep '^strict_mode:' | sed 's/strict_mode: *//' | sed 's/^"\(.*\)"$/\1/')
# Check if enabled
if [[ "$ENABLED" != "true" ]]; then
exit 0 # Disabled
fi
# Use configuration in hook logic
if [[ "$STRICT_MODE" == "true" ]]; then
# Apply strict validation
# ...
fi
See examples/read-settings-hook.sh for complete working example.
From Commands
Commands can read settings files to customize behavior:
---
description: Process data with plugin
allowed-tools: ["Read", "Bash"]
---
# Process Command
Steps:
1. Check if settings exist at `.claude/my-plugin.local.md`
2. Read configuration using Read tool
3. Parse YAML frontmatter to extract settings
4. Apply settings to processing logic
5. Execute with configured behavior
From Agents
Agents can reference settings in their instructions:
---
name: configured-agent
description: Agent that adapts to project settings
---
Check for plugin settings at `.claude/my-plugin.local.md`.
If present, parse YAML frontmatter and adapt behavior according to:
- enabled: Whether plugin is active
- mode: Processing mode (strict, standard, lenient)
- Additional configuration fields
Parsing Techniques
Extract Frontmatter
# Extract everything between --- markers
FRONTMATTER=$(sed -n '/^---$/,/^---$/{ /^---$/d; p; }' "$FILE")
Read Individual Fields
String fields:
VALUE=$(echo "$FRONTMATTER" | grep '^field_name:' | sed 's/field_name: *//' | sed 's/^"\(.*\)"$/\1/')
Boolean fields:
ENABLED=$(echo "$FRONTMATTER" | grep '^enabled:' | sed 's/enabled: *//')
# Compare: if [[ "$ENABLED" == "true" ]]; then
Numeric fields:
MAX=$(echo "$FRONTMATTER" | grep '^max_value:' | sed 's/max_value: *//')
# Use: if [[ $MAX -gt 100 ]]; then
Read Markdown Body
Extract content after second ---:
# Get everything after closing ---
BODY=$(awk '/^---$/{i++; next} i>=2' "$FILE")
Common Patterns
Pattern 1: Temporarily Active Hooks
Use settings file to control hook activation:
#!/bin/bash
STATE_FILE=".claude/security-scan.local.md"
# Quick exit if not configured
if [[ ! -f "$STATE_FILE" ]]; then
exit 0
fi
# Read enabled flag
FRONTMATTER=$(sed -n '/^---$/,/^---$/{ /^---$/d; p; }' "$STATE_FILE")
ENABLED=$(echo "$FRONTMATTER" | grep '^enabled:' | sed 's/enabled: *//')
if [[ "$ENABLED" != "true" ]]; then
exit 0 # Disabled
fi
# Run hook logic
# ...
Use case: Enable/disable hooks without editing hooks.json (requires restart).
Pattern 2: Agent State Management
Store agent-specific state and configuration:
.claude/multi-agent-swarm.local.md:
---
agent_name: auth-agent
task_number: 3.5
pr_number: 1234
coordinator_session: team-leader
enabled: true
dependencies: ["Task 3.4"]
---
# Task Assignment
Implement JWT authentication for the API.
**Success Criteria:**
- Authentication endpoints created
- Tests passing
- PR created and CI green
Read from hooks to coordinate agents:
AGENT_NAME=$(echo "$FRONTMATTER" | grep '^agent_name:' | sed 's/agent_name: *//')
COORDINATOR=$(echo "$FRONTMATTER" | grep '^coordinator_session:' | sed 's/coordinator_session: *//')
# Send notification to coordinator
tmux send-keys -t "$COORDINATOR" "Agent $AGENT_NAME completed task" Enter
Pattern 3: Configuration-Driven Behavior
.claude/my-plugin.local.md:
---
validation_level: strict
max_file_size: 1000000
allowed_extensions: [".js", ".ts", ".tsx"]
enable_logging: true
---
# Validation Configuration
Strict mode enabled for this project.
All writes validated against security policies.
Use in hooks or commands:
LEVEL=$(echo "$FRONTMATTER" | grep '^validation_level:' | sed 's/validation_level: *//')
case "$LEVEL" in
strict)
# Apply strict validation
;;
standard)
# Apply standard validation
;;
lenient)
# Apply lenient validation
;;
esac
Creating Settings Files
From Commands
Commands can create settings files:
# Setup Command
Steps:
1. Ask user for configuration preferences
2. Create `.claude/my-plugin.local.md` with YAML frontmatter
3. Set appropriate values based on user input
4. Inform user that settings are saved
5. Remind user to restart Claude Code for hooks to recognize changes
Template Generation
Provide template in plugin README:
## Configuration
Create `.claude/my-plugin.local.md` in your project:
\`\`\`markdown
---
enabled: true
mode: standard
max_retries: 3
---
# Plugin Configuration
Your settings are active.
\`\`\`
After creating or editing, restart Claude Code for changes to take effect.
Best Practices
File Naming
✅ DO:
- Use
.claude/plugin-name.local.mdformat - Match plugin name exactly
- Use
.local.mdsuffix for user-local files
❌ DON'T:
- Use different directory (not
.claude/) - Use inconsistent naming
- Use
.mdwithout.local(might be committed)
Gitignore
Always add to .gitignore:
.claude/*.local.md
.claude/*.local.json
Document this in plugin README.
Defaults
Provide sensible defaults when settings file doesn't exist:
if [[ ! -f "$STATE_FILE" ]]; then
# Use defaults
ENABLED=true
MODE=standard
else
# Read from file
# ...
fi
Validation
Validate settings values:
MAX=$(echo "$FRONTMATTER" | grep '^max_value:' | sed 's/max_value: *//')
# Validate numeric range
if ! [[ "$MAX" =~ ^[0-9]+$ ]] || [[ $MAX -lt 1 ]] || [[ $MAX -gt 100 ]]; then
echo "⚠️ Invalid max_value in settings (must be 1-100)" >&2
MAX=10 # Use default
fi
Restart Requirement
Important: Settings changes require Claude Code restart.
Document in your README:
## Changing Settings
After editing `.claude/my-plugin.local.md`:
1. Save the file
2. Exit Claude Code
3. Restart: `claude` or `cc`
4. New settings will be loaded
Hooks cannot be hot-swapped within a session.
Security Considerations
Sanitize User Input
When writing settings files from user input:
# Escape quotes in user input
SAFE_VALUE=$(echo "$USER_INPUT" | sed 's/"/\\"/g')
# Write to file
cat > "$STATE_FILE" <<EOF
---
user_setting: "$SAFE_VALUE"
---
EOF
Validate File Paths
If settings contain file paths:
FILE_PATH=$(echo "$FRONTMATTER" | grep '^data_file:' | sed 's/data_file: *//')
# Check for path traversal
if [[ "$FILE_PATH" == *".."* ]]; then
echo "⚠️ Invalid path in settings (path traversal)" >&2
exit 2
fi
Permissions
Settings files should be:
- Readable by user only (
chmod 600) - Not committed to git
- Not shared between users
Real-World Examples
multi-agent-swarm Plugin
.claude/multi-agent-swarm.local.md:
---
agent_name: auth-implementation
task_number: 3.5
pr_number: 1234
coordinator_session: team-leader
enabled: true
dependencies: ["Task 3.4"]
additional_instructions: Use JWT tokens, not sessions
---
# Task: Implement Authentication
Build JWT-based authentication for the REST API.
Coordinate with auth-agent on shared types.
Hook usage (agent-stop-notification.sh):
- Checks if file exists (line 15-18: quick exit if not)
- Parses frontmatter to get coordinator_session, agent_name, enabled
- Sends notifications to coordinator if enabled
- Allows quick activation/deactivation via
enabled: true/false
ralph-loop Plugin
.claude/ralph-loop.local.md:
---
iteration: 1
max_iterations: 10
completion_promise: "All tests passing and build successful"
---
Fix all the linting errors in the project.
Make sure tests pass after each fix.
Hook usage (stop-hook.sh):
- Checks if file exists (line 15-18: quick exit if not active)
- Reads iteration count and max_iterations
- Extracts completion_promise for loop termination
- Reads body as the prompt to feed back
- Updates iteration count on each loop
Quick Reference
File Location
project-root/
└── .claude/
└── plugin-name.local.md
Frontmatter Parsing
# Extract frontmatter
FRONTMATTER=$(sed -n '/^---$/,/^---$/{ /^---$/d; p; }' "$FILE")
# Read field
VALUE=$(echo "$FRONTMATTER" | grep '^field:' | sed 's/field: *//' | sed 's/^"\(.*\)"$/\1/')
Body Parsing
# Extract body (after second ---)
BODY=$(awk '/^---$/{i++; next} i>=2' "$FILE")
Quick Exit Pattern
if [[ ! -f ".claude/my-plugin.local.md" ]]; then
exit 0 # Not configured
fi
Additional Resources
Reference Files
For detailed implementation patterns:
references/parsing-techniques.md- Complete guide to parsing YAML frontmatter and markdown bodiesreferences/real-world-examples.md- Deep dive into multi-agent-swarm and ralph-loop implementations
Example Files
Working examples in examples/:
read-settings-hook.sh- Hook that reads and uses settingscreate-settings-command.md- Command that creates settings fileexample-settings.md- Template settings file
Utility Scripts
Development tools in scripts/:
validate-settings.sh- Validate settings file structureparse-frontmatter.sh- Extract frontmatter fields
Implementation Workflow
To add settings to a plugin:
- Design settings schema (which fields, types, defaults)
- Create template file in plugin documentation
- Add gitignore entry for
.claude/*.local.md - Implement settings parsing in hooks/commands
- Use quick-exit pattern (check file exists, check enabled field)
- Document settings in plugin README with template
- Remind users that changes require Claude Code restart
Focus on keeping settings simple and providing good defaults when settings file doesn't exist.
原文・著作権は Anthropic および各プラグイン作者に帰属します。日本語訳は Claude API による自動翻訳です。