import { redirect } from '@sveltejs/kit'; import type { LayoutServerLoad } from './$types'; import { getSettings } from '$lib/server/pocketbase'; import { log } from '$lib/server/logger'; // Routes that are accessible without being logged in const PUBLIC_ROUTES = new Set(['/login', '/disclaimer', '/privacy', '/dmca', '/terms', '/catalogue']); export const load: LayoutServerLoad = async ({ locals, url, cookies }) => { // Allow public routes, /auth/*, and all book-browsing URLs (/books/[slug] and deeper) // Note: /books (the personal library) is intentionally NOT public const isPublic = PUBLIC_ROUTES.has(url.pathname) || url.pathname.startsWith('/auth/') || url.pathname.startsWith('/books/'); if (!isPublic && !locals.user) { redirect(302, `/login`); } let settings = { autoNext: false, voice: 'af_bella', speed: 1.0, theme: 'amber', locale: 'en', fontFamily: 'system', fontSize: 1.0, announceChapter: false, audioMode: 'stream' }; try { const row = await getSettings(locals.sessionId, locals.user?.id); if (row) { settings = { autoNext: row.auto_next ?? false, voice: row.voice ?? 'af_bella', speed: row.speed ?? 1.0, theme: row.theme ?? 'amber', locale: row.locale ?? 'en', fontFamily: row.font_family ?? 'system', fontSize: row.font_size || 1.0, announceChapter: row.announce_chapter ?? false, audioMode: row.audio_mode ?? 'stream' }; } } catch (e) { log.warn('layout', 'failed to load settings', { err: String(e) }); } // If user is logged in, keep the PARAGLIDE_LOCALE cookie in sync with // the saved locale so it persists across page loads and navigations. if (locals.user) { const savedLocale = settings.locale ?? 'en'; const currentCookieLocale = cookies.get('PARAGLIDE_LOCALE'); if (savedLocale === 'en') { // Clear the cookie when the user's locale is English (the default) if (currentCookieLocale) { cookies.delete('PARAGLIDE_LOCALE', { path: '/' }); } } else if (currentCookieLocale !== savedLocale) { cookies.set('PARAGLIDE_LOCALE', savedLocale, { path: '/', maxAge: 34560000, sameSite: 'lax', httpOnly: false }); } } return { user: locals.user, isPro: locals.isPro, settings }; };