SPAはなぜCore Web Vitalsで不利になりやすいのか

SPAはなぜCore Web Vitalsで不利になりやすいのか

シングルページアプリケーション(SPA)は、体感的には「速い」と感じる場面が多いのに、検索順位やSEO評価で不利になりやすいです。これは単なる印象論ではなく、Googleが評価に使っているCore Web Vitals(コアウェブバイタル)という指標の性質と、SPAの仕組みが根本的に噛み合っていないためです。

つまり、SPAが遅いのではありません。測られている“速さの種類”が違うのです。

ここを理解しないまま「SPAはSEOに弱い」とだけ覚えてしまうと、原因を誤解したまま対策をしてしまいます。

Core Web Vitalsとは何を測っているのか

Core Web Vitalsは、次の3つの指標で構成されています。

指標 内容 何を意味するか
LCP Largest Contentful Paint 最も大きな要素が表示されるまでの時間
FID(現在はINP) Interaction to Next Paint 操作に反応するまでの時間
CLS Cumulative Layout Shift 画面のガタつき

この中でも特にSPAが苦手とするのがLCPです。

LCPは「ユーザーが最初にページを開いたとき、主要コンテンツがどれだけ早く表示されるか」を測っています。ここが重要です。最初にページを開いた瞬間だけが評価対象なのです。

SPAはこの「最初」に弱い構造になっています。

SPAの初期表示で何が起きているか

通常のWebページ(MPA)では、ブラウザはHTMLを受け取った時点で表示を始めます。HTMLの中にテキストがあれば、CSSが揃う前でも文字が見え始めます。

しかしSPAでは違います。

SPAは最初、ほぼ空のHTMLを返します。

<!DOCTYPE html>
<html>
<head>
  <script src="/app.js"></script>
</head>
<body>
  <div id="app"></div>
</body>
</html>

画面の内容はすべてJavaScriptが実行されてから生成されます。つまり次の順番になります。

  • HTMLをダウンロード
  • JavaScriptをダウンロード
  • JavaScriptを実行
  • API通信
  • データ取得
  • DOM生成
  • 初めて表示

この間、ユーザーは「真っ白な画面」を見続けます。

この“何も表示されていない時間”が、LCPを極端に悪化させます。

「SPAは速い」は間違いではない

ここで混乱が起きます。

SPAは画面遷移が速いです。リンクを押した瞬間に画面が切り替わる体験は、確かに快適です。

ただしCore Web Vitalsが評価しているのは「初回表示」です。

  • 2ページ目以降 → SPAが有利
  • 初回表示 → SPAが不利

SEOは初回アクセスの品質を重視します。検索流入のユーザーは必ず「初回」だからです。

つまりGoogleの評価軸と、SPAの強みの軸がずれているのです。

LCPが悪化する本当の原因はAPI通信

多くの人が「JavaScriptが重いから遅い」と考えますが、本質はそこではありません。

問題はAPI通信です。

SPAでは、画面を描画するためにデータが必要です。そのためJavaScript実行後にAPIを呼びます。

fetch("/api/articles")
  .then(r => r.json())
  .then(data => render(data));

この通信が終わるまで、主要コンテンツは表示できません。つまりLCPは「サーバ応答時間 + JavaScript実行時間 + API応答時間」の合計になります。

MPAやSSRでは、サーバ側でデータ取得してHTMLを返すため、この待ち時間がユーザーから見えません。

なぜSSRがSEOで有利になるのか

SSR(Server Side Rendering)では、サーバがHTMLを完成させてから返します。

  • サーバがDB取得
  • HTML生成
  • ブラウザは即表示

ユーザーは「ページが表示された」と感じます。この時点でLCPが計測されます。JavaScriptの実行はその後です。

つまりSSRは、ユーザーの待ち時間を隠しているのではなく、待ち時間の場所を変えているのです。

SPAは「ブラウザ側で待つ」
SSRは「サーバ側で待つ」

Core Web Vitalsはブラウザ側の待ち時間を評価するため、SSRが有利になります。

CLSもSPAで悪化しやすい

SPAでは後からデータが入るため、レイアウトが変わります。

  • 読み込み中のカード
  • 画像サイズ未確定
  • フォントロード

これらによって表示がズレます。これがCLSです。

特にAPI取得後にリストが伸びるUIはCLSを悪化させやすいです。スケルトンスクリーンを使っても、サイズが一致していないと評価は改善しません。

よくある誤解:キャッシュすれば解決する?

CDNキャッシュは確かに重要ですが、SPAのLCP問題は完全には解決しません。

なぜならキャッシュできるのはJavaScriptファイルまでで、APIレスポンス待ちは消えないからです。

つまり「JS配信の速さ」と「コンテンツ表示の速さ」は別問題です。

実際に起きやすい失敗

SPAを導入した直後に起きやすい現象があります。

  • PageSpeed Insightsが急落
  • 検索順位が下がる
  • クロールはされているのに評価が上がらない

多くの場合、原因はJavaScriptのサイズではなく「最初のコンテンツが存在しないこと」です。

対策はSPAをやめることではない

ではSPAは間違いなのでしょうか。そうではありません。重要なのはレンダリング戦略です。

主な解決策は3つあります。

  • SSRを併用する(Next.jsなど)
  • SSGで事前生成する
  • 重要部分だけプリレンダリングする

特にブログや記事サイトではSSGが非常に有効です。ビルド時にHTMLを生成しておけば、SPAの操作性とSEOの両立が可能です。

注意点:SSRにもコストがある

SSRは万能ではありません。

  • サーバ負荷が増える
  • キャッシュ設計が必要
  • セッション管理が難しくなる

特に高トラフィックでは、単純なSSRはスケールしません。エッジキャッシュや再検証設計(revalidation)が必須になります。

まとめ

SPAがCore Web Vitalsで不利になる理由は、技術の優劣ではありません。評価指標が「初回表示」を基準にしているためです。

SPAはユーザー体験としては優れていますが、初回表示では「コンテンツが存在しない時間」が発生します。これがLCPを悪化させ、結果としてSEO評価を下げます。

大事なのはSPAかSSRかを二択で考えることではありません。どのページを誰が最初に開くのかを基準にレンダリング方法を選ぶことです。

アプリケーション的な画面はSPA、検索流入のページはSSRやSSG。この使い分けができると、パフォーマンスとSEOは対立しなくなります。