---
title: "Supabase raw_user_meta_data: kaip registracija tapo Owner"
description: "handle_new_user trigeris ėmė role_id iš raw_user_meta_data, kurį nustato naršyklė. Kaip kiekvienas tapo Owner, pataisa per kvietimus ir 1 min. patikra."
url: "https://madsalt.tech/lt/notes/supabase-raw-user-meta-data-role/"
author: "Denys Zaichenko"
language: "lt"
published: 2026-10-18
---

# Supabase raw_user_meta_data: kaip registracija tapo Owner

Trumpai

`raw_user_meta_data` laiko viską, ką naršyklė perdavė `supabase.auth.signUp()`. Vienoje produkcinėje programoje `handle_new_user` trigeris iš ten skaitė naujo vartotojo rolę, todėl bet kas galėjo užsiregistruoti su Owner rolės id ir perimti paskyrą. Pataisa: rolė imama iš lentelės, kurią rašo tik serveris ir kuri užpildoma prieš išsiunčiant kvietimą.

Tai nutiko [audito įmonės laiko apskaitos](https://madsalt.tech/lt/work/audit-firm-time-tracking/) programoje, Supabase programoje, kur kiekviena prieigos taisyklė gyvena duomenų bazėje. Klaida buvo trigeryje, kuris kiekvienam naujam vartotojui sukuria profilį.

## Ką darė trigeris?

Supaprastintai jis atrodė taip:

```sql
create function public.handle_new_user()
returns trigger
language plpgsql
security definer set search_path = ''
as $$
declare
  _role_id uuid := (new.raw_user_meta_data ->> 'role_id')::uuid;
begin
  insert into public.profiles (id, full_name, role_id)
  values (new.id, new.raw_user_meta_data ->> 'full_name', _role_id);
  return new;
end;
$$;
```

Kvietimų srautas ten įrašydavo teisingą `role_id`, todėl įprastai naudojant viskas veikė. Tačiau `raw_user_meta_data` yra registracijos `options.data`, o jo turinį nusprendžia naršyklė:

```js
await supabase.auth.signUp({
  email: 'me@example.com',
  password: '...',
  options: { data: { role_id: '<owner role uuid>' } },
})
```

Leidimų patikra savininkams grąžindavo true dar prieš žiūrėdama į bet ką kita, todėl vien šis laukas suteikdavo visišką paskyros kontrolę. Pati Supabase [Users guide](https://supabase.com/docs/guides/auth/users) sako, kad vartotojo metaduomenų negalima naudoti RLS politikose ar autorizacijos logikoje, nes vartotojas gali juos keisti be jokių patikrų.

![Iš kur atėjo naujo vartotojo rolė. handle_new_user trigeris prieš pataisą ir po jos. Prieš: kiekvienas, kas registruojasi: signUp options.data → raw_user_meta_data → handle_new_user → Owner rolė; Po: tik pakviesti žmonės: Kvietimo funkcija → pending_invites → handle_new_user → Kviestinė rolė.](https://madsalt.tech/charts/lt/supabase-raw-user-meta-data-role.svg)

*Iš produkcinės Supabase programos registracijos trigerio, 2026 m. birželis.*

## Kas tai pataisė?

Dabar rolė imama iš privačios lentelės, prie kurios klientas neprieina:

```sql
create table private.pending_invites (
  email text primary key,
  role_id uuid,
  invited_by uuid,
  created_at timestamptz default now()
);
revoke all on table private.pending_invites from anon, authenticated;
```

Kvietimo funkcija veikia serveryje, patikrinus kviečiančiojo teisę. Ji pirmiausia įrašo laukiantį kvietimą ir tik tada sukuria kvietimo nuorodą. Trigeris suranda rolę pagal el. paštą ir ištrina eilutę. Vardas vis dar ateina iš metaduomenų, ir tai gerai: tai rodoma informacija.

Eilės tvarka svarbi. Kvietimas vartotoją sukuria iš karto: Supabase [Users guide](https://supabase.com/docs/guides/auth/users) pažymi, kad naujo el. pašto pakvietimas sukuria nepatvirtintą vartotoją. Trigeris suveikia tuo metu, todėl laukiančios eilutės turi jau egzistuoti.

## Kaip patikrinti savo programą?

Atidarykite savo `handle_new_user` funkciją ar bet kurį trigerį ant `auth.users` ir ieškokite `raw_user_meta_data`. Vardas ir avataras iš ten tinka. Rolė, įmonė, planas, nuomininkas ar bet kas kita, kas suteikia prieigą, turi ateiti iš lentelės arba iš `raw_app_meta_data`, kurio vartotojas pakeisti negali.

Tada išbandykite: užsiregistruokite per API, į `options.data` įrašę `role_id` arba `role: 'admin'`. Nauja paskyra neturi gauti nieko papildomo.

Tokia patikra yra pirmas mano [RLS testavimo metodo](https://madsalt.tech/lt/blog/how-to-test-supabase-rls/) žingsnis. Daugelio nuomininkų programoms taip pat žr. [ką RLS praleidžia vartotojui dviejose org.](https://madsalt.tech/lt/notes/supabase-rls-user-in-two-organizations/). Kitos patikros, kurias atlieku kiekvienoje Supabase programoje, yra mano [Lovable programos saugos sąraše](https://madsalt.tech/lt/blog/lovable-app-security-checklist/). Pirmiausia dashboard'e žiūriu, [kurias schemas pateikia Data API](https://madsalt.tech/lt/notes/supabase-exposed-schemas/). [Supabase saugumo patikra](https://madsalt.tech/lt/tools/supabase-security-check/) apima roles, teises, politikas ir autentifikacijos nustatymus pagal 46 OWASP Top 10:2025 taisykles, bet ne tai, ką trigeris nukopijuoja iš registracijos metaduomenų, todėl ši patikra lieka rankinė.
