Claude Code設定が反映されない原因の探し方 — 配置・書式のよくある見落とし
hooksが発火しない、MCPサーバーが繋がらない。原因の多くはファイルの置き場所か書式の細部にあります。/contextとclaude doctorから辿る切り分け手順をまとめます。
設定が反映されない原因は2つに絞れる
CLAUDE.mdの指示が無視される、hooksが発火しない、追加したはずの機能が現れない。この手の症状は、設定ファイルが読み込まれていないか、読み込まれてはいるが別のファイルに上書きされているかのどちらかがほとんどです。原因を推測で決め打ちせず、Claude Codeが実際に何を読み込んだかを先に確認すると、切り分けの時間が大きく縮みます。
切り分けの順序
- 1
`/context`で読み込み状況を見る
CLAUDE.md・スキル・MCPツールがセッションに入っているかを確認します。入っていなければ「置き場所」の問題です。
- 2
`claude doctor`で壊れたファイルを探す
JSONの構文エラーや、スキーマに合わない値を持つ設定ファイルが一覧に出ます。
- 3
専用コマンドで個別に確認する
hooksは
/hooks、MCPは/mcp、スキルは/skillsで、登録状況と状態を見ます。 - 4
`--safe-mode`で消去法に切り替える
個別の確認で見つからないときの最終手段です。すべてのカスタマイズを外して再現するかを見ます。
まず/contextで実際に読み込まれた内容を確認する
/contextは、現在のセッションでコンテキストウィンドウを占めている内容をカテゴリ別に表示します。システムプロンプト・システムツール・MCPツール・カスタムサブエージェント(読み込み元も表示)・メモリファイル・スキル・会話メッセージが対象です。CLAUDE.mdやスキルが本当に読み込まれているかは、まずここで確認します。
より詳しく特定のカテゴリを見たい場合は、専用コマンドに進みます。
| コマンド | 表示内容 |
|---|---|
/memory | 表示内容ユーザー・プロジェクトスコープのメモリファイルの場所 |
/skills | 表示内容プロジェクト・ユーザー・プラグイン由来の利用可能なスキル |
/hooks | 表示内容現在有効なhook設定 |
/mcp | 表示内容接続中のMCPサーバーとその状態 |
/permissions | 表示内容現在有効な許可・拒否ルール |
/doctor | 表示内容インストール状態・不正な設定ファイル・重複サブエージェント名などの点検 |
/status | 表示内容有効な設定ソース(managed設定が効いているかを含む) |
/contextの一覧にメモリファイルが出ない場合は、CLAUDE.mdの読み込みルールとファイルの場所を照合します。読み込まれていることが確認できたのに特定の指示だけ無視される場合は、読み込みの問題ではなく指示の書き方の問題です。曖昧で複数の解釈ができる表現、2つのファイルが矛盾する方針を書いている、ファイル自体が長くなりすぎて個々のルールへの注意が薄まっている、のいずれかが典型的な原因です。新しいチームメンバーに口頭で伝えるつもりで、プロジェクトの規約やビルドコマンド、ファイルの置き場所を具体的に書くと遵守率が上がります。
claude doctorで壊れた設定ファイルを名指しで探す
セッションを開始せずに設定ファイルの不備だけを見たいときは、ターミナルからclaude doctorを実行します。読み取り専用で、現在のディレクトリの設定ファイルも対象です。一時ディレクトリに2つの不正なファイルを置いて実行しました。hooksのmatcherを配列にした.claude/settings.jsonと、トップレベルキーをserversにした.mcp.jsonです(v2.1.287で確認。パスは/path/to/projectに置き換えています)。
claude doctorInvalid settings
- /path/to/project/.claude/settings.json › hooks.PreToolUse.0: Invalid hook matcher (matcher: Invalid input: expected string, received array) — a PreToolUse/PermissionRequest hook that cannot be loaded may be what guards the permissions declared beside it, so nothing it sits in is applied until the entry is fixed or removed.
- /path/to/project/.claude/settings.json › hooks.PreToolUse.0.matcher: Expected string, but received array
Suggested fix: Hooks use a matcher + hooks array. The matcher is a string: a tool name ("Bash"), pipe-separated list ("Edit|Write"), or empty to match all.
- /path/to/project/.mcp.json › mcpServers: Missing "mcpServers" — found "servers" instead. Claude Code reads MCP servers from the "mcpServers" key.
Suggested fix: Rename the top-level "servers" key to "mcpServers" in /path/to/project/.mcp.json出力は「どのファイルの、どのキーが、なぜ不正か」まで指します。matcherの配列について、doctorは次のように説明しています。読み込めなかったPreToolUse/PermissionRequestのhookが、同じファイルの権限設定を守っていた可能性があるため、そのファイル全体を適用しないというものです。
末尾カンマが残り、閉じ括弧の欠けたsettings.jsonでは、メッセージはInvalid or malformed JSONの1行になりました。この場合は、構文エラーのあるファイルが読み込めていないという意味です。
壊れ方の重さは3段階に分かれる
起動時に何が起きるかは、壊れ方で変わります。
設定ファイルが壊れたときの扱い
Settings Error
user・project・localのファイルでJSONが不正、またはスキーマに合わない値がある場合です。対話セッションの開始時にダイアログが出て、Claudeの助けで直す・終了する・壊れた設定なしで続行する、のいずれかを選べます。
Settings Warning
不正な権限ルールや未知のhookイベント名のように、個々のエントリだけが失敗した場合です。その値だけが飛ばされ、ファイルの残りは有効なままです。
managed設定
ファイル全体は拒否されず、有効な部分が適用され続けます。落とされる項目と、より厳しい値に倒れるキーは、管理者向けのmanaged settingsの文書に一覧があります。
CLAUDE.mdが読み込まれない典型パターン
サブディレクトリに置いたCLAUDE.mdは、セッション開始時には読み込まれません。Claude CodeがそのディレクトリのファイルをReadツール、Writeツール、Editツールのいずれかで操作すると、初めて読み込まれます。v2.1.288より前のバージョンでは、読み込みの引き金になるのはReadツールだけでした。バージョンが古い環境では、ファイルを書き換えさせても読み込まれません。「サブディレクトリのCLAUDE.mdが無視される」と感じたら、バージョンを確認し、まだ古ければそのディレクトリのファイルをReadで開かせてみます。
もう1つの見落としが、組み込みのExploreサブエージェントとPlanサブエージェントです。これらはCLAUDE.mdを読み込みません。メインの会話や、自分で定義したカスタムサブエージェントは通常どおり読み込みます。ただしカスタムサブエージェントの定義がomitClaudeMdを設定している場合は別で、この場合はCLAUDE.mdを読みません。組織のmanaged policyのCLAUDE.mdは、omitClaudeMdを設定しても読み込まれます。例外は、managed settingsで定義されたmanagedサブエージェントです。
ExploreやPlanに重要な指示を守らせたい場合は、CLAUDE.mdではなく委任するプロンプト自体にその指示を書き込みます。カスタムサブエージェントの場合は、エージェント定義ファイルの本文(システムプロンプトになる部分)に重要な指示を置きます。
hooksが登録されているのに発火しない
/hooksに一覧が出ない場合、そもそも設定ファイルが読み込まれていません。hooksは独立したファイルではなく、settings.jsonの"hooks"キー直下に書く必要があります。プラグインだけは例外で、hooks/hooks.jsonという別ファイルから読み込まれます。
/hooksに出ているのに発火しない場合、原因の大半はmatcherフィールドの書き方です。
{
"hooks": {
"PreToolUse": [
{
"matcher": "Edit|Write",
"hooks": [{ "type": "command", "command": "./format.sh" }]
}
]
}
}matcherは単一の文字列で、複数のツール名は|区切りで指定します。,区切りも同等に動きますが、v2.1.191より前のバージョンでは,は正規表現の文字として文字通り評価され、一切マッチしません。バージョンが古い場合は|を使いますmatcherはツール名と大文字小文字まで一致させる必要があります。bashではなくBash、editではなくEditです。綴りを間違えたツール名は何にもマッチせず、エラーも出ませんmatcherが配列になっているのはスキーマエラーです。起動時のダイアログとclaude doctorの両方に出ます。影響範囲は前節の出力のとおりです
settings.jsonへの編集は、保存後に短いファイル安定性の遅延を経てセッションに反映されます。セッションの再起動は不要です。セッション開始後に.claude/フォルダ自体を作った場合も反映されますが、v2.1.257より前のバージョンでは検知されませんでした。
数秒待っても/hooksが古い定義のままなら、もう一度/hooksを実行して表示を更新します。それでも発火しない場合はclaude --debugでセッションを起動します。hook評価のたびにどのmatcherが照合され、終了コードが何だったかをデバッグログで確認できます。
MCPサーバーが設定通りに動かない
/mcpで接続状態と承認状況を確認します。設定自体は正しくてもツールが出てこないケースには、いくつか典型パターンがあります。
- プロジェクトスコープのサーバーは
.mcp.jsonに定義しますが、初回は承認が必要です。承認プロンプトを閉じてしまうと、/mcpから手動で承認するまで無効のままです - 起動に失敗したサーバーは
/mcpで失敗と表示されます。commandやargsに相対パスを使っていることが多い原因で、パスは.mcp.jsonの場所ではなくClaude Codeを起動したディレクトリ基準で解決されます。npxやuvxのようにPATH上にある実行ファイルは、そのままで構いません - 接続済みと表示されるのにツールが0件のサーバーは、起動はしているがツール一覧を返していない状態です。
/mcpから再接続を試します。それでも0件ならclaude --debug=mcpを実行し、~/.claude/debug/<session-id>.txtのサーバー側stderrを確認します
配置場所の間違いも頻出です。プロジェクトのMCP設定は.claude/配下ではなくリポジトリ直下の.mcp.jsonに置き、キーはmcpServersにします。VS Codeのmcp.jsonのようにトップレベルキーがserversになっていたり、.mcp.jsonを.claude/配下に置いてしまうと読み込まれません。前節のclaude doctorの出力が示すとおり、serversは名指しで検出されます。
settings.jsonにmcpServersキーを書いても読み込まれません。プロジェクトサーバーは.mcp.json、ユーザースコープのサーバーはclaude mcp add --scope userで登録します。
サーバーは起動しているのに、そのサーバーが期待する環境変数を受け取っていないケースもあります。Claude Codeがstdioサーバーへ渡す環境は、自分自身の環境から一部の変数を除いたものであり、起動時のシェル環境やワークスペースの信頼設定には依存しません。サーバーが必要とする環境変数は、.mcp.jsonのそのサーバーのエントリ内にenvとして個別に書きます。
設定ファイルの置き場所を間違えやすい2パターン
グローバルな権限・hooks・環境変数を設定したつもりで反映されないとき、よくある原因は~/.claude.jsonへの書き込みです。名前が似ているだけで、2つのファイルは役割が違います。
似た名前の2つのファイル
~/.claude.json
アプリの状態やUIのトグルを保持するファイルで、Claude Code自身が書き込みます。サインインのセッション、MCPサーバー設定、プロジェクトごとの信頼判断もここに入ります。permissions・hooks・envを書いても設定としては読まれません。
~/.claude/settings.json
permissions・hooks・envを書く場所です。ユーザー全体に効かせたい設定は、こちらに書きます。
もう1つは、settings.local.jsonによる上書きです。優先順位はlocalがprojectを上書きし、projectがuserを上書きします。managed設定がある場合は最優先で適用されます。managedの下には、コマンドラインの--settingsがuser・project・localの上位として置かれます。「settings.jsonに書いたのに効かない」ときは、同じキーがsettings.local.jsonに別の値で存在していないかを確認します。
一部の設定はコマンドラインフラグや環境変数でも指定でき、これらも別の上書き層として働きます。ファイルの値がそのまま使われていないときは、同じキーに対応する環境変数がシェルやCIに残っていないかも確認します。どの設定がどのスコープで決まるかは、設定ガイドの優先順位の節で引けます。
スキルが/skillsに出ない・呼ばれない
スキルファイルを.claude/skills/name.mdのように単体で置くと認識されません。.claude/skills/name/SKILL.mdというフォルダ構成が必須です。
/skillsには表示されているのにClaudeが自発的に呼ばない場合は、原因が2つ考えられます。1つはフロントマターのdisable-model-invocation: true、もう1つはdescriptionの言い回しが実際のリクエストと噛み合っていないことです。/skillsのバッジ表示で「user-only」となっているスキルは、Claudeが自分の判断で呼び出すことはありません。
permissionsのdenyルールが効かないことがある
Bash(rm *)のようなdenyルールは、実行される実体のコマンドではなくコマンド文字列そのものにマッチします。そのため/bin/rmのようにパスを直接指定する呼び出しや、bash -c 'rm -rf build/'のようにbash -cで包んだ呼び出しはすり抜けます。確実に止めたい操作がある場合は、denyルールの文字列パターンをバリエーションごとに追加するか、PreToolUse hookやサンドボックスで実行そのものを止める設計にします。
それでも直らないときは消去法に切り替える
ここまでの個別チェックで見つからない場合、次は原因を絞り込むのではなくすべてを一旦無効化してから戻すアプローチに切り替えます。切り分けは、claude --safe-modeとクリーンなCLAUDE_CONFIG_DIRで起動して結果を比べる方法です。手順はClaude Code safe modeで「壊れた」設定を1コマンドで切り分けるにあります。各フィールドの意味は、Claude Code設定ガイドのフィールド一覧で確認できます。
よくある質問
SessionEnd hookが実行されません
SessionEndイベントのhookは、明示的にsettings.jsonへ登録しないと動きません。PreToolUseやPostToolUseのhookを設定していても、SessionEndは別イベントとして個別に登録が必要です。
claude doctorと/doctorはどう使い分けますか
ターミナルのclaude doctorは読み取り専用の診断だけを出します。セッション内の/doctorは同じ点検に加えて、使われていない拡張機能の整理や修正案の提示まで行い、適用する前に確認を求めます。
まとめ
/contextで読み込みを、claude doctorで書式の壊れを先に確かめます。そこで異常が出なければ、残る候補は別のファイルによる上書きと置き場所の違いに絞れます。