クロスオリジンリソース共有

クロスオリジンリソース共有（クロスオリジンリソースきょうゆう、略称：CORS、オリジン間リソース共有、英語：Cross-Origin Resource Sharing ) は、ウェブページを配信したドメインとは異なるドメインのサーバー上にある制限されたリソースへのアクセスを、ウェブページに許可するものである。すなわち、同一生成元ポリシーを安全に回避するための仕組みである。

ウェブページは、オリジン間（cross-origin）の画像、スタイルシート、スクリプト、iframe、動画を自由に埋め込むことができる。特定の「クロスドメイン」リクエスト、特にAjaxリクエストは、同一オリジンポリシーによってデフォルトで禁止されている。CORSは、ブラウザとサーバーが対話し、オリジン間リクエストを許可することが安全かどうかを判断する方法を定義するものである。CORSは、純粋な同一オリジンリクエストよりも高い自由度と機能性を可能にするが、すべてのオリジン間リクエストを単純に許可するよりも安全である。

CORSの仕様は、WHATWGのFetch Living Standardの一部として含まれている。この仕様は、CORSが現在ブラウザでどのように実装されているかを記述している。以前の仕様は、W3C勧告として公開されていた。

 技術概要 
別のドメインを指す<form>タグを使用したり、安全リストにないヘッダーを含んだりすることで作成できないJavaScriptからのHTTPリクエストの場合、仕様はブラウザがリクエストを「プリフライト」することを義務付けている。これは、HTTPのOPTIONSリクエストメソッドを用いてサーバーにサポートされているメソッドを問い合わせ、サーバーからの「承認」を得た上で、実際のHTTPリクエストメソッドで実際のリクエストを送信するものである。サーバーはまた、リクエストと共に「クレデンシャル」（CookieやHTTP認証データを含む）を送信すべきかどうかをクライアントに通知することもできる。

 単純リクエストの例 
ユーザーがhttp://www.example.comにアクセスし、そのページがhttp://service.example.comからデータを取得するためにオリジン間リクエストを試みるとする。CORS互換のブラウザは、次のようにservice.example.comへのオリジン間リクエストを試みる。

ブラウザは、親ページを配信したドメインを含む追加のOriginHTTPヘッダを付けてGETリクエストをservice.example.comに送信する。<nowiki>Origin: http://www.example.com</nowiki>service.example.comのサーバーは、以下の3つの応答のうちの1つを返す。
 リクエストされたデータと、そのオリジンからのリクエストが許可されていることを示すAccess-Control-Allow-Origin (ACAO) ヘッダ。この場合は次のようになるべきである。<nowiki>Access-Control-Allow-Origin: http://www.example.com</nowiki>
 リクエストされたデータと、すべてのドメインからのリクエストが許可されていることを示すワイルドカード付きのAccess-Control-Allow-Origin (ACAO) ヘッダ。Access-Control-Allow-Origin: *
 サーバーがオリジン間リクエストを許可しない場合のエラーページ

ワイルドカードの同一オリジンポリシーは、ページまたはAPIの応答が、どのサイトのどのコードからもアクセス可能であることを意図している場合に適切である。Google Fontsのような公開ホスティングサービスで自由に利用できるウェブフォントがその一例である。

"*"という値は、リクエストがクレデンシャルを提供することを許可しないという点で特別である。つまり、クロスドメインリクエストにおいてHTTP認証、クライアントサイドSSL証明書、またはCookieの送信を許可しない。

CORSアーキテクチャでは、Access-Control-Allow-Originヘッダは元のWebアプリケーションサーバー（www.example.com）ではなく、外部のWebサービス（service.example.com）によって設定されることに注意が必要である。ここで、service.example.comはCORSを使用して、ブラウザがwww.example.comからservice.example.comへのリクエストを承認することを許可する。

サイトが "Access-Control-Allow-Credentials:true" ヘッダを指定している場合、第三者のサイトが特権的なアクションを実行し、機密情報を取得できる可能性がある。

 プリフライトリクエストの例 
特定の種類のクロスドメインAjaxリクエストを実行する際、CORSをサポートするモダンブラウザは、アクションを実行する権限があるかどうかを判断するために、追加の「プリフライト」リクエストを開始する。オリジン間リクエストは、ユーザーデータに影響を与える可能性があるため、このようにプリフライトされる。

