Slide 1

Slide 1 text

Cloudflare Workersで動的コンテンツを キャッシュする際の新たな選択肢 KOITABASHI Yoshitaka 2023/8/24 yoshii0110 1

Slide 2

Slide 2 text

2023/8/24 yoshii0110 2 KOITABASHI Yoshitaka @yoshii0110 Momento - community advocate KDDIアジャイル開発センター – software engineer Amazon EC2, AWS Fargate, AWS App Runner 🥷 🏢 💕

Slide 3

Slide 3 text

静的コンテンツと動的コンテンツ • 静的なコンテンツを配信するwebページ ユーザが毎回閲覧する度に表示内容が変わらず同じものが配信 よくあるLPや個人ブログなども静的なコンテンツとして取り扱ってそう コンテンツ例: HTMLファイルや画像など • 動的なコンテンツを配信するwebページ あるページへアクセスするタイミング、ページの位置、デバイスなどの ユーザ固有の要因に基づいて変化するコンテンツを配信 技術記事プラットフォームなど、大量のユーザが記事を公開/閲覧を 行うサービスなどが該当 2023/8/24 yoshii0110 3

Slide 4

Slide 4 text

モダンなフロントエンドのページレンダリング • Reactive Web Application • Client Side Rendering (CSR) => CSRでできたアプリが、Sigle Page Application (SPA) – React, Vue, Angular とかとか • Server Side Rendering (SSR) – Next, Nuxt とかとか • Static Site Generator (SSG) Jamstackな仕組み, Gatsby, Hugo, Next, Nuxt とかとか • Incremental Static Regeneration (ISR) – Next (9.4で追加された機能) 2023/8/24 yoshii0110 4

Slide 5

Slide 5 text

SSR (Server Side Rendering) • リクエストに対して動的に生成されたHTMLを返却 • JavaScript、仮想DOMなどをサーバーサイドでも利用 • デメリットは、サーバーサイドの重さです。 API通信などを利用すると、レスポンスに時間がかかる 2023/8/24 yoshii0110 5

Slide 6

Slide 6 text

SSG (Static Site Generator) • リクエストに対して事前に生成されたHTMLを返却 • SSGではビルド時にHTMLを生成 • 配信は非常に高速だが、デプロイ後はページ内容を動的に変更できない 2023/8/24 yoshii0110 6

Slide 7

Slide 7 text

ISR (Incremental Static Regeneration) • リクエストに対して静的にビルドされたページを返す。 • 有効期限を超えたら非同期で静的ページの再生成をSSRで行う。 • キャッシュを活用しつつ、静的ページの更新を自動的に行え、一定時間後再度 リクエストがあった場合、次回以降の内容をビルドするので内容が更新される。 2023/8/24 yoshii0110 7

Slide 8

Slide 8 text

静的コンテンツのキャッシュ • 例えば、SSGで作成されたHTML, CSS, JS 画像などの 静的コンテンツを返却する応答時間を短くしたい場合に考える キャッシュ戦略として CDN(content delivery network) を使用する方法があります。 • CDNは、オリジンサーバーへのアクセス集中を防ぎ、地理的に 近いエッジロケーション(エッジサーバー)に誘導するイメージ。 • エッジロケーションは世界中に配置されており、 パブリッククラウドのリージョンにあるデータセンターよりも分散的に より多く設置されている。 2023/8/24 yoshii0110 8

Slide 9

Slide 9 text

CDNの標準的な使われ方 • よくあるのは、エッジロケーションはユーザーからの アクセスがあると、オリジンサーバを参照して次回以降の アクセスのためにコンテンツをキャッシュします。 • 次回以降のアクセスでは、キャッシュしたコンテンツを ユーザーに配信する 2023/8/24 yoshii0110 9

Slide 10

Slide 10 text

モダンなWebアプリケーションとCDN • 近年だと、先ほど紹介したページレンダリングの仕組みが たくさんある中で、ブラウザ側のjavascriptが行う仕事が増え、 jsファイルのサイズも大きくなってきています。 • SSGを使ったとしても、サイズが大きくなったHTML、javascriptをよ りユーザに早く届ける時にCDNが重要です。 • 最近だとCDNを意識しないで使えるサービスもあります。 • Vercel • AWS Amplify 2023/8/24 yoshii0110 10

Slide 11

Slide 11 text

動的コンテンツのキャッシュ • 例えば、SSR/ISRの様にその時々でアクセスする度にコンテンツが 変わったり、webアプリ上のコンテンツを何かしらのスクリプトや トリガーによって変更が走り生成されるパターンがあったりします。 • 動的コンテンツの配信について、ユーザへの応答時間を短縮するには、 ユーザにより遠くにあるオリジンサーバへ毎回アクセスするのではなく、 CDN上でスクリプトが実行できると嬉しいですよね? • これによって、動的コンテンツは”キャッシュされる“ので、クライアント からのリクエストへの応答時間が短縮され、動的コンテンツを扱う webアプリケーションが高速化されます。 2023/8/24 yoshii0110 11

Slide 12

Slide 12 text

