ClaudeNext.js2020/07/27 16:23

Next.js 9.5

要点だけを先に読めるように短く再構成したセクションです。

元記事

Quick Digest

要約

要点だけを先に読めるように短く再構成したセクションです。

claudejamodel: claude-sonnet-4-20250514

Next.js 9.5 - 増分静的再生成の安定化とルーティング機能の強化

Key Points

  • 増分静的再生成(ISR)が安定版として利用可能に
  • ベースパス設定でサブパスホスティングが簡単に
  • リライト・リダイレクト・ヘッダー機能を標準サポート

Summary

Next.js 9.5では、増分静的再生成(ISR)の安定版リリースを中心に、多数の新機能と改善が導入されました。静的サイトの利点を保ちながら動的データに対応する機能が大幅に強化されています。

Key Points

  • 増分静的再生成(ISR)の安定化: revalidateプロパティを使用してデプロイ後に静的ページをバックグラウンドで再生成可能
  • カスタマイズ可能なベースパス: basePath設定でサブパスでのホスティングが簡単に
  • リライト・リダイレクト・ヘッダー対応: next.config.jsで柔軟なルーティング制御が可能
  • トレイリングスラッシュ制御: URLの末尾スラッシュの有無を統一的に管理
  • ページバンドルの永続キャッシュ: コンテンツハッシュによる効率的なキャッシュ戦略
  • Fast Refreshの改善: より信頼性の高いライブ編集体験
  • Webpack 5サポート(ベータ): ビルドサイズと速度の向上

Full Translation

翻訳

原文の流れを保ったまま読める翻訳セクションです。

claudejamodel: claude-sonnet-4-20250514

Next.js 9.5

Next.js 9.5

2020年7月27日(月)

投稿者:Connor Davis @ connordav_is、JJ Kasper @ _ijjk、Joe Haddad @ timer150、Luis Alvarez @ luis_fades、Shu Uesugi @ chibicode、Tim Neutkens @ timneutkens

本日、Next.js 9.5をご紹介できることを嬉しく思います。以下の機能を搭載しています:

  • 安定版 Incremental Static Regeneration:デプロイ後に静的ページをミリ秒単位で再構築
  • カスタマイズ可能なBase Path:ドメインのサブパスでNext.jsプロジェクトを簡単にホスト
  • Rewrites、Redirects、Headersのサポート:バニティURLの書き換え、古いURLのリダイレクト、静的ページへのヘッダー追加
  • URLでのオプショナルなトレイリングスラッシュ:トレイリングスラッシュの有無を一貫して強制
  • ページバンドルの永続キャッシュ:変更されていないページのJavaScriptファイルがビルド間で引き継がれる
  • Fast Refreshの強化:Next.jsライブ編集体験の信頼性向上
  • 本番環境でのReact Profiling:プロジェクトのレンダリング「コスト」を測定する新しいフラグ
  • Optional Catch All Routes:動的ルートがSEO駆動のユースケースでより柔軟性を提供
  • Webpack 5サポート(ベータ版):ビルドサイズと速度を改善するwebpack 5の次期バージョンにオプションで参加

安定版 Incremental Static Regeneration

Next.jsは9.3でStatic Site Generation手法を導入し、明確な目標を掲げました:静的(常に高速、常にオンライン、グローバルに複製)の利点を得つつ、Next.jsが知られている動的データへの優れたサポートを提供することです。

両方の利点を得るため、Next.jsはIncremental Static Generationを導入し、サイトを既に構築した後に静的コンテンツを更新できるようにしました。getStaticPathsfallback: trueオプションを使用することで、実行時に新しい静的ページを登録できます。Next.jsはこの方法で、データセットの大きさに関係なく、オンデマンドで無限数のページを静的に事前レンダリングできます。

本日、Incremental Static Re-generationの一般提供を発表します。これは既存のページを更新するメカニズムで、トラフィックが来るとバックグラウンドで再レンダリングします。stale-while-revalidateにインスパイアされたバックグラウンド再生成により、トラフィックは中断されることなく、常に静的ストレージから提供され、新しく構築されたページは生成完了後にのみプッシュされます。

export async function getStaticProps() {
  return {
    props: await getDataFromCMS(),
    // ページの再生成を試行します:
    // - リクエストが来たとき
    // - 最大で1秒に1回
    revalidate: 1,
  };
}

revalidateフラグは、最大で1回の生成が発生する秒数で、https://en.wikipedia.org/wiki/Cache_stampede を防ぐためです。

従来のSSRとは異なり、Incremental Static Regenerationは静的の利点を保持することを保証します:

  • レイテンシのスパイクなし:ページは一貫して高速に提供されます
  • ページがオフラインになることがない:バックグラウンドページ再生成が失敗した場合、古いページは変更されません
  • データベースとバックエンドの負荷が低い:ページは最大で1回同時に再計算されます

