-- Eine Attrappe des Supabase-Schemas `auth` — nur für die Migrationshistorie. -- -- ═══ Warum das hier steht, obwohl es niemand mehr braucht ═══ -- -- Der **Endstand** des Schemas ist frei von Supabase: kein Fremdschlüssel aus -- `public` zeigt nach `auth`, keine Policy ruft `auth.uid()`, keine -- Spaltenvorgabe nennt es. Geprüft, nicht vermutet. -- -- Die **Historie** ist es nicht. Die erste Migration von Juni 2026 hängt -- profiles an `auth.users`, und ein Dutzend Policies dieser Zeit fragen -- `auth.role() = 'authenticated'`. Abgelöst wurde das erst im August -- (20260805110000, 20260805140000). Wer die Migrationen von vorne abspielt — -- die CI tut das bei jedem Lauf, und genau dafür ist sie da —, kommt ohne -- diese Objekte nicht an der ersten Datei vorbei. -- -- Die Alternative wäre, die alten Migrationen umzuschreiben. Das hiesse, -- Geschichte zu fälschen: die Dateien beschreiben, was damals galt, und ein -- nachträglich geänderter Stand von Juni ist keiner, der je gelaufen ist. -- Eine Attrappe, die beim Abspielen trägt und danach leer stehenbleibt, ist -- die ehrlichere Lösung. -- -- Sie ist bewusst **so dumm wie möglich**: keine Rechte für die -- Anwendungsrolle, keine Zeilen, keine Anmeldung. `auth.users` bleibt leer, -- die Fremdschlüssel darauf verschwinden im Lauf der Migrationen von selbst. create schema if not exists auth; -- Nur das, worauf die frühen Fremdschlüssel zeigen. Ohne weitere Spalten: -- geschrieben wurde in diese Tabelle nie, die Anwendung führt ihre Benutzer -- in `public.app_users`. create table if not exists auth.users ( id uuid primary key ); -- Auf Supabase lasen diese beiden aus dem JWT der Anfrage. Hier gibt es keins -- — und das ist richtig so: der Sitzungskontext dieser Anwendung steht in -- `app.user_id` und wird von withUser() je Transaktion gesetzt (lib/db). -- -- `app_current_user_id()` ruft `auth.uid()` noch auf, gefasst in ein -- `exception when undefined_function`. Es liefe also auch ohne dieses Schema; -- mit ihm liefert es null statt in den Ausnahmezweig zu laufen. Das Ergebnis -- ist dasselbe. create or replace function auth.uid() returns uuid language sql stable as $$ select nullif(current_setting('app.user_id', true), '')::uuid $$; create or replace function auth.role() returns text language sql stable as $$ select case when nullif(current_setting('app.user_id', true), '') is null then 'anon' else 'authenticated' end $$; -- Niemand ausser dem Eigentümer braucht hier etwas. Die Anwendungsrolle -- bekommt bewusst kein `usage` — fiele je wieder ein Bezug auf dieses Schema -- in den laufenden Betrieb, soll er scheitern und nicht stillschweigend -- funktionieren. revoke all on schema auth from public;