COOPとCOEPの利用によりあなたのウェブサイトを「クロスオリジン分離」にする
COOPとCOEPの利用により、クロスオリジンの分離環境を設定し、SharedArrayBuffer
、performance.measureUserAgentSpecificMemory()
、精度の高い高解像度タイマー等の強力な機能を有効にします。
更新
- 2021年8月5日:JSセルフプロファイリングAPIは、クロスオリジン分離を求めるAPIの1つとして言及されるが、 最新の方向転換を反映したので削除されました。
- 2021年5月6日:フィードバックと報告された問題に基づき、ChromeM92で制限されるクロスオリジン分離がないサイトでの
SharedArrayBuffer
の使用のタイムラインを調整することを決めました。 - 2021年4月16日:新規COEPクレデンシャルレスモードとCOOP同一生成元許可ポップアップが、クロスオリジン分離のリラックス状態になることについてのメモを追加しました。
- 2021年3月5日Chrome 89で完全に有効になった
SharedArrayBuffer
、performance.measureUserAgentSpecificMemory()
、およびデバッグ機能の制限を削除しました。今後の機能であるより高精度のperformance.now()
とperformance.timeOrigin
を追加しました。 - 2021年2月19日
allow="cross-origin-isolated"
機能ポリシーとDevToolsのデバッグ機能に関するメモを追加しました。 - 2020年10月15日:
self.crossOriginIsolated
はChrome 87から動けます。これを反映して、self.crossOriginIsolated
がtrue
になったら、document.domain
は不変となります。performance.measureUserAgentSpecificMemory()
はオリジン トライアルを終了し、Chrome89のデフォルトで有効にさせました。AndroidChromeの共有アレイバッファはChrome88から利用できるようになります。
多少のWebAPIは、Spectreのようなサイドチャネル攻撃のリスクを高めます。そのリスクを軽減するために、ブラウザーはクロスオリジン分離と呼ばれるオプトインベースの分離環境を提供します。クロスオリジンの分離状態では、Webページは次のような特権機能を使用できます。
API | 説明 |
---|---|
SharedArrayBuffer | WebAssemblyスレッドに必要です。これはAndroidChrome 88から利用できます。デスクトップバージョンは現在、サイト分離のサポートにより、デフォルトで有効になっているが、クロスオリジン分離状態が要求され、 Chrome92でデフォルトで無効にされます。 |
performance.measureUserAgentSpecificMemory() | Chrome89から動けます。 |
performance.now() 、 performance.timeOrigin | 現在、解像度が100マイクロ秒以上で、多くのブラウザで利用できます。クロスオリジンアイソレーションでは、解像度が5マイクロ秒以上になる可能性があります。 |
クロスオリジンの分離状態は、 document.domain
の変更も防ぎます。( document.domain
を変更できると、同じサイトのドキュメント間の通信が可能になり、同一生成元ポリシーの抜け穴と見なされます。)
クロスオリジンの分離状態にオプトインするには、メインドキュメントで次のHTTP headers を送信する必要があります。
Cross-Origin-Embedder-Policy: require-corp
Cross-Origin-Opener-Policy: same-origin
これらのheadersは、クロスオリジンドキュメントによるロードを選択していないリソースまたはiframeのロードを停止し、クロスオリジンウィンドウがドキュメントと直接対話するのを防ぐようにブラウザーに指示します。これは、クロスオリジンでロードされるリソースにはオプトインを求めるとも意味します。
self.crossOriginIsolated
を調べることで、Webページがクロスオリジンの分離状態にあるかどうかを判断できます。
この記事では、これらの新しいheadersの使用方法を説明します。フォローアップ記事では、より多くのバックグラウンドとコンテキストを提供します。
COOPとCOEPを展開することにより、Webサイトのクロスオリジンを分離します #
COOPとCOEPを統合する #
1. 最上位のドキュメントでCross-Origin-Opener-Policy: same-origin
headersを設定します #
最上位のドキュメントでCOOP: same-origin
を有効にすると、同一生成元のウィンドウ、及びドキュメントから開いたウィンドウは、同じCOOP設定で同じ生成元にない限り、個別の閲覧コンテキスト組を得ます。したがって、開いているウィンドウには分離が適用され、両方のウィンドウ間の相互通信は無効になります。
閲覧コンテキストグループは、同じコンテキストを共有するタブ、ウィンドウ、またはiframeのグループです。 例えば、ウェブサイト(https://a.example
)はポップアップウィンドウ(https://b.example
)を開くと、オープナーウィンドウとポップアップウィンドウは同じ閲覧コンテキストをを共有し、window.opener
などのDOM APIを介して相互にアクセスします。

