2024年1月18日木曜日
Next.js 14.1
投稿者Next.js 14.1には、以下を含む開発者体験の改善が含まれています
- セルフホスティングの改善: 新しいドキュメントとカスタムキャッシュハンドラ
- Turbopackの改善:
next dev --turbo
で5,600件のテストがパス - 開発者体験(DX)の改善: エラーメッセージの改善、
pushState
とreplaceState
のサポート - 並列&インターセプトされたルート: フィードバックに基づき20件のバグを修正
next/image
の改善:<picture>
、アートディレクション、ダークモードのサポート
今すぐアップグレードするか、以下から始めましょう
npx create-next-app@latest
セルフホスティングの改善
Node.jsサーバー、Dockerコンテナ、または静的エクスポートを使用してNext.jsをセルフホストする方法について、より明確な説明を求めるフィードバックをいただきました。セルフホスティングのドキュメントを全面的に見直しました。
Next.js 14.1では、インクリメンタル静的再生成のためのカスタムキャッシュハンドラと、App Routerのためのよりきめ細かいデータキャッシュの提供を安定させました。
module.exports = {
cacheHandler: require.resolve('./cache-handler.js'),
cacheMaxMemorySize: 0, // disable default in-memory caching
};
Kubernetesのようなコンテナオーケストレーションプラットフォームを使用する場合、各ポッドがキャッシュのコピーを持つため、セルフホスティング時にこの設定を使用することが重要です。カスタムキャッシュハンドラを使用することで、Next.jsアプリケーションをホストするすべてのポッド間で一貫性を確保できます。
例えば、キャッシュされた値をRedisやMemcachedなど、どこにでも保存できます。Redisキャッシュハンドラアダプターと例を提供してくれた@neshca
に感謝します。Redisキャッシュハンドラアダプターと例。
Turbopackの改善
ローカルのNext.js開発の信頼性とパフォーマンスに引き続き注力しています。
- 信頼性: TurbopackがNext.js開発テストスイート全体をパスし、Vercelのアプリケーションでドッグフーディングを実施。
- パフォーマンス: Turbopackの初回コンパイル時間とFast Refresh時間の改善。
- メモリ使用量: Turbopackのメモリ使用量の改善。
next dev --turbo
は、引き続きオプトインとして、今後のリリースで安定化する予定です。
信頼性
Turbopackを使用したNext.jsは、前回の更新から600件増え、現在5,600件の開発テスト(94%)をパスしています。進捗状況はareweturboyet.comで確認できます。
vercel.comおよびv0.devを含む、VercelのすべてのNext.jsアプリケーションでnext dev --turbo
のドッグフーディングを継続しています。これらのアプリケーションに携わるすべてのエンジニアは、毎日Turbopackを使用しています。
Turbopackを使用している非常に大規模なNext.jsアプリケーションで、多数の問題を発見し、修正しました。これらの修正のために、既存のNext.js開発テストスイートに新しいテストを追加しました。
パフォーマンス
大規模なNext.jsアプリケーションであるvercel.com
では、以下の改善が見られました。
- ローカルサーバーの起動が最大76.7%高速化
- Fast Refreshによるコード更新が最大96.3%高速化
- キャッシングなしの初回ルートコンパイルが最大45.8%高速化(Turbopackはまだディスクキャッシングをサポートしていません)
v0.devでは、ReactクライアントコンポーネントがTurbopackで検出およびバンドルされる方法を最適化する機会を特定し、その結果、初回コンパイル時間が最大61.5%高速化されました。このパフォーマンス向上はvercel.comでも観測されました。
今後の改善
Turbopackは現在インメモリキャッシュを備えており、Fast Refreshのインクリメンタルコンパイル時間を改善します。
しかし、現在、Next.js開発サーバーを再起動するとキャッシュは保持されません。Turbopackのパフォーマンスの次の大きなステップはディスクキャッシングであり、これにより開発サーバーの再起動時にキャッシュが保持されるようになります。
開発者体験の改善
エラーメッセージとFast Refreshの改善
明確なエラーメッセージがローカル開発体験にいかに重要であるか、私たちは認識しています。next dev
の実行時に表示されるスタックトレースとエラーメッセージの品質を向上させるため、いくつかの修正を行いました。
- 以前は
webpack-internal
のようなバンドラエラーを表示していたエラーが、適切にエラーのソースコードと影響を受けるファイルを表示するようになりました。 - クライアントコンポーネントでエラーが発生し、それをエディタで修正した後、Fast Refreshではエラー画面がクリアされませんでした。手動での再読み込みが必要でした。これらのインスタンスのいくつかを修正しました。例えば、クライアントコンポーネントから
metadata
をエクスポートしようとする場合などです。
例えば、これが以前のエラーメッセージでした。

