概要
gem rack-cors の README を翻訳しました。
-
翻訳について
-
ライセンスについて
- rack-cors のライセンスと同様に、MIT ライセンスに従います。
Rack CORS Middleware
Rack::Cors
は Rack と互換性のあるウェブアプリケーションのために Cross-Origin Resource Sharing (CORS) のサポートを提供します。
CORS を使うことで、Webアプリケーションは JSONP などの回避策を使用せずにクロスドメインの AJAX の呼び出しを行うことができます。Cross-domain Ajax with Cross-Origin Resource Sharing をご覧ください。
##インストール
gem をインストールしてください。
gem install rack-cors
あるいは Gemfile に以下を記載してください。
gem 'rack-cors'
設定
Rails の設定
Rails アプリケーションの config/application.rb
に下記のようなコードを記載します。たとえば、これによってすべてのオリジンからのすべてのリソースに対する GET, POST, OPTIONS リクエストが許可されます。
module YourApp
class Application < Rails::Application
# ...
# Rails 5
config.middleware.insert_before 0, Rack::Cors do
allow do
origins '*'
resource '*', headers: :any, methods: [:get, :post, :options]
end
end
# Rails 3/4
config.middleware.insert_before 0, "Rack::Cors" do
allow do
origins '*'
resource '*', headers: :any, methods: [:get, :post, :options]
end
end
end
end
insert_before
を使用して、Rack::Cors
がスタックの先頭で実行され、他のミドルウェアによる干渉を受けないようにします(共通の落とし穴 セクションの Rack::Cache
の記載をご覧ください)。
rack ミドルウェアの詳細を知るために Rails Guide to Rack あるいは railscast をご覧ください。
Rack 設定
注意: もし Rails を起動しているなら、config/application.rb
を更新するだけで十分です。config.ru
を更新する必要はありません。
config.ru
では、ブロックを use
コマンドに渡すことで Rack::Cors
を設定してください。
use Rack::Cors do
allow do
origins 'localhost:3000', '127.0.0.1:3000',
/\Ahttp:\/\/192\.168\.0\.\d{1,3}(:\d+)?\z/
# 正規表現が使用可能です
resource '/file/list_all/', :headers => 'x-domain-token'
resource '/file/at/*',
methods: [:get, :post, :delete, :put, :patch, :options, :head],
headers: 'x-domain-token',
expose: ['Some-Custom-Response-Header'],
max_age: 600
# 公開するヘッダー
end
allow do
origins '*'
resource '/public/*', headers: :any, methods: :get
# 指定ホストのみリクエストを許可する
resource '/api/v1/*',
headers: :any,
methods: :get,
if: proc { |env| env['HTTP_HOST'] == 'api.example.com' }
end
end
設定リファレンス
ミドルウェア オプション
-
debug (boolean): デバッグロギングとデバッグ用の HTTP ヘッダ
X-Rack-CORS
を有効にします。 -
logger (Object or Proc): proc が与えられた場合は、ロガーが必要なときに proc が呼び出されます。
Rails.logger
のようにRack::Cors
が最初に設定された後にこのオプションは役に立ちます。
オリジン
オリジンには、ストリング、正規表現、「*」(すべてのオリジンを許可) を指定することができます。
セキュリティ上の注意: 正規表現を使用するときは、誤って包括的にならないように注意してください。たとえば、正規表現 /https:\/\/example\.com/
は example.com.randomdomainname.co.uk というドメインにマッチします。正規表現は、開始文字列と終了文字列のアンカー(\A\z
)で囲むことをお勧めします。
さらに、下記の形式のブロックを使用することでオリジンを動的に指定することもできます。
origins { |source, env| true || false }
リソースパスは、正確な文字列のマッチ(/path/to/file.txt
) あるいはワイルドカード(/all/files/in/*
) として指定することができます。ディレクトリとそのサブディレクトリのファイルをすべて含めるためには、 /assets/**/*
の形式を使用してください。リソースは次のオプションを受け取ります。
-
methods (ストリング、配列、
:any
): リソースに対して許可される HTTP メソッド。 -
headers (ストリング、配列、
:any
): CORS のリソースリクエストにおいて許可される HTTP ヘッダ。実際のリクエストですべてのヘッダを許可するには:any
を使用してください。 - expose (ストリング、配列): クライアントに公開されるリソースレスポンスの HTTP ヘッダ。
-
credentials (boolean, デフォルト:
false
):Access-Control-Allow-Credentials
レスポンスヘッダを設定します。**注意:**もしオリジンにワイルドカード (*
)を指定したときは、このオプションをtrue
に設定することはできません。詳細は、 security article をご覧ください。 -
max_age (数値):
Access-Control-Max-Age
レスポンスヘッダを設定します。 - if (Proc): proc の結果が true のとき、有効な CORS リクエストとしてリクエストを処理します。
-
vary (ストリング、配列):
Vary
ヘッダに追加する HTTP ヘッダのリスト。
共通の落とし穴
ミドルウェアスタック内で Rack::Cors
を正しく配置しないと、予想外の結果が出ることがあります。上述の Rails の例では、すべてのミドルウェアの一番上に Rack::Cors
を配置しています。これにより、ほとんどの問題を防ぐことができます。
よくあるケースを紹介します。
-
静的ファイルの配信。 適切な CORS ヘッダと共に静的ファイルが提供されるように、
ActionDispatch::Static
の前に Rack::Cors を設定してください(下記の注意書きをご覧ください)。注意: 通常、静的ファイルはWebサーバ(Nginx, Apache)から提供され、Rails コンテナからは提供されないため、本番環境では動作しないかもしれません。 -
ミドルウェアのキャッシュ。 一度キャッシュされたものではなく、適切な CORS ヘッダが記載されるように、
Rack::Cache
の前に Rack::Cors を設定してください。 -
Wardenによる認証。 認証を必要とするリソースに認証なしでアクセスされた場合、Warden はすぐに動作します。もしスタックの中で
Rack::Cors
より前にWarden::Manager
がある場合、正しい CORS ヘッダが適用されないまま Warden は動作します。必ずWarden::Manager
の前に Rack::Cors を設定するようにしてください。
Rack スタックにおいて CORS ミドルウェアをどこに配置するかを決めるためには、下記のコマンドを実行してください。
bundle exec rake middleware
多くの場合、Rack スタックは本番環境では異なる動作をしています。たとえば、config.serve_static_assets = false
のとき、ActionDispatch::Static
ミドルウェアはスタックには入っていません。本番環境でミドルウェアスタックがどのようになっているかを確認するためには、下記のコマンドを実行してください。
RAILS_ENV=production bundle exec rake middleware