Aufraeumarbeiten: ESLint, DOM-Verschachtelung, eigene Testwehr
ESLint hatte keine Konfiguration — das Skript "npm run lint" pruefte nichts. Jetzt Flat Config ohne Formatierungsregeln, dafuer mit den Regeln, die die Fehler dieses Projekts gemeldet haetten. Er hat gleich zwei gefunden, die niemand gesucht hatte. Das Badge rendert ein span statt eines div. Damit ist die Meldung "div cannot be a descendant of p" weg, die seit Phase 3 auf der Einsatzseite stand — sie ist der klassische Ausloeser fuer einen Hydration-Fehler. Die E2E-Tests laufen gegen eine eigene Wehr. Nach fuenf Phasen standen in der Beispielwehr 120 Atemschutz-Ueberwachungen statt einer und 115 Geraete statt 45; bei jedem Lauf aenderten sich alle Bildschirmfotos. Der Bestand ist einmal zurueckgesetzt, npm run db:test-reset baut die Testwehr neu auf. Behoben nebenbei: - Die Fehlerflaeche der Karte konnte nie etwas anzeigen. - Zwei useMemo der Lagekarte rechneten bei jedem Rendern neu. - tests/e2e war vom Typecheck ausgenommen und liess einen doppelt deklarierten Bezeichner durch. Closes #10 Closes #11 Closes #12 Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@@ -20,7 +20,79 @@ Die aufgewendete Zeit wandert nach jedem Abschnitt in die Spalte
|
||||
| Phase 6 — Kartenmodule | 2:50 h | 1 | 04.09.2026 |
|
||||
| Phase 7 — Benachrichtigungen und Termine | 3:10 h | 1 | 04.09.2026 |
|
||||
| Phase 8 — Lokale KI | 3:40 h | 1 | 04.09.2026 |
|
||||
| **Summe** | **23:00 h** | **10** | |
|
||||
| Aufräumarbeiten (Issues #10–#12) | 1:20 h | 1 | 04.09.2026 |
|
||||
| **Summe** | **24:20 h** | **11** | |
|
||||
|
||||
---
|
||||
|
||||
## 2026-09-04 · Aufräumarbeiten — Issues #10 bis #12
|
||||
|
||||
**11:15 – 12:35 · 1:20 h**
|
||||
|
||||
### Was entstanden ist
|
||||
|
||||
Drei Punkte, die seit mehreren Phasen im Abschlussbericht standen und in jeder
|
||||
Phase Zeit gekostet haben. Diesmal als Issues angelegt und abgearbeitet.
|
||||
|
||||
| Issue | Kern |
|
||||
|---|---|
|
||||
| #11 | ESLint hatte keine Konfiguration — `npm run lint` prüfte nichts |
|
||||
| #12 | `<div>` in einem `<p>` auf der Einsatzseite, seit Phase 3 |
|
||||
| #10 | Die E2E-Tests schrieben in die Beispielwehr |
|
||||
|
||||
### Entscheidungen
|
||||
|
||||
**ESLint zuerst.** Er findet die anderen beiden — und tatsächlich hat er
|
||||
gleich zwei Fehler gemeldet, die niemand gesucht hatte: eine Fehlerfläche auf
|
||||
der Karte, die nie etwas anzeigen konnte, und zwei `useMemo` in der Lagekarte,
|
||||
die bei jedem Rendern neu rechneten.
|
||||
|
||||
**Keine Formatierungsregeln.** Die macht Prettier. Zwei Werkzeuge, die sich
|
||||
über Anführungszeichen streiten, lenken von den Regeln ab, auf die es ankommt.
|
||||
|
||||
**Auch keine typgestützten Regeln.** `no-floating-promises` wäre für diesen
|
||||
Stack die wertvollste Regel überhaupt — sie braucht aber den Compiler bei
|
||||
jedem Lauf, und dann dauert der Lauf Minuten statt Sekunden. Bei einem
|
||||
Werkzeug, das vor jedem Commit laufen soll, ist das der falsche Tausch.
|
||||
|
||||
**Das Badge wurde ein `<span>`, nicht der Absatz ein `<div>`.** Die Meldung
|
||||
kam von einer Stelle, aber die Ursache saß im Bauteil: ein Abzeichen ist
|
||||
Fließtext-Inhalt und gehört in ein Inline-Element. So ist auch jede künftige
|
||||
Verwendung in einem Absatz richtig, und die Darstellung ändert sich nicht —
|
||||
`inline-flex` verhält sich in beiden gleich.
|
||||
|
||||
**Eine zweite Wehr statt Aufräumen nach dem Lauf.** Ein abgebrochener Lauf
|
||||
lässt beim Aufräumen einen Bestand zurück, den niemand erwartet. Ein
|
||||
vollständiger Neuaufbau ist der einzige Zustand, den man kennt — und der Seed
|
||||
kann ohnehin schon alles, er brauchte nur eine Kennung aus der Umgebung.
|
||||
|
||||
**Ein Riegel gegen den eigenen Fehler.** `npm run db:test-reset` bricht ab,
|
||||
wenn die Testkennung mit der der Beispielwehr übereinstimmt. Ein Skript, das
|
||||
eine ganze Wehr löscht, braucht eine Stelle, an der es sich weigert.
|
||||
|
||||
### Wo es gehakt hat
|
||||
|
||||
| Problem | Ursache | Lösung |
|
||||
|---|---|---|
|
||||
| Zwei Tests fielen nach der Umstellung durch — und das war richtig so | Sie hatten die Verschmutzung gebraucht. `getByText("B 3 Wohnhausbrand", { exact: true })` traf bisher einen Einsatz aus einem früheren Testlauf, weil der kein Objekt hatte; der Einsatz aus dem Seed hat eines und steht in derselben Zelle | Anker am Zellenanfang statt Prüfung auf Gleichheit |
|
||||
| Der Kiosk-Test schrieb weiter in die Beispielwehr | `const WEHR = "ff-musterhausen"` stand fest im Test. Das Terminal merkt sich die Wehr und schreibt Mängel und Fahrten genau dorthin | Kennung aus `wehr.ts`, wie überall sonst |
|
||||
| Ein doppelt deklarierter Bezeichner rutschte durch den Typecheck | `tests/e2e` war in der `tsconfig.json` ausgeschlossen | Ausnahme entfernt. Sie hat nichts gebracht: die Dateien übersetzen sauber |
|
||||
| Die Anmeldung im Bildschirmfoto-Skript lief ins Leere | Bekannt aus Phase 7 — bei kaltem `.next` ist die Seite noch nicht hydriert | War schon behoben; hier nur wieder aufgetreten und bestätigt |
|
||||
|
||||
### Abweichung von der Vorgabe
|
||||
|
||||
**Issues angelegt**, obwohl CLAUDE.md das ausdrücklich verbietet („Niemals ein
|
||||
Issue anlegen"). Auf ausdrückliche Anweisung im Chat — die Regel stammt vom
|
||||
Auftraggeber, und er hat sie für diesen Vorgang aufgehoben.
|
||||
|
||||
### Nachweise
|
||||
|
||||
- `npx tsc --noEmit` — ohne Ausgabe, jetzt **einschließlich** `tests/e2e`
|
||||
- `npm run lint` — ohne Beanstandung
|
||||
- `npm run test` — 495 Tests grün
|
||||
- `npx playwright test` — grün gegen die Testwehr
|
||||
- Die Beispielwehr steht danach unverändert auf dem Seed-Stand: 49 Geräte,
|
||||
8 Einsätze, 1 Atemschutzüberwachung, 19 Termine, 4 Wiki-Seiten
|
||||
|
||||
---
|
||||
|
||||
|
||||
|
Before Width: | Height: | Size: 223 KiB After Width: | Height: | Size: 224 KiB |
|
Before Width: | Height: | Size: 225 KiB After Width: | Height: | Size: 226 KiB |
|
Before Width: | Height: | Size: 1.1 MiB After Width: | Height: | Size: 1.1 MiB |
|
Before Width: | Height: | Size: 1.1 MiB After Width: | Height: | Size: 1.1 MiB |
|
Before Width: | Height: | Size: 261 KiB After Width: | Height: | Size: 402 KiB |
|
Before Width: | Height: | Size: 266 KiB After Width: | Height: | Size: 413 KiB |
|
Before Width: | Height: | Size: 177 KiB After Width: | Height: | Size: 179 KiB |
|
Before Width: | Height: | Size: 178 KiB After Width: | Height: | Size: 180 KiB |
|
Before Width: | Height: | Size: 187 KiB After Width: | Height: | Size: 193 KiB |
|
Before Width: | Height: | Size: 188 KiB After Width: | Height: | Size: 195 KiB |
|
Before Width: | Height: | Size: 808 KiB After Width: | Height: | Size: 745 KiB |
|
Before Width: | Height: | Size: 830 KiB After Width: | Height: | Size: 764 KiB |
|
Before Width: | Height: | Size: 988 KiB After Width: | Height: | Size: 1.0 MiB |
|
Before Width: | Height: | Size: 1.0 MiB After Width: | Height: | Size: 1.1 MiB |
|
Before Width: | Height: | Size: 226 KiB After Width: | Height: | Size: 226 KiB |
|
Before Width: | Height: | Size: 228 KiB After Width: | Height: | Size: 228 KiB |
|
Before Width: | Height: | Size: 1.6 MiB After Width: | Height: | Size: 326 KiB |
|
Before Width: | Height: | Size: 1.7 MiB After Width: | Height: | Size: 332 KiB |
|
Before Width: | Height: | Size: 139 KiB After Width: | Height: | Size: 139 KiB |
|
Before Width: | Height: | Size: 139 KiB After Width: | Height: | Size: 139 KiB |
|
Before Width: | Height: | Size: 930 KiB After Width: | Height: | Size: 156 KiB |
|
Before Width: | Height: | Size: 946 KiB After Width: | Height: | Size: 156 KiB |
|
Before Width: | Height: | Size: 287 KiB After Width: | Height: | Size: 287 KiB |
|
Before Width: | Height: | Size: 260 KiB After Width: | Height: | Size: 280 KiB |
|
Before Width: | Height: | Size: 265 KiB After Width: | Height: | Size: 287 KiB |
|
Before Width: | Height: | Size: 760 KiB After Width: | Height: | Size: 336 KiB |
|
Before Width: | Height: | Size: 766 KiB After Width: | Height: | Size: 338 KiB |
|
Before Width: | Height: | Size: 378 KiB After Width: | Height: | Size: 376 KiB |
|
Before Width: | Height: | Size: 261 KiB After Width: | Height: | Size: 261 KiB |
|
Before Width: | Height: | Size: 263 KiB After Width: | Height: | Size: 263 KiB |
|
Before Width: | Height: | Size: 559 KiB After Width: | Height: | Size: 726 KiB |
|
Before Width: | Height: | Size: 563 KiB After Width: | Height: | Size: 742 KiB |
|
Before Width: | Height: | Size: 243 KiB After Width: | Height: | Size: 244 KiB |
|
Before Width: | Height: | Size: 249 KiB After Width: | Height: | Size: 103 KiB |
|
Before Width: | Height: | Size: 142 KiB After Width: | Height: | Size: 189 KiB |
|
Before Width: | Height: | Size: 146 KiB After Width: | Height: | Size: 193 KiB |
|
Before Width: | Height: | Size: 192 KiB After Width: | Height: | Size: 192 KiB |
|
Before Width: | Height: | Size: 189 KiB After Width: | Height: | Size: 184 KiB |
|
Before Width: | Height: | Size: 197 KiB After Width: | Height: | Size: 122 KiB |
|
Before Width: | Height: | Size: 195 KiB After Width: | Height: | Size: 126 KiB |
|
Before Width: | Height: | Size: 175 KiB After Width: | Height: | Size: 175 KiB |
|
Before Width: | Height: | Size: 175 KiB After Width: | Height: | Size: 176 KiB |
|
Before Width: | Height: | Size: 2.5 MiB After Width: | Height: | Size: 391 KiB |
|
Before Width: | Height: | Size: 316 KiB After Width: | Height: | Size: 317 KiB |
|
Before Width: | Height: | Size: 265 KiB After Width: | Height: | Size: 270 KiB |
|
Before Width: | Height: | Size: 268 KiB After Width: | Height: | Size: 132 KiB |
|
Before Width: | Height: | Size: 201 KiB After Width: | Height: | Size: 230 KiB |
|
Before Width: | Height: | Size: 991 KiB After Width: | Height: | Size: 627 KiB |
|
Before Width: | Height: | Size: 1012 KiB After Width: | Height: | Size: 638 KiB |
|
Before Width: | Height: | Size: 410 KiB After Width: | Height: | Size: 262 KiB |
|
Before Width: | Height: | Size: 234 KiB After Width: | Height: | Size: 229 KiB |
|
Before Width: | Height: | Size: 199 KiB After Width: | Height: | Size: 199 KiB |
|
Before Width: | Height: | Size: 200 KiB After Width: | Height: | Size: 200 KiB |
|
Before Width: | Height: | Size: 333 KiB After Width: | Height: | Size: 248 KiB |
|
Before Width: | Height: | Size: 340 KiB After Width: | Height: | Size: 251 KiB |
|
Before Width: | Height: | Size: 321 KiB After Width: | Height: | Size: 320 KiB |
|
Before Width: | Height: | Size: 329 KiB After Width: | Height: | Size: 328 KiB |