メインコンテンツまでスキップ

CORS plugin

Cors plugin(技術名 cors、Security グループ)は、標準の CORS ヘッダー(Access-Control-Allow-Origin、Access-Control-Allow-Methods など)を response に追加し、別のオリジンの Web ページが response を読み取れるかどうかをブラウザーに伝えます。

警告

CORS はサーバー側のセキュリティの仕組みではありません。 CORS ヘッダーはブラウザーへの指示にすぎません。curl、Postman、別のサーバーから送信された request は CORS を無視し、そのままバックエンドに届きます。API を呼び出せる相手を制御するには、JWT Auth や OpenID Connect などの認証 plugin も併用してください。

ユースケース​

CORS plugin は、API Gateway とは別のドメインで動作し、JavaScript(fetch / XHR)で API を呼び出すフロントエンド(SPA、モバイル Web)に適しています。CORS ヘッダーがないと、request がバックエンドに届いて処理されても、ブラウザーは JavaScript による response の読み取りをブロックします。

主なケース:

  • https://app.example.com のフロントエンドが https://api.example.com の API を呼び出す: allow_origins に https://app.example.com を宣言します。
  • *.customer.example.com のような動的なサブドメインを持つ多数のテナントが同じ API を呼び出す: ドメインを 1 つずつ列挙する代わりに allow_origins_by_regex を使います。
  • 多数の Route / Service が 1 つのオリジン一覧を共有する: allow_origins_by_metadata を使って一元的に 1 回だけ宣言します。
  • request が cookie や Authorization ヘッダーを運ぶ: allow_credential をオンにし、オリジン、method、ヘッダーを明示的に宣言します(* は使いません)。
  • バックエンドが返すカスタムヘッダー(X-Request-Id など)をクライアントの JavaScript で読み取る必要がある: そのヘッダーを expose_headers に宣言します。

CORS plugin を作成する​

CORS plugin を作成するには、次の手順を実行します。

  1. 左側のメニューで API Gateway → Plugin を選択し、右上で API Gateway を選択して New plugin をクリックし、Add plugin ポップアップで Cors(Security グループ)を選択します。Route / Service の Plugins タブから追加することもできます。Plugin の追加を参照してください。

  2. Basic Information セクションで Display Name を入力します。Basic Informationを参照してください。

  3. Configuration セクションを選択します。フォームには plugin の 10 個の属性がすべて表示されており、Manage Attribute パネルに追加できる属性はありません。

デフォルト値の CORS plugin の Configuration セクション

属性必須説明
allow_originsYクロスオリジンの呼び出しを許可するオリジンで、scheme://host:port 形式(例: https://app.example.com)でカンマ区切りで指定します。* はすべてのオリジンを許可し、allow_credential がオフの場合にのみ機能します。デフォルトは * です。
allow_origins_by_metadataN各 plugin で再入力する代わりに、Plugin metadata で定義したオリジン一覧を参照します。多数の Route / Service が 1 つのオリジン一覧を共有する場合に使います。+ Add をクリックして 1 行ずつ追加します。
allow_origins_by_regexN許可するオリジンに一致する正規表現です(例: .*\.test\.com$)。ドメインが多すぎる場合やテナントごとにドメインが生成される場合に使います。設定すると、allow_origins の内容にかかわらず、正規表現に一致するオリジンのみが受け付けられます。
allow_methodsYCORS を有効にする HTTP method で、*、**、GET、HEAD、POST、PUT、DELETE、OPTIONS、TRACE、PATCH から選択します。*(または **)を選択すると、個別の method はクリアされます。デフォルトは * です。
allow_headersNクライアントがクロスオリジンの request で送信できるヘッダーで、カンマ区切りで指定します(例: Authorization,Content-Type)。* はすべてを許可し、allow_credential とは併用できません。デフォルトは * です。
expose_headersNクライアントの JavaScript が読み取れる response ヘッダーです(例: X-Request-Id)。空の場合、plugin は Access-Control-Expose-Headers ヘッダーを変更しません。
max_ageNブラウザーがプリフライトの OPTIONS の結果をキャッシュする時間(秒)です。値を大きくするとプリフライトの request が減ります。-1 はキャッシュを無効にします。-1 以上の整数のみ使用できます。デフォルトは 5 です。
allow_credentialNrequest が資格情報(cookie、Authorization ヘッダー)を運ぶことを許可します。オンの場合、allow_origins、allow_methods、allow_headers に * は使わないでください。デフォルトはオフです。
timing_allow_originsNリソースの読み込みタイミング(Timing-Allow-Origin ヘッダー)の読み取りを許可するオリジンです。Resource Timing API にのみ関係し、通常の API 呼び出しには関係しません。
timing_allow_origins_by_regexNtiming_allow_origins と同じですが、正規表現で宣言します。
危険

