こんにちは、テクマトリックスの長久保です。
私は日常的にClaude Codeを気に入って使っているのですが、先日Anthropic公式のブログ記事「Steering Claude Code: CLAUDE.md files, skills, hooks, rules, subagents and more」が公開されていたので、改めて学び直そうと思い読んでみました。
記事を読むだけでは「なんとなくわかった気になる」で終わってしまいそうだったので、書かれている内容を参考に、実際に手元で動かして確かめてみました。
本記事は、Webページを読みながら手を動かして検証してみた記録です。Claude Codeを使っていて「仕組みは知っているけれど、結局どれをどう使い分ければいいのか曖昧」という方の参考になれば嬉しいです。
目次
前提
本ブログは2026/06/24時点の情報と、「Steering Claude Code: CLAUDE.md files, skills, hooks, rules, subagents and more」を元に記載しています(以下、元記事と記載します)。
また、Claude CodeはWindowsにインストール(v2.1.187)し、Opus 4.8(high)を利用して実行します。
各仕組みの整理
Claude Codeは(個人的体感として Opus 4.6 くらいから)特に細かい指示をしなくても「いい感じ」に動くようになりました。
そのうえで、「こう動いてほしい」を伝える方法が複数あり、用途ごとに使い分けるのがコツとなります。それぞれの方法について、一覧表として整理しました。
| 名称 | 配置場所 | 読み込まれるタイミング | トークンコスト | 向いている用途 |
|---|---|---|---|---|
| CLAUDE.md | プロジェクト直下など | セッション開始時に読み込まれ、以降ずっと保持 | 高 | ビルドコマンド・構成・規約などの「事実」情報 |
| Rules | .claude/rules | 常時/該当ファイルにアクセスした時 | 中 | 横断的な規約(例:APIは必ず入力検証をするなど特定のファイルを編集する際のルールを記載する) |
| Skills | .claude/skills | 名称と説明は常時/本文は呼び出し時 | 低 | デプロイ手順・チェックリストなどの手順書 |
| Subagents | .claude/agents | 名前・説明・使用可能ツール一覧は常時/本文は呼び出し時 | 低 | 独立コンテキストで並列・隔離して走らせる作業(読み込み量は多いが結論は短い作業) |
| Hooks | .claude/settings.json | イベント発火時 | 低 | 自動実行・通知・コマンド禁止(強制力は高いが設計に注意) |
| Output styles | .claude/output-styles | セッション開始時(システムプロンプト内の既定スタイルを書き換え) | 高 | 応答スタイルを丸ごと変更したいとき |
| Append system prompt | 起動時のCLIフラグ | その起動セッション限り | 中 | その場限りの規約・出力フォーマットの付与 |
なお、元記事ではこれらを「いつ読み込まれるか」「コンパクション(長い会話の自動圧縮)で内容が残るか」「コンテキスト(トークン)コスト」「どんな用途に向くか」といった観点で記載されているのであわせてご確認ください。
サンプルプロジェクト
手元のClaude Codeで実行できるようにzipファイルを用意しました。
該当のGitHubへアクセスしzipファイルを解凍すると以下のファイルが入っています。
claude-steering-lab/
├── CLAUDE.md ← ① 常時ロードされる事実情報
├── README.md ← サンプルの実験ガイド
├── PROTECTED.md ← Hook で編集ブロックするデモ用
├── secrets/api_key.txt ← Permissions(deny)でアクセス拒否するデモ用(⑤ の補足で解説)
├── demo-append-system-prompt.ps1 ← ⑦ Append system prompt のデモ起動スクリプト
├── src/
│ ├── tasks.py ← サンプルコード(ルール対象外)
│ └── api.py ← サンプル API(Path-scoped Rule の対象)
└── .claude/
├── settings.json ← ⑤ Hooks + Permissions の設定
├── rules/api-validation.md ← ② Rules(paths でスコープ限定)
├── skills/deploy-checklist/SKILL.md ← ③ Skills
├── agents/log-analyzer.md ← ④ Subagents
├── output-styles/sensei.md ← ⑥ Output styles(独自スタイル)
└── hooks/ ← ⑤ Hooks の実体(Python)
├── protect_file.py
└── log_edit.py吹き出しブロックはプロンプトです。手元で動かせる方は実行してみてください。
①:CLAUDE.md が読み込まれるかの確認
■確認内容
CLAUDE.md は何も指示しなくても、起動のたびに自動で読み込まれることを確認する。
起動して何も処理をしていない状態で、以下のプロンプトを入力します。
このプロジェクトのテストはどうやって実行する?

