supabase とは何ですか#
supabaseは、Firebase の代替となるオープンソースの BaaS プロジェクトです。安定した、強力で、使いやすく、拡張性のあるバックエンド機能を提供し、さまざまなモダンなアプリケーションに必要なものを提供します。Supabase は、PostgreSQL データベースと RESTful API に基づいて構築されており、認証、リアルタイムデータプッシュ、ストレージなど、一般的なバックエンドサービスも提供しています。
サーバーを購入する必要はなく、簡単な SQL 文とデータベースの知識さえあれば、バックエンドサービスを作成することができます。もちろん、その機能は非常に強力ですが、この記事では Next.js での使用方法についてのみ説明します。
supabase の使用方法#
学習タスクの内容は、公式ドキュメントを詳しく読む必要があります。
公式ドキュメントのUse Supabase with NextJSのセクションに従って、次の手順で使用します。
ここでは、supabase を使用してブログの閲覧数を保存します。
プロジェクトとテーブルの作成#
https://app.supabase.com/projectsでプロジェクトを作成します。
SQL エディタまたはグラフィカルなデータベースエディタを使用して、Views という名前のテーブルを作成します。
ここではグラフィカルなデータベースエディタを使用していますが、データベース内の New table をクリックして Views テーブルを作成することもできます。
列の slug はブログのタイトルを、count は対応するブログの閲覧数を表します。
Next.js プロジェクトの作成#
npx create-next-app@latest --typescript
supabase-js のインストール#
npm install @supabase/supabase-js
supabase の作成#
ルートディレクトリに lib フォルダを作成し、supabase.ts という名前のファイルを作成します。
import { createClient } from '@supabase/supabase-js';
const supabaseUrl = process.env.NEXT_PUBLIC_SUPABASE_URL as string;
const supabaseKey = process.env.NEXT_PUBLIC_SUPABASE_KEY as string;
export const supabase = createClient(supabaseUrl, supabaseKey);
project_url と supabase_key はプロジェクトの設定オプションで見つけることができます。
同様に、キーを公開しないようにするために、env.local に保存することをお勧めします。
💡 ヒント: Next.js で env.local を使用する場合、NEXT_PUBLIC の接頭辞を付ける必要があります。そうしないとエラーが発生します。
CRUD#
詳細なコマンドは、JavaScriptドキュメントで確認できます。
ブログ記事ページを開いたときに、現在のブログの閲覧数をクエリする必要がある場合は、次のようにします。
fetch(`/api/views`);
pages/api/views ディレクトリに index.ts を作成します。
import { supabase } from '@/lib/supabase';
import type { NextApiRequest, NextApiResponse } from 'next';
export default async function handler(
req: NextApiRequest,
res: NextApiResponse
) {
try {
let { data } = await supabase.from('Views').select('*');
return res.status(200).json(data);
} catch (e: any) {
console.log(e);
return res.status(500).json({ message: e.message });
}
}
SQL のような文を書くことで、Views テーブルからすべてのデータを取得できます。
また、post リクエストを使用して slug を渡し、対応するデータをクエリすることもできます。
同時に、ブログ記事ページを開いたときには、現在のブログの閲覧数を 1 つ増やす必要があります。そのためには、slug パラメータを post リクエストで渡すことができます。
fetch(`/api/views/${slug}`, {
method: 'POST'
});
pages/api/views ディレクトリに[slug].ts
を作成します。
import { supabase } from '@/lib/supabase';
import type { NextApiRequest, NextApiResponse } from 'next';
export default async function handler(
req: NextApiRequest,
res: NextApiResponse
) {
try {
const slug = req.query?.slug as string;
if (!slug) {
return res.status(400).json({ message: 'Slug is required.' });
}
const { data } = await supabase
.from('Views')
.select('count')
.eq('slug', slug);
const views = !data?.length ? 0 : Number(data[0].count);
if (req.method === 'POST') {
if (views === 0) {
await supabase.from('Views').insert({ count: views + 1, slug: slug });
return res.status(200).json({
total: views + 1
});
} else {
await supabase
.from('views')
.update({ count: views + 1 })
.eq('slug', slug);
return res.status(200).json({
total: views + 1
});
}
}
if (req.method === 'GET') {
return res.status(200).json({ total: views });
}
} catch (e: any) {
console.log(e);
return res.status(500).json({ message: e.message });
}
}
insert を使用して新規作成し、update を使用して更新します。これにより、閲覧数が supabase に保存されます。
その他の機能#
supabase はバケットストレージ機能もサポートしています。私のプロジェクトでは、og イメージを supabase に保存しています。
次のプロジェクトでは、Firebase の代わりに supabase を引き続き使用する準備をしています。