このドキュメントでは、以前にプレキャッシュについて説明しましたが、それを正しく行う方法については十分に説明されていません。Workbox を使用するかどうかに関係なく、事前キャッシュが多すぎてデータと帯域幅が浪費されやすいため、このことは重要です。ペイロードのプリキャッシュがユーザー エクスペリエンスに及ぼす影響に注意する必要があります。
このドキュメントを読むことで、これらは一般的なガイドラインであることを理解できます。アプリケーションのアーキテクチャと要件によっては、ここで提案したものとは異なる処理を行う必要がある場合がありますが、これらのガイドラインは適切なデフォルトです。
推奨事項: 重要な静的アセットを事前キャッシュに保存する
プレキャッシュの最適な候補は重要な静的アセットですが、どれが「重要」と見なされます?デベロッパーの観点からは、アプリケーション全体を「重大」に考えたくなるかもしれませんが、最も重要なのはユーザーの視点です。重要なアセットとは、ユーザー エクスペリエンスを提供するために必要不可欠なアセットです。
- グローバル スタイルシート。
- グローバル機能を提供する JavaScript ファイル。
- アプリケーション シェルの HTML(アーキテクチャに適用する場合)。
注: これらは一般的なガイドラインであり、厳格な推奨事項ではありません。アセットをプレキャッシュする際は、プレキャッシュを増やすのではなく減らすことをおすすめします。
推奨事項: 複数ページのウェブサイトの場合、オフラインのフォールバックを事前キャッシュに保存する
一般的な複数ページのウェブサイトでは、ナビゲーション リクエストにネットワークファーストまたはネットワークのみのキャッシュ戦略を採用しているかもしれません。
このような場合は、ユーザーがオフラインのときにナビゲーション リクエストを行ったときに、Service Worker がオフラインのフォールバック ページを事前キャッシュに保存して応答するようにします。Workbox でこれを行う方法の 1 つは、ネットワークのみの戦略とオフライン フォールバックを使用することです。その際、ナビゲーションのプリロードも利用します。
import {PrecacheFallbackPlugin, precacheAndRoute} from 'workbox-precaching';
import {registerRoute, Route} from 'workbox-routing';
import {NetworkOnly} from 'workbox-strategies';
import * as navigationPreload from 'workbox-navigation-preload';
navigationPreload.enable();
// Ensure that /offline.html is part of your precache manifest!
precacheAndRoute(self.__WB_MANIFEST);
// The network-only callback should match navigation requests, and
// the handler for the route should use the network-only strategy, but
// fall back to a precached offline page in case the user is offline.
const networkOnlyNavigationRoute = new Route(({request}) => {
return request.mode === 'navigate';
}, new NetworkOnly({
plugins: [
new PrecacheFallbackPlugin({
fallbackURL: '/offline.html'
})
]
}));
registerRoute(networkOnlyNavigationRoute);
これにより、ユーザーがオフラインになってキャッシュにないページに移動した場合でも、少なくとも一部のオフライン コンテンツが提供されるようになります。
推奨: 投機的プレキャッシュを検討する
これは大きな「かもしれない」ただし、特定のシナリオでのみ使用されるアセットを事前キャッシュすると、潜在的なメリットを享受できます。次のように考えてください。ユーザーには事前のデータ ダウンロードが追加で発生しますが、それらのアセットに対する将来のリクエストを高速化できるという投機的メリットもあります。
ここで大きな注意点として、これを決心する場合は十分に注意してください。このようにするとデータが無駄になりやすいので、必ずデータドリブンな意思決定を行ってください。また、頻繁に変更されるアセットを投機的に事前キャッシュすることは避けてください。事前キャッシュ コードが新しいリビジョンを検出するたびに、ユーザーの追加のデータ使用量が発生するためです。アナリティクスのユーザーフローを観察して、ユーザーがどこにアクセスする傾向にあるかを確認します。アセットを投機的に事前キャッシュすることについて疑問がある場合は、そうしないほうがよいでしょう。
推奨しない: 静的 HTML を事前キャッシュする
このガイドラインは、アプリケーションのバックエンドによって動的に生成または提供されるのではなく、個別の HTML ファイルが静的サイト生成ツールによって生成されるか、または手動で作成される静的サイトに適用されます。これがご使用のアーキテクチャの場合は、ウェブサイトのすべての HTML ファイルをプリキャッシュしないのがおそらく最善でしょう。
サイト全体の HTML ファイルをプリキャッシュする際の問題の一つとして、この時点でプリキャッシュされたマークアップは、Service Worker が更新されるまで常にキャッシュから提供されるということがあります。これはパフォーマンスの向上には有効ですが、ウェブサイトの HTML が頻繁に変更されると、キャッシュのチャーンが大幅に発生する可能性があります。
ただし、このルールにはいくつかの例外があります。少数の静的 HTML ファイルを含む小規模なウェブサイトをデプロイする場合は、それらのページをオフラインで使用できるように事前にキャッシュしておくとよいでしょう。特に大規模なウェブサイトの場合は、価値の高い少数のページを予測的に事前キャッシュし、オフラインでの代替キャッシュを用意し、ランタイム キャッシュを使用して他のページをキャッシュに保存することを検討してください。
非推奨: レスポンシブ画像やファビコンを事前キャッシュに保存する
これは一般的なガイドラインというより、ルール的なものです。レスポンシブ画像は、多くのユーザーが多くのデバイスで画面のサイズ、ピクセル密度、サポートする代替形式が異なるという複雑な問題に対する複雑な解決策です。レスポンシブな画像セット全体を事前キャッシュした場合、ユーザーがそのうちの 1 つしかダウンロードしない可能性があるときに、複数の画像を事前キャッシュすることになるでしょう。
ファビコンも同じような状況で、ウェブサイトでは多くの場合、さまざまな状況でファビコン一式がデプロイされます。ほとんどの場合、リクエストされるファビコンは 1 つのみであるため、ファビコン セット全体の事前キャッシュも同様に無駄になります。
ユーザーの都合を考慮して、レスポンシブ画像やファビコン セットを事前キャッシュしないようにしてください。代わりにランタイム キャッシュを使用してください。画像を事前キャッシュに保存する必要がある場合は、レスポンシブ画像やファビコンの一部ではない、広く使用されている画像を事前キャッシュに保存します。SVG はデータ使用量の点でリスクが低く、特定の画面のピクセル密度に関係なく、1 つの SVG が最適にレンダリングされます。
非推奨: ポリフィルを事前キャッシュに保存する
ブラウザでの API のサポートの違いはウェブ デベロッパーにとって永続的な課題であり、ポリフィルはその実現方法の一つです。ポリフィルのパフォーマンス コストを最小限に抑える方法の一つは、機能チェックを行い、ポリフィルを必要とするブラウザでのみポリフィルを読み込むことです。
条件付きでポリフィルの読み込みは、現在の環境に対する実行時に行われるため、ポリフィルの事前キャッシュはギャンブルです。この機能が役立つユーザーもいれば、不要なポリフィルのために帯域幅を浪費してしまうユーザーもいます。
ポリフィルを事前キャッシュに保存しないでください。ランタイム キャッシュを使用することで、データが無駄にならないよう必要なブラウザでのみキャッシュされるようにします。
まとめ
プリキャッシュでは、ユーザーが実際にどのようなアセットを必要としているかを前もって考える必要がありますが、将来のパフォーマンスと信頼性を優先する方法で確実に正しく取得することができます。
特定のアセットを事前キャッシュする必要があるかどうかわからない場合は、それらのアセットを除外するように Workbox に指示し、それらのアセットを処理するランタイム キャッシュ ルートを作成することをおすすめします。いずれにしても、プリキャッシュの詳細についてはこのドキュメントの後半で説明しますので、将来的にこれらの原則をプリキャッシュ ロジックに適用できます。