Claude Codeは起動(セッション開始)時にCLAUDE.mdを読み込み、その内容をセッション中ずっとコンテキストに保持するため、上記のように回答してくれます。
CLAUDE.mdは常にコンテキストに載る=トークンを消費し続けるうえ、大量のトークンを読み込ませるとプロンプトの実行精度も低下します。そのため、CLAUDE.mdには「事実」だけを書き、短く保つ(元記事には200行以下を推奨とあります)ことが大切です。
細かい手順書のようなものは後述のSkillsに記載します。
②:特定のファイルにだけ有効な Rules(Path-scoped)
■確認内容
ルールが「関係あるファイルを触ったときだけ」発動することを確認する。
.claude/rules/api-validation.md を見ていただけると分かる通り、frontmatterで paths: ["src/api.py"] と対象を限定していて「API のエンドポイントは必ず入力検証する」という制約を持たせています。

まずはRulesの対象外のファイルを対象として、以下のように指示を出します。
src/tasks.pyのadd_taskに、日本語のコメントを1行足して。

このようにsrc/tasks.pyはPath-scoped Rulesの対象外なので指示通り対応してくれました。また、この時の「規約通り、コメントは日本語で記載しています」というのはCLAUDE.mdに書いたチーム規約です。このように明示的に指示をしなくても守られていることが分かります。
次にPath-scoped Rulesの対象のファイルを操作させます。
src/api.py に、タスクを削除するエンドポイント:delete_task を追加して。


少し気を利かせたことも追加で実行してくれましたが、src/api.pyに更新が入る際は、定義済みのRulesに従って処理を追加してくれます。
必要な時に必要なファイルだけを読み込んで実行することができるので、コンテキストも抑えることができ便利な仕組みだと思います。
③:呼び出したときだけ利用される手順書としてのSkills
■確認内容
必要なタイミングで必要な内容が読み込まれることを確認する。
Skillsはセッション開始時に名前と説明(description)だけが読み込まれ、実際に呼び出されたときに本文が読み込まれる仕組みです。これにより、たくさんのSkillsを登録してもトークン消費を小さく抑えることができます。
.claude/skills/deploy-checklist/SKILL.mdにデプロイ前の手順を記載しています。

Skillsに関しては
/deploy-checklist
とコマンドのようにプロンプトに書くことで呼び出すこともできますし、
デプロイ前のチェックをやって
と自然言語で指示を出しても、それらしいSkillsを自動的に選んで実行してくれます。
必ず特定の処理をしてほしい場合は、Skillsの名称を直接指定したほうが良いでしょう。今回は自然言語で指示を出します。


このようにSkillsが読み込まれ、SKILL.mdに記載した通り
- スモークテスト実行
- API規約チェック
- 変更要約
- 合否宣言
が自動で読み込まれて処理が実行されました。
④:別に処理を走らせて結果だけを受け取るSubagents
■確認内容
Subagents は独立したコンテキストで動作し、途中の処理自体はメインのエージェントに持ち込まず結果だけを返すことを確認する。
実際にClaude Codeを使っていると、会話が長くなってコンテキストが膨らむほど精度が落ちるため、メインのコンテキストはできるだけ少なくしておきたいものです。/clearや/compactなどで対応することもできますが、Subagentを使えば、調査などの途中経過は別コンテキストに隔離し、結果だけをメインに返せるので、メインのコンテキストを膨らませずに済みます。
Subagentの役割や指示はあらかじめ定義しておくことが可能です。

まず分析対象のログファイルを作成します。
ここまでの操作で後述のHooksによりlogs/edits.logが生成されているはずですが、もし無ければ、何かClaude Codeにファイルを編集させてください。
log-analyzer サブエージェントを使って、logs/edits.log を分析して。
どのファイルが何回編集されたか集計して要約だけ返して。

処理自体は独立したコンテキストで実行され、処理が完了すると結果を返してくれます。

