Base webui and backend additions
This commit is contained in:
@@ -0,0 +1,95 @@
|
||||
import { afterEach, describe, expect, it, vi } from 'vitest'
|
||||
import {
|
||||
THEME_STORAGE_KEY,
|
||||
applyResolvedTheme,
|
||||
applyThemeFromPreference,
|
||||
isThemePreference,
|
||||
readThemePreference,
|
||||
resolveTheme,
|
||||
writeThemePreference,
|
||||
} from './theme'
|
||||
|
||||
function createMemoryStorage(initial: Record<string, string> = {}) {
|
||||
const store = new Map(Object.entries(initial))
|
||||
return {
|
||||
getItem(key: string) {
|
||||
return store.has(key) ? store.get(key)! : null
|
||||
},
|
||||
setItem(key: string, value: string) {
|
||||
store.set(key, value)
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
describe('isThemePreference', () => {
|
||||
it('accepts light, dark, and auto', () => {
|
||||
expect(isThemePreference('light')).toBe(true)
|
||||
expect(isThemePreference('dark')).toBe(true)
|
||||
expect(isThemePreference('auto')).toBe(true)
|
||||
})
|
||||
|
||||
it('rejects invalid values', () => {
|
||||
expect(isThemePreference('mocha')).toBe(false)
|
||||
expect(isThemePreference('')).toBe(false)
|
||||
})
|
||||
})
|
||||
|
||||
describe('readThemePreference', () => {
|
||||
it('defaults to auto when nothing is stored', () => {
|
||||
expect(readThemePreference(createMemoryStorage())).toBe('auto')
|
||||
})
|
||||
|
||||
it('returns a stored preference', () => {
|
||||
const storage = createMemoryStorage({ [THEME_STORAGE_KEY]: 'dark' })
|
||||
expect(readThemePreference(storage)).toBe('dark')
|
||||
})
|
||||
|
||||
it('falls back to auto for invalid stored values', () => {
|
||||
const storage = createMemoryStorage({ [THEME_STORAGE_KEY]: 'neon' })
|
||||
expect(readThemePreference(storage)).toBe('auto')
|
||||
})
|
||||
})
|
||||
|
||||
describe('writeThemePreference', () => {
|
||||
it('persists the preference', () => {
|
||||
const storage = createMemoryStorage()
|
||||
writeThemePreference('light', storage)
|
||||
expect(storage.getItem(THEME_STORAGE_KEY)).toBe('light')
|
||||
})
|
||||
})
|
||||
|
||||
describe('resolveTheme', () => {
|
||||
it('maps light to latte and dark to mocha', () => {
|
||||
expect(resolveTheme('light', true)).toBe('latte')
|
||||
expect(resolveTheme('dark', false)).toBe('mocha')
|
||||
})
|
||||
|
||||
it('maps auto from the browser preference', () => {
|
||||
expect(resolveTheme('auto', true)).toBe('mocha')
|
||||
expect(resolveTheme('auto', false)).toBe('latte')
|
||||
})
|
||||
})
|
||||
|
||||
describe('applyResolvedTheme', () => {
|
||||
afterEach(() => {
|
||||
delete document.documentElement.dataset.theme
|
||||
})
|
||||
|
||||
it('sets data-theme on the root element', () => {
|
||||
applyResolvedTheme('mocha')
|
||||
expect(document.documentElement.dataset.theme).toBe('mocha')
|
||||
})
|
||||
})
|
||||
|
||||
describe('applyThemeFromPreference', () => {
|
||||
afterEach(() => {
|
||||
delete document.documentElement.dataset.theme
|
||||
vi.restoreAllMocks()
|
||||
})
|
||||
|
||||
it('applies the resolved theme from preference and system preference', () => {
|
||||
const resolved = applyThemeFromPreference('auto', true)
|
||||
expect(resolved).toBe('mocha')
|
||||
expect(document.documentElement.dataset.theme).toBe('mocha')
|
||||
})
|
||||
})
|
||||
Reference in New Issue
Block a user