両方のインクリメンタル機能(ページの追加と遅延更新)およびpreview modeは、現在安定しており、next startとVercel edgeプラットフォームの両方で既に完全にサポートされています。

この新機能を紹介するため、特定のissueの様々なGitHub reactionの数を表示する静的ページを再生成する例を作成しました:https://reactions-demo.vercel.app/

絵文字リアクション後の最初の訪問後、新しいページ生成がバックグラウンドで開始されます。すべてのリクエストは静的キャッシュから提供されます。

次に、2つの追加のインクリメンタル静的生成機能に対処するための補足RFCに取り組む予定です:

  • 複数のページを一度に再生成・無効化(ブログインデックスと特定のブログ投稿など)
  • イベントを監視して再生成(CMSウェブフックなど)、ユーザートラフィックより先に

詳細については、getStaticPropsドキュメントをご確認ください。

カスタマイズ可能なBase Path

Next.jsプロジェクトは常にドメインのルートから提供されるわけではありません。時には/docsのようなサブパスでNext.jsプロジェクトをホストして、Next.jsプロジェクトがドメインのそのサブセクションのみをカバーするようにしたい場合があります。

これまでも可能でしたが、かなりの追加設定が必要でした。例えば、すべての<Link>にプレフィックスを追加し、Next.jsが正しいパスからJavaScriptバンドルを提供していることを確認する必要がありました。

この問題点に対処するため、新しい設定オプションを導入しています。basePathにより、ドメインのサブパスでNext.jsプロジェクトを簡単にホストできます。

basePathの使用を開始するには、next.config.jsに追加できます:

// next.config.js
module.exports = {
  basePath: '/docs',
};

basePathを設定すると、プロジェクトは自動的に提供されたパスからルーティングされます。この場合は/docsです。

next/linknext/routerでプロジェクト内の他のページにリンクする際、basePathは自動的にプレフィックスされます。これにより、プロジェクトを変更することなくbasePathを変更できます。

例えば、next/linkを使用して別のページにルーティングする場合:

import Link from 'next/link';

export default function HomePage() {
  return (
    <>
      <Link href="/documentation-page">
        <a>Documentation page</a>
      </Link>
    </>
  );
}

この方法でnext/linkを使用すると、Webブラウザに以下のHTMLがレンダリングされます:

<a href="/docs/documentation-page">Documentation page</a>

詳細については、basePathドキュメントをご確認ください。

Rewrites、Redirects、Headersのサポート

Rewrites

Next.jsプロジェクトを構築する際、特定のルートを別のURLにプロキシしたい場合があります。例えば、Next.jsをスタックに段階的に採用したい場合、Next.jsプロジェクトに存在するページをルーティングし、マッチしなかったものすべてを移行元の古いプロジェクトにルーティングしたいでしょう。

Next.js 9.5では、rewritesという新しい設定オプションを導入しています。これにより、受信リクエストパスを外部URLを含む異なる宛先パスにマップできます。

例えば、特定のルートをexample.comに書き換えたい場合:

// next.config.js
module.exports = {
  async rewrites() {
    return [
      {
        source: '/backend/:path*',
        destination: 'https://example.com/:path*'
      },
    ];
  },
};

この場合、/backend下のすべてのパスがexample.comにルーティングされます。

Next.jsプロジェクトのルートがマッチするかチェックし、マッチしない場合は前のプロジェクトに書き換えることもできます。これはNext.jsの段階的採用に非常に有用です:

module.exports = {
  async rewrites() {
    return [
      // プロキシを試行する前にNext.jsプロジェクトルートがマッチするかチェック
      {
        source: '/:path*',
        destination: '/:path*',
      },
      {
        source: '/:path*',
        destination: `https://example.com/:path*`,
      },
    ];
  },
};

この場合、最初にすべてのパスをマッチします。マッチしない場合は、前のプロジェクトであるexample.comにプロキシします。

rewritesの詳細については、rewritesドキュメントをご確認ください。

Redirects

ほとんどのWebサイトには少なくともいくつかのリダイレクトが必要です。特にプロジェクトルートの構造を変更する際、例えば/blog/newsに移動する場合などです。

以前は、Next.jsプロジェクトでリダイレクトのリストを持つには、カスタムサーバーまたはカスタム_errorページを設定してルートにリダイレクトが設定されているかチェックする必要がありました。しかし、これは重要な静的およびサーバーレス最適化を無効にする(サーバーを持つことで)か、十分にエルゴノミックではありませんでした。

Next.js 9.5から、next.config.jsredirectsキー下でリダイレクトのリストを作成できるようになりました:

// next.config.js
module.exports = {
  async redirects() {
    return [
      {
        source: '/about',
        destination: '/',
        permanent: true,
      },
    ];
  },
};

redirects機能の詳細については、redirectsドキュメントをご確認ください。

Headers

Next.jsでは、Static GenerationとServer-Side Renderingの両方を使用するハイブリッドプロジェクトを構築できます。Server-Side renderingでは、受信リクエストにヘッダーを設定できます。静的ページでは、これまでヘッダーの設定は不可能でした。

現在、すべてのNext.jsルートに適用されるnext.config.jsheadersプロパティを導入しました:

// next.config.js
module.exports = {
  async headers() {
    return [
      {
        source: '/:path*',
        headers: [
          {
            key: 'Feature-Policy',
            // マイクと位置情報を無効化
            value: "microphone 'none'; geolocation 'none'",
          },
        ],
      },
    ];
  },
};

headersオプションにより、Feature-PolicyやContent-Security-Policyなどの一般的に必要なヘッダーを設定できます。

headers機能の詳細については、headersドキュメントをご確認ください。

URLでのオプショナルなトレイリングスラッシュ

Next.jsが3年前に導入された際、デフォルトの動作はトレイリングスラッシュを持つすべてのURLが常に404ページを返すことでした。効果的でしたが、一部のユーザーはこの動作を変更する機能を要求していました。例えば、以前は常にトレイリングスラッシュが強制されていた既存のプロジェクトをNext.jsに移行する場合です。

Next.js 9.5では、next.config.jstrailingSlashという新しいオプションを導入しました。この新しいオプションにより、Next.jsは自動的にトレイリングスラッシュの動作を処理します:

  • トレイリングスラッシュURLをトレイリングスラッシュなしのURLに自動的にリダイレクト、例:/about/から/about
  • trailingSlashtrueに設定されている場合、トレイリングスラッシュなしのURLはトレイリングスラッシュありのURLにリダイレクト、例:/aboutから/about/
  • 不要なリダイレクトを避けるため、next/linkにトレイリングスラッシュが自動的に適用/削除されることを保証
// next.config.js
module.exports = {
  // トレイリングスラッシュを強制、デフォルト値はトレイリングスラッシュなし(false)
  trailingSlash: true,
};

trailingSlash機能の詳細については、trailingSlashドキュメントをご確認ください。

ページバンドルの永続キャッシュ

Next.jsページを書く際、すべてのスクリプトバンドル、CSSスタイルシート、HTMLの作成は完全に自動で、あなたから抽象化されています。Next.js 9.5以前の生成された<script>タグを調べると、そのURLが以下のようなパターンに従っていることがわかります:

/_next/static/ovgxWYrvKyjnlM15qtz7h/pages/about.js

上記のovgxWYrvKyjnlM15qtz7hパスセグメントは、私たちがbuild IDと呼んでいたものです。これらのファイルはエッジやユーザーのマシンで簡単にキャッシュ可能でしたが、アプリを再ビルドした後、build IDが変更され、すべてのキャッシュが無効になりました。

ほとんどのプロジェクトでこのトレードオフは問題ありませんでしたが、変更されていないページのブラウザキャッシュを無効にしないことで、この動作をさらに最適化したいと考えていました。

Google Chromeチームとの協力で開発されたNext.js 9.2の改良されたコード分割戦略の導入により、Next.jsページバンドル生成のこれらの改善の基盤が築かれました。

Next.js 9.5から、すべてのページJavaScriptバンドルはbuild IDの代わりにコンテンツハッシュを使用します。これにより、デプロイ間で変更されていないページは、再度ダウンロードする必要なく、ブラウザとエッジキャッシュに残ることができます。

対照的に、これらの変更後のURLパターンは以下のようになります:

/_next/static/chunks/pages/about.qzfS4o5gIEXRME6sTEahL.js

グローバルbuild IDの代わりに、qzfS4o5gIEXRME6sTEahL部分はabout.jsバンドルの決定論的ハッシュで、サイトのそのセクションのコードが変更されない限り安定します。

さらに、Next.jsが自動的に設定するCache-Control: public,max-age=31536000,immutableにより、再デプロイ間で長期間キャッシュされるようになりました。

Fast Refreshの強化

Next.js 9.4でFast Refreshを導入しました。これは、Reactコンポーネントに加えた編集に対して瞬時のフィードバックを提供する新しいホットリロード体験です。

Next.js 9.5では、Fast Refresh実装をさらに洗練し、成功に必要なツールを提供します:

  • 理解しやすいエラー:すべてのコンパイルおよびランタイムエラーが更新され、エラーを引き起こしたコードのコードフレームを含む関連情報のみを表示
  • 開発時のヒント:継続的な