スクリーンショットのとおり、ログの読み込みや集計は別コンテキストで行われ、メインには要約だけが返ってきます。そのためメインのコンテキストを圧迫しません。
ログ調査のような「読み込み量は多いが結論は短い」場合に、Subagentは非常に有効です。
なお、元記事によると、Subagentは最大5階層までネストでき、ワークフロー次第では数十~数百のバックグラウンドエージェントを並行で動かすこともできるとのことです。
⑤:「指示」ではなく「強制」させる Hooks
■確認内容
Hooks が対象イベントの発火時に必ず実行され、編集の自動ログ記録や禁止操作のブロックが、指示の有無にかかわらず強制されることを確認する。
先述のCLAUDE.md はあくまで「指示」なので、「〜して」と記載しても従う保証はありません。
最近のモデルは賢く、ある程度は文脈をくみ取って従ってくれるようになりましたが、確実にやらせる/やらせないを担保したいときはHooksで実現します。
.claude/settings.jsonに2つのHookを登録しています。元記事ではツール実行を検査するHookとしてPreToolUseが紹介されていますが、今回は検証用に以下の形にしました。
- PostToolUse
編集のたびに自動でログを記録する - PreToolUse
ツール呼び出しを検査し、終了コード 2 を返して禁止操作をブロックする

Subagentsで用いたログファイルは、Hooksによって生成されたものです。
Claudeがファイルを変更するたびにlog_edit.pyが実行され、logs/edits.logに1行追加されます。
PreToolUseで.claude/hooks/protect_file.pyを呼び出すことで、禁止操作をブロックすることもできます。

このようにPROTECTED.mdを編集しようとするとメッセージとともにエラーを返すようにしています。
PROTECTED.md の一番下に「test」と追記して。

検証用のフォルダということを理解しているからか、想像以上に気を利かせた内容が返ってきましたが、.claude/hooks/protect_file.pyで定義した通り「PROTECTED.md は保護されています。Hook(PreToolUse)により編集をブロックしました。」とレスポンスも返ってきました。
Hooksは「必ず実行される」が、「禁止」を意図どおり強制するには注意が必要
Hooksは対象のイベントが発火すれば必ずトリガーされます。
ただし、「必ずトリガーされる」ことと「意図したとおりに禁止を強制できる」ことは別問題になり、ここには注意が必要です。
今回のprotect_file.pyはPreToolUseでEdit / Write ツールを検査してブロックしています。そのためClaudeに通常の編集を依頼するとブロックされます。

ただしあくまでEdit / Write ツールを用いての書き込みを禁止しているだけなので、簡単に編集させることができます。
今回は検証だから大丈夫。追記して

説明してくれている通りですが、Hookの検査対象外のツールを用いることで書き込むことは可能です。
- Edit / Write ツールには
PreToolUseHookが効くため、Claude経由の編集はブロックされる - 一方で Bash 経由の追記(
>>やAdd-Contentなど)は、そのHookの対象外なので書き込めてしまう
ということです。本当に保護したいファイルであれば、Edit/Writeだけでなく、Bashなども含めて保護対象にしないと「抜け道」が残ります。
元記事でも、本当に守りたいものに対しては「指示」ではなくより強固な仕組みが必要で、その手段としてHooksとPermissions(権限設定)が挙げられています(”A real guardrail needs to be deterministic, and the enforcement methods are hooks and permissions.”)。さらに組織全体に強制したい場合は、管理者が配布するManaged Settingsも紹介されています。
Permissionsは特定のツールやコマンドを許可/拒否するルールです。

このようにサンプルのsettings.jsonにはsecretsに関してのdenyルールを入れています。

この通り、読み取りがブロックされます。今回のようなBash経由の抜け道もBashをPermissionsのdenyで塞ぐか(ただしうまく設計しないと非常に使い勝手が悪くなる)、Hookの検査対象にBashを含めることで対処できます。
このようにHooksは確実に発火しますが、「どのツール/イベントを対象にするか」まで正しく設計して初めて意図したガードレールとして機能します。
⑥:応答スタイルを丸ごと変える Output styles
■確認内容
Output styles を切り替えると、Claude の「話し方(応答スタイル)」そのものが変わることを確認する。
.claude/output-styles/sensei.mdに「結論→なぜ→具体例」の三部構成でかみ砕いて説明する”sensei”スタイルを用意しました。

