こんにちは!
ROBOT PAYMENTでサブスクペイの開発を担当している小林です。
IIS上でASP.NETアプリを運用していると、クロスオリジン通信に欠かせないCORSのプリフライト(OPTIONS
)リクエストがうまく通らずに悩んだことはありませんか?
今回はその “陥りやすいポイント” とその解決策 を紹介します。
対象読者: IIS上でASP.NET Web API / WebForms を運用している方
陥りやすいポイント1:既定ハンドラが OPTIONS
を処理してしまい、アプリ層に届かない
現象
- プリフライト(
OPTIONS
)に対してIISが 405/500 を返し、メインのリクエストまで進めない - DevToolsのNetworkタブで確認すると、
Access-Control-Allow-Headers
が付与されていない
原因
IISにはメソッドごとの既定ハンドラが登録されており、OPTIONS
は OPTIONSVerbHandler
が担当しています。そのため、アプリ層に届く前にIISが応答し、CORSヘッダーを付与できません。
解決策
OPTIONSVerbHandler
を削除 し、拡張子なしURLのハンドラを verb="*"
で再登録することで、アプリ層までプリフライトリクエストが到達するようになります。
Microsoft公式ドキュメントでも、IISがプリフライトを処理しないように構成変更する必要があると記載されています。
ASP.NET アプリが OPTION 要求を受信して処理できるように IIS を構成するには、
セクション内のアプリの web.config ファイルに次の構成を追加します。
webServer>
name="ExtensionlessUrlHandler-Integrated-4.0" />
name="OPTIONSVerbHandler" />
name="ExtensionlessUrlHandler-Integrated-4.0" path="*." verb="*" type="System.Web.Handlers.TransferRequestHandler" preCondition="integratedMode,runtimeVersionv4.0" />
webServer>
出典: Enabling Cross-Origin Requests in Web API — Microsoft Learn
注意点
verb="*"
を指定すると全てのHTTP動詞がアプリ層に届きます。必要に応じてRequest Filtering機能で拒否設定を行ったり、適切なハンドラを個別に登録してください。
陥りやすいポイント2:Request Filtering によるブロック
現象
web.config
を修正しても、OPTIONS
が依然として 404 や 405 で落ち続ける。
原因
IIS の 要求のフィルター(Request Filtering) 機能には、HTTP 動詞を許可/拒否する仕組みがあります。Microsoft公式ドキュメントにも、次のように記載されています。
「一覧に含まれていない HTTP 動詞へのアクセスを拒否します」
出典:要求のフィルタリング
— IIS
つまり、もし OPTIONS
を拒否対象に含めていると、IIS がそのリクエストを最初の段階で拒否し、アプリ層まで届かなくなってしまいます。
さらに、HTTP 詳細エラーコードの説明にはこう記載されています。
「404.6 – 要求フィルター モジュールが、要求の HTTP 動詞を拒否しました。」
出典: IIS エラーコード解説 (Microsoft Docs 日本語版)
これにより、拒否された HTTP 動詞がある場合、IIS が 404.6 で応答することがわかります。
解決策
IISマネージャーで対象サイトを選択し、「要求フィルター」 → 「HTTP 動詞」を確認します。
OPTIONS
が拒否リストに含まれていれば削除するか「許可」に変更します。
確認手順まとめ
-
ハンドラ設定の変更
web.config
に
を追加し、OPTIONSVerbHandler
を削除 →ExtensionlessUrlHandler-Integrated-4.0
をverb="*"
で登録する -
Request Filtering を確認
IISの Request Filtering で
OPTIONS
が拒否されていないかチェック。
拒否されていたら許可に変更する -
アプリ側でCORS応答を実装
Web APIなら
[EnableCors]
属性やグローバル設定、WebFormsならGlobal.asax
でヘッダ等の実装を行う -
ブラウザで検証
DevToolsでプリフライト→メインのリクエストの順に成功するかを確認する
実装後
以下の点を確認しておくのがよいと思います。
- OPTIONS レスポンスに Access-Control-Allow-Headersなどが付与されているか
- メインのリクエストが200系で通るか
- アプリログやデバック等で OPTIONS がアプリ層まで届いていることが確認できるか
まとめ
IIS 環境での CORS 対応は、「IISの設定」+「アプリ側の実装」 の両面から見直す必要があります。今回の内容が、同じように悩んだ方の問題解決や理解の一助になれば幸いです。
参考文献
We are hiring!!
ROBOT PAYMENTでは一緒に働く仲間を募集しています!!!