1. イントロダクション
このセクションは規範的ではありません。
Web Bundles によるサブリソースの読み込み仕様は、 複数のリソースをまとめて効率よく読み込むためのフォーマット Web Bundles を用いる方法について説明します。 この仕様は、ウェブブラウザがそれらのリソースをどのように読み込むかを記述しています。 また、[HTML]、 [FETCH]、 [CSP] 仕様に対するいくつかのモンキーパッチとして表現され、 ここで定義するアルゴリズムを呼び出します。
注意: この仕様は作成中です。#708 を参照してください。
2. 構造体
フェッチされたウェブバンドル は [draft-ietf-wpack-bundled-responses-latest] で定義される ウェブバンドルフォーマットの表現です。
ウェブバンドルフェッチエントリ とは、以下の項目を持つ 構造体です:
-
source:ウェブバンドルの URL。
-
credentials:認証情報モード。
-
state:内部状態であり、"fetching"・"fetched"・"failed" のいずれか。 初期値は "fetching"。
-
fetched bundle:フェッチされたウェブバンドルまたは null。
ウェブバンドルフェッチエントリ の より良い名称?
ウェブバンドルフェッチエントリ entry は、Document document の ウェブバンドル登録リストが、 その ウェブバンドル登録の fetch entryとして entry を 含むとき、 登録で使用中とみなされます。
-
fetch entry:ウェブバンドルフェッチエントリ。
-
rule:バンドルルール。
すべての環境設定オブジェクトは、 ウェブバンドル登録リスト アルゴリズムを持ち、 これは リストとして ウェブバンドル登録を返します。
Document
は ウェブバンドル登録リストを持ち、
ウェブバンドル登録のリスト
(初期値は空)。
ウィンドウ環境設定オブジェクトのセットアップ
では、settings object の ウェブバンドル登録リスト は
windowの関連付けられたDocumentの
ウェブバンドル登録リストを返します。
ワーカー環境設定オブジェクトのセットアップ では、settings object の ウェブバンドル登録リスト は 空のリストを返します。
Document
は ウェブバンドルフェッチエントリリストを持ち、
ウェブバンドルフェッチエントリのリスト
(初期値は空) となります。
リストが ウェブバンドルフェッチエントリリスト に 使われているが、順序は重要でないはずです。
3. HTML へのモンキーパッチ
ウェブバンドルをスクリプト要素の準備アルゴリズムで 既存スクリプトタイプ (classicやmodule) と同様に処理するため、次の変更を行います:
-
スクリプトの type は "classic"、"module"、"webbundle" のいずれかにすること
-
ウェブバンドル結果を導入し、 これは 構造体で、 2つの項目を持ちます:
-
registration:ウェブバンドル登録;
-
再スローするエラー:解析エラーを表す JavaScript値、nullの場合はエラーなし。
-
-
スクリプトの result は "uninitiated"、null、 script、または ウェブバンドル結果 のいずれか。
注意: ウェブバンドル結果を script の 新しいサブクラスにせず、 他のスクリプト実行系の仕様への影響はありません。
3.1. スクリプト要素の準備
スクリプト要素の準備 アルゴリズム内で、次の変更を行う:
-
スクリプト要素の準備 ステップ10に、次のステップを挿入:
-
スクリプトブロックの type 文字列が ASCII大文字・小文字を区別しない形で 文字列 "
webbundle" と一致する場合、el の type を "webbundle" に設定する。
-
-
スクリプト要素の準備 ステップ26.7に、次のケースを挿入:
-
"
webbundle":-
タスクをキューに追加し、 その要素で error というイベントを発火し、リターンする。
注意:
<script type="webbundle" src=...>はサポートされていない。ここでのエラー処理に特別な要件はないため、現在はsrc属性が空の場合と同様にerrorイベントが発火される。
-
-
-
スクリプト要素の準備 ステップ27.2に、次のケースを挿入:
-
"
webbundle":-
ウェブバンドルの準備を、element、source text、base URLで行う。
-
-
-
スクリプト要素の準備 ステップ28に、次のケースを挿入:
-
スクリプトの type が "
webbundle" の場合:-
アサーション:スクリプトの ready to be parser-executed は true である。
-
並列で、ウェブバンドルのイベント処理をelementで行う。
-
-
注: CSP はインラインWebバンドルにもステップ15で適用され、Classic/Moduleスクリプトと同様である。
ウェブバンドルの準備とは、HTMLScriptElement
element、string sourceText、および URL baseURL
を与えられたときに行う:
-
parse result を、ウェブバンドル文字列の解析に sourceText、baseURL を与えて得る。
-
例外がスローされた場合:
-
スクリプトの result を、ウェブバンドル結果( registration は null、 error to rethrow がスローされた例外)の新規インスタンスに設定する。
-
ready にマークする。
-
リターン。
-
-
document を element の ノードドキュメントとする。
-
fetch entry を null に設定する。
-
document の ウェブバンドルフェッチエントリリスト の各 r について:
-
r の source が parse result の source かつ、r の credentials が parse result の credentials である場合:
-
r が document 内で 登録で使用中でないなら、 fetch entry に rを設定する。
注: これは、スクリプト結果の registration の fetch entry が r であった他のスクリプト要素が削除されたことを意味する。 これは、同じ source と credentials を持つ
HTMLScriptElementのフェッチエントリが、削除されて追加された場合に 再取得・生成されないことを保証する。
-
-
-
fetch entry が null である場合:
-
fetch entry を新しい ウェブバンドルフェッチエントリ(source に parse result の source、 credentials に parse result の credentials、 state に "fetching"、fetched bundle に null)に設定する。
-
append fetch entry を document の ウェブバンドルフェッチエントリリスト に追加する。
-
並列で、ウェブバンドルのフェッチを fetch entry で行う。
-
-
registration を新しい ウェブバンドル登録(fetch entry は fetch entry、 rule は parse result の rule)にする。
-
append registration を document の ウェブバンドル登録リストに追加する。
-
スクリプトの result を新しい ウェブバンドル結果 (registration は registration、error to rethrow は null)に設定する。
-
ready にマークする。
3.2. イベントの発火
スクリプト要素の実行 で、ステップ6に次のケースを追加:
-
"
webbundle":-
アサーション:到達しないことを保証する。
注意: ウェブバンドルは ウェブバンドルのイベント処理 で処理され、スクリプト要素の実行では処理されない。
-
ウェブバンドルのイベント処理とは、HTMLScriptElement
element を与えられたとき:
-
result を element のスクリプトの result とする。
-
アサーション:element の スクリプトの type は "
webbundle" である。 -
アサーション:result は ウェブバンドル結果 である。
-
次のいずれかの条件が満たされるまで、非同期的に待機する:
-
result の 再スローするエラー が null でない場合
-
result の registration が null でない、かつ result の registration の fetch entry の state が "fetched" または "failed" になった場合
注意: 他のスクリプトタイプと異なり、ここでは ウェブバンドルのフェッチ を待機してから
loadイベントをHTMLScriptElementに発火する。ここでは loadイベントの遅延は行わない。これは ready にマーク を スクリプト要素の準備 内で同期的に実施しているため。 ウェブバンドルのフェッチ はプリロードに近い動作となるため意図した挙動である。 -
-
element のスクリプト result が null の場合、return。
注意: これは前段階で element が ドキュメントから削除されたときに起こりうる。
注意: これは whatwg/html#2673 に合わせて記述されている。 現状ではこのケースで
errorイベントは発火しないが、 もし whatwg/html#2673 で発火するよう変更された場合は この手順もそれに合わせて変更すること。 -
アサーション:element の ノードドキュメント は element の 準備時のドキュメント と等しい。
-
result の 再スローするエラー が null でない場合:
-
アサーション:result の registration は null でない。
-
result の registration の fetch entry の state が "failed" の場合:
-
error イベントを element で発火する。
-
return。
-
-
アサーション:result の registration の fetch entry の state は "fetched"。
-
load イベントを element で発火する。
3.3. 削除
script 要素が ドキュメントから削除された場合、ユーザーエージェントは次のアルゴリズムを実行する:
-
スクリプトの type が "
webbundle" でない場合、return。 -
スクリプトの result が null の場合、return。
-
アサーション:スクリプト result は ウェブバンドル結果 である。
-
registration を スクリプト result の registration とする。
-
スクリプト result を null に設定する。
-
registration が null の場合、return。
-
document を ノードドキュメントとする。
-
アサーション:document の ウェブバンドル登録リスト が registration を含む。
-
registration を document の ウェブバンドル登録リスト から削除する。
-
-
fetch entry を registration の fetch entryとする。
-
fetch entry が document で 登録で使用中なら、return。
-
fetch entry を documentの ウェブバンドルフェッチエントリリスト から削除する。
注意: fetch entry が、document の ウェブバンドルフェッチエントリリスト に既に含まれていない場合がありうる。 これは、fetch entry が複数の
script要素の ウェブバンドル登録 に使われており、そのscript elementsが削除された場合に起こる。注意: この時点で fetch entry は 以後のサブリソースフェッチや ウェブバンドルの準備では使われないが、 そのフェッチ結果は 進行中のフェッチ処理で引き続き使われる可能性がある。
-
4. Fetchへのモンキーパッチ
4.1. fetchへのモンキーパッチ
fetch にて、
taskDestination を null とする。
の前に次の手順を追加:
-
find a matching web bundle registration を request で呼んだ結果が null なら、request の service-workers mode を "
none" に設定する。
注意: これは webbundle から読み込まれたサブリソースに対して service worker のイベントが発火しなくなることを意味する。
4.2. fetch schemeへのモンキーパッチ
fetch
scheme に
"uuid-in-package" を追加する。
注意: これにより
navigate アルゴリズムが uuid-in-package: URL には
process a navigate fetch アルゴリズムを使うことが保証される。
注意: origin が
"uuid-in-package" スキームのURLは不透明なoriginとなる。
4.3. HTTP-network-or-cache fetchへのモンキーパッチ
HTTP-network-or-cache fetch で、
8.22. httpCache を、httpRequest で HTTP キャッシュパーティションを決定した結果に設定する。
の前に次の手順を追加:
-
response を ウェブバンドルからサブリソースのフェッチ の httpRequest を与えた結果に設定する。
5. CSPへのモンキーパッチ
5.1. 「Does request match source list?」へのモンキーパッチ
Does request match source list? を次の手順で書き換える:
-
url を request の current url とする。
-
url の scheme が "
uuid-in-package" の場合:-
registration を find a matching web bundle registration に request を与えて実行した結果とする。
-
registration が null でない場合、url を registration の fetch entry の source に設定する。
-
-
url、source list、policy の self-origin、 及び request の redirect count で Does url match source list in origin with redirect count? を実行した結果を返す。
注意: これにより CSP の制約は uuid-in-package: URL
ではなく
バンドルのURLに対して評価される。詳細は #651 を参照。
5.2. 「Does response to request match source list?」へのモンキーパッチ
Does response to request match source list? を次の手順で書き換える:
-
url を response の url とする。
-
url の scheme が "
uuid-in-package" の場合:-
registration を find a matching web bundle registration に request を与えて実行した結果とする。
-
registration が null でない場合、url を registration の fetch entry の source に設定する。
-
-
url、source list、policyの self-origin、 及び request の redirect count で Does url match source list in origin with redirect count? を実行した結果を返す。
注意: これにより CSP の制約は uuid-in-package: URL
ではなく
バンドルのURLに対して評価される。詳細は #651 を参照。
6. アルゴリズム
6.1. 構文解析
ウェブバンドル文字列をパースするために、文字列 sourceText と URL baseURL を与えられたとき:
-
parsed を JSON を Infra 値へパースした結果にする。引数は sourceText。
-
もし parsed が map でなければ、 トップレベルの値は JSON オブジェクトでなければならないことを示す
TypeErrorを送出する。 -
source を、パースした parsed["
source"] と、base URL として baseURL を用いて得た結果とする。 -
もし source が null なら、
TypeErrorを送出する。 -
credentials を "
same-origin" にする。 -
もし parsed["
credentials"] が 存在すれば:-
もし parsed["
credentials"] が "omit" なら、credentials を "omit" に設定する。 -
それ以外で、parsed["
credentials"] が "include" なら、credentials を "include" に設定する。
-
-
resources を空の リストとする。
-
もし parsed["
resources"] が 存在すれば:-
resources を、URL リストをパースするの parsed["
resources"] と source を引数にした結果に設定する。
-
scopes を空の リストとする。
-
もし parsed["
scopes"] が 存在すれば:-
scopes を、URL リストをパースするの parsed["
scopes"] と source を引数にした結果に設定する。
-
もし parsed の キーが "
source"、"credentials"、"resources"、"scopes" 以外を 含む場合、 ウェブバンドル文字列に不正なトップレベルキーが存在したことを コンソールに警告する。注: これはタイポ検出の助けになります。これはエラーではなく、将来の拡張を後方互換で追加できるようにするためです。
-
web bundle parse result を返す。source は source、credentials は credentials、rule は rule。
URLリストの解析は、 リスト originalList、および URL baseURL を与えて実行する:
-
parsed URL list を空の リストとする。
-
各 originalList の item について、
-
item が 文字列なら、
-
URL を パース(item, baseURL)した結果とする。
-
URL が nullでなければ、parsed URL list に append する。
-
-
-
parsed URL list を返す。
6.2. ウェブバンドルの取得
ウェブバンドルの取得は、ウェブバンドルフェッチエントリ fetch entry と fetch params fetch params を受けて実行する:
-
アサーション:fetch entry の state は "fetching"。
-
request を fetch params の request とする。
-
request の url を fetch entry の source に設定する。
注意: source URL は document の base URL で解決される。
-
request の destination を "webbundle" に設定。
-
request の mode を "cors" に設定。
-
request の credentials mode を fetch entry の credentials に設定。
-
request の service-workers mode を "
none" に設定。 -
ヘッダー ("Accept", "application/webbundle;v=b2") の組を request の header list に追加する。
注意:最終的な [draft-ietf-wpack-bundled-responses-latest] ではバージョン
1を使う予定だが、この仕様はブラウザが実装しているドラフト版に合わせている。 -
Fetch を request に対し processResponse アルゴリズム(ウェブバンドルレスポンス処理 を fetch entry で部分適用したもの)で呼び出す。
注意: Chromiumの現実装ではネストされたバンドルは許可されず、ウェブバンドルは他のウェブバンドルからフェッチされることはない。
6.3. ウェブバンドルレスポンス処理
ウェブバンドルレスポンス処理は、 ウェブバンドルフェッチエントリ fetch entry と response response を受けて実行する:
-
response の status が ok status の場合、
-
response の body を [draft-ietf-wpack-bundled-responses-latest] に従いウェブバンドルとしてパースする。
注意: response の body はこの時点で完全には利用できない場合がある。 UA はサブリソースを早く提供するために 非同期で断片的に読むことで bundle を解析することがある。
注意: 現状の Chromium 実装のパースでは web bundle フォーマットのバージョンは "b2" のみ受け付ける。
-
パースアルゴリズムが非同期で完了したとき、fetch entry の fetched bundle にパース結果を設定し、 fetch entry の state を "fetched"にする。もしパース失敗や他の準拠違反があれば fetched bundle を null、state を "failed"にする。
-
-
それ以外なら fetch entry の state を "failed"にする。
6.4. ウェブバンドルからのサブリソースの取得
ウェブバンドルからサブリソースの取得は、 request httpRequest を受け取って行う:
-
registration を find a matching web bundle registration に httpRequest を与えた結果とする。
-
registration が null でなければ:
-
response を get response from web bundle fetch entryに httpRequest の url と registration の fetch entry を与えた結果とする。
-
response が null なら ネットワークエラー を返す。
注意: この場合、ブラウザはサブリソースをネットワークからフェッチするフォールバックを行わない。
-
それ以外であれば response を返す。
-
-
null を返す。
注意: ここでnullを返すとHTTPキャッシュや通常のネットワークフェッチへのフォールバックが可能となる。上記のネットワークエラーとは区別される。
get response from web bundle fetch entryは、 url url と ウェブバンドルフェッチエントリ fetch entry を受けて行う:
-
fetch entry の state が "fetching" なら、 state が "fetched" か "failed" になるまで非同期的にawaitする。
-
fetch entry の state が "failed" なら null を返す。
-
アサーション:fetch entry の fetched bundle はnullでない。
-
fetch entry の fetched bundle から url に該当するresponse を返す([draft-ietf-wpack-bundled-responses-latest])。url に該当する内容がなければnullを返す。
6.5. マッチする登録の探索
find a matching web bundle registrationは、 request httpRequest を受け取って呼び出す:
-
url を httpRequest の urlとする。
-
httpRequest の client の ウェブバンドル登録リスト の各 registration について:
-
rule を registration の rule とする。
-
url の scheme が "
uuid-in-package" でない場合、-
url の origin と registration の fetch entry の source の origin が same origin でなければ continue。
-
allowed path を registration の fetch entry の source の path を shorten した結果とする。
-
-
url が rule の scopes のいずれかで始まるなら registration を返す。
-
-
null を返す。