Copilot StudioのMCPクライアントからのリクエストがWAFでブロックされていた件
ヒトもAIも使えるマニュアル「Runbook」を開発運用しています、クローバの門屋です。先日、RunbookのMCPサーバーがMicrosoftのCopilot Studioから接続できないという報告を受けて調べたらめちゃめちゃハマったので、共有します。
調べたら、OAuthの認可サーバーからメタデータを取得できないというエラーが出ていたのですが、認可サーバーのアクセスログにはメタデータのログが残っていました。なのに取得できないとはどういうことか。
よくよく調べたら、WAFのログにもメタデータへのアクセスをブロックしたでー、というログが残っていて、要するにWAFによってブロックされるリクエストと、されないリクエストがあるということのようです。
いきなり原因から
Copilot StudioのMCPクライアントが、リクエストのX-Forwarded-Forヘッダーに"true"を乗せていた。
Accept: application/json
x-ms-correlation-request-id: b2de0390-6a09-4ec3-88ee-9af92b171e8e
X-Forwarded-For: true
Content-Type: application/json; charset=utf-8
Host: xxx.runbook.jp
Content-Length: 348
Connection: Keep-AliveWAFの設定で、X-Forwarded-Forヘッダーによって判定するルールがあるのですが、そこにIP アドレスフォールバックという機能があります。X-Forwarded-Forヘッダーは通常、プロキシーサーバーを通してウェブサーバーへ接続したクライアントの、送信元 IP アドレスが記載されます。
もしIPアドレスと認識できない値が入っていた場合どうするか、というのがIPアドレスフォールバックなのですが、当初ルールに一致する(ブロックする)として扱っていました。IPアドレス以外の値をわざわざ送ってくるのは行儀の悪いボットくらいだからです。だからCopilot StdioのMCPサーバーが送ってくる"true"という不正なヘッダーのリクエストをWAFがブロックしていたというわけです。原因がわかれば対処は簡単なのですが、前述したようにX-Forwarded-Forヘッダーのない(ブロックされない)リクエストも混在して送ってくるので、原因を究明するのにかなり手間取りました。
なぜX-Forwarded-Forヘッダーに"true"をつけているのか
実際のところ理由は不明です。こちらのサイトに書かれているように、IMDSがX-Forwarded-Forヘッダーのあるリクエストを弾くことから、SSRF対策の可能性が高いと思われます。にしても"true"って。。
まとめ
というわけで、無効なX-Forwarded-Forをブロックしないようにすることで、無事Copilot StudioのMCPクライアントと接続ができるようになりました。Copilot Studioをお使いのみなさんはヒトもAIも使えるマニュアル「Runbook」をぜひお試しください!