個人ブログをGatsbyからNext.jsに移行した
元々Gatsbyで作っていた個人ブログをNext.jsで書き直すことにしました。
使っていたGatsbyのバージョンが2.0系と古く、先日購入したM1MaxMBPでビルドもできない状態で、新しくブログ記事を書いてもローカル確認できないままNetlifyにアップしていました。
さすがにそのままというわけにはいかないだろうということで、考えたのは次の選択肢でした。
- GatsbyのバージョンアップしてM1MaxMBPでもビルドできる状態にする
- Gatsbyの最新バージョンで1から作り直す
- Next.jsで作り直す
当時調べた感じだと、M1のMacでGatsbyを動かすには、Gatsby v3.0系である必要がありそうだったので、Gatsby v2.0から最新バージョンまでアップグレードするか、もしくは1から作り直してMDXファイルをコピーする。
もしくは、Next.jsに移行してしまうのも手かなという感じでした。
で、結局Next.jsに移行することに決めたわけですが、これにはいくつか理由があります。
- 仕事などブログ以外のことでGatsbyを使うことがほぼないので、Gatsbyのノウハウを他で活かすことができない
- Next.jsは他でも利用しているので、相互にノウハウを活かすことができる
- Next.jsにしたとしてもMDXはそのまま利用するのでGatsby時代に培ったRemarkやUnifiedのエコシステムのノウハウはそのまま利用できる
- Next.jsだと公式にサンプルが多数あるので、それを組み合わせればすぐに構築できそう
ざっとこんな感じです。が、結局のところ今更Gatsbyはテンションが上がらないっていうことで、Next.jsで書き直すことにしました。個人開発なのでテンションも大切ということで。
最後のすぐに構築できそうという予想は残念ながらハマりポイントがあって裏切られることになりましたが。こちらは後で触れようと思います。
Next.js移行に合わせて変更したところ
まずはNext.jsに合わせて色々変更することにしたので、その辺りの紹介からです。
Chakra UIを使ってみる
せっかく作り直すのでUI周りを調整することにしました。
Gatsby時代はmaterial-ui(最近はMUI)を使っていましたが、せっかくなので以前からReactと組み合わせるならこれが一番いいんじゃないかと小耳に挟んでたChakra UIを使うことにしました。
Chakra UIは、Tailwind CSSみたいなイメージでいい感じにスタイル調整できて、ダークモードとかレスポンシブとかにも対応してるイケてるUIコンポーネント集って感じでしょうか。
スタイル周りのベースはEmotionらしく、私はEmotion推しなのでその辺りも良いポイントですね。
ということで、Next.js + Chakra UIで構築する場合のサンプルもしっかりと公式に用意されていたので、これを使ってブログを構築することにしました。
Chakra UIのBreakpointsを調整する
今どきどう設定するのが良いか迷ったので、既存のUIコンポーネントの初期値がどうなっているかなど調査しました。詳しくはzennのスクラップの方へ。
デプロイ先をNetlifyからVercelに変更する
Gatsbyの時はNetlifyを使っていたんですが、Next.jsを使うならばやはりVercelを使いたいなということで、デプロイ先をNetlifyからVercelにデプロイ先を変更することにしました。
Vercelに独自ドメインの設定をしたり、DNSの向き先を変更したりも実施済みです。
ドメインやパスが変わったりはしていないので、リダイレクト設定などは必要ないのでこの辺りは楽でした。
OGP画像の生成方法を変える
Gatsbyの時はcatchy-imageの作者の方のブログ記事を参考にして、自作したGatsbyプラグインを使ってビルドの度にOGP画像を生成していたんですが、Next.jsではそれをやめて、OGP画像生成用のアプリを別途立ち上げることにしました。
皆さん使われているvercel/og-imageをベースにカスタマイズしたものを使ってます。
next-mdx-remoteでMDXを処理する
Gatsbyの時はgatsby-plugin-mdxを使っていましたが、これは使えないのでnext-mdx-remoteを使うことにしました。
Next.jsは公式にMDXに対応しているので、/pages
配下に.mdx
ファイルを置くといい感じに処理してくれるようなんですが、GatsbyからMDXファイルを移行することを考えるとちょっと使い勝手が良くなさそうだと判断して、このプラグインを使うことにしました。
もしかしたら最初からNext.jsでブログ構築をする場合は公式対応の方法でも良いのかもしれないですが未検証です。
Storybookが原因でハマる
冒頭で触れた通り、Next.jsへの移行はスムーズにはいきませんでした。
それは「Storybookプラグインが依存している@mdx-js/mdx
のバージョンとnext-mdx-remote
が依存している@mdx-js/mdx
のバージョンが違うため、MDXを正しく処理できない」というものでした。
next-mdx-remoteはMDX v2.0系に依存している
Next.jsへの移行作業を始めたのが2月中旬だったんですが、2月2日に@mdx-js/mdx
のv2.0がリリースされていました。
next-mdx-remote
はすぐにMDX v2に対応していて、2月19日にnext-mdx-remote
のv4.0がリリースされています。
なので、構築当初はnext-mdx-remote
のv4.0を使ってMDXを処理するようにブログの構築していたんですが、Storybookを導入したあとからMDXが正しく処理されなくなってしまいました。
StorybookはMDX v1.6系に依存している
Storybookの方はというと、次の2つのnpmパッケージが@mdx-js/mdx
に依存しています。
- @storybook/addon-docs
- @storybook/csf-tools
残念なことにv2.0ではなくて、1つ前のv1.6に依存してました。
しかも、後者の@storybook/csf-tools
は@storybook/core
から参照されているのでStorybookを入れた時点で@mdx-js/mdx
のv1.6も導入されているような歪な状態になっていました。
v1.6に合わせるようにして解決
調査の結果、@mdx-js/mdx
が正しく処理されていなかったようなので、next-mdx-remote
のバージョンをv3.0系に落とすことで@mdx-js/mdx
のv2.0を取り除いてv1.6だけ使用するような形にすればよさそうだということが分かったので、そのように対応しました。
過去にもStorybookのnpmパッケージの依存周りが原因でハマったことがあり、今回もハマってしまって、Storybookかなり嫌いになってます。
次環境構築する時はnpmかyarnなどのworkspaces機能使ってStorybookと本体を分けて管理するような形にしようと思います。Storybook辛い…
まとめ
ということで、紆余曲折ありましたがとりあえずGatsbyからNext.jsへの移行は完了しました。
もちろんM1MaxMBPで開発したいたので、ローカルでも問題なく動作しています。
もし何か変なところがあればTwitter等でご連絡いただければ幸いです。
今後も記事を書いたりブログを改善していきたいと思います!
参考
記事詳細のデザイン、タイポグラフィの調整時に参考にしました。