Vercel、
中身どうなってるの?
続編。

今回は「もう少し深く」。
Anycast / Cold Start / ISR って何?
VOL.2 / 少し深掘り

Vol.1 で 5 ステップ を辿りました

git push → Webhook → ビルド → 配布 → DNS切替 → 公開、までの流れを追いました。
でも、その中で「あとで詳しく」と言って飛ばした言葉が3つありました。
— CH.01
Anycast
同じURLなのに、なんでみんな最寄りの拠点に繋がるの?
— CH.02
Cold Start
Serverless の「最初だけ遅い」って何?
— CH.03
ISR
Vercel の "賢いキャッシュ" って、どう動いてる?
今日はこの 3 つを、自分の理解できた範囲で説明してみます。

1 リクエストが中で辿る道筋

Vercel に届いた 1 つのリクエストは、こんな順番で内部を通り抜けて、レスポンスになって戻ります。今日話す Anycast / Cold Start / ISR は、この図のどの部分の話か を意識すると分かりやすいです。
VERCEL EDGE NETWORK User Request STEP 01 Firewall DDoS / WAF STEP 02 Routing 最寄り PoP へ振り分け STEP 03 Edge Cache HITなら即返却 CACHE HIT → 即レスポンス MISS STEP 04 Vercel Functions App Router API Routes 動的処理 / SSR / DB アクセス (Edge or Serverless) DB等 CACHE MISS → 動的処理 → レスポンス
今日話す Anycast = Routing の中身、Cold Start = Functions 起動時、ISR = Edge Cache の戦略。それぞれこの図のどこか、を意識してみてください。
— CHAPTER 01 / 03

Anycast

同じ住所、なのに違う建物に着く
素朴な疑問
東京の人もNYの人も、同じ mysite.com を打ってるのに、なぜ違う場所に繋がるの?

「同じ IP アドレスを 世界中の複数の場所で広告する」というネットワークの技。これを Anycast といいます。

普通の通信(Unicast)は「1つの IP = 1つの場所」ですが、Anycast は「1つの IP = 複数の場所」。ネットワーク側が 最も近い場所を勝手に選んでくれます。

仕組み的にはインターネットのルーティングプロトコル(BGP)を使っていて、「私はこのIPを持ってます」を世界中のルーターに知らせている、らしいです。

Unicast (普通):
[ User ] ──→ 203.0.113.5[ Server 1 つ ]


Anycast (これ):
                  ┌→ PoP Tokyo
[ User Tokyo ] ──→ 203.0.113.5
                  └→ PoP NY
                     PoP London
                     PoP Sydney同じ IP を世界中で広告
→ ネットワーク側が最寄りを選ぶ
TERM
Anycast
同じIPを複数の場所で広告するルーティング方式。ユーザーは「最も近い拠点」に自動で繋がる。BGP(経路情報を交換するプロトコル)が裏で動いている。
— CHAPTER 01 (続き)

Anycast が 勝手にやってくれること

障害時の自動迂回もここで効く
Anycast の嬉しいところは「速さ」だけじゃなくて、障害時の自動回復もあるらしいです。
— もし Unicast だったら
1拠点が落ちると終わり
  • 東京拠点がダウン → 東京のユーザー全滅
  • 復旧するまで誰もアクセスできない
  • DNS で切り替える → 反映に時間がかかる
— Anycast なら
勝手に次の拠点へ
  • 東京拠点がダウン → ネットワークが検知
  • 東京のユーザー → 自動で大阪 or ソウルへ
  • 切替は数秒〜分のオーダー (BGP収束時間)
障害発生!
                  ┌→ PoP Tokyo [ダウン]
[ Tokyo User ] ──→                  ↓ 自動迂回
                  └→ PoP Osaka  (代替)

※ ユーザーは何もしてない、URL も変えてない
— CHAPTER 02 / 03

Cold Start

Serverless の「最初だけ遅い」問題
素朴な疑問
「Serverless は速い」って聞くのに、「Cold Start が遅い」とも聞くのは何故…?

Serverless は リクエストが来た瞬間に関数を起動する ので、しばらく呼ばれてないと 関数が眠った状態 になります。

その状態で次のリクエストが来ると、まず 関数を起こす(コンテナを準備、コードを読み込む、依存関係をロード) 必要があって、これに時間がかかる。これが Cold Start。

1回起きたあとは 暖まった状態 (Warm) でしばらく残るので、2回目以降は速い。だから「最初だけ遅い」現象が起きる、と理解しました。

[ 初回: Cold Start ]
Request → 起動準備 → 実行 → レスポンス
          ~数百ms〜数秒

   ・コンテナの作成
   ・コードのダウンロード
   ・依存関係のロード
   ・初期化処理

[ 2回目以降: Warm Start ]
Request → 実行 → レスポンス
          ~数ms〜数十ms

   ※ 暖まった関数を再利用
TERM
Cold Start / Warm Start
関数を新規起動する時のオーバーヘッドが Cold Start、既に起動済みの関数を再利用するのが Warm Start。Cold Start を減らす工夫が Serverless 設計の腕の見せどころ。
— CHAPTER 02 (続き)

Cold Start を 減らす工夫

Vercel が Edge Function を推す理由
Vercel には Serverless FunctionEdge Function という2種類があって、Cold Start の重さがかなり違うらしいです。
— SERVERLESS FUNCTION
Node.js を丸ごと起動
  • 裏で動いてるのは AWS Lambda
  • Node.js の VM を立ち上げる必要がある
  • Cold Start: 数百 ms 〜 数秒
  • でも普通の Node.js コードが書ける(強み)
