export type Scenario = | 'default' | 'slow' | 'loading' | 'empty' | 'error' // upload-only (the multipart POST is hand-written XHR, so it bypasses the HTTP // interceptor — these are simulated in upload.adapter.ts instead): | 'upload-slow' | 'upload-fail'; export const SCENARIOS: readonly Scenario[] = [ 'default', 'slow', 'loading', 'empty', 'error', 'upload-slow', 'upload-fail', ]; const STORAGE_KEY = 'dev-scenario'; const isScenario = (v: string | null): v is Scenario => !!v && SCENARIOS.includes(v as Scenario); /** * Reads the active demo scenario so a demo can force each async state. * Sticky within the tab (sessionStorage), mirroring `role.ts`: a `?scenario=` in the * URL sets it; later navigation (which drops the query param) keeps the remembered * value. Set `?scenario=default`, use the dev switcher, or open a fresh tab to reset. * Dev-only — the interceptor that consumes this is wired only under `isDevMode()`. */ export function currentScenario(): Scenario { const fromUrl = new URLSearchParams(window.location.search).get('scenario'); if (isScenario(fromUrl)) { sessionStorage.setItem(STORAGE_KEY, fromUrl); return fromUrl; } const stored = sessionStorage.getItem(STORAGE_KEY); return isScenario(stored) ? stored : 'default'; } /** Dev switcher entry point: persist the chosen scenario for the tab (WP-33). */ export function setScenario(s: Scenario): void { sessionStorage.setItem(STORAGE_KEY, s); }