allow_credential をオンにすると、まだ * を使っている allow_origins、allow_methods、allow_headers のフィールドすべてに You cannot use '*' here while allow_credential is enabled. という警告が表示されます。警告は Create ボタンをブロックしませんが、その設定はブラウザーで正しく機能しません。* の代わりに、許可するオリジン、method、ヘッダーを明示的に列挙してください。

** の値は、このルールにかかわらず * を強制します。これはセキュリティ上のリスク(CSRF 攻撃の余地を生みます)があるため、本番環境では使わないでください。

allow_credential がオンでアスタリスクが残っている場合の警告

  1. Scope セクションを選択します。すべての API が同じフロントエンドのグループを対象にしている場合は、シンプルにするために Global を選びます。API グループごとにオリジン一覧が異なる場合は、Route / Service ごとに Scoped の CORS plugin を複数作成します。Scopeを参照してください。

  2. Create をクリックします。Plugin created successfully というメッセージが表示され、plugin が一覧に表示されます。

設定例​

すべてのオリジンに開放されたデフォルトの設定です。すぐに機能しますが、本番環境ではこのままにしないでください。

{
"allow_origins": "*",
"allow_methods": "*",
"allow_headers": "*",
"expose_headers": "",
"max_age": 5,
"allow_credential": false
}

https://app.example.com の SPA が Authorization ヘッダー付きで API を呼び出す場合です。(allow_credential がオンのため)* の代わりに各値を明示的に列挙し、プリフライトの request が通るように allow_methods に OPTIONS を残し、ブラウザーのプリフライトの頻度を下げるために max_age を大きくします。

{
"allow_origins": "https://app.example.com",
"allow_methods": "GET,POST,OPTIONS",
"allow_headers": "Authorization,Content-Type",
"expose_headers": "X-Request-Id",
"max_age": 3600,
"allow_credential": true
}

動的なサブドメイン(https://acme.customer.example.com、https://beta.customer.example.com など)を持つ多数のテナントで、allow_origins_by_regex を使う場合です。

{
"allow_origins": "https://app.customer.example.com",
"allow_origins_by_regex": [
"^https://[a-z0-9-]+\\.customer\\.example\\.com$"
],
"allow_methods": "GET,POST,PUT,DELETE,OPTIONS",
"allow_headers": "Authorization,Content-Type",
"max_age": 3600,
"allow_credential": true
}
ヒント
  • allow_origins_by_regex を設定すると、正規表現に一致するオリジンのみが受け付けられます。allow_origins は必須フィールドのため値が必要です。allow_credential がオンの間は、* ではなく特定のオリジンを入力してください。
  • 正規表現は ^ と $ で固定し、ドットをエスケープ(\.)してください。そうしないと . が任意の文字に一致し、https://evil-customerXexample.com のようなドメインも通ってしまいます。

動作を確認する​

plugin を作成したら、テスト request を送信して、API Gateway が設定どおりに response に CORS ヘッダーを追加しているかを確認します。次の例では、この設定の cors plugin を使います。

{
"max_age": 5,
"allow_headers": "Test_content",
"allow_methods": "*",
"allow_origins": "*",
"allow_credential": false
}

CORS plugin を確認するには、次の手順を実行します。

  1. plugin の詳細画面の Configuration セクションを開き、有効な設定を確認します。Plugin の詳細表示を参照してください。

allow_origins、allow_methods、allow_headers、max_age がある cors plugin の Configuration セクション

  1. plugin の Scope 内にある Route の path を付けた Gateway URL に request を送信します(例: POST https://YOUR_GATEWAY_URL/v2/pet)。Gateway URL の取得方法と request の送信方法については、Route のテストを参照してください。

  2. response の Headers タブを開き、設定と比較します。

属性設定値response のヘッダー
allow_origins*Access-Control-Allow-Origin: *
allow_methods*Access-Control-Allow-Methods: *
allow_headersTest_contentAccess-Control-Allow-Headers: Test_content
max_age5Access-Control-Max-Age: 5
allow_credentialfalseAccess-Control-Allow-Credentials ヘッダーなし

CORS plugin が追加した Access-Control-* ヘッダー付きの 200 OK response

response に表のすべての Access-Control-* ヘッダーがあれば、plugin は機能しています。これらのヘッダーがない場合は、request が plugin の Scope 内の Route / Service を経由しているか、plugin が有効になっているかを確認してください。Plugin の有効化・無効化を参照してください。

よくある問題​

エラー原因対処方法
You cannot use '*' here while allow_credential is enabled.allow_credential がオンなのに、allow_origins / allow_methods / allow_headers でまだ * を使っています* の代わりに、オリジン、method、ヘッダーを明示的に列挙します。
Invalid regular expression.allow_origins_by_regex の正規表現の構文が無効です正規表現を修正します。
Enter a whole number greater than or equal to -1.max_age が整数でないか、-1 より小さい値です-1 以上の整数を入力します。

次のステップ​

に最終更新