You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Hiding the signup button in the frontend is not enough. If the **Auth server still allows signups**, an attacker can call the API directly with the public `anon` key and create arbitrary users.
- Disable email/password signups in the Dashboard: Authentication → Providers → Email → Disable sign ups (invite-only), or set the equivalent GoTrue setting.
147
+
- Verify the API now returns 4xx to the previous call and no new user is created.
148
+
- If you rely on invites or SSO, ensure all other providers are disabled unless explicitly needed.
149
+
150
+
## RLS and Views: Write bypass via PostgREST
151
+
152
+
Using a Postgres VIEW to “hide” sensitive columns and exposing it via PostgREST can change how privileges are evaluated. In PostgreSQL:
153
+
- Ordinary views execute with the privileges of the view owner by default (definer semantics). In PG ≥15 you can opt into `security_invoker`.
154
+
- Row Level Security (RLS) applies on base tables. Table owners bypass RLS unless `FORCE ROW LEVEL SECURITY` is set on the table.
155
+
- Updatable views can accept INSERT/UPDATE/DELETE that are then applied to the base table. Without `WITH CHECK OPTION`, writes that don’t match the view predicate may still succeed.
156
+
157
+
Risk pattern observed in the wild:
158
+
- A reduced-column view is exposed through Supabase REST and granted to `anon`/`authenticated`.
159
+
- PostgREST allows DML on the updatable view and the operation is evaluated with the view owner’s privileges, effectively bypassing the intended RLS policies on the base table.
160
+
- Result: low-privileged clients can mass-edit rows (e.g., profile bios/avatars) they should not be able to modify.
161
+
162
+
Illustrative write via view (attempted from a public client):
- Prefer exposing base tables with explicit, least-privilege grants and precise RLS policies.
176
+
- If you must expose a view:
177
+
- Make it non-updatable (e.g., include expressions/joins) or deny `INSERT/UPDATE/DELETE` on the view to all untrusted roles.
178
+
- Enforce `ALTER VIEW <v> SET (security_invoker = on)` so the invoker’s privileges are used instead of the owner’s.
179
+
- On base tables, use `ALTER TABLE <t> FORCE ROW LEVEL SECURITY;` so even owners are subject to RLS.
180
+
- If allowing writes via an updatable view, add `WITH [LOCAL|CASCADED] CHECK OPTION` and complementary RLS on base tables to ensure only allowed rows can be written/changed.
181
+
- In Supabase, avoid granting `anon`/`authenticated` any write privileges on views unless you have verified end-to-end behavior with tests.
182
+
183
+
Detection tip:
184
+
- From `anon` and an `authenticated` test user, attempt all CRUD operations against every exposed table/view. Any successful write where you expected denial indicates a misconfiguration.
185
+
186
+
### OpenAPI-driven CRUD probing from anon/auth roles
187
+
188
+
PostgREST exposes an OpenAPI document that you can use to enumerate all REST resources, then automatically probe allowed operations from low-privileged roles.
189
+
190
+
Fetch the OpenAPI (works with the public anon key):
- Automate the previous probes for both `anon` and a minimally `authenticated` user and integrate them in CI to catch regressions.
236
+
- Treat every exposed table/view/function as a first-class surface. Don’t assume a view “inherits” the same RLS posture as its base tables.
237
+
130
238
### Passwords & sessions
131
239
132
240
It's possible to indicate the minimum password length (by default), requirements (no by default) and disallow to use leaked passwords.\
@@ -160,7 +268,13 @@ It's possible to set an SMTP to send emails.
160
268
161
269
It's possible to **store secrets** in supabase also which will be **accessible by edge functions** (the can be created and deleted from the web, but it's not possible to access their value directly).
162
270
163
-
{{#include ../banners/hacktricks-training.md}}
164
-
271
+
## References
165
272
273
+
-[Building Hacker Communities: Bug Bounty Village, getDisclosed’s Supabase Misconfig, and the LHE Squad (Ep. 133) – YouTube](https://youtu.be/NI-eXMlXma4)
0 commit comments