supabase-sql について
Supabase SQL Editor に貼り付ける前に、SQL マイグレーションを整理・整形するスキルです。冪等な記述、適切な service role の RLS ポリシー、依存関係の記録を重視します。
主な機能
- 01SQLコメントと書式の修正
- 02ポリシー・トリガー・インデックスの冪等化
- 03service role の RLS ポリシー修正
- 04未使用の列挙型や冗長部分の削除
- 05マイグレーション依存関係の記録
活用シーン
- 01Supabase SQL Editor 用のマイグレーション準備
- 02ポリシーやトリガーの再実行に備える
- 03service role のアクセス規則を確認
- 04必要なテーブルや関数を記録
インストール
コマンドをコピーしてターミナルで実行します。
$
npx skills add https:/ / github.com/ scientiacapital/ skills --skill supabase-sqlインストール後、Claude Code で/supabase-sqlを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
config.jsonreference/function-patterns.mdrls-patterns.md詳細
Supabase SQL Editor に直接貼り付けるための SQL マイグレーションをクリーンアップして整形します。冪等性、適切な RLS ポリシー(特にサービスロールのパターン)、標準化されたフォーマット、依存関係のドキュメント化を保証します。
<quick_start> 任意の SQL マイグレーションをクリーンアップする:
- タイポを修正する(コメントは
-→--) - 冪等性を追加する(
IF NOT EXISTS、DROP ... IF EXISTS) - RLS ポリシーを修正する(サービスロールは JWT チェックではなく
TO service_roleを使用する) - デッドコードを削除する(未使用の enum)
- 大文字・小文字を標準化する(
NOW()、TIMESTAMPTZ) - 末尾に依存関係のコメントを追加する
DROP POLICY IF EXISTS "Policy name" ON table_name;
CREATE POLICY "Policy name" ON table_name ...
</quick_start>
<success_criteria> SQL クリーンアップは次の場合に成功です:
- すべてのポリシーとトリガーが
CREATEの前にDROP ... IF EXISTSを使用している - サービスロールのポリシーが(JWT チェックではなく)
TO service_roleを使用している - インデックスが
IF NOT EXISTSを使用している - 未使用の enum が残っていない
- 依存関係がマイグレーションの末尾に記載されている
- SQL が Supabase SQL Editor でエラーなく実行される </success_criteria>
<core_patterns> Supabase SQL Editor に直接貼り付けるための SQL マイグレーションをクリーンアップします。
クリーンアップチェックリスト
各項目を順に確認します:
- タイポを修正する - よくある例: コメント行で
--の代わりに-になっている - 冪等性を追加する - インデックスには
IF NOT EXISTS、ポリシーやトリガーの前にはDROP ... IF EXISTS - デッドコードを削除する - 作成されたが一度も使用されない enum(多くの場合 TEXT + CHECK が好まれる)
- RLS ポリシーを修正する - サービスロールは JWT チェックではなく
TO service_roleを使用する必要がある - 大文字・小文字を標準化する -
now()ではなくNOW()、timestamptzではなくTIMESTAMPTZ - 不要なものを削除する - 冗長な RAISE NOTICE ブロック、重複したコメント、ファイルパスのヘッダー
- 依存関係を検証する - 必要なテーブルを末尾に列挙する
出力フォーマット
-- ============================================
-- 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 ...
よくある修正
サービスロールの RLS ポリシー
-- 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);
冪等なポリシー
-- Always drop before create
DROP POLICY IF EXISTS "Policy name" ON table_name;
CREATE POLICY "Policy name" ON table_name ...
冪等なトリガー
DROP TRIGGER IF EXISTS trigger_name ON table_name;
CREATE TRIGGER trigger_name ...
未使用の enum
enum が作成されているのに、テーブルが代わりに TEXT CHECK (...) を使用している場合は、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: businesses, call_logs, subscription_plans
-- Requires function: update_updated_at_column()
参照ファイル
reference/rls-patterns.md- Supabase 向けの一般的な RLS ポリシーパターンreference/function-patterns.md- トリガー関数、アトミック操作
結果サイドカーを出力する
最後のステップとして、~/.claude/skill-analytics/last-outcome-supabase-sql.json に書き込みます:
{"ts":"[UTC ISO8601]","skill":"supabase-sql","version":"1.0.0","variant":"default",
"status":"[success|partial|error]","runtime_ms":[estimated ms from start],
"metrics":{"migrations_written":[n],"tables_modified":[n],"rls_policies_created":[n]},
"error":null,"session_id":"[YYYY-MM-DD]"}
一部のステージが失敗したが結果が生成された場合は、ステータスに "partial" を使用します。出力がまったく生成されなかった場合にのみ "error" を使用します。
コメント
Markdown 対応