diagnose について
diagnoseは、難しい不具合やリグレッションを調査する開発者・コーディングエージェント向けのデバッグスキルです。再現確認を先行させ、仮説検証と変更後の再検証を手順化します。
主な機能
- 01不具合の整理と再現
- 02修正前の失敗検知ループ
- 03反証可能な仮説の順位付け
- 04スタック別デバッグ手順
- 05変更ごとの再検証
活用シーン
- 01難しいリグレッションの調査
- 02最小再現ケースへの縮小
- 03不安定な失敗の診断
- 04.NET、Angular、Python、Reactのデバッグ
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ afonsoft/ skills --skill diagnoseインストール後、Claude Code で/diagnoseを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
references/angular-debugging.mdcondition-based-waiting.mddefense-in-depth.mddotnet-debugging.mdpython-debugging.mdreact-debugging.mdroot-cause-tracing.mdscripts/find-polluter.shhitl-loop.template.sh詳細
診断
難しいバグやリグレッションに対処するための手法です。明確な理由がある場合に限り、フェーズを省略してください。ユーザーへの質問や調査結果はすべて**ポルトガル語(pt-BR)**で報告してください。
コードベースを調査する際は、関連モジュールの全体像を把握するため、プロジェクトのドメイン用語集(.claude/CONTEXT.md が存在する場合)を参照し、作業対象の領域に関する決定事項や ADR を docs/architecture/ で確認してください。
再検証ループ:仮説、修正、変更を行うたびに、バグが解決したと判断する前に、再現手順とリグレッションチェックを再実行してください。
鉄則:レッドループを経て根本原因を確認するまでは、修正を行わないでください。フェーズ 1 で失敗の兆候が確認され、フェーズ 4 で仮説が裏付けられる前に行われた変更は、推測にすぎません。プレッシャーの中での推測は、1つのバグを3つに増やす原因です。これは特に、時間に追われているとき、バグが「単純に見える」とき、そして以前の修正がすでに失敗した後に重要です。まさにそうした状況で、このプロセスの効果が発揮されます。このプロセスの文言に反することは、デバッグの精神に反することです。
パイプライン
Phase 0 Frame the bug → symptom, expected vs actual, env, frequency, scope
Phase 1 Build a feedback loop → ONE tight, red-capable command (the core of this skill)
Phase 2 Reproduce + minimise → smallest scenario that still goes red
Phase 3 Hypothesise → 3–5 ranked, falsifiable predictions
Phase 4 Instrument → one probe per prediction, one variable at a time
Phase 5 Fix + regression test → test at a correct seam, watch red → green
Phase 6 Cleanup + re-validate → remove probes, re-run the original repro
↺ If the bug survives or mutates, return to Phase 3.
↺ If every hypothesis dies, see "Stuck — when hypotheses run out".
コード以外の障害に関するエントリーポイント:
- バグがエージェントセッション自体にある → エージェントの自己デバッグ
- 問題を起こしているシステムがエージェント/AI ワークフローである → AI ワークフローの診断
- コードは「動作」しているが、意図しない結果や何も起きない状態がひそかに発生している → サイレント失敗の調査
編集時の注意
このスキルでは、コマンド、出力、取得した成果物を表示します。まずすべてのシークレットを編集してください:該当箇所を <REDACTED> に置き換えます。認証情報を表示内容ではなく環境内に保持できるよう、環境変数を使ってループを構築してください。取得した成果物には認証ヘッダーが含まれています。シグナルがある行だけを引用してください。
編集済みの出力だけではバグを診断できない場合は、その旨を伝え、ユーザーに依頼してください(ポルトガル語で)。
使用するタイミング
- ユーザーが英語でこのスキルを依頼または言及した場合(例:「use /diagnose」「run diagnose」)。
- ユーザーがポルトガル語でこのスキルを依頼または言及した場合(例:「use /diagnose」「execute diagnose」)。
- 障害がエージェントセッション自体にある場合(ループ、コンテキストのずれ、ツール呼び出しの繰り返し)→ エージェントの自己デバッグに進んでください。
- 問題を起こしているシステムがエージェントまたは AI ワークフローである場合 → AI ワークフローの診断を実行してください。
スタック別プレイブック
対象のコードベースが次のいずれかのスタックに該当する場合は、ループを構築する前に references/ から該当するプレイブックを読み込んでください。すぐに使える再現コマンド、デバッガー/プロファイラーのワークフロー、計測コードのスニペット、ログ検索の早見表が記載されています。
references/dotnet-debugging.md— .NET/ASP.NET Core/EF Core(dotnet-counters、dotnet-stack、dotnet-dump、dotnet-trace、EF のLogTo/TagWith、journalctl/jq クエリ)references/angular-debugging.md— Angular(Angular DevTools プロファイラー、ng.*コンソール API、RxJS のtap、変更検出のプロファイリング)references/python-debugging.md— Python(breakpoint()/pdb、pytest の--pdb、py-spy、faulthandler、tracemalloc、asyncio のデバッグ)references/react-debugging.md— React(React DevTools プロファイラー、why-did-you-render、再レンダリング/エフェクトのバグパターン)
フェーズ 0 — バグを明確にする
何かを作り始める前に、「壊れている」とはどういう意味かを明確にします。症状が曖昧だとループも曖昧になり、そのループによって後続のすべてのフェーズが無駄になります。
ユーザー、バグ報告、または証拠から、次の情報を記録します。
- 症状、原文のまま — 正確なエラーメッセージ、誤った値、またはタイミングです。引用し、言い換えないでください。
- 期待値と実際の結果 — どうなるべきか、実際にはどうなるかです。
- 環境 — ローカル/CI/ステージング/本番、OS、ランタイム、バージョン、設定プロファイルです。
- いつからか — 最初に確認された時点、それと関連するデプロイ、コミット、データ変更、または「常に」です。
- 発生頻度 — 毎回、断続的(およそどのくらいの頻度か)、または一度だけです。
- 影響範囲 — 1 人のユーザー/入力/環境か、すべてかです。
- 最近の変更 — コード、依存関係、設定、データ、インフラです。
報告内容が不十分な場合は、コードに触れる前に報告者に質問します(ポルトガル語で)。
Antes de investigar, preciso enquadrar o bug:
1. O que deveria acontecer vs o que aconteceu? (mensagem de erro exata, se houver)
2. Onde acontece — local, CI, staging, produção?
3. Desde quando? Relacionado a algum deploy ou mudança recente?
4. Com que frequência — sempre, às vezes (quantas?), ou uma vez só?
5. Atinge um caso específico ou tudo?
フェーズ 0 の成果物:バグを一文で説明します — 「<env> で、<input/action> により、<when> から(<frequency>)、<expected> ではなく <actual> が発生する。」 この一文を書けない場合は、聞き取りを続けてください。フェーズ 1 を始めてはいけません。
フェーズ 1 — フィードバックループを構築する
これがスキルです。 それ以外はすべて機械的な作業です。このバグで失敗する、厳密な合否シグナルがあれば、原因を見つけられます。二分探索、仮説検証、計測は、いずれもそのシグナルを利用するだけです。シグナルがなければ、どれだけコードを見つめても解決できません。
ここには、通常よりかなり多くの労力をかけてください。積極的に。創意工夫を凝らして。諦めずに。
ループを構築する方法 — おおよそ次の順序で試す
- バグに到達できる境界での失敗するテスト — ユニット、統合、E2E。
- 実行中の開発サーバーに対する curl/HTTP スクリプト。
- フィクスチャ入力を使った CLI 呼び出し。標準出力を既知の正常なスナップショットと比較します。
- ヘッドレスブラウザースクリプト(Playwright/Puppeteer) — UI を操作し、DOM/コンソール/ネットワークを検証します。
- 記録したトレースを再生します。 実際のネットワークリクエスト/ペイロード/イベントログをディスクに保存し、コードパスを分離して再生します。
- 使い捨てのハーネス。 システムの最小限の部分(1 つのサービス、モックした依存関係)を起動し、1 回の呼び出しでバグのコードパスを実行します。
- プロパティ/ファズループ。 バグが「出力がときどき間違う」ことなら、ランダムな入力を 1000 件実行し、失敗パターンを探します。
- 二分探索用ハーネス。 既知の 2 つの状態(コミット、データセット、バージョン)の間でバグが発生した場合は、「状態 X で起動して確認する」を自動化し、
git bisect runできるようにします。「どのテストがこの不要なファイル/状態を作成したのか」を調べるには、scripts/find-polluter.shがテストファイルを 1 つずつ実行し、不要なファイルが現れるまで確認します。 - 差分ループ。 同じ入力を旧バージョンと新バージョン(または 2 つの設定)で実行し、出力を比較します。
- HITL bash スクリプト。 最終手段です。人間がクリックする必要がある場合は、
scripts/hitl-loop.template.shでその人を操作し、ループを構造化されたままにします。記録された出力はフィードバックとして戻されます。
適切なフィードバックループを構築すれば、バグは 90% 解決したも同然です。
ループを改善する
ループをプロダクトとして扱います。ループを 1 つ作ったら、それを改善します。
- もっと速くできるか? セットアップをキャッシュし、無関係な初期化を省き、テスト範囲を絞ります。
- シグナルをもっと明確にできるか? 「クラッシュしなかった」ではなく、具体的な症状を検証します。
- もっと決定的にできるか? 時刻を固定し、乱数生成器のシードを設定し、ファイルシステムを分離し、ネットワークを固定します。
30 秒かかる不安定なループは、ループがないのとほとんど変わりません。2 秒で終わる決定的なループは、デバッグを飛躍的に強化します。
非決定的なバグ
目標は、完璧に再現することではなく、再現率を上げることです。トリガーを 100 回ループさせ、並列化し、ストレスを加え、タイミングの範囲を絞り、スリープを挿入します。50% の確率で発生するバグはデバッグできますが、1% ではできません。デバッグ可能になるまで、再現率を上げ続けてください。
sleep/setTimeout でタイミングを推測するテスト内で不安定さが発生している場合、不安定な待機そのものがバグの可能性があります。推測した遅延を、条件をポーリングする方法に置き換えてください(references/condition-based-waiting.md)。
本当にループを構築できない場合
構築できないことを、ポルトガル語で明確に伝えてください。試したことを列挙してください。次のいずれかを求めてください。(a)問題を再現できる環境へのアクセス、(b)マスキングした取得済みの成果物(HAR ファイル、ログのダンプ、コアダンプ、タイムスタンプ付きの画面録画)、または(c)一時的な本番環境の計測を追加する許可。ループなしで仮説を立てて先に進んではいけません。
Preciso de um exemplo mínimo que reproduza o erro. Você consegue me fornecer:
1. O comando ou ação que dispara o problema.
2. A saída ou mensagem de erro exata.
3. O ambiente (local, CI, staging, produção).
4. Se possível, um artefato capturado (HAR, dump de log, gravação de tela) com segredos redigidos.
➡️ Se não tiver, vou tentar construir um caso de reprodução sozinho.
完了条件:失敗するタイトなループ
フェーズ 1 は、1 つのコマンド(スクリプトのパス、テストの実行コマンド、curl)を挙げられ、そのコマンドをすでに少なくとも 1 回実行している場合に完了です。実行コマンドと、その出力(マスキング済み)を示してください。また、そのコマンドは次の条件を満たす必要があります。
- 失敗を検出できる — 実際のバグのコードパスを実行し、ユーザーが示した正確な症状をアサートするため、このバグがある状態では失敗し、修正後は成功します。「エラーなしで実行できる」だけでは不十分です。この特定のバグを検出できる必要があります。
- 決定論的 — 毎回同じ判定になります(不安定なバグの場合は、高い再現率を固定します)。
- 高速 — 数秒で完了し、数分はかかりません。
- エージェントが実行できる — 人手を介さずに実行できます。人手が必要なのは
scripts/hitl-loop.template.shを通す場合に限ります。
このコマンドが存在する前に、理論を立てるためにコードを読み始めていると気づいたら、そこで止めてください。すぐに仮説へ飛びつくことこそ、このスキルが防ぐべき失敗です。 失敗を検出できるコマンドがなければ、フェーズ 2 には進めません。
フェーズ 2 — 再現と最小化
ループを実行します。バグが現れて失敗することを確認します。次の点を確認してください。
- ループが再現するのは、ユーザーが説明した障害モードであり、たまたま近くで発生する別の障害ではありません。間違ったバグを修正しても、正しい修正にはなりません。
- 複数回の実行で障害を再現できます(非決定的なバグの場合は、デバッグに十分な高い再現率が得られます)。
- 正確な症状(エラーメッセージ、誤った出力、処理時間の遅延)を記録しています。後のフェーズで、修正が実際に問題に対処しているか確認できるようにします。
最小化
再現ケースを、失敗が続く最小のシナリオまで縮小します。一度に 1 つずつ取り除き、削るたびにループを再実行して、失敗に不可欠なものだけを残します。
- バグが消えるまでコードを削除します。
- データを削除します。
- 設定を削除します。
- 依存関係を削除します。
- 環境を削除します。
最小化する理由:再現ケースを小さくすると、フェーズ 3 で検討すべき仮説の範囲が狭まり(疑うべき要素が減り)、フェーズ 5 では明確な回帰テストになります。
残った要素がすべて不可欠になった時点で完了です。いずれか 1 つを取り除くとループが成功する状態です。再現し、かつ最小化するまで先に進まないでください。
フェーズ 3 — 仮説を立てる
テストを始める前に、優先順位を付けた仮説を 3~5 個立ててください。仮説を 1 つだけ立てると、最初に思いついたもっともらしい考えに引きずられます。
各仮説は反証可能でなければなりません。予測される結果を明示してください。
「<X> が原因なら、<Y> を変更するとバグが消える/<Z> を変更すると悪化する」
予測を明示できない場合、その仮説は単なる勘です。捨てるか、具体化してください。
仮説を立てるための情報源 — 手間のかからない確認から始めます。
- 最近の差分 — 変更された箇所を対象に
git log -p --since="<first sighting>"を実行し、依存関係や設定の変更も確認します。バグは直近の変更と強く相関します。「以前は動いていた」という状況なら、二分探索の出番です。 - 動作する経路と壊れている経路 — 動作する類似のフローを見つけ、2 つの経路を比較します(入力、設定、呼び出しチェーン、データの形)。
- 環境の差分 — 動作する環境と動作しない環境の間で、環境変数、設定ファイル、機能フラグ、依存関係のバージョンを比較します。
- 境界の確認 — 不正な値は入口の境界ですでに誤っているのか、それともパイプラインの途中で現れるのかを確認します。各境界で問題がないと確認できるたびに、疑わしい範囲は半分になります。
- 逆方向のトレース — エラーがコールスタックの深い場所で発生する場合、例外が発生した箇所は原因ではなく症状です。仮説を立てる前に、不正な値をたどって元のきっかけを突き止めてください(
references/root-cause-tracing.md)。
バグが潜んでいる可能性のある場所。おおよそ以下の順で確認します。
- コード — バグは、見ているコード、そのコードが呼び出すコード、またはそのコードを呼び出すコードのどこにありますか?
- ドキュメント — ドキュメントに記載されている動作は本当に正しいですか?
- ログ — ログは事実を伝えていますか、それとも実際のエラーを覆い隠していますか?
- テスト — テストは実際の経路をカバーしていますか?
- コードベース — 同じパターンを使っている呼び出し箇所がほかにもありますか?
テストを始める前に、優先順位を付けたリストをユーザーに見せてください。ドメイン知識があれば、順位はすぐに変わります(「#3 に変更をデプロイしたばかりです」「#2 はすでに除外済みです」)。わずかな確認で大幅に時間を節約できます。ユーザーの返答を待って作業を止める必要はありません。ユーザーが離席中なら、自分の順位付けに従って進めてください。
Hipóteses ranqueadas:
1. [HIPOTESE_1] — previsão: [PREDICAO_1]
2. [HIPOTESE_2] — previsão: [PREDICAO_2]
3. [HIPOTESE_3] — previsão: [PREDICAO_3]
Vou validar a nº [N] com [ACAO_EXPERIMENTAL]. Se confirmar, o próximo passo é [PROXIMO_PASSO].
Concorda, ou quer que eu teste outra hipótese primeiro?
診断ジャーナル
複雑な問題では、ジャーナルを継続して記録してください。却下した仮説を再検証せずに済み、コンテキストのずれや圧縮があっても記録が残ります。
## Diagnostic Journal — <one-sentence bug statement>
- Loop: `<the Phase 1 command>` → currently red
- Min repro: <smallest red scenario>
| Hypothesis | Prediction | Test run | Result |
|---|---|---|---|
| H1: ... | ... | ... | rejected / confirmed |
- Root cause: <filled at the end>
フェーズ 4 — 計測する
各プローブは、フェーズ 3 で立てた特定の予測に対応させてください。一度に変更する変数は 1 つだけです。
ツールの優先順位:
- デバッガー/REPL での調査。環境が対応している場合はこれを使います。ブレークポイント 1 つはログ 10 個に勝ります。
- 対象を絞ったログ。仮説を区別できる境界に配置します。
- メトリクス/トレース。疑わしい動作を測定し、リクエストの経路を追います。
- アサーション。不変条件に違反した場合、すぐに失敗させます。
- 「すべてをログに記録して grep する」方法は使わないでください。
すべてのデバッグログに、たとえば [DEBUG-a4f2] のような一意のプレフィックスを付けてください。最後のクリーンアップで、grep を 1 回実行するだけで済みます。タグのないログは残り、タグ付きログは削除されます。
プローブの配置。 仮説の候補を絞り込める境界にプローブを配置します。関数の入口と出口、各変換の前後、外部呼び出し(ネットワーク、DB、ファイルシステム)のすべて、各状態遷移が対象です。H1 と H2 を区別できるプローブ 1 つは、区別できないプローブ 10 個に勝ります。
複数コンポーネントの調査。 バグがパイプラインのどこにでも潜んでいる可能性がある場合(CI → ビルド → デプロイ、API → サービス → DB、フロントエンド → ゲートウェイ → バックエンド)は、詳細に掘り下げる前に、証拠を得るための実行を 1 回だけ行います。すべてのコンポーネント境界で、入るものと出るもの(データの形、環境/設定の伝播、状態)を一度に記録します。その実行で通常は問題のあるレイヤーが判明するので、パイプライン全体にプローブを仕込まず、そのレイヤーに集中してください。
相関付け。 リクエスト/トレース ID はできるだけ早く付与し、各プローブで記録してください。そうしないと、同時進行するフローが入り交じり、証拠が曖昧になります。
パフォーマンスの分岐。 パフォーマンスの低下では、ログは通常、適切な手段ではありません。まず基準値を測定し(計測用ハーネス、プロファイラー、クエリプランなど)、その後で二分探索します。先に測定し、修正はその後です。
フェーズ 5 — 修正+回帰テスト
修正に着手する前に回帰テストを作成します。ただし、適切なシームがある場合に限ります。つまり、呼び出し箇所で発生する実際のバグのパターンをテストで再現できるシームです。利用できるシームが浅すぎる場合(バグの引き金となった一連の流れを再現できない単体テストなど)、そこで回帰テストを作成しても誤った安心感を与えます。
適切なシームがない場合、それ自体が発見事項です。 アーキテクチャがバグの再発を防ぐテストを妨げています。フェーズ 6 と improve-codebase-architecture に向けて、その点を指摘してください。
適切なシームがある場合:
- 最小化した再現ケースを、そのシームで失敗するテストにします。
- テストが失敗することを確認します。
- 根本原因を取り除く、最小限で安全な変更を適用します。応急処置はしません。
- テストが通ることを確認します。
- 元の(最小化していない)シナリオに対して、フェーズ 1 のフィードバックループを再実行します。
- 根本原因が、システムの深部まで到達した不正なデータまたは不変条件の違反だった場合は、データが通過した各レイヤーを強化します。単一のチェックでこのバグは修正できますが、各レイヤーで検証することで、同種のバグが起き得ないようにできます(
references/defense-in-depth.md)。
修正が多くのファイルに及ぶ場合は、編集する前にポルトガル語で計画をユーザーに提示します。
Raiz do problema: [RAIZ].
Correção proposta: [DESCRICAO_DA_CORRECAO].
Arquivos afetados: [LISTA].
Posso aplicar a correção e depois rodar os testes?
フェーズ 6 — クリーンアップ+再検証
完了を宣言する前に、以下を必ず実施します。
- 元の再現ケースで問題が再現しなくなったことを確認する(フェーズ 1 のループを再実行)。
- 回帰テストが通ることを確認する(または、適切なシームがないことを文書化する)。
- 該当するテストレイヤー(単体、統合、E2E)を実行し、隣接するフローでも軽量な回帰テストを実施する。
-
[DEBUG-...]の計測コードをすべて削除する(プレフィックスをgrepで検索)。 - 使い捨てのプロトタイプを削除する(または、デバッグ用であることが明確な場所に移動する)。
- 正しいと判明した仮説をコミットメッセージまたは PR メッセージに記載し、次にデバッグする人が学べるようにする。
結果はポルトガル語で報告します。
Correção aplicada em [ARQUIVOS].
- Reprodução original: [não reproduz mais / ainda falha]
- Teste de regressão: [PASS/FAIL]
- Testes afetados: [PASS/FAIL]
- Instrumentação removida: [SIM/NÃO]
O bug está resolvido. Quer que eu abra uma Issue para documentar a causa raiz com /create-issues?
行き詰まったとき — 仮説が尽きた場合
三振ルール。 数えるのは仮説ではなく、適用した修正です。3 回修正してもバグが残る、または形を変えて現れる場合――修正のたびに別の箇所で新たな問題が発覚する、あるいは修正を適用するのに回避策が必要になる場合――は、パターンそのものが疑わしいと考えてください。修正 #4 を試す前に立ち止まり、ユーザーと(ポルトガル語で)アーキテクチャを検討してください。この設計は根本的に妥当なのか、それとも誤った構造の症状を修正しているのか。その話し合いは improve-codebase-architecture の領域であり、さらなるパッチで対処するものではありません。
すべての仮説が否定された場合、失敗の原因は前提より上流にあります。
- ループを疑う — このバグで本当に失敗状態になり得ますか。フェーズ 1 の完了チェックリストを再確認してください。失敗状態にならないループでは、その後のフェーズはすべて形だけになります。
- 前提を疑う — フェーズ 0 を再実行します。報告された症状は、実際の問題より下流にある可能性があります(たとえば、ユーザーにはタイムアウトと見えていても、根本原因はその 10 秒前に発生したデッドロックかもしれません)。
- 調査範囲を広げる — 原因はコードの外にある可能性があります。データ、設定、インフラストラクチャ、依存関係の挙動の変化などです。ソースコードの差分だけでなく、環境全体を比較します。
- 証拠をユーザーに提示する — 診断記録をポルトガル語で報告します。試したこと、各テストで証明または否定できたこと、次に必要なもの(アクセス権、成果物、または判断)を伝えます。
- 「根本原因なし」は最終手段であり、結論ではありません — 「環境の問題/説明不能」という判定の多くは、調査が不十分な状態です。証拠が本当にシステムの外部(タイミング、外部サービス、ハードウェア)を示している場合は、何を除外できたかを記録し、境界での処理(再試行、タイムアウト、明示的なエラー)を追加し、
observability-and-instrumentationを通じて継続的な監視を追加します。そうすれば、次に発生したときに証拠も一緒に得られます。
エージェントの自己デバッグ/内省(障害の原因がエージェント自体にある場合に使用)
バグがコードベースではなくエージェントのセッションにある場合――ツール呼び出しの失敗の繰り返し、ループ、コンテキストのずれ、または想定したファイルシステムの状態と実際の状態との不一致など――は、エージェント内省ループを適用します。
Phase A — 失敗の記録
復旧を試みる前に、以下を記録します。
- エラーの種類、メッセージ、可能な場合はスタックトレース
- 直近の意味のあるツール呼び出しの順序
- エージェントが何をしようとしていたか
- 現在のコンテキスト負荷:繰り返されるプロンプト、巨大な貼り付けログ、重複した計画、または膨れ続けるメモ
- 現在の環境に関する前提:cwd、ブランチ、関連サービスの状態、想定されるファイル
## Failure Capture
- Session / task:
- Goal in progress:
- Error:
- Last successful step:
- Last failed tool / command:
- Repeated pattern seen:
- Environment assumptions to verify:
Phase B — 根本原因の診断
失敗を既知のパターンに当てはめます。
| パターン | 考えられる原因 | 確認方法 |
|---|---|---|
| ツール呼び出しの上限到達/同じコマンドの繰り返し | ループ、または終了しない監視経路 | 直近の N 件のツール呼び出しを調べ、繰り返しがないか確認する |
| コンテキストのオーバーフロー/推論の劣化 | 上限のないメモ、繰り返される計画、巨大なログ | 直近のコンテキストに重複や情報量の少ない大量の内容がないか調べる |
ECONNREFUSED/タイムアウト | サービスが利用できない、またはポートが誤っている | サービスの健全性、URL、ポートに関する前提を確認する |
429/クォータの枯渇 | リトライの集中、またはバックオフの欠如 | 呼び出しの繰り返し回数を数え、リトライ間隔を調べる |
| 書き込み後にファイルが見つからない/差分が古い | 競合状態、誤った cwd、またはブランチのずれ | パス、cwd、git status、実際のファイルの存在を再確認する |
| 「修正」後もテストが失敗する | 仮説が誤っている | 失敗しているテストを特定し、バグを改めて導き出す |
診断のための質問:
- これはロジックの失敗、状態の失敗、環境の失敗、ポリシーの失敗のどれですか?
- エージェントは本来の目標を見失い、誤ったサブタスクの最適化を始めていませんか?
- この失敗は決定的ですか、それとも一時的ですか?
- 診断を検証できる、最小限で元に戻せる操作は何ですか?
Phase C — 範囲を限定した復旧
以下の順に介入することを推奨します。
- 本来の目標を一文で言い直します。
- 記憶を信用せず、実際の状態を確認します。
- 失敗している範囲を小さくします。
- 原因を切り分けられる確認を1つ実行します。
- その後でのみ再試行します。
悪いパターン:少し表現を変えながら、同じ操作を3回再試行すること。 良いパターン:失敗を記録 → パターンを分類 → 直接確認を1つ実行 → 確認結果が裏付ける場合にのみ計画を変更する。
Phase D — 自己デバッグレポート
最後に、以下を記載します。
## Agent Self-Debug Report
- Session / task:
- Failure:
- Root cause:
- Recovery action:
- Result: success | partial | blocked
- Token / time burn risk:
- Follow-up needed:
- Preventive change to encode later:
AI ワークフロー診断
問題が発生しているシステムがコードパスではなく、エージェントまたは AI ワークフローの場合、5 つの観点から監査します。それぞれを1~5で評価し、具体的な所見をポルトガル語で報告します。
観点 1 — プロンプトの品質
構成(役割、コンテキスト、指示、出力領域);明確な出力スキーマ;指示の明瞭さ;エッジケースへの対応;アンチパターン(長文の羅列、矛盾、暗黙の形式)。
観点 2 — コンテキスト効率
コンテキスト予算の配分(計画的か、その場しのぎか);注意の勾配(重要な情報が冒頭/末尾にあるか);コンテキストウィンドウの利用状況;状態管理(明示的か、暗黙的か);会話の長さに適したメモリ戦略。
観点 3 — ツールの健全性
ツール数(3~7個が理想、13個以上は問題);説明の品質;エラー処理;スキーマの網羅性(入力/出力/エラー);冪等性。スコープの帰属:プロジェクトで設定されたツールと、エージェントレベル/組み込みツールを区別します。プロジェクトが実際に制御できる負荷のみを指摘します。
観点 4 — アーキテクチャの適合性
トポロジーの適切さ(単一エージェントかマルチエージェントか、その選択に根拠があるか);エージェントの境界(明確か、重複しているか);ハンドオフプロトコル(構造化されているか、その場しのぎか);可観測性;コストへの配慮。
観点 5 — 安全性と信頼性
入力の検証;出力のフィルタリング(PII、コンテンツポリシー — 状況に応じて範囲を判断します。ユーザー自身のフロントエンドからバックエンドへの通信は、外部サービスよりリスクが低くなります);コスト制御;エラーからの復旧;評価戦略(ゴールデンテストか、「動作しているように見える」か)。
レポート形式
╔══════════════════════════════════════╗
║ WORKFLOW DIAGNOSTIC ║
╠══════════════════════════════════════╣
║ Prompt Quality ████░ 4/5 ║
║ Context Efficiency ███░░ 3/5 ║
║ Tool Health ██░░░ 2/5 ║
║ Architecture ████░ 4/5 ║
║ Safety & Reliability ██░░░ 2/5 ║
╠══════════════════════════════════════╣
║ Overall Score: 15/25 ║
╚══════════════════════════════════════╝
ACHADOS CRÍTICOS:
1. [Problema mais severo — ação imediata]
2. [Segundo mais severo]
3. [Terceiro]
AÇÕES RECOMENDADAS:
1. [Correção específica para o achado nº 1]
2. [Correção específica para o achado nº 2]
3. [Correção específica para o achado nº 3]
スコアガイド
| スコア | 意味 | 推奨アクション |
|---|---|---|
| 5 | 本番環境でも非常に優れている | 対応不要 |
| 4 | 良好だが、軽微な不足がある | プロンプトの明確さや出力スキーマを改善する |
| 3 | 機能するが、リスクがある | エラー処理を追加するか、複雑さを減らす |
| 2 | 重大な問題がある | 直ちに対応する — リトライやガードを追加する |
| 1 | 破損している、または存在しない | 明確な構造で一から作り直す |
サイレント障害の調査
コードが「動作」しているのに静かに誤動作する場合は、バグが解決したと判断する前に、サイレント障害を調査してください。
調査対象
- 空の Catch ブロック —
catch {}、無視された例外、コンテキストを示さずにエラーをnull/空の配列に変換する処理。 - 不十分なロギング — コンテキストが不足したログ、重大度の誤り、ログを記録して放置する処理。
- 危険なフォールバック — 実際の失敗を隠す既定値、
.catch(() => [])、一見正常に見えるものの、後続のバグの診断を難しくする処理経路。 - エラー伝播の問題 — スタックトレースの喪失、汎用的な再スロー、非同期処理の扱いの不備。
- エラー処理の欠如 — ネットワーク/ファイル/データベース処理にタイムアウトやエラー処理がない、トランザクション処理にロールバックがない。
出力形式
各調査結果について、以下を示してください。
- 場所
- 重大度
- 問題
- 影響
- 修正の推奨事項
再検証ループ
診断は反復的に行います。変更するたびに、再現手順を再実行してください。バグの発生箇所や状態が変わった場合は、フェーズ 3 に戻ってください。再現テストに合格し、回帰テストスイートがすべて成功するまで、バグが修正されたと判断しないでください。
危険信号 — 停止してパイプラインに戻る
次のような考えが浮かんだら、プロセスから外れています。飛ばしたフェーズに戻ってください。
- 「とりあえず応急処置して、調査は後で。」
- 「X を変えて、うまくいくか試してみよう。」
- 「おそらく X だろう。修正してみよう。」(仮説を確認せずに修正するのは、推測にすぎません)
- 「変更をいくつかまとめて、テストを実行しよう。」(何が効いたのかわからなくなります)
- 「再現テストは省略して、手動で確認しよう。」
- 「よくわからないけれど、これでうまくいくかもしれない。」
- 「単純なバグに見える。プロセス全体は必要ない。」(単純なバグにも根本原因はあります。単純なバグなら、このループは迅速です)
- 「緊急事態だから、プロセスを踏む時間はない。」(特に切迫しているときは、場当たり的な対応より体系的な対応が有効です)
- 2 回以上失敗した後に「もう一度だけ修正を試そう」 — 修正に 3 回失敗した場合、仮説ではなくアーキテクチャが間違っています(「行き詰まった場合」を参照)。
ユーザーからの指摘も、外部からの同じ危険信号です。「本当にそうなっていますか?」「確認しましたか?」「推測はやめてください」「同じところをぐるぐる回っています」。こうした指摘を受けたら、手を止めて、飛ばしたフェーズに戻ってください。
よくある間違い
| 間違い | 修正方法 |
|---|---|
| 曖昧な症状を調査する | まずフェーズ 0 を実施します。バグを一文で説明できない場合は、ヒアリングを続けます。 |
| 再現する前に修正する | コードを変更する前に、失敗を再現できるループを構築します。 |
| 緊密なループができる前に仮説を立てる | まずフェーズ 1 の完了条件を満たします。失敗を示すコマンドがなければ、仮説も立てません。 |
| 最初に思いついたもっともらしい仮説だけを検証する | 反証可能な仮説を 3~5 個挙げ、優先順位を付けます。 |
| 最小化を省略する | まず最小化します。そうしないと、原因ではなく症状を修正することになります。 |
| 症状の代わりに「クラッシュしなかった」と断言する | シグナルを明確にします。ユーザーから報告された正確な失敗をアサートします。 |
| 回帰テストの境界が浅すぎる | 適切な境界を使うか、該当する境界がないことを記録します。 |
| 計測ログを早々に削除する | 修正を検証するまで [DEBUG-...] ログを残し、その後 grep でクリーンアップします。 |
| 回帰テストを追加しない | 修正したバグには、すべてテストを追加します。 |
| 却下した仮説を再検証する | 診断ジャーナルを残し、すべての結果を記録します。 |
| 最近の変更は無関係だと思い込む | まず差分を確認します。新しいコードが最有力の容疑対象です。 |
| 並行するフローから曖昧な証拠が得られる | 相関 ID を付与し、すべての調査ポイントでログに記録します。 |
| 間違った環境をデバッグする | 結果を信頼する前に、環境がフェーズ 0 の報告と一致していることを確認します。 |
| 再検証せずに完了を宣言する | 再現手順とテストスイートを再実行します。 |
| エラーがスローされる箇所を修正する | 不正な値の発生源までさかのぼって追跡します(references/root-cause-tracing.md)。 |
| 直接の原因だけを修正する | 不正なデータが通過するすべての層に検証を追加します(references/defense-in-depth.md)。 |
sleep を延ばして不安定なテストを修正する | 推測した時間ではなく、実際の条件を待ちます(references/condition-based-waiting.md)。 |
| パイプライン全体を一度に計測する | まずすべてのコンポーネント境界を一巡し、その後、失敗している層を詳しく調べます。 |
参考資料
scripts/hitl-loop.template.sh— 人間が介在する再現ドライバーscripts/find-polluter.sh— テストファイルを二分探索し、余計なファイルや状態を作成するファイルを特定しますreferences/root-cause-tracing.md— コールスタックをさかのぼり、不正な値の発生源を追跡しますreferences/defense-in-depth.md— すべての層で検証し、バグの種類が発生し得ないようにしますreferences/condition-based-waiting.md— 不安定なテストで推測に基づく sleep を条件ポーリングに置き換えますreferences/dotnet-debugging.md— .NET の診断ツールとログクエリreferences/angular-debugging.md— Angular DevTools、変更検知、RxJS のデバッグreferences/python-debugging.md— pdb/pytest/py-spy によるデバッグとログクエリreferences/react-debugging.md— React DevTools と再レンダリングのデバッグqa-analyst— テスト計画とバグ報告向けwrite-specs— バグによって要件の不足が明らかになった場合の仕様書作成向けimprove-codebase-architecture— 診断によって境界の不足や構造上の問題が明らかになった場合向けobservability-and-instrumentation— 一時的な調査用計測ではなく、継続的なログ/メトリクス/トレースが修正に必要な場合向けcreate-issues— 記録した根本原因を追跡するためagent-introspection-debugging— 失敗がエージェントのセッション自体にある場合(ループ、コンテキストのずれ、ツール呼び出しの繰り返し)向けsilent-failure-hunter— コードは動作しているものの、ひそかに誤動作している場合向け