跳至主要内容

[NextDoc] Advanced Features

此篇為 Next.js 官方文件 Advanced Features 之整理,非原創文章。

Dynamic Import and Code Splitting

基本使用

使用 next/dynamic 可以在 Next.js 中做到 dynamic import 及 code splitting 的效果。在 React18 之後,Next.js 支援可以直接使用 lazy 來做 dynamic import。

需要留意幾點:

  • import 的路徑一定要是靜態的定值,不能是 template string 或變數。
  • import 的語法一定要放在 dynamic()
// https://nextjs.org/docs/advanced-features/dynamic-import#basic-usage

import dynamic from 'next/dynamic';

const DynamicComponent = dynamic(() => import('../components/hello'));

function Home() {
return (
<div>
<Header />
<DynamicComponent />
<p>HOME PAGE is here!</p>
</div>
);
}

export default Home;

Named Exports

在 Next.js 中,可以支援動態載入 Named Exports 的元件,寫法如下:

import dynamic from 'next/dynamic';

const DynamicComponent = dynamic(() =>
import('../components/Todo').then((mod) => mod.TodoList);
)

// 也可以用 async/await 的寫法
const DynamicComponent = dynamic(async () => {
const mod = await import('../components/Todo');
return mod.TodoList;
})

使用 React 官方的 lazy

在 React 18 後,Suspense 本身就已經支援 SSR,所以在 Next.js 中,可以使用 lazy 而不用使用 dynamic + suspense 的寫法:

// https://nextjs.org/docs/advanced-features/react-18/streaming
import dynamic from 'next/dynamic';
import { lazy, Suspense } from 'react';

// 下面的寫法有一樣的效果
const Profile = dynamic(() => import('./profile'), { suspense: true });
const Footer = lazy(() => import('./footer'));

export default function Home() {
return (
<div>
<Suspense fallback={<Spinner />}>
<Profile />
</Suspense>

<Suspense fallback={<Spinner />}>
<Footer />
</Suspense>
</div>
);
}

其他 Options

import dynamic from 'next/dynamic';

const DynamicLazyComponent = dynamic(() => import('../components/Hello'), {
ssr: false, // 只要在 client side 時才動態載入此元件
suspense: true, // React 18 之後在 SSR 也支援 Suspense 的用法
loading: () => <p>loading...</p>, // React 18 之後可以用 Suspense 達到類似的效果
});

function Home() {
return (
<div>
<Suspense fallback={<p>loading...</p>}>
<DynamicLazyComponent />
</Suspense>
</div>
);
}