SPA ルーティング
SPA でブラウザの URL とコンポーネントの表示を同期させ、ページ遷移なしで画面を切り替える仕組み
フロントエンド
SPA ルーティングとは
SPA ルーティングは、Single Page Application でブラウザの URL とコンポーネントの表示を同期させる仕組みである。ページ全体をリロードせずに、URL の変更に応じて表示するコンポーネントを切り替える。History API (pushState, popstate) を使って、ブラウザの戻る/進むボタンにも対応する。
仕組み
従来の MPA (Multi Page Application):
/about にアクセス → サーバーが about.html を返す → ページ全体をリロード
SPA ルーティング:
/about にアクセス → JavaScript が URL を検知 → About コンポーネントを表示
(サーバーへのリクエストなし、ページリロードなし)
React Router での実装
import { BrowserRouter, Routes, Route, Link } from 'react-router-dom';
function App() {
return (
<BrowserRouter>
<nav>
<Link to="/">Home</Link>
<Link to="/about">About</Link>
<Link to="/users/123">User</Link>
</nav>
<Routes>
<Route path="/" element={<Home />} />
<Route path="/about" element={<About />} />
<Route path="/users/:id" element={<UserProfile />} />
<Route path="*" element={<NotFound />} />
</Routes>
</BrowserRouter>
);
}
Hash ルーティング vs History ルーティング
| 方式 | URL 例 | サーバー設定 |
|---|---|---|
| Hash | example.com/#/about |
不要 |
| History | example.com/about |
フォールバック設定が必要 |
History ルーティング (推奨) は # がなくクリーンな URL だが、サーバー側で全パスを index.html にフォールバックする設定が必要だ。
/about にアクセスすると S3 は 404 を返すが、CloudFront が index.html にフォールバックし、SPA の JavaScript がルーティングを処理する。
コード分割との連携
const About = lazy(() => import('./pages/About'));
const UserProfile = lazy(() => import('./pages/UserProfile'));
// /about にアクセスした時だけ About のコードを読み込む
<Route path="/about" element={
<Suspense fallback={<Loading />}>
<About />
</Suspense>
} />
SEO の課題
SPA は初期 HTML が空 (<div id="root"></div>) のため、検索エンジンのクローラーが JavaScript を実行しないとコンテンツを認識できない。対策:
- SSR (Next.js): サーバーで HTML を生成
- SSG: ビルド時に静的 HTML を生成
- プリレンダリング: クローラー向けに事前レンダリング
ルーティング方式の比較
| 方式 | URL 例 | サーバー設定 |
|---|---|---|
| Hash | /#/about | 不要 |
| History API | /about | フォールバック必要 |
実務での活用方法は関連書籍にも詳しい。