NextはStatic Renderingがデフォルト
2023-04-02

Nextの進化がすごい今日この頃です。
キャッチアップしている中で学びがあったので、せっかくなので?記事にすることにしました。

遭遇した事象

例えば、Note一覧を表示するような際に以下のような実装をしていました。

app/notes/page.tsx
export default async function Page() {
   const notes = await getNotes();

   return (
    <div>
      {/* Note一覧を表示 */}
    </div>
   )
}

挙動を確認したところ、どれだけNoteを追加しても一覧に反映されないという事象に遭遇しました。

原因

Next13ではRouteページはデフォルトでStatic Renderingになるようです。(公式
static_rendering.png

要はビルド時に生成したHTMLを各リクエスト時に再利用されるということです。
さらに、fetchAPIはcacheのオプションを何も付与しなければ、force-cacheオプションが付与されるのと同様の挙動になるとのことです。

static_data_fetching.png

そのため、ビルド後当該ページにアクセスしてもNote取得の処理が走らず、レコードが追加されたところで一覧には表示されない、という事象が起こっていました。

ちなみにStaticであることは、ビルド時の出力で確認することが可能です。(/notesにはStaticを意味する○がついています。)

terminal
Route (app)                                Size     First Load JS
┌ ○ /                                      5.3 kB         78.9 kB
├ λ /api/notes                             0 B                0 B
(略)
├ ○ /notes                                 6.21 kB        90.3 kB
(略)
λ  (Server)  server-side renders at runtime (uses getInitialProps or getServerSideProps)
○  (Static)  automatically rendered as static HTML (uses no initial props)

解決

Route Segment Configを指定することで解決しました。
いくつか方法はあるようですが、今回はrevalidate = 0を指定することで、ページアクセス時に常にfetchが実行されるようにしました。 (fetchAPIcacheオプションにno-storeを指定した状態)

app/notes/page.tsx
export const revalidate = 0;

export default async function Page() {
   const notes = await getNotes();

   return (
    <div>
      {/* Note一覧を表示 */}
    </div>
   )
}

再度ビルド時の出力を確認すると、Serverになっていることが分かるかと思います。

terminal
Route (app)                                Size     First Load JS
┌ ○ /                                      5.3 kB         78.9 kB
├ λ /api/notes                             0 B                0 B
(略)
├ λ /notes                                 6.21 kB        90.3 kB
(略)
λ  (Server)  server-side renders at runtime (uses getInitialProps or getServerSideProps)
○  (Static)  automatically rendered as static HTML (uses no initial props)

ちなみにrevalidateに任意の数値を指定することもでき、そうすると指定した時間以後にリクエストがあった際にページを再生成するような挙動になるようです。

終わりに

ドキュメントを読むことの大切さを感じる日々です。
読んでいく中で技術力だけでなく、英語力も向上されるとさらに嬉しいですね。

参考にさせていただいた記事など

https://eh-career.com/engineerhub/entry/2023/04/18/093000

© 2023 yutasb