Edge Runtime 環境で始める Next.js + Hono + Supabase + Prisma 開発
概要
Web開発を始めて1年が経ち、学生として様々な技術に触れ、ハッカソンにも参加してきました。その経験を活かし、今まで学んできた技術を全て活用できるTypeScriptのフルスタックテンプレートを作成しました。
対象ユーザー
- TypeScriptから学習を始めた初学者
- 最新のトレンド技術に挑戦したい開発者
- ハッカソンなどの短期開発で即座に使えるテンプレートを求める人
制作背景
- 自身の技術スタックを活用したプロジェクト構築
- 開発初心者向けの明確なプロジェクト構造の提供
- ハッカソンなどの短期開発での即時利用を想定
技術スタック
- フロントエンド & バックエンド: Next.js(Hono & Supabase Auth 統合)
- データベース: Supabase(Prisma Accelerate 経由で接続)
- ORM: Prisma
- 認証: Supabase Auth
- スタイリング: CSS Modules
- UIライブラリ: Mantine UI
- ホスティング: Vercel
- コード品質管理: ESLint & stylelint
- エッジランタイム対応: Prisma Accelerate
プロジェクト構造
project-root/
├── src/
│ ├── app/ # Next.js App Routerのルートディレクトリ
│ │ ├── api/ # APIエンドポイント用ディレクトリ
│ │ │ └── [[route]]/ # 動的ルーティング用ディレクトリ
│ │ │ └── route.ts # Honoを使用したAPIルート定義
│ │ ├── auth/ # Supabase Auth認証関連ページ
│ │ ├── layout.tsx # 共通レイアウトコンポーネント
│ │ ├── page.module.tsx # トップページ用スタイル
│ │ └── page.tsx # トップページコンポーネント
│ ├── components/ # 再利用可能なUIコンポーネント
│ │ └── Header/ # ヘッダーコンポーネント
│ └── features/ # 機能ごとのコンポーネント
│ └── TodoApp/ # Todoアプリ機能
├── prisma/ # Prisma関連ファイル
│ └── schema.prisma # データベーススキーマ定義
├── styles/ # グローバルスタイル
│ └── globals.css # アプリ全体に適用されるCSS
├── .env # 環境変数(非公開)
├── .env.example # 環境変数のサンプル
├── .gitignore # Gitの追跡対象外ファイル設定
├── .eslintrc.ts # ESLint設定
├── next.config.js # Next.js設定
├── package.json # プロジェクト依存関係
├── README.md # プロジェクト説明
├── stylelint.config.js # Stylelint設定
└── tsconfig.json # TypeScript設定
Edge Runtime対応のAPI実装
APIルートは以下のように実装しています:
import { PrismaClient } from "@prisma/client/edge";
import { Hono } from "hono";
import { handle } from "hono/vercel";
export const runtime = "edge";
const app = new Hono().basePath("/api");
const prisma = new PrismaClient();
app.get("/todos", async (c) => {
const todos = await prisma.todo.findMany();
return c.json(todos);
});
app.post("/todos", async (c) => {
// 省略
});
app.put("/todos/:id", async (c) => {
// 省略
});
app.delete("/todos/:id", async (c) => {
// 省略
});
export const GET = handle(app);
export const POST = handle(app);
export const PUT = handle(app);
export const DELETE = handle(app);
Edge Runtimeの特徴と注意点
Next.jsのEdge Functionsを使用することで、Vercelなどのエッジネットワーク上で動的なAPIを作成できます。これにより、ユーザーに近い場所でコードが実行され、レスポンス時間が短縮されます。
Edge Runtimeは通常のNode.js Runtimeとは異なる制約があります:
-
Prismaを使用する場合は @prisma/client/edge からインポートする必要があります
-
TCP接続がサポートされていないため、Prismaのデフォルト設定ではデータベースに接続できません
-
Prisma Data Platformを使用して、Prisma Data Proxyがデータベースとの間に入ることで、Edge環境に適した接続方法を提供します
認証
Supabase Authを採用しているのでSupabaseのdashboardを使います。
実装している機能は以下の通りです:
- サインアップ
- ログイン
- ログアウト
- パスワードリセット
Supabase Authを使用する場合は、環境変数に SUPABASE_URL と SUPABASE_ANON_KEY を設定する必要があります。これらの値はSupabaseのダッシュボードから取得できます。
メリット
- フルスタックのテンプレートでNext.js内で一通り開発ができて構造が理解しやすい点
(初心者に優しい) - エッジランタイムのおかげでデプロイが数秒で完了
(ハッカソンで後半デプロイ祭りでグダらない!) - モダンな技術スタックを採用
(Next.js, Hono, Supabase, Prisma) - Edge Runtimeによる高速なレスポンス時間
- Prisma Accelerateを使用したエッジ環境でのデータベースアクセス
- Supabase Authによる認証機能の簡単な実装
デメリット
- Edge Runtimeの制約(TCP接続非対応など)により、一部の機能に制限がある
- Prisma AccelerateやSupabaseの設定が初学者には少し複雑
- パスワードリセット機能など、認証周りで追加の設定が必要な場合がある
最後に
まだプロジェクトとしては未完成な部分が多いですが、一度は作ってみたかったフルスタックテンプレートだったのでとても良い経験になりました。また、参考になるソースコードや実装も是非みていただけたらと思います。
このテンプレートは、Edge Runtimeを活用し、最新のWeb開発技術を統合しています。初学者でも理解しやすい構造を目指しながら、高度な機能も実装可能な柔軟性を持たせました。ハッカソンや個人プロジェクトでの即時利用を想定し、開発の効率化と学習促進を目的としています。
Discussion