LoginSignup
53
31

More than 3 years have passed since last update.

Next.jsのDynamic Routing + Static HTML exportを組み合わせて使う

Last updated at Posted at 2019-10-28

Next.js 9ではDynamic Routingが標準でサポートされ使用感が大きく改善されました。
このDynamic Routingで構築したアプリをexportした場合に一手間必要だったので考慮したことをまとめておきます。

この構成でデプロイを行う際には、ビルド時にデータを全部仕込むか、クライアント側で(APIを叩くなどして)データを仕込むかで大きく対処方法が変わります。

今回の想定アプリ

次のようなページを持つアプリケーションを想定します。

/
/about
/show/[id]

1.ビルド時にデータを仕込む方法

exportする際には、next.config.jsexportPathMapを利用し、出力するファイルの調整を行っていきます。
exportPathMapで、キーにpath、バリューにpage(pageコンポーネントの位置)、query(クエリパラメータ)などの情報をもたせたオブジェクトをそれぞれ作り返り値とします。コードを見たほうが早いでしょう。

const fetch = require('isomorphic-unfetch');

module.exports = {
  exportPathMap: async function() {
    const paths = {
      '/': { page: '/' },
      '/about': { page: '/about' }
    };
    const res = await fetch('https://api.tvmaze.com/search/shows?q=batman');
    const data = await res.json();
    const shows = data.map(entry => entry.show);

    shows.forEach(show => {
      paths[`/show/${show.id}`] = { page: '/show/[id]', query: { id: show.id } };
    });

    return paths;
  }
};

https://nextjs.org/learn/excel/static-html-export/exporting-other-pages より

この際、showのデータを参照するためにAPIを叩いて、結果からexportPathMapのデータを生成します。

2. クライアント側でデータを読み込む場合

ビルド後にもデータが増えることが想定されている場合、ビルド時にexportPathMapを使わない選択肢もあります。
exportPathMapを設定しない場合は、次のようなファイルが生成されます。

/index.html
/about/index.html
/show/[id]/index.html

問題は/show/[id]/index.htmlです。ただ、NetlifyやFirebase Hostingにデプロイするだけでは、example.com/show/[id]でしか開くことができません。
そこで各プラットフォームに、example.com/show/1などのURLを叩いた時に、/show/[id]/index.htmlの内容を返すリライトの設定を行います。

例えばNetlifyでは、公開ディレクトリに次のような_redirectsを用意します。

/show/:id /show/[id] 200

同じくFirebase hostingではfirebase.jsonにリライトの設定を追加します。

こういった設定を加えることで、データが増えた場合でも404を返さずにコンテンツを表示できます。
ただ、この対応だけでは動的にogpを返却することや、速度的なデメリット(1の方法ではHTML読み込み時点でコンテンツが表示されている)を背負うことになります。


特に2.の方法は今後SSRを使いたいけど、今はSSRを行わず静的ファイルとして返す暫定対応的な使い方になると思います。

覚えて置くと初期フェーズからNext.jsの採用を行え、将来SSRをする際に移行コストが小さくなるのでおすすめです。

53
31
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
53
31