Cloudflare Workers Cache: エッジキャッシュでサーバーレスオリジンを高速化

Cloudflare Workers Cache: エッジキャッシュでサーバーレスオリジンを高速化

Cloudflare は Workers Cache をリリースしました。これは Worker の直前に配置される階層型キャッシュシステムです。このアーキテクチャにより、Cloudflare は Worker を呼び出さずにキャッシュ済みレスポンスを提供でき、キャッシュヒット時の CPU 課金がなくなり、エンドユーザーのレイテンシが低減します。

アーキテクチャの変化: Worker がオリジンになる

従来、Cloudflare Workers はキャッシュとオリジンの 前に 位置していました。これはリクエスト変換、URL 書き換え、A/B テストなど、リクエストがキャッシュされたオリジンに到達する前に処理したいケースに最適でした。しかし、Astro、Next.js、Remix、SvelteKit などのモダンフレームワークが Worker を主なサーバー(オリジン)として利用するケースが増えるにつれ、以前のモデルでは同一レスポンスでも毎回 Worker が起動されていました。

Workers Cache はこのモデルを逆転させます。キャッシュを Worker の前に置くことで、Cloudflare はエッジから直接レスポンスを返せるようになりました。新鮮なキャッシュが存在すれば Worker は実行されず、CPU 時間は課金されません。キャッシュミス時には Worker が一度実行され、キャッシュが生成され、以降のリクエストはグローバルにキャッシュから提供されます。

主な技術的特徴

標準化された HTTP 制御

Workers Cache は wrangler.jsonc の 1 行設定で有効化でき、標準の HTTP ヘッダーで管理します:

  • Cache-Control: TTL(Time‑to‑Live)とキャッシュ動作を定義。
  • stale-while-revalidate: Cloudflare が古いレスポンスを即座に返しつつ、バックグラウンドでコンテンツを更新できるようにし、ユーザーが再描画を待つことがなくなります。
  • Vary: コンテンツネゴシエーションを有効化。Accept-LanguageAccept-Encoding など、指定したリクエストヘッダーに基づいて別々のキャッシュバリアントを保存し、各クライアントに適切な表現を提供します。
  • Cache-Tag: ctx.cache.purge() を使って特定コンテンツグループをプログラム的かつ細粒度に無効化できます。

リージョン別階層キャッシュ

キャッシュが有効なすべての Worker はデフォルトで 2 段階トポロジーを使用します:

  1. 下位層: ユーザーに最も近いデータセンターに配置。
  2. 上位層: 下位層を補完するリージョナル集約層。

この構造により、世界中のどこかで最初にリクエストが来たときに上位層が埋められ、フラットキャッシュに比べてネットワーク全体のキャッシュヒット率が大幅に向上します。

ctx.props によるマルチテナント安全性

認証済みやユーザー固有データを扱うため、Workers Cache は ctx.props と連携します。サービスバインディング経由で Worker が呼び出される際、ctx.props に渡された識別子(例: userIdtenantId)がキャッシュキーの一部となります。これによりユーザー間でデータが漏れないようにしつつ、認証済みレスポンスもエッジでキャッシュ可能です。

高度な構成パターン

Workers Cache はすべての Worker エントリーポイント(名前付き WorkerEntrypointctx.exports 呼び出しを含む)の前に位置するため、開発者はメモ化されたステージのチェーンとしてアプリケーションを構築できます:

  • ゲートウェイステージ: キャッシュ無効(デフォルト)で外部エントリーポイントを提供し、認証やリクエスト正規化を処理。
  • バックエンドステージ: キャッシュ有効で内部エントリーポイントを提供し、高コストなデータ取得やレンダリングを実行。

このパターンにより、セキュリティ確保のために「ゲートウェイ」はすべてのリクエストで必ず実行され、「バックエンド」はキャッシュミス時のみ実行されます。Durable Objects のラップや、トラッキングパラメータを除去して URL を正規化する前処理などにも拡張可能です。

課金と可観測性

課金モデル

キャッシュヒットは CPU 時間課金が発生しないためコスト削減につながりますが、標準の Workers リクエストレート料金は依然としてかかります。

結果 リクエスト課金 CPU 時間課金
Cache HIT 標準レート 課金なし
Cache MISS 標準レート 課金あり
Cache BYPASS 標準レート 課金あり

注: 従来は無料だったリクエスト(静的アセットや worker‑to‑worker 呼び出しなど)も、キャッシュが有効になると標準リクエストレートで課金されます。これはキャッシュ参照が必要になるためです。

可観測性

キャッシュのパフォーマンスは Workers Observability ダッシュボードに統合され、ヒット・ミス・更新(SWR)・バイパスの各インボケーションデータが表示されます。これにより開発者は max-agestale-while-revalidate 設定を調整しやすくなります。

コミュニティの声

技術実装は HTTP 標準への準拠が高く評価された一方で、課金変更に懸念を示す声もありました:

"静的アセットリクエストが課金対象になるんですか!全く意味が分かりません…バグでお金が増えるだけのように思えます。"

別の意見では、SSR パフォーマンスへのインパクトが強調されました:

"常に心配していたのは『なぜ Workers がキャッシュの前にあるのか?キャッシュ結果を返すだけなら無駄な呼び出しになる』という点でした。"

フレームワーク統合

Workers Cache は既に Astro の Cloudflare アダプタに cacheCloudflare プロバイダーとして組み込まれており、開発者は Astro 設定で routeRulesmaxAgeswr を直接記述できます。

Sources