Next.js 14.1では、これが次のように改善されました。

window.history.pushState
およびwindow.history.replaceState
App Routerでは、ブラウザの履歴スタックをページを再ロードせずに更新するために、ネイティブのpushState
およびreplaceState
メソッドの使用が可能です。
pushState
およびreplaceState
呼び出しはNext.js App Routerと統合されており、usePathname
およびuseSearchParams
と同期できます。
これは、フィルタ、ソート順、その他の再読み込み時に維持したい情報など、状態を保存する際にURLを即座に更新する必要がある場合に役立ちます。
'use client';
import { useSearchParams } from 'next/navigation';
export default function SortProducts() {
const searchParams = useSearchParams();
function updateSorting(sortOrder: string) {
const params = new URLSearchParams(searchParams.toString());
params.set('sort', sortOrder);
window.history.pushState(null, '', `?${params.toString()}`);
}
return (
<>
<button onClick={() => updateSorting('asc')}>Sort Ascending</button>
<button onClick={() => updateSorting('desc')}>Sort Descending</button>
</>
);
}
Next.jsでのネイティブHistory APIの使用について詳しくはこちらをご覧ください。
データキャッシュのログ記録
next dev
実行時のNext.jsアプリケーションにおけるキャッシュデータの可視性を向上させるため、logging
設定オプションにいくつかの改善を加えました。
キャッシュがHIT
またはSKIP
だったかどうか、およびリクエストされた完全なURLを表示できるようになりました。
GET / 200 in 48ms
✓ Compiled /fetch-cache in 117ms
GET /fetch-cache 200 in 165ms
│ GET https://api.vercel.app/products/1 200 in 14ms (cache: HIT)
✓ Compiled /fetch-no-store in 150ms
GET /fetch-no-store 200 in 548ms
│ GET https://api.vercel.app/products/1 200 in 345ms (cache: SKIP)
│ │ Cache missed reason: (cache: no-store)
これはnext.config.js
を介して有効にできます。
module.exports = {
logging: {
fetches: {
fullUrl: true,
},
},
};
next/image
が<picture>
とアートディレクションをサポート
Next.js Imageコンポーネントは、<Image>
を直接使用する必要のないgetImageProps()
(安定版)を介して、より高度なユースケースをサポートするようになりました。これには以下が含まれます。
background-image
またはimage-set
での動作- キャンバスの
context.drawImage()
またはnew Image()
での動作 <picture>
メディアクエリによるアートディレクションまたはライト/ダークモード画像の動作
import { getImageProps } from 'next/image';
export default function Page() {
const common = { alt: 'Hero', width: 800, height: 400 };
const {
props: { srcSet: dark },
} = getImageProps({ ...common, src: '/dark.png' });
const {
props: { srcSet: light, ...rest },
} = getImageProps({ ...common, src: '/light.png' });
return (
<picture>
<source media="(prefers-color-scheme: dark)" srcSet={dark} />
<source media="(prefers-color-scheme: light)" srcSet={light} />
<img {...rest} />
</picture>
);
}
getImageProps()
について詳しくはこちら。
並列&インターセプトされたルート
Next.js 14.1では、並列&インターセプトされたルートに20の改善を加えました。
過去2回のリリースでは、Next.jsのパフォーマンスと信頼性の向上に注力してきました。皆様からのフィードバックに基づき、並列ルートとインターセプトされたルートに多くの改善を加えることができました。特に、キャッチオールルートとサーバーアクションのサポートを追加しました。
- 並列ルートを使用すると、同じレイアウト内で1つまたは複数のページを同時に、または条件付きでレンダリングできます。ダッシュボードやソーシャルサイトのフィードなど、アプリの非常に動的なセクションでは、並列ルートを使用して複雑なルーティングパターンを実装できます。
- インターセプトされたルートを使用すると、アプリケーションの別の部分から現在のレイアウト内にルートを読み込むことができます。例えば、フィード内の写真をクリックすると、フィードの上に写真をモーダルとして重ねて表示できます。この場合、Next.jsは
/photo/123
ルートをインターセプトし、URLをマスクして/feed
の上に重ねて表示します。
並列ルートとインターセプトされたルートについて詳しく学ぶか、例を見る。
その他の改善
14.0
以降、コミュニティから多数の賛成票を得たバグを修正しました。
また、最近、キャッシュの説明動画と、App Routerでよくある間違いに関する動画を公開しました。これらがお役に立てば幸いです。
- [ドキュメント] リダイレクトに関する新しいドキュメント
- [ドキュメント] テストに関する新しいドキュメント
- [ドキュメント] 本番環境チェックリストを含む新しいドキュメント
- [機能]
next/third-parties
に<GoogleAnalytics />
コンポーネントを追加 (ドキュメント) - [改善]
create-next-app
のインストールがより小さく、より高速になりました (PR) - [改善] ネストされたルートでエラーが発生しても、
global-error
で捕捉できるようになりました (PR) - [改善] サーバーアクションで使用される際に、
redirect
がbasePath
を尊重するようになりました (PR) - [改善] App Routerでの
next/script
とbeforeInteractive
の使用を修正 (PR) - [改善] ルート起動の高速化のため、
@aws-sdk
とlodash
を自動的にトランスパイルするようにしました (PR) - [改善]
next dev
およびnext/font
使用時のスタイルなしコンテンツのフラッシュを修正 (PR) - [改善]
notFound
エラーがセグメントのエラー境界を越えて伝播されるようになりました (PR) - [改善] Pages Router i18nでロケールドメインから公開ファイルを配信する問題を修正 (PR)
- [改善] 無効な
revalidate
値が渡された場合にエラーを出すようになりました (PR) - [改善] Windowsで作成されたビルドでLinuxマシン上のパスの問題を修正 (PR)
- [改善]
basePath
を持つマルチゾーンアプリ使用時のFast Refresh / HMRを修正 (PR) - [改善] 終了シグナルからの正常なシャットダウンを改善 (PR)
- [改善] 異なるルートからインターセプトする際のモーダルルートの競合を修正 (PR)
- [改善]
basePath
設定を使用している場合のインターセプトされたルートを修正 (PR) - [改善] 不足している並列スロットが404を返す場合に警告を表示するようにしました (PR)
- [改善] キャッチオールルートで使用される場合のインターセプトされたルートを改善 (PR)
- [改善]
revalidatePath
で使用される場合のインターセプトされたルートを改善 (PR) - [改善] 並列ルートで
@children
スロットを使用する問題を修正 (PR) - [改善] 並列ルートでparamsを使用する際のTypeErrorを修正 (PR)
- [改善] デフォルト並列ルートのキャッチオールルートの正規化を修正 (PR)
- [改善]
next build
サマリーでの並列ルートの表示を修正 (PR) - [改善] インターセプトされたルートを使用する際のルートパラメータの問題を修正 (PR)
- [改善] 深くネストされた並列/インターセプトされたルートを改善 (PR)
- [改善] ルートグループと組み合わせたインターセプトされたルートの404を修正 (PR)
- [改善] サーバーアクション/ルーターキャッシュの再検証を伴う並列ルートを修正 (PR)
- [改善] インターセプトされたルートと
rewrites
の使用を修正 (PR) - [改善] サーバーアクションがサードパーティライブラリから機能するようになりました (PR)
- [改善] Next.jsがESMパッケージ内で使用できるようになりました (PR)
- [改善] Material UIのようなライブラリに対するバレルファイル最適化 (PR)
- [改善]
useSearchParams
がSuspense
なしで不正に使用された場合、ビルドが失敗するようになりました (PR)
貢献者
Next.jsは、3,000人を超える個人開発者、GoogleやMetaなどの業界パートナー、そしてVercelのコアチームの共同作業の成果です。ぜひGitHub Discussions、Reddit、Discordでコミュニティにご参加ください。
このリリースは以下の方々によってもたらされました
- Next.jsチーム: Andrew, Balazs, Jiachi, Jimmy, JJ, Josh, Sebastian, Shu, Steven, Tim, Wyatt, and Zack.
- Turbopackチーム: Donny, Leah, Maia, OJ, Tobias, and Will.
- Next.js Docs: Delba, Steph, Michael, and Lee.
そして、以下の貢献者の方々: @OlehDutchenko, @eps1lon, @ebidel, @janicklas-ralph, @JohnPhamous, @chentsulin, @akawalsky, @BlankParticle, @dvoytenko, @smaeda-ks, @kenji-webdev, @rv-david, @icyJoseph, @dijonmusters, @A7med3bdulBaset, @jenewland1999, @mknichel, @kdy1, @housseindjirdeh, @max-programming, @redbmk, @SSakibHossain10, @jamesmillerburgess, @minaelee, @officialrajdeepsingh, @LorisSigrist, @yesl-kim, @StevenKamwaza, @manovotny, @mcexit, @remcohaszing, @ryo-manba, @TranquilMarmot, @vinaykulk621, @haritssr, @divquan, @IgorVaryvoda, @LukeSchlangen, @RiskyMH, @ash2048, @ManuWeb3, @msgadi, @dhayab, @ShahriarKh, @jvandenaardweg, @DestroyerXyz, @SwitchBladeAK, @ianmacartney, @justinh00k, @tiborsaas, @ArianHamdi, @li-jia-nan, @aramikuto, @jquinc30, @samcx, @Haosik, @AkifumiSato, @arnabsen, @nfroidure, @clbn, @siddtheone, @zbauman3, @anthonyshew, @alexfradiani, @CalebBarnes, @adk96r, @pacexy, @hichemfantar, @michaldudak, @redonkulus, @k-taro56, @mhughdo, @tknickman, @shumakmanohar, @vordgi, @hamirmahal, @gaspar09, @JCharante, @sjoerdvanBommel, @mass2527, @N-Ziermann, @tordans, @davidthorand, @rmathew8-gh, @chriskrogh, @shogunsea, @auipga, @SukkaW, @agustints, @OXXD, @clarencepenz, @better-salmon, @808vita, @coltonehrman, @tksst, @hugo-syn, @JakobJingleheimer, @Willem-Jaap, @brandonnorsworthy, @jaehunn, @jridgewell, @gtjamesa, @mugi-uno, @kentobento, @vivianyentran, @empflow, @samennis1, @mkcy3, @suhaotian, @imevanc, @d3lm, @amannn, @hallatore, @Dylan700, @mpsq, @mdio, @christianvuerings, @karlhorky, @simonhaenisch, @olci34, @zce, @LavaToaster, @rishabhpoddar, @jirihofman, @codercor, @devjiwonchoi, @JackieLi565, @thoushif, @pkellner, @jpfifer, @quisido, @tomfa, @raphaelbadia, @j9141997, @hongaar, @MadCcc, @luismulinari, @dumb-programmer, @nonoakij, @franky47, @robbertstevens, @bryndyment, @marcosmartini, @functino, @Anisi, @AdonisAgelis, @seangray-dev, @prkagrawal, @heloineto, @kn327, @ihommani, @MrNiceRicee, @falsepopsky, @thomasballinger, @tmilewski, @Vadman97, @dnhn, @RodrigoTomeES, @sadikkuzu, @gffuma, @Schniz, @joulev, @Athrun-Judah, @rasvanjaya21, @rashidul0405, @nguyenbry, @Mwimwii, @molebox, @mrr11k, @philwolstenholme, @IgorKowalczyk, @Zoe-Bot, @HanCiHu, @JackHowa, @goncy, @hirotomoyamada, @pveyes, @yeskunall, @ChendayUP, @hmaesta, @ajz003, @its-kunal, @joelhooks, @blurrah, @tariknh, @Vinlock, @Nayeem-XTREME, @aziyatali, @aspehler, and @moka-ayumu.