← スキル一覧に戻る

supabase
by git-tao
AI content factory pipeline for generating technically verified articles using Claude Code
⭐ 0🍴 0📅 2026年1月20日
SKILL.md
name: supabase description: Supabase open-source Firebase alternative with PostgreSQL database, authentication, storage, real-time subscriptions, and edge functions
Supabase Skill
Comprehensive assistance with Supabase development - the open-source Firebase alternative with PostgreSQL database, Auth, Storage, Realtime, and Edge Functions.
When to Use This Skill
This skill should be triggered when:
- Working with Supabase database, auth, storage, or realtime
- Building full-stack applications with PostgreSQL
- Implementing user authentication and authorization
- Working with Row Level Security (RLS)
- Building real-time features with subscriptions
- Deploying Edge Functions (Deno)
- Using Supabase with React, Next.js, Vue, Flutter, etc.
Quick Reference
Initialize Supabase Client (JavaScript)
import { createClient } from '@supabase/supabase-js'
const supabase = createClient(
'https://your-project.supabase.co',
'your-anon-key'
)
Initialize for Server-Side (Next.js)
import { createServerClient } from '@supabase/ssr'
import { cookies } from 'next/headers'
export async function createClient() {
const cookieStore = await cookies()
return createServerClient(
process.env.NEXT_PUBLIC_SUPABASE_URL!,
process.env.NEXT_PUBLIC_SUPABASE_ANON_KEY!,
{
cookies: {
getAll() {
return cookieStore.getAll()
},
setAll(cookiesToSet) {
cookiesToSet.forEach(({ name, value, options }) =>
cookieStore.set(name, value, options)
)
},
},
}
)
}
Authentication
// Sign up
const { data, error } = await supabase.auth.signUp({
email: 'user@example.com',
password: 'password123'
})
// Sign in with email/password
const { data, error } = await supabase.auth.signInWithPassword({
email: 'user@example.com',
password: 'password123'
})
// Sign in with OAuth (Google, GitHub, etc.)
const { data, error } = await supabase.auth.signInWithOAuth({
provider: 'google',
options: {
redirectTo: 'http://localhost:3000/auth/callback'
}
})
// Sign out
await supabase.auth.signOut()
// Get current user
const { data: { user } } = await supabase.auth.getUser()
// Listen to auth changes
supabase.auth.onAuthStateChange((event, session) => {
console.log(event, session)
})
Database Queries
// SELECT
const { data, error } = await supabase
.from('posts')
.select('*')
// SELECT with relations
const { data, error } = await supabase
.from('posts')
.select(`
id,
title,
author:users(name, email)
`)
// INSERT
const { data, error } = await supabase
.from('posts')
.insert({ title: 'Hello', content: 'World' })
.select()
// UPDATE
const { data, error } = await supabase
.from('posts')
.update({ title: 'Updated' })
.eq('id', 1)
.select()
// DELETE
const { error } = await supabase
.from('posts')
.delete()
.eq('id', 1)
// UPSERT
const { data, error } = await supabase
.from('posts')
.upsert({ id: 1, title: 'Upserted' })
.select()
Query Filters
// Equality
.eq('column', 'value')
// Not equal
.neq('column', 'value')
// Greater than / Less than
.gt('column', 10)
.lt('column', 100)
.gte('column', 10)
.lte('column', 100)
// Pattern matching
.like('column', '%pattern%')
.ilike('column', '%pattern%') // case insensitive
// IN / NOT IN
.in('column', ['a', 'b', 'c'])
// IS NULL / IS NOT NULL
.is('column', null)
.not('column', 'is', null)
// Full text search
.textSearch('column', 'search terms')
// Ordering
.order('created_at', { ascending: false })
// Pagination
.range(0, 9) // First 10 rows
.limit(10)
Row Level Security (RLS)
-- Enable RLS on table
ALTER TABLE posts ENABLE ROW LEVEL SECURITY;
-- Allow users to read their own posts
CREATE POLICY "Users can read own posts"
ON posts FOR SELECT
USING (auth.uid() = user_id);
-- Allow users to insert their own posts
CREATE POLICY "Users can insert own posts"
ON posts FOR INSERT
WITH CHECK (auth.uid() = user_id);
-- Allow users to update their own posts
CREATE POLICY "Users can update own posts"
ON posts FOR UPDATE
USING (auth.uid() = user_id);
-- Allow users to delete their own posts
CREATE POLICY "Users can delete own posts"
ON posts FOR DELETE
USING (auth.uid() = user_id);
-- Public read access
CREATE POLICY "Public read access"
ON posts FOR SELECT
TO anon
USING (true);
Storage
// Upload file
const { data, error } = await supabase.storage
.from('avatars')
.upload('user1/avatar.png', file)
// Download file
const { data, error } = await supabase.storage
.from('avatars')
.download('user1/avatar.png')
// Get public URL
const { data } = supabase.storage
.from('avatars')
.getPublicUrl('user1/avatar.png')
// Create signed URL (temporary access)
const { data, error } = await supabase.storage
.from('private-bucket')
.createSignedUrl('path/to/file.pdf', 3600) // 1 hour
// Delete file
const { error } = await supabase.storage
.from('avatars')
.remove(['user1/avatar.png'])
// List files
const { data, error } = await supabase.storage
.from('avatars')
.list('user1', { limit: 100 })
Realtime Subscriptions
// Subscribe to database changes
const channel = supabase
.channel('posts-changes')
.on(
'postgres_changes',
{ event: '*', schema: 'public', table: 'posts' },
(payload) => {
console.log('Change received!', payload)
}
)
.subscribe()
// Subscribe to specific events
const channel = supabase
.channel('posts-inserts')
.on(
'postgres_changes',
{ event: 'INSERT', schema: 'public', table: 'posts' },
(payload) => console.log('New post:', payload.new)
)
.subscribe()
// Broadcast (for presence/custom events)
const channel = supabase.channel('room1')
// Send message
channel.send({
type: 'broadcast',
event: 'cursor-pos',
payload: { x: 100, y: 200 }
})
// Listen to broadcasts
channel.on('broadcast', { event: 'cursor-pos' }, (payload) => {
console.log(payload)
})
// Presence (track who's online)
channel
.on('presence', { event: 'sync' }, () => {
const state = channel.presenceState()
console.log('Online users:', state)
})
.subscribe(async (status) => {
if (status === 'SUBSCRIBED') {
await channel.track({ user_id: 'user1', online_at: new Date() })
}
})
// Unsubscribe
supabase.removeChannel(channel)
Edge Functions (Deno)
// supabase/functions/hello/index.ts
import { serve } from 'https://deno.land/std@0.168.0/http/server.ts'
import { createClient } from 'https://esm.sh/@supabase/supabase-js@2'
serve(async (req) => {
// Get auth token from request
const authHeader = req.headers.get('Authorization')!
// Create Supabase client with user's auth
const supabase = createClient(
Deno.env.get('SUPABASE_URL') ?? '',
Deno.env.get('SUPABASE_ANON_KEY') ?? '',
{ global: { headers: { Authorization: authHeader } } }
)
// Get user
const { data: { user } } = await supabase.auth.getUser()
return new Response(
JSON.stringify({ message: `Hello ${user?.email}!` }),
{ headers: { 'Content-Type': 'application/json' } }
)
})
Call Edge Function
const { data, error } = await supabase.functions.invoke('hello', {
body: { name: 'World' }
})
RPC (Remote Procedure Calls)
-- Create a function in Postgres
CREATE OR REPLACE FUNCTION get_user_posts(user_id uuid)
RETURNS SETOF posts AS $$
SELECT * FROM posts WHERE posts.user_id = $1;
$$ LANGUAGE sql;
// Call from client
const { data, error } = await supabase
.rpc('get_user_posts', { user_id: 'uuid-here' })
Environment Variables
# Public (safe for client-side)
NEXT_PUBLIC_SUPABASE_URL=https://your-project.supabase.co
NEXT_PUBLIC_SUPABASE_ANON_KEY=your-anon-key
# Private (server-side only)
SUPABASE_SERVICE_ROLE_KEY=your-service-role-key
CLI Commands
# Initialize project
supabase init
# Start local development
supabase start
# Stop local development
supabase stop
# Link to remote project
supabase link --project-ref your-project-ref
# Push database migrations
supabase db push
# Pull remote schema
supabase db pull
# Create new migration
supabase migration new migration_name
# Generate TypeScript types
supabase gen types typescript --local > types/supabase.ts
# Deploy Edge Functions
supabase functions deploy function-name
# Serve Edge Functions locally
supabase functions serve
Reference Files
This skill includes comprehensive documentation in references/:
- getting_started.md - Quickstarts and tutorials (83 pages)
- database.md - PostgreSQL, tables, queries, extensions (192 pages)
- auth.md - Authentication, OAuth, SSO, MFA (176 pages)
- storage.md - File uploads, buckets, CDN (68 pages)
- realtime.md - Subscriptions, broadcast, presence (17 pages)
- edge_functions.md - Deno functions, deployment (51 pages)
- ai_vectors.md - pgvector, embeddings, semantic search (48 pages)
- api.md - REST API, Management API (241 pages)
- cli.md - Supabase CLI commands (3 pages)
- self_hosting.md - Docker, self-hosted setup (14 pages)
Use view to read specific reference files when detailed information is needed.
Key Concepts
Service Role Key vs Anon Key
- Anon Key: Safe for client-side, respects RLS policies
- Service Role Key: Bypasses RLS, server-side only, never expose to client
Row Level Security (RLS)
- Enabled per-table with
ALTER TABLE ... ENABLE ROW LEVEL SECURITY - Policies define who can SELECT/INSERT/UPDATE/DELETE
- Use
auth.uid()to get current user's ID in policies
Realtime
- Enable on tables: Dashboard > Database > Replication
- Uses Postgres logical replication under the hood
Resources
- Dashboard: https://supabase.com/dashboard
- Documentation: https://supabase.com/docs
- GitHub: https://github.com/supabase/supabase
- Discord: https://discord.supabase.com
Notes
- This skill was automatically generated from 938 pages of official Supabase documentation
- Reference files contain detailed examples for each feature area
- Code examples use the latest Supabase JavaScript client (v2)
スコア
総合スコア
50/100
リポジトリの品質指標に基づく評価
✓SKILL.md
SKILL.mdファイルが含まれている
+20
○LICENSE
ライセンスが設定されている
0/10
○説明文
100文字以上の説明がある
0/10
○人気
GitHub Stars 100以上
0/15
○最近の活動
3ヶ月以内に更新がある
0/10
○フォーク
10回以上フォークされている
0/5
✓Issue管理
オープンIssueが50未満
+5
✓言語
プログラミング言語が設定されている
+5
○タグ
1つ以上のタグが設定されている
0/5
レビュー
💬
レビュー機能は近日公開予定です