DevToolsでウィンドウオープナーとそのopeneeが別々の閲覧コンテキストグループに属しているかどうかをチェックすることができます。
2.リソースのCORPまたはCORSが有効になっていることを確認すること #
ページ内のすべてのリソースにはCORP又はCORS HTTP headersがロードされていることを確認してください。このステップは、COEPを有効にするステップ4に必要です。
次はリソースの性質に応じて、実施する必要となることです。
- リソースを同じオリジンのみからロードしたい場合は、
Cross-Origin-Resource-Policy: same-origin
headerをご設定ください。 - リソースを同じサイトのみから、かつ、オリジンを介してロードしたい場合は、
Cross-Origin-Resource-Policy: same-site
headerをご設定ください。 - リソースを制御しクロスオリジンからロードをする場合は、可能であれば
Cross-Origin-Resource-Policy: cross-origin
headerをご設定ください。 - 制御できないクロスオリジンリソースの場合:
- リソースがCORSで提供される場合は、読み込み中のHTMLタグで
crossorigin
属性をご使用ください。 (たとえば、<img src="***" crossorigin>
.) - CORSまたはCORPのいずれかをサポートする必要がある場合は、リソースの所有者に連絡してください。
- リソースがCORSで提供される場合は、読み込み中のHTMLタグで
- iframeの場合、CORPとCOEP headerを次のように使用します。Cross
Cross-Origin-Resource-Policy: same-origin
(またはコンテキストに応じてsame-site
、cross-origin
)とCross-Origin-Embedder-Policy: require-corp
。
3. COEP Report-Only HTTP headerを使用して、埋め込まれたリソースを評価すること #
COEPを完全に有効にする前に、 Cross-Origin-Embedder-Policy-Report-Only
headerを使用してドライランを実行し、ポリシーが実際に機能するかどうかを確認できます。埋め込まれたコンテンツをブロックせずにレポートを受け 取ります。これをすべてのドキュメントに再帰的に適用します。 Report-Only HTTP headerの詳細情報については、Observe issues using the Reporting APIをご参照ください。
4. COEPを有効にする #
全てが機能し、すべてのリソースを正常にロードできることを確認したら、Cross-Origin-Embedder-Policy: require-corp
HTTP headerを、iframeを介して埋め込まれているドキュメントを含むすべてのドキュメントに適用します。
self.crossOriginIsolated
と共に分離が成功したかどうかを判断します #
self.crossOriginIsolated
プロパティは、Webページがクロスオリジン分離状態になり、すべてのリソースとウィンドウが同じ閲覧コンテキストグループ内で分離されている場合にtrue
を返します。このAPIを使用して、閲覧コンテキストグループを正常に分離し、 performance.measureUserAgentSpecificMemory()
などの強力な機能にアクセスできたかどうかを判断できます。
ChromeDevToolsで問題をデバッグする #
画像などの画面に表示されるリソースの場合は、リクエストがブロックされ、ページに画像がないと示されるため、COEPの問題を簡単に検出できます。ただし、必ずしも視覚的な影響を与えないスクリプトやスタイルなどのリソースの場合、COEPの問題が見過ごされる恐れがあります。それらについては、DevToolsネットワークパネルをご利用ください。COEPに関する問題が発生する場合は、ステータス列にある(blocked:NotSameOriginAfterDefaultedToSameOriginByCoep)
をご覧ください。
次に、エントリをクリックしたら、詳細をご覧ください。
アプリケーションパネルでiframeとポップアップウィンドウの状態を確認することもできます。左側の「Frames」セクションに移動し、「Top」を開き、リソース構造の内訳をご確認ください。
SharedArrayBuffer
の可用性などのiframeの状態を確認できます。
クロスオリジンが分離されているかどうかなのポップアップウィンドウの状態を確認することもできます。
ReportingAPIで問題を観察する #
Reporting APIは、種々な問題を検出できるメカニズムの一つです。 COEPがリソースのロードをブロックするか、COOPがポップアップウィンドウを分離するたびにレポートを送信するようにユーザーのブラウザーに指示するという仕組みでReportingAPIを構成できます。Chromeは、バージョン69以降から、COEPやCOOPなどのさまざまな用途でReportingAPIをサポートしています。
Reporting APIを構成し、レポートを受信するようにサーバーを設定する方法については、Using the Reporting APIに移動して、ご参考ください。
COEPレポートの例 #
クロスオリジンリソースがブロックされている場合のCOEPレポートペイロードの例は次のようになります。
[{
"age": 25101,
"body": {
"blocked-url": "https://third-party-test.glitch.me/check.svg?",
"blockedURL": "https://third-party-test.glitch.me/check.svg?",
"destination": "image",
"disposition": "enforce",
"type": "corp"
},
"type": "coep",
"url": "https://cross-origin-isolation.glitch.me/?coep=require-corp&coop=same-origin&",
"user_agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4249.0 Safari/537.36"
}]
COOPレポートの例 #
ポップアップウィンドウが開かれ、分離されたときのCOOPレポートペイロードの例は、次のようになります。
[{
"age": 7,
"body": {
"disposition": "enforce",
"effectivePolicy": "same-origin",
"nextResponseURL": "https://third-party-test.glitch.me/popup?report-only&coop=same-origin&",
"type": "navigation-from-response"
},
"type": "coop",
"url": "https://cross-origin-isolation.glitch.me/coop?coop=same-origin&",
"user_agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4246.0 Safari/537.36"
}]
異なる閲覧コンテキストグループが相互にアクセスすると(「report-only」モードのみ)、COOPもレポートを送信します。例えば、 postMessage()
が試行されたとき、レポートは、次のようになります。
[{
"age": 51785,
"body": {
"columnNumber": 18,
"disposition": "reporting",
"effectivePolicy": "same-origin",
"lineNumber": 83,
"property": "postMessage",
"sourceFile": "https://cross-origin-isolation.glitch.me/popup.js",
"type": "access-from-coop-page-to-openee"
},
"type": "coop",
"url": "https://cross-origin-isolation.glitch.me/coop?report-only&coop=same-origin&",
"user_agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4246.0 Safari/537.36"
},
{
"age": 51785,
"body": {
"disposition": "reporting",
"effectivePolicy": "same-origin",
"property": "postMessage",
"type": "access-to-coop-page-from-openee"
},
"type": "coop",
"url": "https://cross-origin-isolation.glitch.me/coop?report-only&coop=same-origin&",
"user_agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/87.0.4246.0 Safari/537.36"
}]
結論 #
Webページを特別なクロスオリジン分離状態にオプトインするために、COOPとCOEP HTTP headerの組み合わせを使用します。 self.crossOriginIsolated
を調べて、Webページがクロスオリジンの分離状態にあるかどうかを判断できます。
新しい機能がこのクロスオリジンの分離された状態に有効になり、COOPとCOEPに関するDevToolsがさらに改善されるので、本投稿は更新され続けます。
資力 #
- 強力な機能に「クロスオリジン分離」が必要な理由
- クロスオリジン分離を有効にするためのガイド
- Android Chrome88およびDesktopChrome92でのSharedArrayBufferの更新
measureUserAgentSpecificMemory()
使用してWebページの合計メモリ使用量を監視します