Next.js 16.3:インスタントナビゲーション
公開日: 2026-06-25
Next.js 16.3 Preview がパブリックテスト用に公開されました。npm に @preview タグで新しいリリースを公開しているため、今日から 16.3 を試せます。今後数週間で安定版を磨いて出荷する予定です。プレビューについてのフィードバックは GitHub で歓迎します。
Next.js 16.3 は多数の改善を含みます:ネイティブ Node.js ストリームによる高負荷時のレンダリング向上、ローカル開発での起動時間の短縮、エージェントベースワークフローとのより深い統合などです。本稿では、その中でも「Instant Navigations(インスタントナビゲーション)」と呼ぶ新機能群に焦点を当てます。これは、サーバ駆動モデルの利点を犠牲にせずに、クライアント駆動の SPA のような応答性を Next.js に持ち込むためのツール群です。
背景:なぜ必要か
サーバ駆動アプリでは、ナビゲーションにネットワークリクエストが必要になりがちです。リンクをクリックしても何も起こらず、サーバからの応答を待って次のページが表示される──この "ウェブサイトらしい" 体験は、新聞やブログのようなコンテンツ中心のサイトでは問題にならないこともありますが、レスポンスの良さ(スナッピネス)を期待する多くのアプリでは不満につながります。
クライアント駆動アプリでは、クリック直後に次ページのシェルを即座に表示し(データはまだ読み込み中でも)、その後サーバ応答で完全表示する、という体験が一般的です。これが SPA を好む理由の一つです。
我々のアプローチ
Next.js 16.3 では、オプトインの挙動を導入して、サーバ駆動の利点を保ちつつナビゲーションを即時化できます。要点は次の通りです。
- サーバの利点を維持しつつ、ナビゲーションを SPA のように即時に見せる。
- 新しいフラグでこれらの挙動を有効化できる(将来のメジャーでデフォルト化予定)。
まずは Cache Components を有効にする
これらの新しい挙動を試すには、cacheComponents フラグを有効にします。
import type { NextConfig } from 'next';
const nextConfig: NextConfig = {
cacheComponents: true,
};
export default nextConfig;
過去1年で、Next.js はデフォルトで動的(dynamic by default)かつ隠れた暗黙のキャッシュをなくす方向に単純化してきました。このフラグはその新しい挙動を有効化し、将来のメジャーバージョンでデフォルトになる予定です。
Stream、Cache、または Block
サーバ側でルートがデータを await する場合、以下のいずれかを選べます。Instant Insights パネルは遅いナビゲーションを自動的に可視化します。
- Stream(
<Suspense> を使う): ユーザーは即座にロード中の状態(シェル)を見ます。残りの UI はストリーミングで続きます。
- Cache(
'use cache' を使う): ユーザーは以前にキャッシュされた UI を即座に見ます(リクエスト間で再利用)。
- Block(サーババウンドにする): あるルートでロード中のシェルを表示したくない場合、そのルートをブロックできます。例えばブログの投稿ページでシェルを表示しない選択をする場合などです。
Block にする例:
export const instant = false;
このようにして、どのルートを即時表示にするかを開発者が制御できます。即時表示にしたければ Stream するか Cache を使い、遅延させたいルートは Block します。
Agent skill
既存アプリで Cache Components を初めて採用する場合、エージェントに手順を案内させるための Skill を用意しています。プロンプトをコピーしてエージェントに渡せます。
Instant Insights とテストヘルパー
Instant Insights により、開発中は遅いナビゲーションをエラーとして検出します。回帰を捕捉しやすくするために、Playwright 用の instant テストヘルパーも提供しています。
import { expect, test } from '@playwright/test';
import { instant } from '@next/playwright';
test('product title is available immediately', async ({ page }) => {
await page.goto('/products/shoes');
await instant(page, async () => {
await page.click('a[href="/products/hats"]');
await expect(page.locator('h1')).toContainText('Baseball Cap');
await expect(page.getByText('Checking inventory...')).toBeVisible();
});
await expect(page.getByText('12 in stock')).toBeVisible();
});
このヘルパーにより、リンククリック直後に即座に表示されるべき要素を細かく検証できます。ビルド時にも同じエラーを可視化する方法を検討中で、即時ルートの回帰をビルド段階で検出できるようにする予定です。
リンクのプリフェッチ(再考)
真に SPA のような即時性を実現するには、次の 2 つのギャップを埋める必要がありました。
- クライアントがサーバと通信する間の遅延(ネットワーク遅延)
- サーバ側でレスポンスを生成する時間(サーバ処理の遅さ)
Stream や use cache によって 2 番目のギャップは解消されますが、クライアントとサーバ間のギャップは残ります。従来、Next.js はビューポート内の各リンクに対してページ単位でプリフェッチリクエストを送っていましたが(スクロール時に大量のリクエストが発生する)、これを改善します。
SPA は次ページ表示に必要なコードをバンドルしてクライアントに配布することで即時応答を実現しています。これを参考に、Next.js では「ページごとのプリフェッチ」ではなく「ルートごとの再利用可能なシェル」をプリフェッチする方式に変えました。シェルはクライアントにキャッシュされ、一度だけ取得されます。
例えばサイドバーに20個のチャットリンクがあっても、従来はリンクごとにプリフェッチが走っていましたが、16.3 では /chat/[id] というルートごとに一つのシェルをプリフェッチするだけになります。
このシェルの再利用はオフラインナビゲーションの基礎にもなります。将来、プリフェッチ済みルートがネットワーク切断時にもナビゲート可能になる仕組みを検討しています。
Partial Prefetching を有効にする
この新しいプリフェッチ挙動(Partial Prefetching)を試すには、次のように設定します。
import type { NextConfig } from 'next';
const nextConfig: NextConfig = {
cacheComponents: true,
partialPrefetching: true,
};
export default nextConfig;
cacheComponents と同様に、partialPrefetching も将来のメジャーリリースでデフォルトにする予定です。
ローディングシェルの検査
Next.js DevTools に新しい Navigation Inspector を追加しました。これにより、開発中に各ナビゲーションをシェルで一時停止して、どのルートが何をプリフェッチしているかを確認できます。「Resume」を押すと完全なページが表示されます。実際のプリフェッチは本番環境でのみ有効になります。
シェル以上をプリフェッチしたい場合
Partial Prefetching を有効にすると、デフォルトでプリフェッチされる量を削減します。ビューポート内の各 distinct なルートに対して再利用可能なシェルのみをプリフェッチし、セッションを通じてキャッシュします。
しかし、チャットページでヘッダーだけは即時にポップインさせたい、などシェル以上の内容をプリフェッチしたい場合もあるでしょう。その場合は、個別のリンクに <Link prefetch={true}> を付与して、リンク単位でのプリフェッチを有効化できます。なお、この場合でも Next.js はルート全体を深くまで同期的にレンダリングしようとはせず、同期的に利用可能な部分や 'use cache' としてマークされた部分までしかレンダリングしません。
- インスタントシェルがベースラインを提供し、
<Link prefetch={true}> と 'use cache' により追加のリンク単位プリフェッチでより深い部分を取得できます。
- リンク単位のプリフェッチはビルド時に分かっているコンテンツに限定してコストを抑えています。もしランタイムでのキャッシュ化コンテンツもリクエストしてよければ、
export const prefetch = 'allow-runtime' を使って拡張できます。
社内での導入例
我々は v0 のアプリでこれらのツールを先行採用してきました。v0 は多くのリッチクライアント機能を持っていますが、ナビゲーションの即時性はしばらく課題でした。Instant Insights によって即時化されていないルートが可視化され、修正を進めた結果、ナビゲーション時間(クリックからルート切替まで)は大幅に改善しました。今後さらにプリフェッチ最適化を進め、これらの数値をゼロに近づけていく予定です。
まとめ
Stream(<Suspense>)または Cache('use cache')を使うと、ルートへのナビゲーションが即時になります。
export const instant = false を使うと、そのルートはブロック(同期的に待つ)になります。
- Next.js は各即時ルートの再利用可能なシェルを自動生成し、1 回だけプリフェッチします。
- 回帰を防ぐために
instant() テストヘルパーを使えますし、Navigation Inspector でシェルを視覚的に検査できます。
- より深いリンク単位のプリフェッチは
<Link prefetch> と 'use cache' で可能です。
- これらの変更は
cacheComponents: true と partialPrefetching: true フラグの背後にあります。
これらによって、サーバ中心のモデルとその全体的なパフォーマンスを損なうことなく、Next.js の初回クリック(first-click)ナビゲーション体験を SPA と同等に向上させています。
今すぐ試す
Instant Navigations を試すには、16.3 Preview をインストールしてください:
npm install next@preview
Instant Navigations のプレビューに関する詳細は preview docs を参照してください。これはプレプロダクションリリースです。我々自身のアプリでも使用していますが、本番デプロイする前には慎重に検討してください。