1. はじめに
このセクションは規範的ではありません。
ロックリクエストは、スクリプトによって特定のリソース名とモードで行われます。スケジューリングアルゴリズムは現在および過去のリクエストの状態を調べ、最終的にロックリクエストを許可します。ロックは許可されたリクエストであり、リソース名とモードを持ちます。これはスクリプトに返されるオブジェクトとして表現されます。ロックが保持されている間は、(名前やモードによって)他のロックリクエストが許可されなくなる場合があります。ロックはスクリプトによって解放でき、その時点で他のロックリクエストが許可される可能性があります。
APIは必要に応じて利用できる追加機能を提供します。例:
-
非同期タスクから値を返すこと、
-
共有・排他ロックモード、
-
条件付き取得、
-
ロック状態のクエリ診断、
-
デッドロック対策のためのエスケープ手段。
協調的な調整は、agentが同じstorage bucketを共有する範囲内で行われます。これは複数のagent clusterにまたがる場合もあります。
注: agentはウィンドウ(タブ)、iframe、workerなどに概ね対応します。agent clusterは、一部のユーザーエージェント実装では独立したプロセスに対応します。
1.1. 利用概要
APIの使用方法は以下の通りです:
-
ロックを要求する。
-
ロックを保持した非同期タスクで作業を行う。
-
タスク完了時にロックが自動的に解放される。
API利用の基本例は以下のとおりです:
navigator. locks. request( 'my_resource' , async lock=> { // ロックを取得しました。 await do_something(); await do_something_else(); // ここでロックが解放されます。 });
非同期関数内では、リクエスト自体を await することも可能です:
// ロックを要求する前。 await navigator. locks. request( 'my_resource' , async lock=> { // ロックを取得しました。 await do_something(); // ここでロックが解放されます。 }); // ロックが解放された後
1.2. 動機となるユースケース
ウェブベースの文書編集ツールは、高速なアクセスのために状態をメモリ上に保存し、変更を(記録の一連として)Indexed Database APIなどのストレージAPIへ永続化して回復性とオフライン利用を実現し、さらにサーバーへも保存してデバイス間同期も可能にします。同じ文書を2つのタブで編集する場合、どちらか一方だけが変更や同期を行えるように、タブ間で作業を調整する必要があります。これは、どちらのタブが実際に変更(およびストレージAPIとの同期)を行うか調整し、アクティブなタブが消失(遷移、閉じる、クラッシュ)した際に他のタブがアクティブになる仕組みが必要です。
データ同期サービスでは「プライマリタブ」が指定され、このタブだけが特定の操作(ネットワーク同期、キュー済みデータのクリーンアップ等)を実行します。プライマリタブはロックを保持し続け、他のタブがロック取得を試みるとキューされます。プライマリタブがクラッシュや閉じられた場合、他のタブがロックを取得し新しいプライマリとなります。
Indexed Database APIは、オリジン内の複数の名前付きストレージパーティション間で共有読み取り・排他書き込みアクセスを可能にするトランザクションモデルを定義しています。この概念をプリミティブとして公開することで、Web Platformの任意の活動をリソース可用性に基づいてスケジューリングできるようになります。例えば、他のストレージタイプ(Cache [Service-Workers])やストレージ種別をまたいだトランザクションの構成、さらには非ストレージAPI(例:ネットワークフェッチ)を組み合わせることも可能になります。
2. 概念
この仕様の目的上:
-
ブラウザ内の別々のユーザープロファイルは、別々のユーザーエージェントとみなされます。
-
すべてのプライベートモードの閲覧セッションは、別々のユーザーエージェントとみなされます。
ユーザーエージェントは、ロックタスクキューを持ちます。これは新しい並列キューを開始した結果です。
以下のタスクソースは、enqueuedされた手順のためのweb locks tasks sourceです。
2.1. リソース名
リソース名は、ウェブアプリケーションが抽象的なリソースを表すために選択するJavaScript文字列です。
リソース名はスケジューリングアルゴリズム以外に外部的な意味はなく、agentが同じstorage bucketを共有している範囲でグローバルです。ウェブアプリケーションは自由に任意のリソース命名スキームを利用できます。
encodeURIComponent( db_name) + '/' + encodeURIComponent( store_name)
U+002D HYPHEN-MINUS (-)で始まるリソース名は予約されています。これらをリクエストすると例外が発生します。
2.2. ロックマネージャー
ロックマネージャーは、ロックとロックリクエストの状態をカプセル化します。各storage bucketには、Web Locks API用の関連storage bottleを通じて、1つのロックマネージャーが含まれます。
注: 同じユーザーエージェント内で開かれたロックマネージャーは、storage bucketを共有するページやワーカー(agent)間で共有されます。たとえそれらが無関係な閲覧コンテキストであってもです。
-
mapを、ローカルストレージボトルマップを取得した結果(environmentと"
web-locks
"を指定)とする。 -
mapが失敗なら、失敗を返す。
-
bottleをmapの関連storage bottleとする。
-
bottleの関連ロックマネージャーを返す。
[Storage]との統合方法(与えられた環境からロックマネージャーを適切に取得する方法を含む)をここでさらに詳しく記述すること。
2.3. モードとスケジューリング
モードは "exclusive
"
または "shared
"
のいずれかです。モードは典型的なリーダ-ライターロックパターンのモデル化に利用できます。"exclusive
"ロックが保持されている場合、その名前の他のロックは許可されません。"shared
"ロックが保持されている場合は、同じ名前の他の"shared
"ロックは許可されますが、"exclusive
"ロックは許可されません。APIのデフォルトモードは"exclusive
"です。
タイムアウト、公平性など、追加のプロパティがスケジューリングに影響を与える場合があります。
2.4. ロック
ロックは共有リソースへの排他的なアクセスを表します。
ロックは、clientId(不透明な文字列)を持ちます。
ロックは、mode("exclusive
"または"shared
")を持ちます。
ロックは、waiting promise(Promise)を持ちます。
ロックは、released promise(Promise)を持ちます。
-
ロックが許可された際にコールバックによって暗黙的または明示的に提供されるPromiseで、ロックが保持される期間を決定します。このPromiseがsettle(完了)するとロックが解放されます。これがロックのwaiting promiseです。
-
LockManager
のrequest()
メソッドから返されるPromiseで、ロックが解放されるかリクエストが中止されるとsettleします。これがロックのreleased promiseです。
const p1= navigator. locks. request( 'resource' , lock=> { const p2= new Promise( r=> { // ロックを使用するロジック、およびPromiseを解決… }); return p2; });
上記の例では、p1
がreleased promiseであり、p2
がwaiting promiseです。
多くの場合、コールバックはasync
関数として実装され、返されるPromiseは暗黙的となります。以下の例のようになります:
const p1= navigator. locks. request( 'resource' , async lock=> { // ロックを使用するロジック… });
上記コードではwaiting
promiseは名前付きで示されていませんが、匿名のasync
コールバックの戻り値として存在します。コールバックがasync
でなく非Promise値を返す場合、その値は即座に解決されるPromiseでラップされます。ロックは次のマイクロタスクで解放され、released promiseも次のマイクロタスクで解決されます。
各ロックマネージャーは、保持ロック集合(set of ロック)を持ちます。
lock lockのwaiting promiseがsettle(fulfillまたはreject)した時、以下の手順をロックタスクキューにenqueueします:
-
ロック lockを解放する。
-
resolve lockのreleased promise(lockのwaiting promiseで)を解決する。
2.5. ロックリクエスト
ロックリクエストは、ロックに対する保留中のリクエストを表します。
ロックリクエストキューは、キューであり、ロックリクエストの集合です。
各ロックマネージャは、ロックリクエストキューマップを持ちます。これは、マップであり、リソース名からロックリクエストキューへの対応関係です。
ロックリクエストキューを取得するには、ロックリクエストキューマップ queueMap から リソース名 name を使って、以下の手順を実行します:
-
もし queueMap[name] が 存在しない場合、新しく空の ロックリクエストキューを queueMap[name] に設定します。
-
queueMap[name] を返します。
ロックリクエスト requestがgrantable(付与可能)とされるのは、以下の手順が true を返す場合です:
-
manager を request の manager とします。
-
queueMap を manager の ロックリクエストキューマップ とします。
-
name を request の name とします。
-
queue を ロックリクエストキューを取得する結果として queueMap から name で取得します。
-
held を manager の 保持中ロック集合とします。
-
mode を request の mode とします。
-
もし mode が "
exclusive
" なら、held 内のいずれの ロックも name が name と等しくなければ true、そうでなければ false を返します。 -
それ以外の場合、mode は "
shared
" です。held 内のいずれの ロックも mode が "exclusive
" かつ name が name と等しくなければ true、そうでなければ false を返します。
2.6. ロックの終了
ドキュメントのアンロードクリーンアップ手順がdocumentで実行されるとき、残りのロックとリクエストを終了するをそのagentで実行します。
agentが終了するとき、残りのロックとリクエストを終了するをその agent で実行します。
これは現在ワーカーのみを対象としており、ワーカー終了時に手順を実行する規範的な方法がないため、定義が曖昧です。
残りのロックとリクエストを終了するには agent を使い、以下の手順をロックタスクキューにエンキューします:
3. API
3.1. Navigatorミックスイン
[SecureContext ]interface mixin {
NavigatorLocks readonly attribute LockManager locks ; };Navigator includes NavigatorLocks ;WorkerNavigator includes NavigatorLocks ;
各環境設定オブジェクトは、LockManager
オブジェクトを持ちます。
locks
ゲッターの手順は、thisの関連設定オブジェクトのLockManager
オブジェクトを返すことです。
3.2. LockManager
クラス
[SecureContext ,Exposed =(Window ,Worker )]interface {
LockManager Promise <any >request (DOMString ,
name LockGrantedCallback );
callback Promise <any >request (DOMString ,
name LockOptions ,
options LockGrantedCallback );
callback Promise <LockManagerSnapshot >query (); };callback =
LockGrantedCallback Promise <any > (Lock ?);
lock enum {
LockMode ,
"shared" };
"exclusive" dictionary {
LockOptions LockMode = "exclusive";
mode boolean =
ifAvailable false ;boolean =
steal false ;AbortSignal ; };
signal dictionary {
LockManagerSnapshot sequence <LockInfo >;
held sequence <LockInfo >; };
pending dictionary {
LockInfo DOMString ;
name LockMode ;
mode DOMString ; };
clientId
LockManager
インスタンスは、スクリプトがロックリクエストを行い、
ロックマネージャの状態を問い合わせることを可能にします。
3.2.1.
request()
メソッド
- promise = navigator . locks .
request
(name, callback)- promise = navigator . locks .
request
(name, options, callback) - promise = navigator . locks .
-
request()
メソッドはロックを要求するために呼び出されます。name(最初の引数)はリソース名の文字列です。
callback(最後の引数)は、コールバック関数であり、
Lock
が付与されたときに呼び出されます。これはスクリプトで指定され、通常はasync
関数です。ロックはコールバック関数が完了するまで保持されます。非async関数が渡された場合は、自動的に即座に解決されるPromiseでラップされるため、ロックは同期コールバックの実行中のみ保持されます。
返されるpromiseは、ロックが解放された後にコールバックの結果で解決(または拒否)されるか、リクエストが中止された場合は拒否されます。
例:
try { const result= await navigator. locks. request( 'resource' , async lock=> { // ロックがここで保持されます。 await do_something(); await do_something_else(); return "ok" ; // ロックはここで解放されます。 }); // |result| にはコールバックの戻り値が入ります。 } catch ( ex) { // コールバックが例外を投げた場合、ここで捕捉されます。 }
コールバックが何らかの理由で終了すると、ロックは解放されます ― 戻り値が返された場合も、例外が投げられた場合も同様です。
options辞書を2番目の引数として指定できます。callback引数は常に最後です。
- options . mode
-
mode
オプションは "exclusive
"(指定しない場合のデフォルト)または "shared
" です。 複数のタブやワーカーが "shared
" モードで同じリソースのロックを保持できますが、"exclusive
" モードでは1つのタブ/ワーカーのみがロックを保持できます。最も一般的な用途は、複数のリーダーが同時にリソースへアクセスできるようにし、変更を防ぐことです。 リーダーロックが解放された後、単一の排他的ライターがロックを取得して変更を行い、その後再び排他的ライターや複数の共有リーダーが取得できます。
await navigator. locks. request( 'resource' , { mode: 'shared' }, async lock=> { // ロックがここで保持されます。他のコンテキストも共有モードでロックを保持している可能性がありますが、排他モードでは他のコンテキストは保持しません。 });
- options . ifAvailable
-
ifAvailable
オプションがtrue
の場合、追加の待機なしでロックが付与できる場合のみ付与されます。これは同期ではなく、多くのユーザーエージェントではロックが付与できるかどうかを確認するためにプロセス間通信が必要です。ロックが付与できない場合、コールバックはnull
で呼び出されます。(これは想定されるため、リクエストは拒否されません。)
await navigator. locks. request( 'resource' , { ifAvailable: true }, async lock=> { if ( ! lock) { // 取得できませんでした。適切な処理を行うことができます。 return ; } // ロックがここで保持されます。 });
- options . signal
-
signal
オプションにはAbortSignal
を設定できます。 これにより、例えばリクエストがタイムリーに付与されない場合にロックリクエストを中止できます:
const controller= new AbortController(); setTimeout(() => controller. abort(), 200 ); // 最大200ms待機 try { await navigator. locks. request( 'resource' , { signal: controller. signal}, async lock=> { // ロックがここで保持されます。 }); // ロックの利用が完了しました。 } catch ( ex) { // |ex| はタイマーが発火した場合 "AbortError" のエラー名を持つ DOMException になります。 }
ロックが付与される前に中止が通知された場合、リクエストのPromiseは AbortError
で拒否されます。
ロックが付与された後は signal は無視されます。
- options . steal
-
steal
オプションがtrue
の場合、そのリソースに対して保持されているロックはすべて解放され(そのreleased promiseはAbortError
で解決されます)、 リクエストは付与され、キューされている他のリクエストより優先されます。Webアプリケーションが回復不能な状態を検出した場合 ― 例えば、Service Workerがロックを保持しているタブが応答しなくなったと判断した場合 ― このオプションでロックを「奪う」ことができます。
steal
オプションの使用には注意してください。
使用した場合、以前ロックを保持していたコードは、もはやリソースへの唯一のアクセス権が保証されない状態で実行されることになります。
同様に、このオプションを使用したコードも、他のコンテキストが抽象リソースへのアクセス権を持っているかのように実行されていない保証はありません。
これは、アプリケーションやユーザーエージェントの不具合など、すでに動作が予測できない状況で回復を試みる必要があるWebアプリケーション向けに設計されています。
request(name, callback)
および
request(name, options, callback)
メソッドの手順は以下の通りです:
-
optionsが渡されなかった場合、新しい
LockOptions
辞書(デフォルトメンバー付き)をoptionsとします。 -
environmentをthisの関連設定オブジェクトとします。
-
もしenvironmentの関連グローバルオブジェクトの関連付けられたDocumentが完全にアクティブでない場合、"
InvalidStateError
"DOMException
でPromiseを拒否して返します。 -
managerをロックマネージャを取得するでenvironmentを渡して得ます。失敗した場合は、"
SecurityError
"DOMException
でPromiseを拒否して返します。 -
もしnameがU+002D HYPHEN-MINUS(-)で始まる場合、"
NotSupportedError
"DOMException
でPromiseを拒否して返します。 -
もしoptions["
steal
"]とoptions["ifAvailable
"]が両方ともtrueの場合、"NotSupportedError
"DOMException
でPromiseを拒否して返します。 -
もしoptions["
steal
"]がtrueかつoptions["mode
"]が"exclusive
"でない場合、"NotSupportedError
"DOMException
でPromiseを拒否して返します。 -
もしoptions["
signal
"]が存在し、かつoptions["steal
"]またはoptions["ifAvailable
"]のいずれかがtrueの場合、"NotSupportedError
"DOMException
でPromiseを拒否して返します。 -
もしoptions["
signal
"]が存在し、かつ中止されている場合、options["signal
"]の中止理由でPromiseを拒否して返します。 -
promiseを新しいPromiseとします。
-
ロックをリクエストするをpromise、現在のagent、environmentのid、manager、callback、name、options["
mode
"]、options["ifAvailable
"]、options["steal
"]、options["signal
"]で実行します。 -
promiseを返します。
3.2.2.
query()
メソッド
- state = await navigator . locks .
query
() -
query()
メソッドは、オリジンのロックマネージャの状態のスナップショットを生成するために使用できます。これにより、Webアプリケーションはロックの利用状況を調査したり、ログやデバッグ目的で利用できます。返されるPromiseはstate(プレーンなデータ構造、つまりJSONライクなデータ)で解決され、以下の形式になります:
{ held: [ { name: "resource1" , mode: "exclusive" , clientId: "8b1e730c-7405-47db-9265-6ee7c73ac153" }, { name: "resource2" , mode: "shared" , clientId: "8b1e730c-7405-47db-9265-6ee7c73ac153" }, { name: "resource2" , mode: "shared" , clientId: "fad203a5-1f31-472b-a7f7-a3236a1f6d3b" }, ], pending: [ { name: "resource1" , mode: "exclusive" , clientId: "fad203a5-1f31-472b-a7f7-a3236a1f6d3b" }, { name: "resource1" , mode: "exclusive" , clientId: "d341a5d0-1d8d-4224-be10-704d1ef92a15" }, ] }
clientId
フィールドは一意なコンテキスト(フレームまたはワーカー)に対応し、Client
の
id
属性で返される値と同じです。
query()
メソッドの手順は以下の通りです:
-
environmentをthisの関連設定オブジェクトとします。
-
もしenvironmentの関連グローバルオブジェクトの関連付けられたDocumentが完全にアクティブでない場合、"
InvalidStateError
"DOMException
でPromiseを拒否して返します。 -
managerをロックマネージャを取得するでenvironmentを渡して得ます。失敗した場合は、"
SecurityError
"DOMException
でPromiseを拒否して返します。 -
promiseを新しいPromiseとします。
-
以下の手順をエンキューして、managerのロック状態のスナップショットをpromiseとともにロックタスクキューに追加します。
-
promiseを返します。
3.3. Lock
クラス
[SecureContext ,Exposed =(Window ,Worker )]interface {
Lock readonly attribute DOMString name ;readonly attribute LockMode mode ; };
name
ゲッターの手順は、関連付けられたロックのnameを返すことです。
mode
ゲッターの手順は、関連付けられたロックのmodeを返すことです。
4. アルゴリズム
4.1. ロックをリクエストする
-
requestを新しいロックリクエスト(agent, clientId, manager, name, mode, callback, promise, signal)とします。
-
signalが存在する場合、アルゴリズム signal to abort the request request をsignalに追加します。
-
-
queueMapをmanagerのロックリクエストキューマップとします。
-
queueをロックリクエストキューを取得するでqueueMapからnameで取得します。
-
heldをmanagerの保持中ロック集合とします。
-
stealがtrueの場合、以下の手順を実行します:
-
各 lock(heldの要素)について:
-
lockのnameがnameと等しい場合、以下の手順を実行します:
-
Reject lockのreleased promiseを"
AbortError
"DOMException
で拒否します。
-
-
Prepend requestをqueueに追加します。
-
-
それ以外の場合、以下の手順を実行します:
-
ifAvailableがtrueかつrequestがgrantableでない場合、以下の手順をcallbackの関連設定オブジェクトの責任イベントループにエンキューします:
-
rをコールバック関数を呼び出すで callbackに
null
のみを引数として渡した結果とします。 -
Resolve promiseをrで解決し、これらの手順を中止します。
-
-
Enqueue requestをqueueに追加します。
-
-
ロックリクエストキューを処理する queue。
-
-
requestを返します。
4.2. ロックを解放する
-
managerをlockのmanagerとします。
-
queueMapをmanagerのロックリクエストキューマップとします。
-
nameをlockのリソース名とします。
-
queueをロックリクエストキューを取得するでqueueMapからnameで取得します。
-
ロックリクエストキューを処理する queue。
4.3. リクエストを中止する
-
managerをrequestのmanagerとします。
-
nameをrequestのnameとします。
-
queueMapをmanagerのロックリクエストキューマップとします。
-
queueをロックリクエストキューを取得するでqueueMapからnameで取得します。
-
Remove requestをqueueから削除します。
-
ロックリクエストキューを処理する queue。
4.4. 指定されたリソース名のロックリクエストキューを処理する
-
各 request(queueの要素)について:
-
requestがgrantableでない場合、returnします。
NOTE: キュー内の最初の項目のみがgrantableです。したがって、grantableでない場合、以降の項目も自動的にgrantableではありません。
-
Remove requestをqueueから削除します。
-
agentをrequestのagentとします。
-
managerをrequestのmanagerとします。
-
clientIdをrequestのclientIdとします。
-
nameをrequestのnameとします。
-
modeをrequestのmodeとします。
-
callbackをrequestのcallbackとします。
-
pをrequestのpromiseとします。
-
signalをrequestのsignalとします。
-
waitingを新しいPromiseとします。
-
lockを新しいロック(agent agent, clientId clientId, manager manager, mode mode, name name, released promise p, waiting promise waiting)とします。
-
以下の手順をcallbackの関連設定オブジェクトの責任イベントループにエンキューします:
-
signalが存在する場合、以下の手順を実行します:
-
rをコールバック関数を呼び出すでcallbackに新しい
Lock
オブジェクト(lockに関連付け)を唯一の引数として渡した結果とします。 -
Resolve waitingをrで解決します。
-
-
4.5. ロック状態のスナップショット
保持中ロック状態のスナップショットについては順序保証はありません。
5. 利用上の注意
このセクションは規範的ではありません。
5.1. デッドロック
デッドロックは並行計算における概念であり、このAPIによって特定のロックマネージャにスコープされたデッドロックが発生する可能性があります。
スクリプト1:
navigator. locks. request( 'A' , async a=> { await navigator. locks. request( 'B' , async b=> { // AとBを使った処理 }); });
スクリプト2:
navigator. locks. request( 'B' , async b=> { await navigator. locks. request( 'A' , async a=> { // AとBを使った処理 }); });
スクリプト1とスクリプト2がほぼ同時に実行されると、スクリプト1がロックAを保持し、スクリプト2がロックBを保持し、どちらもそれ以上進行できなくなる(デッドロック)可能性があります。これはユーザーエージェント全体やタブの停止、同一オリジンの他のスクリプトには影響しませんが、この機能自体はブロックされます。
デッドロックを防ぐには注意が必要です。一つの方法は、複数のロックを必ず厳密な順序で取得することです。
以下のようなヘルパー関数を使うことで、複数のロックを一貫した順序でリクエストできます。
async function requestMultiple( resources, callback) { const sortedResources= [... resources]; sortedResources. sort(); // 必ず同じ順序でリクエストする。 async function requestNext( locks) { return await navigator. locks. request( sortedResources. shift(), async lock=> { // このロックと、これまでに取得したロックを保持している。 locks. push( lock); // 必要なら次のロックを再帰的にリクエスト。 if ( sortedResources. length> 0 ) return await requestNext( locks); // すべて取得したらコールバックを実行。 return await callback( locks); // コールバックが返る(またはthrow)と全ロックが解放される。 }); } return await requestNext([]); }
実際には、複数ロックの利用はそれほど単純ではなく、ライブラリや他のユーティリティが意図せず利用状況を複雑にすることがあります。
6. セキュリティとプライバシーに関する考慮事項
6.1. ロックスコープ
ロックマネージャのスコープ定義は、プライバシー境界を定めるため重要です。ロックは一時的な状態保持手段として使われるほか、ストレージAPI同様に通信手段としても使われ得るため、ストレージ機能以上の権限を持ってはなりません。ユーザーエージェントがこれらのサービスの一つに細かい粒度を課す場合、他のサービスにも同様の粒度を課す必要があります。例えば、プライバシーのために同一オリジン内でトップレベルページ(ファーストパーティ)とクロスオリジンiframe(サードパーティ)に異なるストレージパーティションを提供する場合、ロックも同様に分割しなければなりません。
これはWebアプリケーションの作者にとっても合理的な期待を与えます。ストレージリソースに対してロックを取得した場合、同一オリジンのすべての閲覧コンテキストが同じ状態を観測できなければなりません。
6.2. プライベートブラウジング
すべてのプライベートモードの閲覧セッションは、このAPIの目的上、別のユーザーエージェントとみなされます。つまり、そのようなセッション外でリクエスト・保持されたロックは、セッション内のリクエスト・保持に影響せず、逆も同様です。これにより、ウェブサイトがセッションが「シークレット」であるかを判定したり、セッション間で通信手段として使うことを防ぎます。
6.3. 実装上のリスク
実装では、ロックがオリジンをまたがらないことを保証しなければなりません。これを怠ると、2つのオリジンで動作するスクリプト間の通信のためのサイドチャネルが生じたり、一方のオリジンのスクリプトが他方の動作を妨害(例:サービス拒否)することが可能になります。
6.4. チェックリスト
W3C TAGは、仕様編集者が参考として回答できるセキュリティ・プライバシー自己レビュー質問票を作成しています。ここでの質問を再確認します:
-
この仕様は個人を特定できる情報や高価値データを扱いません。
-
オリジンに対してブラウジングセッションをまたいで永続する新しい状態は導入されません。
-
ウェブに新たな永続的・クロスオリジン状態は公開されません。
-
オリジンが現在アクセスできない新しいデータは公開されません(例:[IndexedDB-2]のポーリングなど)。
-
新しいスクリプト実行・ロード機構は有効化されません。
-
この仕様はオリジンに以下へのアクセスを許可しません:
-
ユーザーの位置情報
-
ユーザー端末のセンサー
-
ユーザーのローカル計算環境の側面
-
他のデバイスへのアクセス
-
ユーザーエージェントのネイティブUIへの制御
-
-
ウェブに一時的な識別子は公開されません。すべてのリソース名はウェブアプリケーション自身が指定します。
-
ストレージが区別される場合、ユーザーエージェント内でファーストパーティ・サードパーティの挙動も区別されます。§ 6.1 ロックスコープ参照。
-
ユーザーエージェントの「シークレット」モードでの挙動は§ 6.2 プライベートブラウジングで説明されています。
-
このAPIによってユーザーのローカル端末にデータが永続化されることはありません。
-
このAPIはデフォルトのセキュリティ特性を低下させることを許可しません。
7. 謝辞
この提案の作成に協力いただいた Alex Russell, Andreas Butler, Anne van Kesteren, Boris Zbarsky, Chris Messina, Darin Fisher, Domenic Denicola, Gus Caplan, Harald Alvestrand, Jake Archibald, Kagami Sascha Rosylight, L. David Baron, Luciano Pacheco, Marcos Caceres, Ralph Chelala, Raymond Toy, Ryan Fioravanti, そして Victor Costan に感謝します。
また、Bikeshed(本ドキュメント作成に使用した仕様作成ツール)を作成・管理し、執筆全般に助言いただいたTab Atkins, Jr.にも特別な謝意を表します。