Use cases, aktivity a testy cloud UI

Tato stránka je plán pokrytí cloud UI (/, /app, /admin, /docs/): z use cases vycházejí aktivity, z aktivit úkoly (tasky) a ke každému úkolu je uvedeno, jakým testem se ověří.

Stav

Use cases a aktivity jsou odvozené z reálného kódu stránek (app.html, admin.html, landing.html) a z tras serveru. Sloupec Test říká, kde se má aktivita ověřit. Stávající testy (ui-tests/, jsdom s mockovaným fetch) pokrývají jen chování stránek, ne server a prohlížeč; e2e testy proti skutečnému serveru přidává Plán realizace.

Úrovně testů

Kód Co to je Co dokazuje Kde běží
JSDOM stávající ui-tests/*.js (skutečný DOM, fetch je mock) logika stránky, vazby ovládacích prvků, XSS/CSP allowlist lokálně, bez serveru
API Rust testy proti skutečnému Postgresu (route_status) oprávnění, stavové kódy, DB cargo test -p glass-cloud
E2E Playwright v prohlížeči proti běžícímu glass-cloud + Postgres celý řetěz: server → HTML → JS → API → DB → zobrazení ui-tests/e2e/

Pravidlo: co lze ověřit levněji (JSDOM/API), se nezdvojuje v E2E; E2E drží cesty napříč vrstvami a to, co jen skutečný prohlížeč umí (CSP, přesměrování, localStorage, chyby v konzoli, responsivita).


Uživatel (tester / hráč)

U1 — Zjistit, co je Scryglass, a stáhnout aplikaci

Aktér: návštěvník. Stránka: /.

Aktivita Tasky Test
U1.1 Zobrazit úvodní stránku stránka vrací 200, nadpis a navigace (Features, Download, Docs, Dashboard) jsou vidět E2E
U1.2 Přejít na Dashboard / Docs Dashboard vede na /app, Docs na /docs/ (200, ne 401) E2E
U1.3 Stáhnout aplikaci jako alpha uživatel po přihlášení /me vrátí alpha, tlačítka stažení se ukážou; GET /download/{platform} vrací soubor E2E + API
U1.4 Stažení bez alpha je odepřeno uživatel bez role alpha dostane 403 z /download/… a tlačítka nevidí API + E2E

U2 — Přihlásit se

Stránka: /app, /auth/*.

Aktivita Tasky Test
U2.1 Přihlášení e-mailovým kódem e-mail → krok 2 → správný 6místný kód → dashboard; špatný kód → chybová hláška, zůstat na kroku 2 E2E
U2.2 Změnit e-mail v kroku 2 tlačítko Change vrátí na krok 1 JSDOM (stávající)
U2.3 Přihlášení heslem Use a password instead → formulář → přihlášení; špatné heslo → hláška E2E
U2.4 Přihlášení passkey tlačítko je vidět; bez podpory WebAuthn hláška místo pádu JSDOM + E2E (virtuální authenticator)
U2.5 Magic link GET odkazu ukáže stránku s tlačítkem (nespotřebuje token), tlačítko vytvoří session E2E + API
U2.6 Session přežije reload token v localStorage; po obnovení zůstane přihlášen E2E
U2.7 Odhlášení Sign out smaže token, server ho zneplatní (/auth/logout), reload ukáže přihlašovací kartu E2E + API
U2.8 Výpadek sítě není odhlášení při selhání načtení dat se ukáže Couldn't reach Scryglass + Retry, ne přihlašovací formulář JSDOM (stávající)
U2.9 Neplatný / vypršelý token 401 z /me vede na přihlašovací kartu E2E

U3 — Přehled (Overview)

Aktivita Tasky Test
U3.1 První spuštění (prázdný účet) ukáže se Welcome to Scryglass se třemi kroky a poznámkou o kreditu; ne tabulka zápasů JSDOM (stávající) + E2E
U3.2 Dlaždice statistik Total Matches, Win rate, Training Events, AI Guide budget odpovídají datům účtu E2E (seed)
U3.3 Poslední zápasy tabulka Recent Matches (When / Deck / Opponent / Result); prázdný stav No recent matches E2E (seed)
U3.4 Cizí data se nezobrazí uživatel A nikdy nevidí zápasy uživatele B API
U3.5 Bezpečné vykreslení název balíčku nebo soupeře s <script>/HTML se zobrazí jako text JSDOM (stávající) + E2E

U4 — Balíčky a AI průvodce (Decks)

Aktivita Tasky Test
U4.1 Seznam balíčků synchronizovaných z aplikace tabulka Deck / Colors / Archetype / AI Guide; prázdný stav No decks synced yet E2E (seed přes PUT /me/decks)
U4.2 Vygenerovat průvodce tlačítko založí úlohu (POST /guide/jobs), stav se zobrazí E2E (LLM vypnuté → očekávaný stav) + API
U4.3 Bez alpha / bez kreditu odepřeno s jasnou hláškou, kredit se nestrhne API + E2E
U4.4 Zobrazit průvodce markdown se vykreslí bez spuštění skriptu, odkazy mají noopener JSDOM (stávající, 160 payloadů)
U4.5 Vybrat model (Fast/Standard) PUT /me/model-tier; volba přežije reload API + E2E
U4.6 Verze balíčku ACTIVE / STALE odznak odpovídá tomu, zda pravidla patří k nejnovější verzi JSDOM

U5 — Zabezpečení účtu (Security)

Aktivita Tasky Test
U5.1 Nastavit heslo min. 10 znaků; shoda obou polí; po uložení hláška o úspěchu a přihlášení heslem funguje E2E
U5.2 Přidat passkey WebAuthn registrace s virtuálním authenticatorem; passkey se objeví v seznamu E2E
U5.3 Smazat passkey zmizí ze seznamu a přestane fungovat E2E + API
U5.4 Přehled zařízení / session /me/sessions; odvolání jedné session ji zneplatní API + E2E
U5.5 Odvolat ostatní session /me/revoke-others ponechá aktuální API

U6 — Statistiky (Stats)

Aktivita Tasky Test
U6.1 Filtry (balíček, rozsah, min. her) změna přepočítá KPI a grafy; prázdný rozsah ukáže vysvětlení E2E (seed)
U6.2 Grafy podle hodiny a soupeře SVG se vykreslí; Table view přepne na tabulku se stejnými čísly JSDOM + E2E
U6.3 Info dialogy ⓘ otevře dialog; Esc, klik na pozadí i × ho zavřou E2E

U7 — Ovládání a přístupnost

Aktivita Tasky Test
U7.1 Karty (tabs) klávesnicí šipky přepínají, právě jedna karta je v tab pořadí JSDOM (stávající)
U7.2 Bez inline handlerů (CSP) odpověď /app má script-src bez unsafe-inline; konzole bez CSP chyb; všech 11 vazeb funguje JSDOM + Rust (stávající) + E2E (konzole)
U7.3 Mobilní šířka žádné vodorovné posouvání při 375 px E2E

U8 — Dokumentace

Aktivita Tasky Test
U8.1 Otevřít /docs/ a projít stránky všechny stránky vrací 200, navigace funguje E2E
U8.2 Odkazy na docs z UI landing, dashboard i admin mají odkaz Docs E2E
U8.3 Docs neprozradí cizí soubory /docs/../…, neexistující cesta → 404 (ne 200/500) API (stávající) + E2E

Administrátor

A1 — Vstoupit do administrace

Stránka: /admin.

Aktivita Tasky Test
A1.1 Admin uvidí odkaz Admin v dashboardu /me má is_admin, odkaz se odkryje; běžný uživatel ho nevidí E2E
A1.2 Běžný uživatel na /admin datová volání vrátí 403 a UI ukáže odepření (ne prázdná data) E2E + API
A1.3 Token zařízení nestačí admin se sync tokenem dostane na privilegovaných trasách 403 (jen web session) API (stávající)
A1.4 Vypršelá session 401 vede na přihlášení, ne na tichý prázdný přehled E2E

A2 — Přehled provozu (Overview)

Aktivita Tasky Test
A2.1 Souhrnné dlaždice Matches / Clients / Reactive Decisions odpovídají /stats E2E (seed)
A2.2 Top archetypy soupeřů tabulka seřazená sestupně; prázdný stav No archetype data JSDOM + E2E
A2.3 Automatické obnovení (30 s) přehled se překreslí, aniž by se ztratil vybraný uživatel JSDOM

A3 — Uživatelé a přístup (Users & Access)

Aktivita Tasky Test
A3.1 Tabulka uživatelů sloupce Account / Created / Matches / Last event / Build / Schema / Engine / Alpha E2E (seed)
A3.2 Verze klienta a schéma Build ukazuje last_app_version; Schema ukazuje nejnovější replay schéma a je žlutá, je-li nižší než serverové; STALE · version unknown pro klienta bez verze E2E + API (stávající DB test)
A3.3 Filtr Real accounts / All anonymní účty se skryjí / ukážou JSDOM
A3.4 Detail účtu klik na řádek otevře detail: profil, role, poslední build a replay schema, aktivita, balíčky, zápasy E2E
A3.5 Alpha pozvánka e-mail → POST /admin/alpha → řádek v allowlistu; neplatný e-mail → hláška E2E + API
A3.6 Odvolat alpha první klik vyžádá potvrzení (Really revoke?), druhý odešle právě jeden požadavek JSDOM (stávající)
A3.7 Přidělit / odebrat roli admin a corpus_reader přes /admin/roles/grant|revoke; seznam rolí se obnoví; jen RoleAdmin API + E2E
A3.8 Sloučit anonymní účet POST /admin/merge-anon přesune historii; nelze sloučit sám se sebou API

A4 — Ekonomika (Economy)

Aktivita Tasky Test
A4.1 Přehled spotřeby LLM tabulka uživatelů: úlohy, tokeny, použito, zůstatek (záporný zůstatek je vidět) JSDOM (stávající) + E2E
A4.2 Přidat kredit / nastavit zůstatek POST /admin/guide/credit s důvodem; kniha zůstává append-only; jen Billing (owner) API
A4.3 Nastavit model uživateli POST /admin/users/{id}/model-tier API
A4.4 Celkové součty sedí součet použitého = součet řádků JSDOM (stávající)

A5 — Data (Data)

Aktivita Tasky Test
A5.1 Artefakty tabulka distribuovaných verzí bundlů (Kind/Version/Created) E2E
A5.2 Spustit obnovu meta POST /refresh (operátor/admin); výsledek v /jobs API
A5.3 Druhy událostí uživatele /admin/users/{id}/event-kinds API

A6 — Označená rozhodnutí (Flags)

Aktivita Tasky Test
A6.1 Seznam flagged decisions nejnovější první; obsahuje build (engine_git_sha) API + E2E
A6.2 Prázdný stav srozumitelná hláška, ne rozbitá tabulka JSDOM

A7 — Audit (Audit)

Aktivita Tasky Test
A7.1 Změny rolí, kreditu a alpha každá akce z A3/A4 vytvoří řádek (kdo, co, komu) API + E2E
A7.2 Čtení korpusu každé čtení /admin/replays čtenářem zapíše corpus_read s počtem a kurzorem API (stávající)
A7.3 Stránkování kurzor (ts,id) je stabilní při souběžných zápisech API

A8 — Korpus her (mimo UI, součást produktu)

Aktivita Tasky Test
A8.1 Čtenář stáhne hry token corpus_reader → GET /admin/replays 200 bez e-mailů; ostatní admin trasy 403 API (stávající)
A8.2 Vydání tokenu POST /admin/corpus-token jen pro RoleAdmin a jen pro účet s rolí API (stávající)
A8.3 Neplatný kurzor odmítnut 400, ne návrat na první stránku API

A9 — Dokumentace a navigace

Aktivita Tasky Test
A9.1 Odkazy v hlavičce admina Dashboard, Docs, ← Public Site vedou správně E2E
A9.2 Bezpečnostní hlavičky admin má CSP s nonce; /docs/ má vlastní CSP a nosniff Rust (stávající) + E2E (response.headers)

Průřezové kontroly (každý E2E běh)

  • Žádná chyba v konzoli (console.error, neodchycená výjimka, CSP violation) na žádné stránce.
  • Žádný požadavek na cizí doménu, který CSP nepovoluje.
  • Žádný 5xx z API během scénáře.
  • Screenshot a trace při selhání.

Plán realizace

Doporučené pořadí — od nejvyššího rizika:

  1. Infrastruktura E2E (jednou):
    • ui-tests/e2e/ s Playwrightem (@playwright/test, Chromium),
    • global-setup: throwaway Postgres (postup v Provoz) → spustit binárku glass-cloud na volném portu s DATABASE_URL, CLOUD_TOKEN, OWNER_EMAILS, DOCS_DIR → čekat na /health,
    • seed přes API/SQL (ne přes UI): uživatelé s rolemi a tokeny všech druhů (session, sync), zápasy, replay záznamy různých schémat, balíčky; přihlášení v testu = vložení tokenu do localStorage (scry-web-token),
    • e-mailový kód: server v testu nemá poštu → kód se čte z DB / testovacího hooku, nikdy ne z produkčního e-mailu.
  2. Kouřový sloupec (U1.1, U2.1, U2.6, U2.7, U3.1, A1.1, A1.2, U8.1): dokazuje, že server + stránky + přihlášení drží pohromadě.
  3. Nová funkce tohoto týdne (A3.2, A3.4, U8.2, A9.1): sloupec Schema, odkazy na docs.
  4. Oprávnění na úrovni UI (A1.2, A3.7, A4.2, U4.3): že UI ukáže odepření, ne prázdná data.
  5. Passkey (U2.4, U5.2, U5.3) s virtuálním authenticatorem — nejvíc práce, nejnižší priorita.

Pravidla kvality testů

  • Každý E2E test musí selhat na rozbité verzi — před slučováním ho spustit proti záměrně rozbitému UI/serveru (např. odstranit sloupec Schema, vrátit unsafe-inline do CSP) a ověřit červenou. Test, který nikdy nemůže selhat, je horší než žádný.
  • Seed je deterministický a každý test si vytváří vlastní účty (e-maily s náhodnou příponou), takže jde spouštět opakovaně i paralelně.
  • E2E netestuje LLM ani skutečnou poštu; ty jsou vypnuté a jejich hranice se ověřuje v API testech.
  • Trace a screenshot se ukládají jen při selhání.

Stav pokrytí E2E (2026-09-30)

79 testů (1 volitelný E2E_ONLINE), každý prošel fail-first (75 mutací, ui-tests/e2e/mutate_e2e.py). Všechny use cases výše jsou pokryté: E2E v prohlížeči, API kontraktem proti skutečnému serveru, nebo stávajícími jsdom / Rust testy (U2.2, U4.4, U4.6, U7.2, A2.3, A3.1 — viz sloupec Test).

Use case Spec
U1.1 U1.2 U2.1 U2.6 U2.7 U3.1 A1.1 A1.2 U8.1 e2e/smoke.spec.js
U1.3 U1.4 e2e/downloads.spec.js
U2.3 U2.9 U4.1 U5.1 e2e/account.spec.js
U2.4 U5.2 U5.3 (passkey) e2e/passkey.spec.js
U2.5 (magic link) e2e/magic-link.spec.js
U3.4 A3.8 e2e/isolation-and-merge.spec.js
U4.2 U4.3 U4.5 U5.4 U5.5 e2e/sessions-and-guide.spec.js
U6.1 U6.2 U6.3 U7.1 U7.3 e2e/stats.spec.js
A3.2 A3.4 A9.1 A9.2 U8.2 U8.3 + info dialog admina e2e/admin-users.spec.js
A3.5 A3.7 U3.2 U3.3 U3.5 e2e/admin-actions.spec.js
A2.1 A2.2 A4.1 A4.2 A4.3 A6.1 A6.2 A7.1 e2e/admin-economy.spec.js
A1.3 A1.4 A3.3 A3.6 A5.1 A5.2 A5.3 A7.3 A8.2 A8.3 e2e/admin-data.spec.js

Záměrně mimo E2E: generování guide přes skutečný LLM (hranice se ověřuje v API testech: 403 / 400 / 503, kredit se nestrhne) a stahování instalátoru z GitHubu (jen s E2E_ONLINE=1).

Otevřené otázky

  • ~~Má se kouřový sloupec přidat do scripts/preflight.sh?~~ Rozhodnuto 2026-09-30: E2E běží samostatně (npm run e2e v ui-tests/), preflight beze změny.