Azure のネットワーク障害を調査する AI エージェントのチームを、GitHub Copilot のカスタムエージェントとスキルだけで作りました。DNS・ネットワーク・監視・VM を担当する4つの専門エージェントが並列で調べ、その根拠を親エージェントが突き合わせて原因を特定します。人間のインシデント対応を模した、インシデント調査チームです。
つくるきっかけは、@shyamagu さんの「AIエージェントだけでスクラムを回してみた」 です。「ロール(人格)はカスタムエージェント、作業手順はスキルに分ける」という設計と、エージェントに名字をつけてチームらしく動かす発想に強く影響を受けました。あとで出てくる「エージェント=人、スキル=武器」も、ここが下敷きです。
検証では、システム構成を知らせず・読み取り権限だけという制約で、2件の障害を調査させました。約20分・約700 AI Credit で「誰がどのサーバーを止めたのか」まで到達したケースもあれば、権限の壁で途中までしか進めなかったケースもあります。
「インシデント調査チーム」とは何か
1人の進行役(親エージェント)と4人の専門家(子エージェント)が、1つの障害を分担して調べるチームです。親は指示を出し、結果を集め、矛盾がないかを突き合わせて最終レポートを書きます。子は得意領域だけを深掘りします。
エージェント=人、スキル=武器
いちばん割り切ったのは、「人格」と「調査手順」を分けたことです。エージェント(*.agent.md) には人格・担当領域・出力の約束事だけを書き(=人)、スキル(SKILL.md) に具体的な調査手順・コマンド例・KQL を書きます(=武器)。分ける理由は、1つの武器を複数の人が使い回せるからです。「URL からバックエンドを逆引きする」手順は親も DNS 担当も使うので、1本にまとめておけば研ぐのは1回で済みます。武器は8本+入口の entaku で、Microsoft Learn で裏取りする microsoft-learn-grounding も入れて憶測を防ぎます。証拠の JSON スキーマや会話ルールだけは、条件付きで読まれるスキルではなく instructions(.github/instructions/) に置き、全員へ常時適用します。
検証に使ったシステムとハンデ
題材は Application Gateway(AppGW)の裏に Web 層(vm-web-1 / vm-web-2)と App 層(vm-app-1 / vm-app-2)が2台ずつ並ぶ、よくある2層構成です。
ここであえて2つのハンデを課しました。これが肝です。
- 調査チームは構成図を知りません。 「この URL が変」という報告とサブスクリプション ID だけが渡されます。
- 権限は読み取り専用(Reader 相当)だけ。 設定変更も VM 内のコマンド実行もできません。
現場でいきなり呼ばれたときに近い状況です。その制約下でどこまで迫れるかを見たかったのです。
障害① vm-app-2 しか応答しない
AppGW のパブリック IP を叩くと、返るのはいつも同じ1台でした。
$ curl http://<AppGW のパブリック IP>/
HTTP/1.1 200 OK
{"host":"vm-app-2","status":"ok","tier":"app"}
# 10回試して、10回とも vm-app-2
200 OK は返る。でも、もう1台(vm-app-1)の気配がありません。依頼は症状とサブスクリプション ID だけで、構成の説明は一切していません。
4人が並列で調べ、こう報告してきました。
| 担当 | 調べた結果 |
|---|---|
| 高橋さん(DNS) | IP 直指定。名前解決は原因ではないと早々に切り分け |
| 佐藤さん(Network) | 経路は AppGW 経由で正常 |
| 鈴木さん(Monitor) | 操作ログに「app-1 を停止した」記録と実行者が残っていた |
| 山本さん(VM) |
app-1 は停止中、app-2 は稼働中 |
結論:作業者が vm-app-1 を停止していました。 Activity Log から実行したアカウントまで特定でき、次の一手(起動して正常化を確認)も明快です。構成図なし・読み取り権限だけで、症状から犯人までたどり着いたのがポイント。ここまでは「まあできるだろう」と思っていました。想定外は次の②でした。
障害② 502 Bad Gateway — 仕込んでいない"本物"の障害
①の検証中に、仕込んだ覚えのない障害が出ました。今度は 200 すら返りません。
$ curl -v http://<AppGW のパブリック IP>/
< HTTP/1.1 502 Bad Gateway
< Server: Microsoft-Azure-Application-Gateway/v2
台本のない一発本番です。そのまま調査チームに投げました。
| 担当 | 調べた結果 |
|---|---|
| 佐藤さん(Network) | 経路はゲートウェイまで到達。入口側は生きている |
| 鈴木さん(Monitor) | 振り分け先の2台とも「不健全」。5xx が同時間帯に増加 |
| 山本さん(VM) | VM 自体は起動中。ただし中身の確認は権限不足でできない |
結論:VM は起動しているが、アプリケーション(nginx)が落ちている。 502 は AppGW が nginx に届かず「上流が壊れている」と返していた筋書きです。
面白いのはこの先です。調査チームはこう続けました。
nginx が落ちた原因までは、VM 内の操作権限がないため調査できず、不明。
「たぶん設定ミスでしょう」とそれっぽく締めることもできたはずですが、権限の壁を壁として報告しました。そのうえで次の一手を3つ(権限を持つ人が VM を見る/AI に VM 操作権限を与える/アプリログを Log Analytics に流して AI に見せる)並べてきました。
これは弱点であると同時に設計思想でもあります。AIは与えられた権限の範囲でしか動きません。 勝手に本番へ踏み込まれても困るわけで、「どこまで分かって、どこから先は権限が要るか」を明示してくれる方が、現場では信頼できます。
①が「AIはここまでやれる」なら、②は「AIの境界はここだ」を実演してくれました。仕込んだ①より、事故の②の方が雄弁でした。
なぜ憶測せず、根拠を出せるのか
「AIに調査させました」で終わると、それっぽい作文を疑う羽目になります。調査チームには裏側の仕掛けを入れています。
① 7フェーズで段取りを踏む。 いきなり結論に飛ばず、人間のインシデント対応と同じ順番で進みます。
②では⑤で「入口は生きているのにバックエンド2台が不健全」という食い違いを拾い、「VM は生きているがアプリが死んでいる」に収束しました。
② 報告は"作文"ではなく構造化データ。 各エージェントは決まった形の JSON(状態・根拠・実行コマンド・確信度)で親に報告します。confidence が low の主張には親が追加確認を投げ、実行コマンドと結果がそのまま残るので、後から人間が検算できます。
③ セキュリティは"最初から狭く"。 エージェントは Reader 相当のみで、設定変更も書き込みもできません。推奨対応は Microsoft Learn MCP で裏取り。全実行ログ(最終レポート・生ログ・JSONL・監査レポート)が entaku-runs/<実行ID>/ に1セットで残り、「誰が何を根拠にこう結論したか」を丸ごと追えます。
どこまで広げられるか
今回は Azure・読み取り権限・4人チームという最小構成でしたが、伸ばせる方向は3つ見えています。
- オンプレ / AWS へ — エージェントの本質は「コマンドを実行して結果を読む」こと。コマンド+権限+到達性さえ揃えば、調査先は Azure に限りません。
- AI チームを増やす — Java・DB 担当…と専門家を足し、(望むなら)修復まで踏み込む権限を与えます。②で見えた「権限の壁」を狙って超えにいく形です。
- Azure SRE Agent へ移植する — ここは地続きです。Azure SRE Agent のインシデント応答の流れは7フェーズとほぼ同じ発想で、Review モードと Autonomous モードを選べます。②で示した「ここから先は権限が要る」の一線を、運用ポリシーに落とし込めます。
まとめ — "並列の専門家"は思ったより実戦的だった
一番の収穫は、構成図なし・読み取り権限だけでも、根拠付きで原因を名指しできたことです。また、権限不足を正直に報告した点にも実戦的な価値を感じました。全部を知ったふりをするAIより、どこまで見えて・どこから権限が要るかを言うAIの方が隣に置いておきたい。今後は専門家を増やしたときの矛盾チェックと、親エージェントのスケールを試したいところです。
- リポジトリ: shitada/entaku-kaigi-AI-team


