diff --git a/src/lib/theme.ts b/src/lib/theme.ts index b30a936..e8ced80 100644 --- a/src/lib/theme.ts +++ b/src/lib/theme.ts @@ -6,9 +6,16 @@ const DARK_QUERY = '(prefers-color-scheme: dark)'; /** * Inline script that sets data-theme before the first paint, so a stored preference - * applies without a flash. Keep it in step with applyTheme below. + * applies without a flash. Keep it, and the literal storage key and media query inside it, in + * step with THEME_STORAGE_KEY, DARK_QUERY and applyTheme below. + * + * Written out as a fixed string rather than built by interpolating those constants into it: + * this is injected into via dangerouslySetInnerHTML, so splicing a value into it, even + * this module's own constant, is exactly the "code built from an interpolated value" pattern + * CodeQL's js/bad-code-sanitization flags (a later, easy-to-miss change to either constant, such + * as reading one from configuration, would turn this into a real DOM-based injection). */ -export const THEME_SCRIPT = `(function(){var p;try{p=localStorage.getItem(${JSON.stringify(THEME_STORAGE_KEY)})}catch(e){}var d=p==='dark'||(p!=='light'&&matchMedia(${JSON.stringify(DARK_QUERY)}).matches);document.documentElement.setAttribute('data-theme',d?'dark':'light')})()`; +export const THEME_SCRIPT = `(function(){var p;try{p=localStorage.getItem("orcahouse-ui.theme")}catch(e){}var d=p==='dark'||(p!=='light'&&matchMedia("(prefers-color-scheme: dark)").matches);document.documentElement.setAttribute('data-theme',d?'dark':'light')})()`; export function readThemePreference(): ThemePreference { try {