CDNのエッジサーバでアプリケーション実行 • 近年だとCDNのエッジ上でjavascriptなどが実行できるサービスに人気が出てま す。 • なぜ、そんな話をしているのかというと、エッジでアプリケーションが実行できると、 動的コンテンツのキャッシュに作用してくるからです。 • ユーザ起因のイベント、web サーバ起因のイベントなどを基に動的コンテンツを生 成してクライアントに提供したり、静的コンテンツを変更、キャッシュの操作ができ る様になります。 • Cloudflare Workers • Vercel Edge Functions • AWS CloudFront Functions • AWS Lambda@Edge 2023/8/24 yoshii0110 12 引用: https://blog.cloudflare.com/eliminating-cold-starts-with-cloudflare-workers/

Slide 13

Slide 13 text

今回実現したいこと • Stale-While-Revalidate から着想された @yusukebe さんの “Dynamic Content Storing” を踏襲する • これをhonoとCloudflare Workers、momento cacheを利用して 実装していく 2023/8/24 yoshii0110 13 https://yusukebe.com/posts/2022/dcs/ https://datatracker.ietf.org/doc/html/rfc5861

Slide 14

Slide 14 text

キャッシュ戦略: Stale-While-Revalidate • web ではキャッシュの制御にHTTPヘッダを用いてブラウザやプロキシを コントロールする。 • Stale-While-Revalidate は、そんなヘッダでキャッシュ制御する仕組みです。 • よくキャッシュの指定でCache-Control,Expires,Etag,Last-Modifiedなどの ものを利用すると思う。 • Stale-While-Revalidateを利用すると動きとして、コンテンツは キャッシュから表示するが、裏で非同期にキャッシュを更新しておく ような動きになります。 2023/8/24 yoshii0110 14 https://docs.fastly.com/ja/guides/serving-stale-content https://datatracker.ietf.org/doc/html/rfc5861

Slide 15

Slide 15 text

Stale-While-Revalidateのフロー 2023/8/24 yoshii0110 15 https://blog.jxck.io/entries/2016-04-16/stale-while-revalidate.html 従来: max-age Stale-While-Revalidate

Slide 16

Slide 16 text

Cloudflare Workers / honoとは? • Cloudflare Workers • Cloudflareのサーバレスサービス • AWS Lambda や Google Cloud Functions などとは異なり、 CDNのエッジサーバーでコードを実行する • V8エンジンのisolateを使い、各リクエストに対して独立した実行環境を提供 • hono • エッジ用に開発された小さく、シンプルかつ超高速な Web フレームワーク • repo: https://github.com/honojs/hono • docs: https://hono.dev/ 2023/8/24 yoshii0110 16

Slide 17

Slide 17 text

Momento とは? • Momento とは、アプリケーションエンジニアにとって快適な世界を 作っていき、彼らによって生み出されたサービスをより早く、 よりセキュアに、より安定的に送り出す仕組みを提供する サーバレスサービスです。 • 機能として、現時点だと3つ ①: momento Cache ②: momento Topics (Pub/Sub) ③: momento Vector Index (AI / ML) 2023/8/24 yoshii0110 17 https://www.gomomento.com/

Slide 18

Slide 18 text

Momento chache を利用したキャッシュ戦略 2023/8/24 yoshii0110 18

Slide 19

Slide 19 text

Momento cache のシンプルさ 2023/8/24 yoshii0110 19

Slide 20

Slide 20 text

Momento chache を利用したキャッシュ戦略 – 基本の動作シーケンス図 2023/8/24 yoshii0110 20 ①: ユーザがあるwebページを 見たときに、Cloudflare workers はoriginではなく、momento cacheから動的コンテンツを取得 ②: momento cacheにコンテンツの キャッシュがなければ、originへ fetchする

Slide 21

Slide 21 text

Momento chache を利用したキャッシュ戦略 – キャッシュ細かい流れに注目したシーケンス図 2023/8/24 yoshii0110 21 前提として、momento cacheには 同じ動的コンテンツが2つキャッシュされている "fresh", "stale"というプレフィックスをつけたkeyで 同じレスポンスをキャッシュする “stale”の方のttlを 長めに設定 ①: まずは"fresh"というプレフィックスの keyでキャッシュしたvalueを返却 ②: "fresh"のキャッシュのTTLが切れたら、 "stale" の キャッシュを返し、 “fresh”はfetchし直したキャッシュと入れ替える

Slide 22

Slide 22 text

検証 2023/8/24 yoshii0110 22 TTLが切れていてもStaleが存在すれば fetchが実行され、 その後キャッシュする動きが見て取れる 検証repo: https://github.com/Yoshiitaka/momento-cloudflare-swr

Slide 23

Slide 23 text

キャッシュヒットとミスなどのメトリクスをコンソールより確認 2023/8/24 yoshii0110 23

Slide 24

Slide 24 text

Momento とCloudflareとの統合 • ブログ: https://www.gomomento.com/blog/momento-cache-is-now-accessible-at- the-edge • 公式ドキュメント: https://docs.momentohq.com/ja/develop/api-reference/http-api • 公式ドキュメント: https://docs.momentohq.com/ja/develop/integrations/cloudflare • サンプルコード: https://github.com/momentohq/client-sdk- javascript/tree/main/examples/cloudflare-workers 2023/8/24 yoshii0110 24

Slide 25

Slide 25 text

他のキャッシュとしての選択肢 • Cache API • KVストア • Upstash • etc… 2023/8/24 yoshii0110 25