1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Supabaseで2026年10月30日から、新しく作るテーブルにGRANTが必要になります(RLSとは別の話)

1
Posted at

個人でWebサイトやアプリを作っています(屋号は sesebox です)。tsumoru、nami、ぶーかつなど、いくつかのアプリのデータベースに Supabase を使っています。

2026年9月23日、Supabaseから全プロジェクトのアカウント宛てに、こんな件名のメールが届きました。

New tables in public need explicit grants from October 30

10月30日から、public スキーマに新しく作るテーブルには、明示的な GRANT が必要になるというお知らせです。自分のプロジェクトへの影響を確かめて、マイグレーション(テーブルを作るSQL)の書き方を変えたので、まとめておきます。

※内容はSupabaseからのメールと、そこにあった公式ディスカッションの案内に基づいています。まだ10月30日前なので、実際に permission denied を踏んだわけではありません。

何が変わるのか

Supabaseでは、public スキーマにテーブルを作ると、これまでは自動でData API(supabase-js やRESTから触れる入口)に公開されていました。

これが10月30日以降は、自動では公開されなくなります。 権限(GRANT)を付けないままだと、supabase-js などから触ったときに permission denied のエラーになる、という内容でした。

10月30日より前に作ったテーブル 10月30日以降に作るテーブル
今の権限 そのまま動く(何もしなくてよい) GRANTが無いとAPIから見えない

新規プロジェクトや、supabase db reset で作り直した場合も対象、とのことでした。

GRANTとRLSは別物

ここで混乱しやすいので、整理しておきます。

  • GRANT:そのロール(anon・authenticatedなど)に、そのテーブルを触る権限そのものを与える
  • RLS(Row Level Security):権限があるロールのうち、どの行を見せるかを絞る

つまり、

  1. GRANTで「触っていい」という入口を開ける
  2. RLSで「見えていい行」だけに絞る

という2段階です。RLSを設定しただけでは足りず、GRANTも別に必要になります。 「RLSを書いたから大丈夫」ではなくなります。

自分のマイグレーションに足したもの

新しくテーブルを作るときは、同じSQLファイルにGRANT文を足すことにしました。

create table public.example (
  id uuid primary key default gen_random_uuid(),
  user_id uuid not null,
  created_at timestamptz not null default now()
);

-- RLSは従来どおり有効にする
alter table public.example enable row level security;

-- ★ここが新しく必要になる部分
grant select on public.example to anon;
grant select, insert, update, delete on public.example to authenticated;
grant select, insert, update, delete on public.example to service_role;

ポイントは、ロールごとに、そのテーブルで何をさせるかを決めて書くことです。

  • authenticated:ログイン済みのユーザー。アプリから読み書きさせるなら付ける
  • service_role:サーバー側の管理用。ふだんはこちらだけで触る設計にしているテーブルもある
  • anon:ログインしていない人。読ませたくないテーブルには付けない

私のアプリには「ログインしていない人には一切読ませない」テーブルがあります。そういうテーブルは anon への grant を書かないのが正解です。全部にコピペで3行付けると、本来閉じておきたい入口を開けてしまうので注意が必要です。

確認のしかた

GRANTの状態は、SQLで確認できます。

select grantee, privilege_type
from information_schema.role_table_grants
where table_schema = 'public' and table_name = 'example'
order by grantee, privilege_type;

テーブルを作った直後に、想定した行だけが出ているかを見れば、付け忘れや付けすぎに気づけます。

いつから何をすればいいか

やること
今あるテーブル 何もしなくてよい(今の権限のまま動く)
10月30日以降に作るテーブル マイグレーションに grant を書く
過去のマイグレーションSQL 触らなくてよい。ただし流用するときは、GRANTが入っているかを見る

私は「新しいテーブルを作るSQLには、grant を必ず一緒に書く」という手順書の1行を足しました。あとから気づくより、作るときにセットで書くほうが確実だからです。

まとめ

  • 10月30日から、public に作る新しいテーブルは自動でAPIに公開されない
  • 今あるテーブルには影響しない
  • GRANT(触っていいか)とRLS(どの行を見せるか)は別物。両方いる
  • 新しいテーブルのSQLに grant を書く。読ませたくないロールには付けない
  • information_schema.role_table_grants で、付いている権限を確認できる

アプリごとにSupabaseを使っているので、こういう仕様変更のお知らせは、メールが来たときに手順書へ書いておくのが安心です。

作っているものの一覧は sesebox.dev に置いています。

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?