👶

Next.js SSGでのルーティングの実装方法がApp Router で変化した部分について

に公開

App RouterのSSGはどう変わったのか?

App Routerでは、従来の(Pages Router) getStaticProps, getStaticPaths は使えなくなっており、その代わりの手段を調べていきます。

ビルド時に静的にルートを生成する方法

ビルド時に静的にルートを生成したい時、従来はgetStaticPathsを使っていたが、App RouterではgenerateStaticParamsに変更になります。

ちなみに旧式Pages Routerでの書き方(getStaticPaths)

export async function getStaticPaths() {
  const products = await getAllProducts();
  return {
    paths: products.map((p) => ({ params: { slug: p.slug } })),
    fallback: false,
  };
}

App Routerでの書き方(generateStaticParams)

https://nextjs.org/docs/app/api-reference/functions/generate-static-params
ビルド時に静的生成する動的セグメントのパラメータ一覧を返すことで、一度だけこの関数を呼び出し、返された各paramsに対応するページを生成します。
関数の返り値には、{ セグメント名: 値 }の配列を指定します。キーに指定するセグメント名は、フォルダ名に指定した動的ルートセグメント名と対応させる必要があります。

export async function generateStaticParams() {
  const list = await getAllProducts() //データ取得の関数

  return list.map((item) => ({
    slug: item.slug,
  }));
}

Server Component 内でのデータフェッチ

App RouterではページコンポーネントをそのままServer Componentとして扱えるため、getStaticPropsは不要となり、コンポーネント内で直接データ取得を完結できます。

const ProductDetailPage = async ({
  params,
}: {
  params: Promise<{ slug: string }>;
}) => {
  const { slug } = await params;
  const detail = await getProductBySlug(params.slug) //データ取得の関数
  if (!detail) return notFound();

  return (
    <main>
      <h1>{data.title}</h1>
      <p>{data.description}</p>
    </main>
  );
};

フォールバックと動的パラメータ:dynamicParams

App Routerではビルド時以外のルートへの挙動を制御をdynamicParamsでシンプルに制御できます。

export const dynamicParams = true | false
  • true(デフォルト):generateStaticParamsに含まれないIDへの初回アクセス時にオンデマンドでページを生成し、静的ファイルとしてキャッシュします。
  • false:generateStaticParamsに含まれないIDへのアクセスは404を返します。

まとめ

App Routerでは、従来のgetStaticPropsやgetStaticPathsといったAPIが廃止され、generateStaticParamsとサーバーコンポーネントによるデータフェッチという新しい設計が導入されました。これにより、ルーティングとデータ取得の責務が簡潔になり、より明確な構造でSSGを実現できるようになっているようです。

Discussion