import { afterEach, beforeEach, describe, expect, it } from 'vitest' import { getLastGardenId, rememberLastGarden, forgetLastGarden } from './lastGarden' // The tests run in the node environment (no DOM), so stand up a minimal // in-memory localStorage rather than pull in jsdom for one thin module. function installStorage(impl?: Partial) { const store = new Map() const base: Storage = { getItem: (k) => store.get(k) ?? null, setItem: (k, v) => void store.set(k, String(v)), removeItem: (k) => void store.delete(k), clear: () => store.clear(), key: (i) => [...store.keys()][i] ?? null, get length() { return store.size }, } ;(globalThis as { localStorage?: Storage }).localStorage = { ...base, ...impl } } beforeEach(() => installStorage()) afterEach(() => { delete (globalThis as { localStorage?: Storage }).localStorage }) describe('lastGarden', () => { it('round-trips a remembered garden id', () => { expect(getLastGardenId()).toBeNull() rememberLastGarden(42) expect(getLastGardenId()).toBe(42) }) it('rejects a non-positive or unparseable stored value', () => { localStorage.setItem('pansy:last-garden', 'not-a-number') expect(getLastGardenId()).toBeNull() localStorage.setItem('pansy:last-garden', '0') expect(getLastGardenId()).toBeNull() localStorage.setItem('pansy:last-garden', '-3') expect(getLastGardenId()).toBeNull() }) it('forgets unconditionally with no argument', () => { rememberLastGarden(7) forgetLastGarden() expect(getLastGardenId()).toBeNull() }) it('forgets only when the stored id matches onlyIfEquals', () => { rememberLastGarden(5) // A 404 on a different (directly-linked) garden must not wipe the good resume. forgetLastGarden(9) expect(getLastGardenId()).toBe(5) // A 404 on the stored garden itself does clear it. forgetLastGarden(5) expect(getLastGardenId()).toBeNull() }) it('swallows storage failures instead of throwing', () => { installStorage({ setItem: () => { throw new Error('quota') }, getItem: () => { throw new Error('blocked') }, }) expect(() => rememberLastGarden(1)).not.toThrow() expect(getLastGardenId()).toBeNull() // getItem throwing → null, not a crash }) })