supabase-sql
SKILL.md
<quick_start> Clean any SQL migration:
- Fix typos (
-→--for comments) - Add idempotency (
IF NOT EXISTS,DROP ... IF EXISTS) - Fix RLS policies (service role uses
TO service_role, not JWT checks) - Remove dead code (unused enums)
- Standardize casing (
NOW(),TIMESTAMPTZ) - Add dependencies comment at end
DROP POLICY IF EXISTS "Policy name" ON table_name;
CREATE POLICY "Policy name" ON table_name ...
</quick_start>
<success_criteria> SQL cleanup is successful when:
- All policies and triggers use
DROP ... IF EXISTSbeforeCREATE - Service role policies use
TO service_role(not JWT checks) - Indexes use
IF NOT EXISTS - No unused enums remain
- Dependencies listed at end of migration
- SQL runs without errors in Supabase SQL Editor </success_criteria>
<core_patterns> Clean SQL migrations for direct paste into Supabase SQL Editor.
Cleanup Checklist
Run through each item:
- Fix typos - Common:
-instead of--on comment lines - Add idempotency -
IF NOT EXISTSon indexes,DROP ... IF EXISTSbefore policies/triggers - Remove dead code - Enums created but never used (TEXT + CHECK often preferred)
- Fix RLS policies - Service role must use
TO service_role, not JWT checks - Standardize casing -
NOW()notnow(),TIMESTAMPTZnottimestamptz - Remove clutter - Verbose RAISE NOTICE blocks, redundant comments, file path headers
- Validate dependencies - List required tables at end
Output Format
-- ============================================
-- Migration Name
-- Created: YYYY-MM-DD
-- Purpose: One-line description
-- ============================================
-- ============================================
-- Table Name
-- ============================================
CREATE TABLE IF NOT EXISTS ...
-- ============================================
-- Indexes
-- ============================================
CREATE INDEX IF NOT EXISTS ...
-- ============================================
-- Row Level Security
-- ============================================
ALTER TABLE ... ENABLE ROW LEVEL SECURITY;
DROP POLICY IF EXISTS "..." ON ...;
CREATE POLICY "..." ON ...
-- ============================================
-- Functions
-- ============================================
CREATE OR REPLACE FUNCTION ...
-- ============================================
-- Triggers
-- ============================================
DROP TRIGGER IF EXISTS ... ON ...;
CREATE TRIGGER ...
Common Fixes
RLS Policy for Service Role
-- WRONG (doesn't work reliably)
CREATE POLICY "Service role access" ON my_table
FOR ALL
USING (auth.jwt() ->> 'role' = 'service_role');
-- CORRECT
CREATE POLICY "Service role access" ON my_table
FOR ALL
TO service_role
USING (true)
WITH CHECK (true);
Idempotent Policies
-- Always drop before create
DROP POLICY IF EXISTS "Policy name" ON table_name;
CREATE POLICY "Policy name" ON table_name ...
Idempotent Triggers
DROP TRIGGER IF EXISTS trigger_name ON table_name;
CREATE TRIGGER trigger_name ...
Unused Enums
If you see enum created but table uses TEXT CHECK (...) instead, remove the enum:
-- DELETE THIS - never used
DO $$
BEGIN
IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'my_enum') THEN
CREATE TYPE my_enum AS ENUM ('a', 'b', 'c');
END IF;
END$$;
-- Table actually uses TEXT with CHECK (keep this)
status TEXT NOT NULL CHECK (status IN ('a', 'b', 'c'))
Dependencies Section
Always end with dependencies note if tables are referenced:
-- Dependencies: businesses, call_logs, subscription_plans
-- Requires function: update_updated_at_column()
Reference Files
reference/rls-patterns.md- Common RLS policy patterns for Supabasereference/function-patterns.md- Trigger functions, atomic operations
Weekly Installs
26
Repository
scientiacapital/skillsGitHub Stars
5
First Seen
Jan 23, 2026
Security Audits
Installed on
codex24
gemini-cli24
opencode23
claude-code22
github-copilot21
amp19