vs
— EDGE FUNCTION
V8 だけを起動
  • 裏は V8 Isolates (Cloudflare Workers 系)
  • Node.js は起動しない、JS エンジンだけ
  • Cold Start: ~5 ms 以下
  • ただし使える API に制限あり
Serverless:           Edge:
┌────────────┐         ┌────────────┐
│ Node.js    │         │ V8 Isolate │
│ ├ V8       │   vs    │ (軽量サンドボックス)│
│ ├ npm modules│       └────────────┘
│ └ Linux env│
└────────────┘         Cold Start ~5ms
Cold Start 数百ms+
※ V8 Isolates の話は Vol.3 で詳しくやります。「なんでこんなに速いの?」のカラクリ部分。
— CHAPTER 03 / 03

ISR

Incremental Static Regeneration
素朴な疑問
CDN に置いた静的ファイル、更新したいときどうするの?毎回ビルドし直し?

そこを解決するのが ISR。普段は CDN のキャッシュを返して速い、でも 裏でこっそり最新版を作って差し替える という仕組み。

例えるなら「お店で前に作った料理(キャッシュ)を出しながら、裏で新しいのを作っている」みたいな。ユーザーは待たない、でも次回には新しいのが届く。

これは stale-while-revalidate というキャッシュ戦略を Vercel が実装したもの。HTTPのキャッシュ仕様にもある考え方らしいです。

[ 1回目のアクセス ]
User → 古いキャッシュ → 表示 (速い)裏で新版を生成中…
        ↓
       新版をキャッシュに上書き

[ 2回目のアクセス ]
User → 新しいキャッシュ → 表示

※ 誰も待たされない
※ でも徐々に最新版に切り替わる
TERM
stale-while-revalidate
「古いやつを返しつつ、裏で更新する」キャッシュ戦略。表示速度と鮮度を両立する設計パターン。HTTPヘッダーにも標準的に存在する。
— CHAPTER 03 (続き)

ISR の 2 種類の更新

時間で更新 / イベントで更新
ISR には更新トリガーが 2 種類あるみたい。状況によって使い分けるみたいです。
— PATTERN A
時間ベース
(Time-based)

「60秒に1回は更新して」のように、一定間隔で勝手に再生成する方式。

ニュースサイト、ブログのトップページなど、大体これくらいの頻度で更新したいものに使う。Next.js なら revalidate: 60 みたいに指定。

— PATTERN B
オンデマンド
(On-demand)

「CMS で記事が公開されたら更新して」のように、特定のイベントが起きたら再生成する方式。

ヘッドレス CMS との連携で Webhook 経由で叩く。記事公開・商品追加など 更新タイミングが予測できないものに向く。

どちらも 「ビルドし直さない」のがキモ。1万ページあっても、更新したいページだけピンポイントで作り直せる。

少し深掘りで、
3 つの仕組みが見えました

— CH.01
Anycast
同じ IP を世界中で広告して、ネットワーク側が最寄り拠点を選んでくれる。障害時の自動迂回もここで効いてた。
— CH.02
Cold Start
Serverless は「眠った関数を起こす」のに時間がかかる。Vercel の Edge Function は V8 Isolates でこれを大幅に短縮。
— CH.03
ISR
"古いやつ出しつつ裏で更新"の戦略。時間ベースとオンデマンドの2種類でビルドし直さずに更新できる。
— 次回予告 / VOL.3
最後は一番深く掘ります:
V8 Isolates って何? Firecracker との違いは? Edge Runtime の制約はどこから来てる?

もっと知りたい人向け リンク集

今日話した Anycast / Cold Start / ISR について、自分が裏取りに使ったソースです。Cloudflare のドキュメントが Anycast の説明として一番分かりやすかったです。
VERCEL OFFICIAL BLOG
Life of a Vercel request
vercel.com/blog/life-of-a-vercel-request-navigating-the-edge-network
Anycast Routing、PoP からエッジリージョンへのルーティング、フェイルオーバーの全体像
CLOUDFLARE ★Anycast 解説
What is Anycast?
cloudflare.com/learning/cdn/glossary/anycast-network
Anycast の仕組みと Unicast との違い。BGP を使った経路広告の話
VERCEL DOCS
ISR (Incremental Static Regeneration)
vercel.com/docs/incremental-static-regeneration
時間ベース / オンデマンド両方の更新トリガー、stale-while-revalidate の挙動
RFC / MDN
stale-while-revalidate (RFC 5861)
developer.mozilla.org/docs/Web/HTTP/Headers/Cache-Control
「古いの返しつつ裏で更新」キャッシュ戦略の HTTP 標準仕様
AWS BLOG
Cold Start (AWS Lambda)
aws.amazon.com/blogs/compute/operating-lambda-performance-optimization
Lambda の Cold Start の中身。Vercel Serverless Function の挙動の根拠
VERCEL DOCS
Edge Runtime の仕様
vercel.com/docs/functions/runtimes/edge
V8 Isolate ベースのランタイム制約、PoP デプロイ、利用可能 API

「便利」の裏には
古典的なネットワーク技術
賢いキャッシュ戦略
あった。

Anycast も stale-while-revalidate も、
実は Vercel が発明したものじゃない。組み合わせと完成度がすごい。
VOL.2 / END.
1 / 11