OPTIONS /
Host: service.example.com
Origin: http://www.example.com
Access-Control-Request-Method: PUT

service.example.comがアクションを受け入れる意思がある場合、以下のヘッダで応答することがある。

Access-Control-Allow-Origin: http://www.example.com
Access-Control-Allow-Methods: PUT

その後、ブラウザは実際のリクエストを行う。service.example.comがこのオリジンからのクロスサイトリクエストを受け入れない場合、OPTIONSリクエストに対してエラーで応答し、ブラウザは実際のリクエストを行わない。

 ヘッダ 
CORSに関連するHTTPヘッダは次のとおりである。

 リクエストヘッダ 
Origin
Host
Access-Control-Request-Method
Access-Control-Request-Headers

 レスポンスヘッダ 
Access-Control-Allow-Origin
Access-Control-Allow-Credentials
Access-Control-Expose-Headers
Access-Control-Max-Age
Access-Control-Allow-Methods
Access-Control-Allow-Headers

ブラウザの対応状況
CORSは、以下のレイアウトエンジンをベースとするすべてのブラウザでサポートされている。
 BlinkおよびChromiumベースのブラウザ（Chrome 28+、Opera 15+、Amazon Silk、Android 4.4+ の WebView、Qt の WebEngine）
 Gecko 1.9.1（Firefox 3.5、SeaMonkey 2.0）以上。
 Trident 6.0（Internet Explorer 10）はネイティブでサポート。Trident 4.0 & 5.0（Internet Explorer 8 & 9）は、XDomainRequestオブジェクトを介して部分的にサポート。
 Prestoベースのブラウザ（Opera）はOpera 12.00およびOpera Mobile 12以降でCORSを実装しているが、Opera Miniでは実装していない。
 WebKit（初期のリビジョンは不明、Safari 4以上、Google Chrome 3以上、おそらくそれ以前）。
 Microsoft Edge 全バージョン。

 歴史 
オリジン間サポートは、当初2004年3月にTellme NetworksのMatt Oshry、Brad Porter、Michael Bodellによって、VoiceXML 2.1に含めるために提案された。これはVoiceXMLブラウザによる安全なオリジン間データリクエストを可能にするためであった。このメカニズムは本質的に一般的であり、VoiceXMLに特有のものではないと見なされ、その後実装ノートとして分離された。W3CのWebAppsワーキンググループは、主要なブラウザベンダーの参加を得て、このノートを正式なW3C勧告に向けたW3C作業草案として形式化し始めた。

2006年5月に最初のW3C作業草案が提出された。2009年3月には草案の名称が「Cross-Origin Resource Sharing」に変更され、2014年1月にはW3C勧告として承認された。

 CORS と JSONP 
JSONPの主な利点は、CORSのサポート以前のレガシーブラウザ（Opera MiniおよびInternet Explorer 9以前）で動作する能力にあった。CORSは現在、ほとんどのモダンなウェブブラウザでサポートされており、JSONPパターンの現代的な代替として使用できる。CORSの利点は次のとおりである。

 JSONPがGETリクエストメソッドのみをサポートするのに対し、CORSは他のタイプのHTTPリクエストもサポートする。
 CORSにより、ウェブプログラマは通常のXMLHttpRequestを使用でき、JSONPよりも優れたエラーハンドリングをサポートする。
 JSONPは、外部サイトが侵害された場合にクロスサイトスクリプティング（XSS）の問題を引き起こす可能性があるが、CORSはウェブサイトが手動で応答を解析してセキュリティを向上させることを可能にする。

 関連項目 
 Content Security Policy
 同一生成元ポリシー
 XMLHttpRequest
 JSONP

 脚注 

 外部リンク 
 Fetch Living Standard (CORSの現行仕様)
 Setting CORS on Apache with correct response headers allowing everything through
 様々な（Web）サーバーでCORSサポートを有効にするための詳細なハウツー情報
 HTML5 Rocks がCORSの仕組みを詳しく解説
 オンラインCORS設定ミススキャナ 

Category:コンピュータ・ネットワーク・セキュリティ
Category:コンピュータセキュリティ手続
Category:ウェブ技術