Files
webmanager-mvp/project_docs/THEME_SELECTION_V1_DESIGN.md
T
2026-03-12 18:26:29 +01:00

178 lines
5.5 KiB
Markdown

# Theme Selection v1
## 1. Doel
Theme-selectie voegt nu waarde toe omdat de UI al een nette light/dark basis heeft, maar nog geen expliciet onderscheid maakt tussen:
- `theme`: de stijlset
- `mode`: light of dark binnen die stijlset
Dat onderscheid maakt de UI uitbreidbaar zonder de dagelijkse snelle UX kwijt te raken. Dit past logisch in de bestaande Settings-structuur:
- `General` voor functionele voorkeuren
- `Interface` voor theme-keuze
- `Logs` voor recente acties
## 2. Scope
Theme Selection v1 omvat:
- nieuw Settings-tabblad: `Interface`
- daarin alleen een pulldown/select: `Theme`
- bestaande snelle dark/light toggle blijft in de hoofdinterface bestaan
- beide keuzes worden opgeslagen in bestaande SQLite settings-opslag
- app leest beide waarden bij startup via backend en past die direct toe
Niet in scope:
- vrije CSS-bestandskeuze
- padinvoer
- upload van themes
- custom theme editor
- theme packs van externe bron
## 3. Theme-model
Aanbevolen model voor v1:
- werk met een whitelist van toegestane theme keys
- werk daarnaast met een aparte whitelist van toegestane color modes
- sla beide als strings op in settings
Aanbevolen settings voor v1:
- `selected_theme: string | null`
- `selected_color_mode: string | null`
Whitelist v1:
- `selected_theme`
- `default`
- `selected_color_mode`
- `dark`
- `light`
Waarom dit veiliger en eenvoudiger is dan bestandsselectie:
- geen vrije filesystemtoegang nodig
- geen risico op ongeldige of kwaadaardige CSS-inhoud
- geen extra upload- of assetbeheer
- duidelijke validatie in backend mogelijk
- stabiel contract tussen backend setting en frontend rendering
## 4. Settings-opslag
Nieuwe settings in bestaande settings-opslag:
- `selected_theme`
- `selected_color_mode`
Semantiek:
- `selected_theme = null` betekent: fallback naar veilige default `default`
- `selected_color_mode = null` betekent: fallback naar veilige default `dark`
- onbekende opgeslagen waarden betekenen: negeren en fallback toepassen
Aanbevolen effectieve defaults:
- theme -> `default`
- mode -> `dark`
## 5. Settings UI
Tabs in Settings worden:
- `General`
- `Interface`
- `Logs`
`Interface` bevat in v1 alleen:
- label: `Theme`
- een select/pulldown met toegestane themes
Belangrijk:
- geen dark/light selector in `Settings > Interface`
- dark/light blijft een snelle hoofdinterface-actie
Aanbevolen v1-UX:
- select toont huidige theme-keuze
- gebruiker kiest andere waarde
- opslaan gebeurt via bestaande settings-saveflow
- keuze wordt direct toegepast in de UI na succesvolle backend-save
## 6. Frontend-impact
Frontend moet bij startup vroeg settings laden en daaruit beide waarden ophalen:
- `selected_theme`
- `selected_color_mode`
Daarna bepaalt frontend het effectieve UI-theme. Aanbevolen intern model:
- `data-theme="default-dark"`
- `data-theme="default-light"`
Aanbevolen volgorde:
1. `GET /api/settings`
2. bepaal effectief theme + mode
3. zet `document.documentElement.dataset.theme`
4. initialiseer de rest van de UI
Relatie met bestaande light/dark toggle:
- toggle blijft bestaan in de hoofdinterface
- toggle wijzigt alleen `selected_color_mode`
- toggle schrijft dus naar backend, niet naar localStorage
Reden:
- snelle dagelijkse UX blijft behouden
- `Settings > Interface` blijft schoon en beperkt tot theme-keuze
- theme en mode blijven conceptueel gescheiden
## 7. Backend-impact
Bestaande settings-API wordt uitgebreid met:
- `selected_theme`
- `selected_color_mode`
Benodigd:
- whitelistvalidatie op backend
- onbekende waarden blokkeren bij write
- bestaande settings repository/service/API uitbreiden
Niet nodig:
- nieuwe dependency
- vrije filesystemtoegang
- nieuwe asset-uploadroute
## 8. Regressierisico
Belangrijkste risico's:
- startup-volgorde: theme moet vroeg genoeg worden toegepast om flicker te beperken
- bestaande theme-toggle logica conflicteert nu nog met localStorage
- onbekende opgeslagen theme/mode-waarden moeten veilig terugvallen
- Settings-tabcomplexiteit mag niet onnodig toenemen
Belangrijkste mitigaties:
- één centrale frontendfunctie die theme en mode uit backend toepast
- localStorage volledig verwijderen als leidende theme-bron
- backend whitelistvalidatie
- fallback naar `default-dark`
## 9. Teststrategie
Backend golden tests:
- default `selected_theme`
- default `selected_color_mode`
- geldige theme save (`default`)
- geldige color mode save (`dark`, `light`)
- ongeldige theme key wordt geblokkeerd
- ongeldige color mode wordt geblokkeerd
- settings response bevat beide velden
UI smoke/regressietests:
- `Settings` bevat tabs `General`, `Interface`, `Logs`
- `Interface` tab bevat alleen theme select
- hoofdinterface bevat nog steeds dark/light toggle
- app leest beide settings via backend
- fallback bij ontbrekende/ongeldige waarde breekt startup niet
Handmatige validatie:
- theme wijzigen in `Settings > Interface`
- mode wisselen via toggle in de hoofdinterface
- app herladen en controleren dat beide keuzes behouden blijven
- controle dat light/dark correct doorwerken in modals, panelen en editor/viewers
## 10. Aanbeveling
Aanbevolen v1-richting met laag regressierisico:
- voeg `Interface` tab toe
- voeg `selected_theme` en `selected_color_mode` toe aan bestaande settings-opslag
- werk alleen met veilige whitelists
- houd v1 beperkt tot:
- theme: `default`
- mode: `dark|light`
- laat startup en toggle beide backendpersistente settings gebruiken
- fallback altijd veilig naar `default-dark`
Deze richting is:
- simpel
- veilig
- onderhoudbaar
- duidelijk uitbreidbaar naar extra themes, zonder de dagelijkse dark/light UX opnieuw te moeten ontwerpen