refactor(frontend): zentrale Test-Infrastruktur + Component-Rendering-Tests + Coverage #268

Closed
opened 2026-07-08 19:04:20 +02:00 by niboer · 0 comments
Owner

Beschreibung

Analog zur Backend-Test-Optimierung (PR #265) soll das Frontend eine zentrale Test-Infrastruktur erhalten:

  • Shared Factories/Helpers statt Inline-Duplikaten
  • Component-Rendering-Tests mit @testing-library/svelte + jsdom (ersetzt fragile readFileSync-Tests)
  • Coverage-Reporting mit Thresholds
  • MSW wird NICHT installiert (BFF-Pattern macht es entbehrlich -- API-Calls in load-Funktionen, Komponenten kriegen Props)

Aktueller Zustand

  • 27 Testdateien in frontend/src/tests/, Vitest v4, Environment node
  • Zwei Patterns: (1) Server-Logik-Tests mit dynamischen Imports + gemocktem fetch, (2) readFileSync-Inspektion (testet Text-Inhalt, nicht Verhalten)
  • @testing-library/svelte (^5.4.2) und jsdom (^29.1.1) in devDependencies aber ungenutzt
  • Keine shared Helpers/Factories -- jede Datei definiert eigene Inline-Helfer
  • Kein vitest.setup.ts
  • Kein Coverage-Reporting
  • 0 .component.test.ts-Dateien (obwohl include-Pattern im vitest.config existiert)

Umsetzung

Status

Phase 1: Shared Test-Infrastruktur

Neues Verzeichnis frontend/src/test-utils/ analog zu backend/src/test/:

src/test-utils/
  vitest.setup.ts        # IntersectionObserver, ResizeObserver, matchMedia-Mocks
  factories/
    person.ts            # buildPerson(overrides?)
    event.ts             # buildEvent(overrides?)
    guest.ts             # buildGuest(overrides?)
  helpers/
    render.ts            # renderWithProviders() + $app/*-Mocks
    app-mocks.ts         # vi.mock('$app/stores'), vi.mock('$app/navigation')
    fetch.ts             # mockFetchOk(), mockFetchError()
    form.ts              # createFormData()
    request.ts           # createRequestEvent()
  index.ts               # Barrel-Export

vitest.config.ts: setupFiles, Coverage-v8 mit Thresholds, per-file jsdom-Environment via // @vitest-environment jsdom in .component.test.ts-Dateien.

Phase 2: StatusBadge-Rendering-Tests (Proof of Concept)

status-badge.component.test.ts -- alle 10 Status-Kombinationen rendern und auf korrektes Label/Variant pruefen.

readFileSync status-badge.test.ts wird entfernt.

Phase 3: Weitere Rendering-Tests

  • empty-state.component.test.ts -> Rendering mit title/description/children, ersetzt readFileSync
  • data-table.component.test.ts -> Rendering mit columns/data/rowIdKey, zunaechst parallel zu readFileSync
  • app-shell.component.test.ts -> NEU (Sidebar im DOM, Props-Durchreichung), readFileSync bleibt zunaechst
  • sidebar.component.test.ts -> NEU, readFileSync bleibt
  • consent-dialog.component.test.ts -> NEU, readFileSync bleibt

Phase 4: Helper-Extraktion aus Server-Logic-Tests

Bestehende Inline-Helfer auslagern:

  • createFormData(values) -> test-utils/helpers/form.ts
  • mockFetchOk(body), mockFetchError(status, msg) -> test-utils/helpers/fetch.ts
  • createRequestEvent(url, cookies) -> test-utils/helpers/request.ts
  • createToken(payload) (aus auth-flow.test.ts) -> test-utils/helpers/auth.ts

Keine Aenderung an der Testlogik -- nur Extraktion.

Phase 5: Coverage-Konfiguration

coverage: {
  provider: 'v8',
  reporter: ['text', 'lcov', 'html'],
  include: ['src/lib/**', 'src/routes/**'],
  exclude: ['src/**/*.test.ts', 'src/**/*.component.test.ts', 'src/test-utils/**'],
  thresholds: {
    statements: 20,
    branches: 15,
    functions: 20,
    lines: 20,
  },
}

Niedrige Start-Thresholds -- erst mit wachsenden Rendering-Tests erhoehen.

Nicht-aendernde Tests

Folgende readFileSync-Tests bleiben (kein Rendering-Aequivalent moeglich/sinnvoll):

  • api-conventions.test.ts -- Meta-Konventions-Pruefung
  • design-tokens.test.ts -- Token-Vollstaendigkeit
  • svelte-config.test.ts, wrangler-config.test.ts -- Config-Validierung
  • svelte-syntax.test.ts -- Syntax-Validierung
  • i18n.test.ts -- Uebersetzungs-String-Pruefung

Labels

component/frontend, type/refactor

## Beschreibung Analog zur Backend-Test-Optimierung (PR #265) soll das Frontend eine zentrale Test-Infrastruktur erhalten: - Shared Factories/Helpers statt Inline-Duplikaten - Component-Rendering-Tests mit @testing-library/svelte + jsdom (ersetzt fragile readFileSync-Tests) - Coverage-Reporting mit Thresholds - MSW wird NICHT installiert (BFF-Pattern macht es entbehrlich -- API-Calls in load-Funktionen, Komponenten kriegen Props) ## Aktueller Zustand - 27 Testdateien in `frontend/src/tests/`, Vitest v4, Environment `node` - Zwei Patterns: (1) Server-Logik-Tests mit dynamischen Imports + gemocktem `fetch`, (2) readFileSync-Inspektion (testet Text-Inhalt, nicht Verhalten) - `@testing-library/svelte` (^5.4.2) und `jsdom` (^29.1.1) in devDependencies aber ungenutzt - **Keine** shared Helpers/Factories -- jede Datei definiert eigene Inline-Helfer - **Kein** `vitest.setup.ts` - **Kein** Coverage-Reporting - **0** `.component.test.ts`-Dateien (obwohl `include`-Pattern im vitest.config existiert) ## Umsetzung ### Status - [x] Phase 1 (#269) - [x] Phase 2 (#269) - [ ] Phase 3 (#270 unvollständig) - [x] Phase 4 (#270) ### Phase 1: Shared Test-Infrastruktur Neues Verzeichnis `frontend/src/test-utils/` analog zu `backend/src/test/`: ``` src/test-utils/ vitest.setup.ts # IntersectionObserver, ResizeObserver, matchMedia-Mocks factories/ person.ts # buildPerson(overrides?) event.ts # buildEvent(overrides?) guest.ts # buildGuest(overrides?) helpers/ render.ts # renderWithProviders() + $app/*-Mocks app-mocks.ts # vi.mock('$app/stores'), vi.mock('$app/navigation') fetch.ts # mockFetchOk(), mockFetchError() form.ts # createFormData() request.ts # createRequestEvent() index.ts # Barrel-Export ``` **vitest.config.ts:** setupFiles, Coverage-v8 mit Thresholds, per-file jsdom-Environment via `// @vitest-environment jsdom` in `.component.test.ts`-Dateien. ### Phase 2: StatusBadge-Rendering-Tests (Proof of Concept) `status-badge.component.test.ts` -- alle 10 Status-Kombinationen rendern und auf korrektes Label/Variant pruefen. readFileSync `status-badge.test.ts` wird entfernt. ### Phase 3: Weitere Rendering-Tests - `empty-state.component.test.ts` -> Rendering mit title/description/children, ersetzt readFileSync - `data-table.component.test.ts` -> Rendering mit columns/data/rowIdKey, zunaechst parallel zu readFileSync - `app-shell.component.test.ts` -> NEU (Sidebar im DOM, Props-Durchreichung), readFileSync bleibt zunaechst - `sidebar.component.test.ts` -> NEU, readFileSync bleibt - `consent-dialog.component.test.ts` -> NEU, readFileSync bleibt ### Phase 4: Helper-Extraktion aus Server-Logic-Tests Bestehende Inline-Helfer auslagern: - `createFormData(values)` -> `test-utils/helpers/form.ts` - `mockFetchOk(body)`, `mockFetchError(status, msg)` -> `test-utils/helpers/fetch.ts` - `createRequestEvent(url, cookies)` -> `test-utils/helpers/request.ts` - `createToken(payload)` (aus auth-flow.test.ts) -> `test-utils/helpers/auth.ts` Keine Aenderung an der Testlogik -- nur Extraktion. ### Phase 5: Coverage-Konfiguration ```ts coverage: { provider: 'v8', reporter: ['text', 'lcov', 'html'], include: ['src/lib/**', 'src/routes/**'], exclude: ['src/**/*.test.ts', 'src/**/*.component.test.ts', 'src/test-utils/**'], thresholds: { statements: 20, branches: 15, functions: 20, lines: 20, }, } ``` Niedrige Start-Thresholds -- erst mit wachsenden Rendering-Tests erhoehen. ## Nicht-aendernde Tests Folgende readFileSync-Tests bleiben (kein Rendering-Aequivalent moeglich/sinnvoll): - `api-conventions.test.ts` -- Meta-Konventions-Pruefung - `design-tokens.test.ts` -- Token-Vollstaendigkeit - `svelte-config.test.ts`, `wrangler-config.test.ts` -- Config-Validierung - `svelte-syntax.test.ts` -- Syntax-Validierung - `i18n.test.ts` -- Uebersetzungs-String-Pruefung ## Labels component/frontend, type/refactor
Sign in to join this conversation.
No description provided.