diff --git a/client/src/components/Layout/Navbar.tsx b/client/src/components/Layout/Navbar.tsx index a8ec8f5c..36d543c1 100644 --- a/client/src/components/Layout/Navbar.tsx +++ b/client/src/components/Layout/Navbar.tsx @@ -61,11 +61,25 @@ export default function Navbar({ tripTitle, tripId, onBack, showBack, onShare }: navigate('/login', { state: { noRedirect: true } }) } + // Keep track of the pending theme-transition cleanup so we can cancel it + // on unmount. Without this the timer fires after jsdom teardown in unit + // tests (document is gone) and triggers an unhandled ReferenceError that + // trips vitest's exit code. + const themeTransitionTimer = useRef(null) + useEffect(() => () => { + if (themeTransitionTimer.current !== null) { + window.clearTimeout(themeTransitionTimer.current) + themeTransitionTimer.current = null + } + }, []) + const toggleDarkMode = () => { document.documentElement.classList.add('trek-theme-transitioning') updateSetting('dark_mode', dark ? 'light' : 'dark').catch(() => {}) - window.setTimeout(() => { + if (themeTransitionTimer.current !== null) window.clearTimeout(themeTransitionTimer.current) + themeTransitionTimer.current = window.setTimeout(() => { document.documentElement.classList.remove('trek-theme-transitioning') + themeTransitionTimer.current = null }, 360) }