Output stylesはシステムプロンプト内の既定の出力スタイルを差し替える形で組み込まれ、セッション開始時に読み込まれます。これまで紹介したどの仕組みよりも応答内容に対して強制力があります。
Path-scoped Rule って何?

このままでも十分丁寧ですが、せっかくなのでOutput styleを切り替えてみます。
/config
をプロンプトとして入力し、Output styleを切り替えます。

設定を切り替えてから先ほどと同じようにプロンプトを投げます。


指示をした通り、「結論→なぜ→具体例」の構成で返ってくるようになりました。
ただし、注意点があります。Output styleの変更はシステムプロンプト内の「デフォルトの出力スタイル」を書き換えてしまうため、安全性の配慮やテスト実行など、Claude Codeが標準で備えているコーディング向けの既定の指示がなくなってしまう恐れがあります。
これを避けたい場合は、スタイルのfrontmatterに keep-coding-instructions: true を指定すると、デフォルトのコーディング指示を保持したままカスタムスタイルを適用できるとのことです。また、元記事は、まず組み込みのProactive / Explanatory / Learningで実現できないかを先に確認することを勧めています。
⑦:その起動限りで指示を足す Append system prompt
■確認内容--append-system-prompt で渡した指示が、その起動のときだけ有効になる(=設定ファイルには残らない)ことを確認する。
Output styles が既定の出力スタイルを「置き換える」のに対し、--append-system-prompt はシステムプロンプトに指示を「加算」するCLIフラグです。
ファイルとして永続化されないので、その場限りの実験的な用途に向きます。なお入力トークンは増えますが、プロンプトキャッシュが効くため2回目以降のコストは軽減されます。
リポジトリに同梱したdemo-append-system-prompt.ps1は、「回答の最後の行に必ず 🦊 を付ける」という指示を渡してClaude Codeを起動するスクリプトです。
pwsh ./demo-append-system-prompt.ps1で起動するか、そのまま
claude --append-system-prompt "あなたは、すべての回答の最後の行に必ず絵文字『🦊』だけを単独で出力します。これは例外なく守ってください。"とClaude Codeを起動してください。
その後適当に質問してみます。

このように『🦊』を追加してくれます。
なお、元記事には「与える指示が多いほど、特に矛盾する指示があるほど追従が弱くなる(diminishing returns)」とあるのでより強制したい場合はこれまでのほかの方法も併せて実行する方が良いでしょう。
まとめ
Claude Codeに「こう動いてほしい」を伝える仕組みを7つ紹介しました。
| 名称 | 配置場所 | 読み込まれるタイミング | トークンコスト | 向いている用途 |
|---|---|---|---|---|
| CLAUDE.md | プロジェクト直下など | セッション開始時に読み込まれ、以降ずっと保持 | 高 | ビルドコマンド・構成・規約などの「事実」情報 |
| Rules | .claude/rules | 常時/該当ファイルにアクセスした時 | 中 | 横断的な規約(例:APIは必ず入力検証をするなど特定のファイルを編集する際のルールを記載する) |
| Skills | .claude/skills | 名称と説明は常時/本文は呼び出し時 | 低 | デプロイ手順・チェックリストなどの手順書 |
| Subagents | .claude/agents | 名前・説明・使用可能ツール一覧は常時/本文は呼び出し時 | 低 | 独立コンテキストで並列・隔離して走らせる作業(読み込み量は多いが結論は短い作業) |
| Hooks | .claude/settings.json | イベント発火時 | 低 | 自動実行・通知・コマンド禁止(強制力は高いが設計に注意) |
| Output styles | .claude/output-styles | セッション開始時(システムプロンプト内の既定スタイルを書き換え) | 高 | 応答スタイルを丸ごと変更したいとき |
| Append system prompt | 起動時のCLIフラグ | その起動セッション限り | 中 | その場限りの規約・出力フォーマットの付与 |
なんとなくCLAUDE.mdに全部書いてしまいがちですが、用途ごとに置き場所を分けるだけでトークンも節約でき、Claude の挙動も安定すると感じました。
気になった方はぜひ元記事も合わせて読んでみてください。
