generateStaticParams

generateStaticParams 函式可與動態路由區段搭配使用,用於在建置時靜態產生路由,而非在請求時按需產生。

app/blog/[slug]/page.js
// 回傳一組 `params` 列表來填充 [slug] 動態區段
export async function generateStaticParams() {
  const posts = await fetch('https://.../posts').then((res) => res.json())

  return posts.map((post) => ({
    slug: post.slug,
  }))
}

// 將會使用 `generateStaticParams` 回傳的 `params`
// 靜態產生此頁面的多個版本
export default function Page({ params }) {
  const { slug } = params
  // ...
}

須知事項

  • 您可以使用 dynamicParams 區段設定選項,來控制當訪問未由 generateStaticParams 產生的動態區段時會發生什麼。
  • next dev 期間,當您導航到路由時會呼叫 generateStaticParams
  • next build 期間,generateStaticParams 會在產生對應的 Layouts 或 Pages 之前執行。
  • 在重新驗證 (ISR) 期間,不會再次呼叫 generateStaticParams
  • generateStaticParams 取代了 Pages Router 中的 getStaticPaths 函式。

參數

options.params (選填)

如果路由中的多個動態區段使用 generateStaticParams,則子 generateStaticParams 函式會針對父級產生的每組 params 執行一次。

params 物件包含從父級 generateStaticParams 填充的 params,可用於在子區段中產生 params

回傳值

generateStaticParams 應回傳一個物件陣列,其中每個物件代表單一路由的已填充動態區段。

  • 物件中的每個屬性都是要為路由填充的動態區段。
  • 屬性名稱是區段的名稱,屬性值則是該區段應填充的值。
範例路由generateStaticParams 回傳型別
/product/[id]{ id: string }[]
/products/[category]/[product]{ category: string, product: string }[]
/products/[...slug]{ slug: string[] }[]

單一動態區段

export function generateStaticParams() {
  return [{ id: '1' }, { id: '2' }, { id: '3' }]
}

// 將會使用 `generateStaticParams` 回傳的 `params`
// 靜態產生此頁面的三個版本
// - /product/1
// - /product/2
// - /product/3
export default function Page({ params }: { params: { id: string } }) {
  const { id } = params
  // ...
}

多個動態區段

export function generateStaticParams() {
  return [
    { category: 'a', product: '1' },
    { category: 'b', product: '2' },
    { category: 'c', product: '3' },
  ]
}

// 將會使用 `generateStaticParams` 回傳的 `params`
// 靜態產生此頁面的三個版本
// - /products/a/1
// - /products/b/2
// - /products/c/3
export default function Page({
  params,
}: {
  params: { category: string; product: string }
}) {
  const { category, product } = params
  // ...
}

萬用動態區段

export function generateStaticParams() {
  return [{ slug: ['a', '1'] }, { slug: ['b', '2'] }, { slug: ['c', '3'] }]
}

// 將會使用 `generateStaticParams` 回傳的 `params`
// 靜態產生此頁面的三個版本
// - /product/a/1
// - /product/b/2
// - /product/c/3
export default function Page({ params }: { params: { slug: string[] } }) {
  const { slug } = params
  // ...
}

範例

同一路由中的多個動態區段

您可以為當前 Layout 或 Page 上方的動態區段產生 params,但無法為下方的區段產生。例如,對於 app/products/[category]/[product] 路由:

  • app/products/[category]/[product]/page.js 可以為 [category][product] 兩者產生 params。
  • app/products/[category]/layout.js 只能[category] 產生 params。

有兩種方法可以為具有多個動態區段的路由產生 params:

從下往上產生 params

從子路由區段產生多個動態區段。

// 為 [category] 和 [product] 產生區段
export async function generateStaticParams() {
  const products = await fetch('https://.../products').then((res) => res.json())

  return products.map((product) => ({
    category: product.category.slug,
    product: product.id,
  }))
}

export default function Page({
  params,
}: {
  params: { category: string; product: string }
}) {
  // ...
}

從上往下產生 params

先產生父級區段,然後使用結果來產生子級區段。

// 為 [category] 產生區段
export async function generateStaticParams() {
  const products = await fetch('https://.../products').then((res) => res.json())

  return products.map((product) => ({
    category: product.category.slug,
  }))
}

export default function Layout({ params }: { params: { category: string } }) {
  // ...
}

子路由區段的 generateStaticParams 函式會針對父級 generateStaticParams 產生的每個區段執行一次。

子級 generateStaticParams 函式可以使用從父級 generateStaticParams 函式回傳的 params 來動態產生自己的區段。

// 使用從父級區段的 `generateStaticParams` 函式傳遞的 `params`
// 來為 [product] 產生區段
export async function generateStaticParams({
  params: { category },
}: {
  params: { category: string }
}) {
  const products = await fetch(
    `https://.../products?category=${category}`
  ).then((res) => res.json())

  return products.map((product) => ({
    product: product.id,
  }))
}

export default function Page({
  params,
}: {
  params: { category: string; product: string }
}) {
  // ...
}

須知事項fetch 請求會自動在 generateMetadatagenerateStaticParams、Layouts、Pages 和 Server Components 之間記憶化相同的資料。如果無法使用 fetch,可以使用 React 的 cache

版本歷史

版本變更內容
v13.0.0引入 generateStaticParams

On this page