From a7cf648f2f942a4553720ef162e261189b000c41 Mon Sep 17 00:00:00 2001 From: Alexis <35.alexis.pele@gmail.com> Date: Fri, 23 Aug 2024 16:34:47 +0200 Subject: [PATCH] Added correct RLS and month api routes --- server/api/calendars/events/[id].delete.ts | 2 +- server/api/calendars/months/[id].delete.ts | 41 ++++++++ server/api/calendars/months/[id].patch.ts | 68 ++++++++++++++ server/api/calendars/months/create.post.ts | 50 ++++++++++ server/api/calendars/months/query.get.ts | 28 ++++++ server/api/characters/query.get.ts | 6 +- supabase/migrations/202401_init.sql | 104 +++++++++++++++++---- 7 files changed, 277 insertions(+), 22 deletions(-) create mode 100644 server/api/calendars/months/[id].delete.ts create mode 100644 server/api/calendars/months/[id].patch.ts create mode 100644 server/api/calendars/months/create.post.ts create mode 100644 server/api/calendars/months/query.get.ts diff --git a/server/api/calendars/events/[id].delete.ts b/server/api/calendars/events/[id].delete.ts index 7a15913..167ca0e 100644 --- a/server/api/calendars/events/[id].delete.ts +++ b/server/api/calendars/events/[id].delete.ts @@ -25,7 +25,7 @@ export default defineEventHandler(async (event) => { .from('calendar_events') .delete() .eq('id', params.id) - .single() + .maybeSingle() if (error) throw error diff --git a/server/api/calendars/months/[id].delete.ts b/server/api/calendars/months/[id].delete.ts new file mode 100644 index 0000000..4783eba --- /dev/null +++ b/server/api/calendars/months/[id].delete.ts @@ -0,0 +1,41 @@ +import { z } from 'zod' +import { serverSupabaseClient } from "#supabase/server" +import type { CalendarMonth } from "~/models/CalendarMonth" + +const paramsSchema = z.object({ + id: z.number({ coerce: true }).positive().int() +}) + +export default defineEventHandler(async (event) => { + const client = await serverSupabaseClient(event) + + const { data: params, error: paramsError} = await getValidatedRouterParams(event, paramsSchema.safeParse) + + if (paramsError) { + throw createError({ + cause: 'Utilisateur', + fatal: false, + message: "L'identifiant de l'évènement est manquant ou mal renseigné.", + status: 401, + }) + } + + try { + const { data, error } = await client + .from('calendar_months') + .delete() + .eq('id', params.id) + .maybeSingle() + + if (error) throw error + + return data + } catch (err) { + throw createError({ + cause: 'Serveur', + status: 500, + fatal: false, + message: 'Une erreur inconnue est survenue.' + }) + } +}) diff --git a/server/api/calendars/months/[id].patch.ts b/server/api/calendars/months/[id].patch.ts new file mode 100644 index 0000000..fdf47ef --- /dev/null +++ b/server/api/calendars/months/[id].patch.ts @@ -0,0 +1,68 @@ +import { z } from 'zod' +import { serverSupabaseClient } from "#supabase/server" +import { calendarMonthSchema, type CalendarMonth } from "~/models/CalendarMonth" + +const paramsSchema = z.object({ + id: z.number({ coerce: true }).positive().int() +}) + +export default defineEventHandler(async (event) => { + const client = await serverSupabaseClient(event) + + const { data: params, error: paramsError} = await getValidatedRouterParams(event, paramsSchema.safeParse) + const { data: bodyData, error: bodyError } = await readValidatedBody(event, body => calendarMonthSchema.safeParse(body)) + + if (paramsError) { + console.log(paramsError) + throw createError({ + cause: 'Utilisateur', + fatal: false, + message: "L'identifiant du mois est manquant ou mal renseigné.", + status: 401, + }) + } + + if (bodyError) { + console.log(bodyData) + throw createError({ + cause: 'Utilisateur', + fatal: false, + message: "Le schéma de la requête n'est pas complet ou mal renseigné.", + status: 401, + }) + } + + try { + const { data, error } = await client + .from('calendar_months') + .update( + { + name: bodyData?.name, + days: bodyData.days, + position: bodyData?.position, + calendar_id: bodyData.calendar_id, + } as never + ) + .eq('id', params.id) + .select(` + id, + name, + days, + position, + calendar_id + `) + .single() + + if (error) throw error + + return data + } catch (err) { + console.log(err) + throw createError({ + cause: 'Serveur', + status: 500, + fatal: false, + message: 'Une erreur inconnue est survenue.' + }) + } +}) diff --git a/server/api/calendars/months/create.post.ts b/server/api/calendars/months/create.post.ts new file mode 100644 index 0000000..5997230 --- /dev/null +++ b/server/api/calendars/months/create.post.ts @@ -0,0 +1,50 @@ +import { serverSupabaseClient } from "#supabase/server"; +import { calendarMonthSchema, type CalendarMonth } from "~/models/CalendarMonth" + +export default defineEventHandler(async (event) => { + const client = await serverSupabaseClient(event) + const { data: bodyData, error: schemaError } = await readValidatedBody(event, body => calendarMonthSchema.safeParse(body)) + + if (schemaError) { + console.log(schemaError) + throw createError({ + cause: 'Utilisateur', + fatal: false, + message: "Le schéma de la requête n'est pas complet ou mal renseigné.", + status: 401, + }) + } + + try { + const { data, error } = await client + .from('calendar_months') + .insert( + { + name: bodyData?.name, + days: bodyData.days, + position: bodyData?.position, + calendar_id: bodyData.calendar_id, + } as never + ) + .select(` + id, + name, + days, + position, + calendar_id + `) + .single() + + if (error) throw error + + return data + } catch (err) { + console.log(err) + throw createError({ + cause: 'Serveur', + status: 500, + fatal: false, + message: 'Une erreur inconnue est survenue.' + }) + } +}) diff --git a/server/api/calendars/months/query.get.ts b/server/api/calendars/months/query.get.ts new file mode 100644 index 0000000..16b627f --- /dev/null +++ b/server/api/calendars/months/query.get.ts @@ -0,0 +1,28 @@ +import { serverSupabaseClient } from "#supabase/server"; +import { z } from 'zod' +import type { CalendarMonth } from "~/models/CalendarMonth"; + +const querySchema = z.object({ + calendarId: z.number({ coerce: true }).positive().int() +}) + +export default defineEventHandler(async (event) => { + const client = await serverSupabaseClient(event) + const query = await getValidatedQuery(event, querySchema.parse) + + const output = client + .from('calendar_months') + .select(` + id, + name, + days, + position, + calendar_id + `) + + if (query.calendarId) { + output.eq('calendar_id', query.calendarId) + } + + return output.returns() +}) diff --git a/server/api/characters/query.get.ts b/server/api/characters/query.get.ts index bd9ffea..79fb25d 100644 --- a/server/api/characters/query.get.ts +++ b/server/api/characters/query.get.ts @@ -3,7 +3,7 @@ import { serverSupabaseClient } from "#supabase/server"; import type { Character } from "~/models/Characters"; const querySchema = z.object({ - world_id: z.number({ coerce: true }).positive().int() + worldId: z.number({ coerce: true }).positive().int() }) export default defineEventHandler(async (event) => { @@ -23,8 +23,8 @@ export default defineEventHandler(async (event) => { secondaryCategories:character_categories!character_categories_links (*) `) - if (query.world_id) { - output.eq('world_id', query.world_id) + if (query.worldId) { + output.eq('world_id', query.worldId) } return output.returns() diff --git a/supabase/migrations/202401_init.sql b/supabase/migrations/202401_init.sql index be2f6f5..dcdfcad 100644 --- a/supabase/migrations/202401_init.sql +++ b/supabase/migrations/202401_init.sql @@ -192,42 +192,110 @@ create policy "Allow individual update access for GMs" on public.calendars for u ); -- Month policies -create policy "Allow individual read access for GMs" on public.calendar_months for select using ( +create policy "Allow GMs to see their calendar's months" + on public.calendar_months + for select + using ( exists ( - select 1 from calendars - where calendars.id = calendar_months.calendar_id + select 1 + from public.calendars c + join public.worlds w on w.id = c.world_id + where + c.id = calendar_months.calendar_id + and w.gm_id = auth.uid() ) ); -create policy "Allow individual insert access for GMs" on public.calendar_months for insert with check ( +create policy "Allow GMs to add months on their calendars" + on public.calendar_months + for insert + with check ( exists ( - select 1 from calendars - where calendars.id = calendar_months.calendar_id + select 1 + from public.calendars c + join public.worlds w on w.id = c.world_id + where + c.id = calendar_months.calendar_id + and w.gm_id = auth.uid() ) ); -create policy "Allow individual update access for GMs" on public.calendar_months for update with check ( +create policy "Allow GMs to update their calendar's months" + on public.calendar_months + for update + using ( exists ( - select 1 from calendars - where calendars.id = calendar_months.calendar_id + select 1 + from public.calendars c + join public.worlds w on w.id = c.world_id + where + c.id = calendar_months.calendar_id + and w.gm_id = auth.uid() + ) +); +create policy "Allow GMs to delete their calendar's months" + on public.calendar_months + for delete + using ( + exists ( + select 1 + from public.calendars c + join public.worlds w on w.id = c.world_id + where + c.id = calendar_months.calendar_id + and w.gm_id = auth.uid() ) ); -- Event policies -create policy "Allow individual read access for GMs" on public.calendar_events for select using ( +create policy "Allow GMs to see their events" + on public.calendar_events + for select + using ( exists ( - select 1 from calendars - where calendars.id = calendar_events.calendar_id + select 1 + from public.calendars c + join public.worlds w on w.id = c.world_id + where + c.id = calendar_events.calendar_id + and w.gm_id = auth.uid() ) ); -create policy "Allow individual insert access for GMs" on public.calendar_events for insert with check ( +create policy "Allow GMs to add their events" + on public.calendar_events + for insert + with check ( exists ( - select 1 from calendars - where calendars.id = calendar_events.calendar_id + select 1 + from public.calendars c + join public.worlds w on w.id = c.world_id + where + c.id = calendar_events.calendar_id + and w.gm_id = auth.uid() ) ); -create policy "Allow individual update access for GMs" on public.calendar_events for update with check ( +create policy "Allow GMs to update their events" + on public.calendar_events + for update + using ( exists ( - select 1 from calendars - where calendars.id = calendar_events.calendar_id + select 1 + from public.calendars c + join public.worlds w on w.id = c.world_id + where + c.id = calendar_events.calendar_id + and w.gm_id = auth.uid() + ) +); +create policy "Allow GMs to delete their events" + on public.calendar_events + for delete + using ( + exists ( + select 1 + from public.calendars c + join public.worlds w on w.id = c.world_id + where + c.id = calendar_events.calendar_id + and w.gm_id = auth.uid() ) );