🚀

Next.js x Notion APIで個人ブログをつくりました

4 min read

一ヶ月くらいかけて、念願だった個人サイトをつくりました。

https://www.shetommy.com/

ポートフォリオサイト + 個人ブログ + Web技術の実験場的な使い方をするためにつくりました。
ポートフォリオサイトとしての実装は割とすぐできたんですが、ブログ機能が大変でした。
この記事ではそこメインで書きたいと思います。
Notion APIをガチャガチャした詳細は長くなるので、後で記事を書いて、とりあえずこの記事は個人サイト開発のまとめとしてもうちょっと雑多に書いていきます。

同じようなことをしたい方の参考になれば幸いです。

ソース

公開しています。

https://github.com/0si43/shetommy.com

技術スタック

  • フレームワーク: Next.js
  • 言語: TypeScript, CSS
  • デプロイ環境: Vercel
  • ブログコンテンツのホスティング: Notion
  • ↑の取得: Notion API

モチベーション

自分のページ欲しいなとはずっと思ってたんですが、なかなか自作するところまで行きませんでした。
6月にNext.jsやTypeScriptのチュートリアルをやって、「あ、これなんかちょっとしたものならつくれそう」と感じたので、
せっかくつくるならずっと欲しかった個人サイトをつくろう、と思うに至りました。

ここ数年、色んなプラットフォームに活動が散っていて、どっかに集約する場所が欲しいと思っていたので、そんな感じで設計しました。

実名のページにするか、匿名のページにするか非常に迷ったんですが、基本的には匿名ベースのページにしました。
「蔀」としてのインターネットの活動をストックしていくところにしています。
会社の活動をプラスするともうちょっと内容充実するんですが、そこまでプライバシー丸裸戦法をするのは抵抗ありまして。

カードデザイン

プロフィールページは、カードデザインを採用しました。
WorksとかActivitiesとかのコンテンツを横にスライドするようにしています。
正直今の数だと折り返した方が見やすいと思うんですが、ここは個人的な好みです。

最近のWebサイトでよく見るレイアウトだけど、どうやって実装しているのか知らなかったんですが、CSSのFlexboxを使うことで実現していました。
完全にJavaScriptの世界だと思っていたので、CSSで実現できるのは意外でした。
今回のサイト開発で、イマドキのWeb開発において、CSSって結構役割大きいんだな、って思いました。

ちなみに横スクロールじゃなくて、折り返しにすることも容易にできます。
すごいぞ、Flexbox。

横にスライドできることをユーザーに伝える

ちょっとしたこだわりポイントを書かせてください。

カードデザイン、ユーザーとして見ると、「あ、ここスワイプできるんだ」という経験することがたまにあります。
僕のサイトだと特に情報量少ないので、普通にレイアウトするとカード部分が一枚しかないと思われて終わることになると思いました。

そこで、サイズを敢えてブラウザ上で見切れるような大きさに調整しました。
ただ、PCのブラウザのウィンドウサイズや、モバイル端末の画面サイズによっては意図した通りになってないかもですが。
本職のWebの人たちはどうしてるんでしょうかね。

ブログ機能で悩む

プロフィールページは比較的簡単だったんですが、個人ブログ機能で悩みました。
ブログ記事ファイルの置き場として、大きく2つの選択肢がありました。

  1. Markdownファイルをリポジトリの中に埋めこんで、そこを読む
  2. Notionでホスティングする

今後のブログ更新を考えたとき、1.だと一つ記事書くたびにGithubにプッシュしなきゃいけないのと、執筆もVSCodeでやる感じになると思われました。
VSCodeで書いて書けないこともないですし、もうちょっと書きやすい何かで書いて、Markdownファイルだけ作成するでも良いは良いですが、
僕は今、文章書くとなると、ほぼNotionでやっているので、Notionで書いた文章をWebサイトが叩いてくれるのが嬉しいと思いました。

以前notion-blogは簡単に使ったことがありました。

https://zenn.dev/st43/articles/9a714916c50b80

ただこちらも使用感があまり良くなかったのと、公式APIがベータ版ですが公開されており、こちらでやるのが筋だろうなと思いました。

https://developers.notion.com/

ただ、こちらの記事なんかを読むと、
Notion APIはまだ色々足りない感があって、方向性に悩んでいました。
以上をまとめると、選択肢は3つになりました。

  1. Markdownファイルをリポジトリの中に埋めこんで、そこを読む
  2. notion-blogベースでやる
  3. Notion APIのドキュメント読んで自前で実装する

自前で実装もやってできなくはないでしょうが、僕のWebのスキルだとおそらく一ヶ月はかかる大仕事になってしまうので、
ちょっとキツいなあと思っていました。

実装としてやらなければいけないことは、H1とかH2とか指定されてるプロパティを読んで、
それをHTML要素に変換するだけなんで、イメージはついていたんですが、
そのぐらいなら、NotionアプリにMarkdown形式でエクスポートする機能もあるので、
それ使って埋めこんだ方が賢いのでは? とも思われました。

Notion API

そんな悩みをTwitterに書いていたら、こんなリプライが。

https://twitter.com/shogocat/status/1412405468891332609?s=20

notion-blogしか知りませんでしたが、こんなリポジトリがありました。

https://github.com/samuelkraft/notion-blog-nextjs

実はこのリプライの前に自分でNotion APIを使ったサンプルを探していたんですが、そのときはこちらは見つけられませんでした。
僕が見つけたのは、

https://github.com/transitive-bullshit/nextjs-notion-starter-kit

でした。こちらの方が多機能なんですが、多機能すぎて僕のようなWeb素人がカスタマイズするにはとっつきづらくて、キツさを感じていました。

samuelkraftさんのnotion-blog-nextjsはまさに僕が求めていたもので、これをベースにしたらイケる、という感覚がありました。

Notion APIを使って生じた課題

詳しくは↓を見て頂きたいんですが、とりあえず公開できるレベルまでは持っていけました。

https://www.shetommy.com/articles

notion-blog-nextjsの仕様だとPage IDでurlをルーティングする仕組みだったんですが、個人的にはタイトルであって欲しかったのでタイトルにしています。

Notion APIのDB情報取得は、 DBの要素を作成日時が新しい順に返します。
Notionはページの作成日時をユーザーが変更する方法がないので、もし変えたければクライアント側でsortする必要があります。

notion-blog-nextjsのつくり的に、sortするのが難しかったので、昔のブログの古いものから順にDBに追加していくことで順序性を保ちました。

また、Notionのブロック取得は100ブロックが上限でして、それを超えると、自分でページネーションしないといけません。
100ブロックを超える長文そうそうないやろ、と思っていたんですが、
どうも過去の僕はなかなかの長文を公開しており、容易に100ブロックを超えました。
これは来週以降対応する課題としています。

あとはNotion API、現状だとテキストライクなブロックしか返せないので、画像やコードブロックは全部unsupportedで返してしまいます。
画像使えないのはかなりキツいかと思います。
(僕のブログはテキストで勝負してたタイプだったので、文字だけでもまあギリいいかな、って感じでしたが)

まとめ

他にも書きたいネタはいくつかあるんですが、尺の都合で割愛します。
(独自ドメインとった話とか、Safariだけ最後のカードがちゃんと表示されない不具合とか)

次回はNotion APIの詳細について共有できればと思います。
そして個人サイトには、まだまだ宿題が残っているので、来週以降ゆっくり対応していけたらと思います。