はじめに
Next.jsのSSG、SSR、CSR、ISRについて、初心者のときに最初に知りたかったポイントをまとめる😊
この記事で伝えたいこと
どういうページがSSGで、どういうページがSSRになるのか理解する。
さらに具体的なコードの書き方も理解する。
結論
✅デフォルトはSSG。
✅データの取得の仕方によってはSSRになる。
【前提】SSG、SSRって何?
簡単にSSGとSSRについてまとめる。
SSG
- あらかじめHTMLを作っておく方式。
-
ビルド時にHTMLを作っておくので表示が早い⭕️
(具体的にはコマンドnpm run buildでビルドした時点でHTMLが生成される。)
-
SSGができるページはSSGがおすすめ。
(SSGができるページとは、ビルド時でもHTMLに必要なデータが用意できるページ。)
(会社概要ページなど)
SSR
- リクエストがきたときにHTMLを作る方式。
-
毎回HTMLを作るので表示が遅い❌
(サーバーが毎回頑張ってHTMLを作ってくれる🥲サーバーの負担やばそう🙏)
-
SSGができないページだけSSRを使う。
(SSGができないページとは、ビルド時ではHTMLに必要なデータが用意できないページ。つまりリクエスト時でないと用意できないデータがある。)
(例:現在の天気を表示するページなど)
SSG、SSRについてもっと知りたい方はこちら
【疑問】Next.jsにおけるSSG、SSRの決まり方
✅ここからが本題!
背景
Next.jsはページごとにSSG、SSRを変えられるのが便利って聞いた😊
疑問が生まれた
でもページごとにSSG、SSRのどっちになるか、どうやって決まるの?😫
→自分で「このページはSSGだよ!」みたいな宣言をするの?💭
→それとも「こういうページは自動でSSGになる!」みたいな条件があるの?💭
【答え】SSG、SSRになる条件が決まっている
データ取得処理がないページはSSGになる
✅デフォルトはSSGなので、通常のページは自動的にSSGになる。
データ取得処理があるページはSSG、SSRを選べる
✅どのようにデータを取得するかでSSG、SSRが決まる。
- getStaticProps関数でデータ取得するとSSGになる。
- getServerSideProps関数でデータ取得するとSSRになる。
使い分け
✅前述のとおり、SSGができるページはSSGがおすすめ!
-
ビルド時にHTMLに必要なデータが用意できるページ
→getStaticProps関数でデータ取得する。SSG。
-
リクエスト時でないとデータが用意できないページ(SSGができない)
→getServerSideProps関数でデータ取得する。SSR
【もっと知る】データ取得処理の書き方
getStaticProps関数でデータ取得(SSG)
前述のとおり、getStaticPropsを使ってデータを取得するとSSGになる。
getStaticProps関数のポイント
- データを取得する処理をする関数。
-
ビルドするときに関数が実行される。
- 具体的にはビルド時に「関数を実行してデータを取得」→「データを使ってHTMLを生成」。
- データ取得処理をユーザーに見られることはないのでAPIキーなどが漏洩することはない。
- リクエスト時はすでに出来上がっているHTMLを返すだけ。(SSG)
- pageフォルダ内でのみ使用可能。
例
以下のページはgetStaticProps関数を使っているためSSGになる。
page/MyPage.jsx
// ✅getStaticProps関数でデータを取得する
export async function getStaticProps() {
// 架空のデータ取得処理
const res = await fetch(`https://...`)
const post = await res.json()
return {
props: {
data,
},
};
}
// コンポーネントでは取得したデータが使える
function Products({ data }) {
return (
<div>
<h1>Products Page</h1>
<p>{data}</p>
</div>
);
}
export default Products;
【注意】開発環境だとSSGにならない
開発環境ではgetStaticProps関数を使ってもSSGではなく、SSRになるので注意。
getServerSideProps関数でデータ取得(SSR)
前述のとおり、getServerSidePropsを使ってデータ取得するとSSRになる。
getServerSideProps関数のポイント
- データを取得する処理をする関数。
-
リクエストがきたときに関数が実行される。
- 具体的にはリクエスト時に「関数を実行してデータを取得」→「データを使ってHTMLを生成」。(SSR)
- データ取得処理はサーバー側で実行する。
- そのためユーザー見られることはないのでAPIキーなどが漏洩することはない。
- pageフォルダ内でのみ使用可能。
例
以下のページはgetServerSideProps関数を使っているためSSRになる。
page/MyPage.jsx
// ✅getServerSideProps関数でデータを取得する
export async function getServerSideProps() {
// 架空のデータ取得処理
const res = await fetch(`https://...`)
const post = await res.json()
return {
props: {
data,
},
};
}
// コンポーネントでは取得したデータが使える
function Products({ data }) {
return (
<div>
<h1>Products Page</h1>
<p>{data}</p>
</div>
);
}
export default Products;
【発展】動的パスでSSG
先ほどのSSGの方法では動的パスに対応できない
/page/products/[id].js
のようなページは /products/123
/products/xyz
など自由にアクセスできてしまう。
つまり[id]に何が入るか不明💦
(ユーザーがアクセスしたときに始めてURLが分かる)
そのためビルド時にファイル名が分からずHTMLを生成することができない。
解決方法
✅getStaticPaths関数を使って、あらかじめどの名前のHTMLファイルを生成するか指定する。
例:「products/1.html」 と 「products/2.html」 を生成する
pages/products/[id].jsx
// ✅事前に生成するHTMLのファイル名を指定する
export async function getStaticPaths() {
// [id]に何が入るか指定
const paths = [
{ params: { id: '1' } }, // 必ずparamsの中に入れる。idはファイル名と合わせる。
{ params: { id: '2' } },
];
return {
paths,
fallback: false, // id=3など、未知のパスにアクセスすると404を返す
};
}
// ----------------------------------------------------
// 以降は通常のSSGと同じ
// getStaticProps関数でデータを取得する
export async function getStaticProps() {
// 架空のデータ取得処理
const res = await fetch(`https://...`)
const post = await res.json()
return {
props: {
data,
},
};
}
// コンポーネントでは取得したデータが使える
function Products({ data }) {
return (
<div>
<h1>Products Page</h1>
<p>{data}</p>
</div>
);
}
export default Products;
→ビルド時に「products/1.html」 と 「products/2.html」 を生成する。
まとめ
getStaticProps関数 | getServerSideProps関数 | |
---|---|---|
何をする関数? | データを取得する関数 | データを取得する関数 |
いつデータを取得する? | ビルド時 | リクエスト時 |
この関数を使うと? | SSGになる | SSRになる |
いつ使えばいい? |
SSGしたいとき
(ビルド時にデータを取得可能なとき) |
SSRしたいとき
(リクエスト時でないとデータ取得できないとき) |
参考サイト
全般
SSR
SSG
動的パスのSSG