Restricting Access on Auth, Storage, and Realtime Schemas on April 21, 2025

Mar 18, 2025

On April 21, we are restricting certain SQL actions you can perform in your database’s auth, storage, and realtime schemas.

Why are we making these restrictions?#

Supabase Auth, Storage, and Realtime services each rely on their respective schemas in order to function properly.

These restrictions prevent unintended side effects like third-party tooling and user defined changes altering schemas or their objects, such as migration tables and database functions, that could disrupt or break functionality.

What this means for your project#

On April 21, you will no longer be able to perform the following actions on the auth, storage, and realtime schemas:

  • Create tables and database functions
  • Drop existing tables or database functions
  • Create indexes on existing tables
  • Perform destructive actions (i.e. INSERT, UPDATE, DELETE, TRUNCATE) on the following migration tables:
    • auth.schema_migrations
    • storage.migrations
    • realtime.schema_migrations
  • Revoking privileges on tables in these schemas from API roles (e.g. anon)

However, you will still have permissions to perform the following actions:

  • Create foreign keys referencing tables in the auth, storage, and realtime schemas
  • Create RLS policies and database triggers on the following tables:
    • auth.audit_log_entries
    • auth.identities
    • auth.refresh_tokens
    • auth.sessions
    • auth.users
    • storage.buckets
    • storage.migrations
    • storage.objects
    • storage.s3_multipart_uploads
    • storage.s3_multipart_uploads_parts
    • realtime.messages

How to determine if you’re affected?#

  • Run the following query to check if you created any tables in the auth, storage, and realtime schemas:

_14
SET search_path = '';
_14
SELECT oid::regclass AS table_name
_14
FROM pg_class
_14
WHERE
_14
(relnamespace = 'auth'::regnamespace AND relowner != 'supabase_auth_admin'::regrole)
_14
OR (relnamespace = 'storage'::regnamespace AND relowner != 'supabase_storage_admin'::regrole)
_14
OR (
_14
relnamespace = 'realtime'::regnamespace
_14
AND relowner NOT IN (
_14
SELECT oid
_14
FROM pg_roles
_14
WHERE rolname IN ('supabase_admin', 'supabase_realtime_admin')
_14
)
_14
);

  • Run the following query to check if you created any database functions in the auth, storage, and realtime schemas:

_14
SET search_path = '';
_14
SELECT pg_catalog.format('%s(%s)', oid::regproc, pg_get_function_identity_arguments(oid::regproc)) AS function_name
_14
FROM pg_proc
_14
WHERE
_14
(pronamespace = 'auth'::regnamespace AND proowner != 'supabase_auth_admin'::regrole)
_14
OR (pronamespace = 'storage'::regnamespace AND proowner != 'supabase_storage_admin'::regrole)
_14
OR (
_14
pronamespace = 'realtime'::regnamespace
_14
AND proowner NOT IN (
_14
SELECT oid
_14
FROM pg_roles
_14
WHERE rolname IN ('supabase_admin', 'supabase_realtime_admin')
_14
)
_14
);

What you need to do#

If any of the above queries return a result, you must move them to either the public schema or a schema that you’ve created. Otherwise, they will be deleted.

  • Here’s how you can move a table to another schema:

_10
CREATE SCHEMA IF NOT EXISTS my_custom_schema;
_10
ALTER TABLE storage.my_custom_table SET SCHEMA my_custom_schema;

  • Here’s how you can move a database function to another schema:

_10
CREATE SCHEMA IF NOT EXISTS my_custom_schema;
_10
ALTER FUNCTION storage.custom_function() SET SCHEMA my_custom_schema;

Additionally, if you're using Migrations or Branching, you'll need to patch your migrations to move these objects to your own schemas. E.g. if you have a migration 20250101000000_add_custom_table.sql like so:


_10
-- ...
_10
CREATE TABLE auth.my_custom_table (
_10
-- id int8 ...
_10
);
_10
-- ...

Then you need to edit it locally into:


_10
-- ...
_10
CREATE SCHEMA IF NOT EXISTS my_custom_schema;
_10
CREATE TABLE my_custom_schema.my_custom_table (
_10
-- id int8 ...
_10
);
_10
-- ...

Then you'll need to repair the migration history on the linked project:


_10
supabase migration repair --status reverted 20250101000000
_10
supabase migration repair --status applied 20250101000000

Build in a weekend, scale to millions