diff --git a/src/app.d.ts b/src/app.d.ts index 79b8954..d100c23 100644 --- a/src/app.d.ts +++ b/src/app.d.ts @@ -44,8 +44,9 @@ declare global { interface PageData { eventName?: string; eventId?: string; + safeGetSession: () => Promise<{ session: Session | null; user: User | null }>; supabase: SupabaseClient; - session: import('@supabase/auth-helpers-sveltekit').SupabaseSession; + session: Session; } namespace App { diff --git a/src/hooks.server.ts b/src/hooks.server.ts index a99914c..240ed5f 100644 --- a/src/hooks.server.ts +++ b/src/hooks.server.ts @@ -74,9 +74,9 @@ const authGuard: Handle = async ({ event, resolve }) => { return redirect(303, '/auth'); } - // if (event.locals.session && event.url.pathname === '/auth') { - // return redirect(303, '/protected-routes/dashboard'); - // } + if (event.locals.session && event.url.pathname === '/auth') { + return redirect(303, '/protected-routes/dashboard'); + } return resolve(event); }; diff --git a/src/routes/+layout.server.ts b/src/routes/+layout.server.ts index bd6e60f..3569e42 100644 --- a/src/routes/+layout.server.ts +++ b/src/routes/+layout.server.ts @@ -1,7 +1,11 @@ +// src/routes/+layout.server.ts import type { LayoutServerLoad } from './$types'; -export const load: LayoutServerLoad = async ({ locals: { session } }) => { +export const load = (async ({ locals: { safeGetSession } }) => { + const { session, user } = await safeGetSession(); + return { - session + session, + user }; -}; +}) satisfies LayoutServerLoad; diff --git a/src/routes/+layout.svelte b/src/routes/+layout.svelte index 5f363fc..095347e 100644 --- a/src/routes/+layout.svelte +++ b/src/routes/+layout.svelte @@ -13,13 +13,11 @@ inject({ mode: dev ? 'development' : 'production' }); - let { data, authChange, children } = $props(); + let { data, children, authChange } = $props(); let { session, supabase } = data; onMount(() => { - const { data } = supabase.auth.onAuthStateChange((_: any, newSession: { expires_at: any }) => { - authChange = !authChange; - + const { data } = supabase.auth.onAuthStateChange((_, newSession) => { if (!newSession) { /** * Queue this as a task so the navigation won't prevent the diff --git a/src/routes/+layout.ts b/src/routes/+layout.ts index c8c4025..5776402 100644 --- a/src/routes/+layout.ts +++ b/src/routes/+layout.ts @@ -1,9 +1,14 @@ import { createBrowserClient, createServerClient, isBrowser, parse } from '@supabase/ssr'; + import { PUBLIC_SUPABASE_ANON_KEY, PUBLIC_SUPABASE_URL } from '$env/static/public'; + import type { LayoutLoad } from './$types'; export const load: LayoutLoad = async ({ data, depends, fetch }) => { - // Declare a dependency so the layout can be invalidated, for example, on session refresh. + /** + * Declare a dependency so the layout can be invalidated, for example, on + * session refresh. + */ depends('supabase:auth'); const supabase = isBrowser() @@ -29,14 +34,18 @@ export const load: LayoutLoad = async ({ data, depends, fetch }) => { } }); - // Fetch the session and authenticated user - const { data: session } = await supabase.auth.getSession(); + /** + * It's fine to use `getSession` here, because on the client, `getSession` is + * safe, and on the server, it reads `session` from the `LayoutData`, which + * safely checked the session using `safeGetSession`. + */ + const { + data: { session } + } = await supabase.auth.getSession(); - const { data: userData, error: userError } = await supabase.auth.getUser(); - if (userError) { - console.error('Error fetching authenticated user:', userError); - } - const user = userData.user; + const { + data: { user } + } = await supabase.auth.getUser(); return { session, supabase, user }; };