
目次
要求定義書ができたので、いよいよ環境を作り始めます。
ただ、ここでいう「環境を作る」というのは、アプリのコードを書くことではありません。コードを書く前に、4つのサービスを準備する必要がありました。
まず、それぞれが何をしているのかを簡単に説明します。
Next.jsは、アプリの本体を作るためのフレームワークです。
ログイン画面や記事の編集画面など、画面に表示されるものはすべてNext.jsで作ります。Insight Notesのときにも使ったので、これは馴染みがありました。
GitHubは、コードの保管庫です。自分のパソコンで書いたコードをGitHubに保存(push)しておくと、パソコンが壊れてもコードが消えません。
もうひとつ大事な役割として、GitHubにpushしたコードが、後述するVercelに自動で反映される仕組みの起点になっています。
Supabaseは、データベースと認証機能を提供するサービスです。
記事のタイトルや本文、公開・非公開の状態、ログインのためのユーザー情報など、アプリが扱うデータはすべてSupabaseに保存されます。
Insight Notesでも使っていたので、ダッシュボードの操作にはある程度慣れていました。
Vercelは、作ったアプリをインターネット上に公開するためのサービスです。
自分のパソコンではlocalhost:3000というアドレスで動いているアプリを、誰でもアクセスできるURLで見られるようにしてくれます。
GitHubと連携しているので、コードをGitHubにpushするだけで、Vercel側も自動で更新されます。
この4つの関係を整理すると、こうなります。
Next.jsでアプリの画面を作り、Supabaseにデータを保存して、GitHubでコードを管理し、Vercelで公開する。
それぞれの役割がはっきり分かれていて、全部がつながって初めてアプリとして動きます。
セットアップの手順はClaudeが順番に教えてくれました。
ターミナルでNext.jsのプロジェクトを作成して、GitHubにリポジトリを作って、Supabaseで新しいプロジェクトを作って、最後にVercelでデプロイする。
Insight Notesのときに一度やっている流れなので、ここは比較的スムーズに進みました。
ひとつだけ気をつけたのは、Supabaseのプロジェクトをどこに作るかです。
自分のSupabaseには2つの「組織(Organization)」があって、有料プランの組織にはBookConnectとMyFavoritePlaceという既存のプロジェクトが入っています。
無料プランの組織にはInsight Notesが1つだけ入っていて、無料プランでは1組織につき2プロジェクトまで作れるので、CMSもどきはInsight Notesと同じ無料の組織に入れました。

Vercelのデプロイが成功して「Congratulations!」の画面が出たとき、Next.jsのデフォルト画面がインターネット上に表示されているのを確認できました。まだ何の機能もない真っ白なアプリですが、ここまでくれば土台は完成です。
土台が整ったので、最初に作る機能はログインでした。
個人用のツールなので、会員登録の画面は作っていません。
Supabaseのダッシュボードから自分のアカウントを1つだけ手動で登録して、そのアカウントでログインできるようにするだけです。
自分しか使わないのだから、これで十分でした。
ログインの仕組みには、「Middleware(ミドルウェア)」という概念が登場しました。
Claudeはこれをホテルのフロントに例えて説明してくれました。
ホテルには各階に客室がありますが、どの部屋に行くにもまずフロントを通りますよね。
フロントで宿泊客かどうかを確認して、予約がある人はそのまま部屋に通し、予約のない人には「予約ページに行ってください」と案内する。
Middlewareはまさにこの役割で、どのページにアクセスしても、まず「この人はログイン済みか?」を確認して、ログインしていなければログイン画面に飛ばす仕組みです。
仕組みはわかったものの、この時点ではMiddlewareのコードの意味を全部理解できていたわけではありません。
Claudeの説明を聞いて「なるほど、番人みたいなものね」というレベルの理解で先に進みました。
コードの1行1行が何をしているかは、正直よくわからない部分もありました。
ただ、「何のために存在するのか」はわかっていたので、ここで立ち止まるよりも実際に動かしてみることを優先しました。


ログインフォームにメールアドレスとパスワードを入力して、ダッシュボードに遷移したときは素直にうれしかったです。Vercelにデプロイして、本番のURLでも同じ動作が確認できました。
ログインができたので、次はCMSの心臓部、記事のCRUD機能を作りました。
CRUDというのは、Create(作成)、Read(読み取り)、Update(更新)、Delete(削除)の頭文字を並べたもので、データを扱うアプリの基本操作をまとめた言葉です。
実装の順番は、まず記事の一覧表示から始めて、次に新規作成、それから編集、最後に削除という流れでした。
この順番にも理由があって、作成機能がないと編集するデータがそもそも存在しないし、一覧表示がないとどの記事を編集するか選べない。依存関係を考えると、この順番が一番スムーズに動作確認できるとClaudeに説明されました。
記事の一覧ページを作ったとき、最初に表示されたのは「記事がありません」という空っぽの画面でした。
まだ1つも記事を作っていないのだから当然です。そこからテスト投稿を作って、一覧に記事のタイトルが表示されたときは、「お、動いてる」とちょっとした手応えがありました。



編集画面では、タイトル、本文、公開状態(下書きか公開済みか)を変更できるようにしました。
削除ボタンも編集画面に置いて、押すと確認ダイアログが出る仕様です。
このあたりの実装は、ログインのときほど苦労しませんでした。
ログインのときに学んだServer ActionやSupabaseへの問い合わせの仕組みがそのまま使えたからです。
でも、Claudeの説明が飛び飛びになる場面は相変わらずで、「なぜこのファイルから先に作るのか」という順番の説明が抜けていて混乱したこともありました。
この問題は、次の記事で書く場面でもっと大きくなっていきます。
次の記事では、Claudeとのコミュニケーションで壁にぶつかった話と、そこから生まれたルール、そしてMarkdownエディタと画像アップロード機能の実装について書いています。