• #Nuxt
  • #SSR
  • #SSG
  • #Nitro
未分類

Nuxt 3: build vs generate の違い

一言で言うと

コマンド出力サーバー
nuxt buildアプリケーション + サーバー必要
nuxt generate静的HTMLファイル不要

本質的な違い

nuxt build

「アプリケーションをビルドする」

  • Node.jsサーバー(または Cloudflare Functions等)で動作するアプリケーションを生成
  • リクエストごとにサーバーでHTMLを生成できる(SSR: Server-Side Rendering)
  • APIルート(server/api/)が動作する
  • 動的なコンテンツ生成が可能
出力: .output/
├── server/          # サーバーコード
│   └── index.mjs    # エントリーポイント
├── public/          # 静的アセット
└── nitro.json       # Nitro設定

nuxt generate

「静的サイトを生成する」

  • ビルド時に全ページをHTMLファイルとして書き出す(SSG: Static Site Generation)
  • サーバー不要、CDNから直接配信可能
  • APIルートは含まれない(ビルド時に存在しないため)
  • 全てのページが事前に生成される
出力: dist/
├── index.html
├── blog/
│   └── index.html
├── 2025-12-24/
│   └── some-article/
│       └── index.html
└── _nuxt/           # JS/CSSアセット

レンダリング戦略の比較

┌─────────────────────────────────────────────────────────────────┐
│                    レンダリングのタイミング                        │
├─────────────────────────────────────────────────────────────────┤
│                                                                 │
│   ビルド時                    リクエスト時                        │
│   ─────────                  ────────────                       │
│                                                                 │
│   ┌─────────┐                ┌─────────┐                        │
│   │   SSG   │                │   SSR   │                        │
│   │ generate│                │  build  │                        │
│   └─────────┘                └─────────┘                        │
│                                                                 │
│   HTMLを事前生成              リクエストごとに                     │
│   サーバー不要                HTMLを生成                          │
│                              サーバー必要                         │
│                                                                 │
└─────────────────────────────────────────────────────────────────┘

ハイブリッドレンダリング

ページごとにレンダリング戦略を選択できるのが、Nuxt 3の特徴だ:

// nuxt.config.ts
export default defineNuxtConfig({
  routeRules: {
    // 静的生成(ビルド時にHTML生成)
    '/blog/**': { prerender: true },

    // SSR(リクエスト時にHTML生成)
    '/dashboard/**': { ssr: true },

    // SPA(クライアントのみ)
    '/admin/**': { ssr: false },

    // ISR(一定時間キャッシュ後に再生成)
    '/products/**': { isr: 3600 }
  }
})

buildでも静的ページは作れる

nuxt buildでもprerender設定があれば静的HTMLを生成する:

// nuxt.config.ts
export default defineNuxtConfig({
  nitro: {
    preset: "cloudflare-pages",
    prerender: {
      crawlLinks: true,
      routes: ['/blog', '/']
    }
  }
})

結果:

  • /blog配下 → 静的HTML(プリレンダリング)
  • /api/* → Cloudflare Functions(サーバー処理)

これがbuildgenerateの最大の違い:

  • generate: 全て静的、サーバーなし
  • build + prerender: 静的ページ + サーバー機能の両方

使い分けの指針

generate を使うべき場合

  • ブログ、ドキュメントサイトなど完全に静的なサイト
  • サーバーコストをゼロにしたい
  • 最高のパフォーマンス(CDN配信)が必要
  • APIルートが不要

build を使うべき場合

  • サーバーAPIが必要(認証、データベース接続、外部API呼び出し)
  • 動的OGP画像生成など、リクエスト時の処理が必要
  • 一部のページだけ動的にしたい
  • ユーザーごとに異なるコンテンツを返したい

今回のプロジェクトでの選択

Before: generate(完全静的)

  • 全ページをビルド時にHTML生成
  • APIルートなし
  • OGP画像は固定

After: build + prerender(ハイブリッド)

  • コンテンツページは静的HTML(prerender)
  • /api/og/japanese-quiz は Cloudflare Functions
  • クイズ結果に応じた動的OGP画像が可能に

まとめ

観点generatebuild
出力HTMLファイルアプリ + サーバー
サーバー不要必要
APIルート
動的コンテンツ
パフォーマンス最高(CDN)良い〜最高
コスト低(静的ホスティング)中(サーバーレス)
柔軟性

generatebuildサブセットと考えると分かりやすい。 buildgenerateの機能を含みつつ、サーバー機能も追加できる。