# DEVLOG — Entwicklungszeiterfassung Flimmer Alle Zeiten per `date`-Befehl erfasst (Europe/Berlin), nicht geschätzt. --- ## Etappe 1 — Projektgerüst, Branding, Docker, DB-Schema, Auth (v0.1.0) | # | Start | Ende | Dauer | Arbeitsschritt | |---|---|---|---|---| | 1.1 | 18:09 | 18:12 | 3 min | Rückfragen geklärt, Repo und Werkzeugkette geprüft, Projekt-`CLAUDE.md` als Gedächtnis angelegt | | 1.2 | 18:12 | 18:22 | 10 min | `package.json`, TypeScript-, Next- und PostCSS-Konfiguration; Abhängigkeiten installiert (Aufräumen nach hängendem npm-Prozess) | | 1.3 | 18:22 | 18:26 | 4 min | Design-Tokens in `globals.css`: Farbwelt dunkel/hell, Verläufe, Bausteine, Mikro-Animation | | 1.4 | 18:26 | 18:33 | 7 min | Logo entworfen: Bildmarke, Wortmarke aus Pfaden, Lockup, monochrom, Maskable; Icon-Generator und alle Rasterableitungen | | 1.5 | 18:33 | 18:36 | 3 min | Prisma-Schema (22 Modelle), Umstellung auf Prisma 7 mit Treiber-Adapter, erste Migration | | 1.6 | 18:36 | 18:40 | 4 min | Kernbibliotheken: Umgebungsprüfung, DB-Singleton, Auth (Passwörter, Sitzungen, API-Schlüssel), Instanz-Einstellungen, i18n | | 1.7 | 18:40 | 18:44 | 4 min | App-Hülle: Layout mit Theme-Bootstrap, Header, Navigation, Nutzermenü, Anmeldung und Registrierung, Healthcheck; visuelle Kontrolle in beiden Themes und Kontrastkorrektur für den hellen Modus | | 1.8 | 18:44 | 18:47 | 3 min | Docker-Setup (Dockerfile, Compose, Entrypoint mit Migrationslauf), OIDC-Anbindung, Seed-Skript, README, Design-Dokumentation, Changelog | **Etappe 1 gesamt: 38 min** (2026-09-01, 18:09 – 18:47) --- ## Etappe 2 — TMDB-Anbindung (v0.2.0) | # | Start | Ende | Dauer | Arbeitsschritt | |---|---|---|---|---| | 2.1 | 18:47 | 18:51 | 4 min | TMDB-Client: Suche, Serien-, Film- und Staffelabruf, Collections, Anbieterlisten; kurzer Antwortspeicher | | 2.2 | 18:51 | 18:54 | 3 min | Katalogschicht: Import von Titeln, Staffeln, Episoden und Streamingdiensten; Bild-Cache mit eigenem Ausliefer-Endpunkt | | 2.3 | 18:54 | 18:57 | 3 min | Oberfläche: Suchseite mit Typfilter, Detailseite mit Staffeln, Poster- und Anbieterkomponenten | | 2.4 | 18:57 | 19:01 | 4 min | Nachgebildete TMDB-Antworten und Testlauf (7 Tests); dabei zwei Fehler gefunden und behoben: veraltete Zähler nach dem Serienimport, kaputtes Bildsymbol statt Rückfallkachel | **Etappe 2 gesamt: 14 min** (2026-09-01, 18:47 – 19:01) --- ## Etappe 3 — Kern-Tracking: Bibliothek, Status, Episodenfortschritt (v0.3.0) | # | Start | Ende | Dauer | Arbeitsschritt | |---|---|---|---|---| | 3.1 | 19:01 | 19:06 | 5 min | Domänenlogik: Aufnehmen, Status, Sichtungen, Rewatch-Durchläufe, Fortschritt, nächste Episode | | 3.2 | 19:06 | 19:10 | 4 min | 14 Tests dazu; dabei ein Fehler im parallelen Testlauf gefunden (Testdateien räumten sich gegenseitig die Fixtures weg) | | 3.3 | 19:10 | 19:14 | 4 min | Server-Aktionen, Rückmeldungen mit Rückgängig, Bedienelemente (Status, Bewertung, Notizen, Tags, Episodenliste, „+1 Episode") | | 3.4 | 19:14 | 19:17 | 3 min | Bibliotheksseite mit Filtern und Facetten, Papierkorb, Umbau der Detailseite auf die interne Titel-ID | | 3.5 | 19:17 | 19:23 | 6 min | Beispieldaten: erfundener Katalog mit lokal erzeugten Postern, gelebte Bibliothek mit Sichtungshistorie; Klickweg im Browser geprüft (+1 Episode, Rückgängig) | | 3.6 | 19:23 | 19:25 | 2 min | Manuelles Anlegen ohne TMDB-Treffer; Build-Absturz durch zu viele Worker eingegrenzt und behoben | **Etappe 3 gesamt: 24 min** (2026-09-01, 19:01 – 19:25) --- ## Etappe 4 — Universen mit Reihenfolgen und Fortschritt (v0.4.0) | # | Start | Ende | Dauer | Arbeitsschritt | |---|---|---|---|---| | 4.1 | 19:25 | 19:30 | 5 min | Domänenlogik: Universen, berechnete Erscheinungsreihenfolge, frei sortierbare Reihenfolgen, Fortschritt aus Sicht des Betrachters, Freigaben | | 4.2 | 19:30 | 19:33 | 3 min | 12 Tests dazu; eine falsche Testannahme zur Reihenfolge korrigiert (nicht den Code) | | 4.3 | 19:33 | 19:36 | 3 min | Server-Aktionen, sortierbare Liste mit Ziehen und Pfeilknöpfen, Reihenfolge-Umschalter, Aufnehmen, Teilen | | 4.4 | 19:36 | 19:39 | 3 min | Seiten für Übersicht, Anlegen und Detailansicht; Build-Fehler durch `server-only` im Browser-Bundle gefunden und behoben; Umsortieren im Browser geprüft | **Etappe 4 gesamt: 14 min** (2026-09-01, 19:25 – 19:39) --- ## Etappe 5 — Dashboard, Kalender, Statistiken (v0.5.0) | # | Start | Ende | Dauer | Arbeitsschritt | |---|---|---|---|---| | 5.1 | 19:39 | 19:43 | 4 min | Auswertungsschicht: Weiterschauen, kommende Episoden, neu verfügbar, Gesamtzahlen, Monatsverlauf, Verteilungen, Jahresrückblick | | 5.2 | 19:43 | 19:46 | 3 min | Diagrammfarben gegen die Prüfungen auf Helligkeit, Sättigung, Farbfehlsichtigkeit und Kontrast gerechnet; SVG-Diagramme und Verteilungsbalken gebaut | | 5.3 | 19:46 | 19:50 | 4 min | Seiten für Übersicht, Kalender und Statistik | | 5.4 | 19:50 | 19:54 | 4 min | Drei Fehler gefunden und behoben: leeres Monatsdiagramm durch Zeitzonenversatz, Hydrationsbruch durch SVG-Titel, Kalender ohne abgeschlossene Serien; 7 Tests nachgezogen | **Etappe 5 gesamt: 15 min** (2026-09-01, 19:39 – 19:54) --- ## Etappe 6 — Benachrichtigungen, Sync, Import/Export, REST-API, PWA (v0.6.0) | # | Start | Ende | Dauer | Arbeitsschritt | |---|---|---|---|---| | 6.1 | 19:54 | 19:58 | 4 min | Benachrichtigungen über vier Wege samt E-Mail-Vorlage; Hintergrundlauf mit Zeitplan und Cron-Endpunkt | | 6.2 | 19:58 | 20:02 | 4 min | Import (Trakt, CSV) und Export (CSV, JSON) | | 6.3 | 20:02 | 20:07 | 5 min | REST-API `/api/v1` mit API-Schlüsseln, OpenAPI-Beschreibung | | 6.4 | 20:07 | 20:12 | 5 min | Einstellungsseiten, Verwaltung, öffentliches Profil; Service Worker und Offline-Seite | | 6.5 | 20:12 | 20:15 | 3 min | 9 Tests für Import, Export, Papierkorb und Doppelversandschutz | | 6.6 | 20:15 | 20:20 | 5 min | TMDB-Ersatz für Screenshots, 18 Aufnahmen, Verkleinerung auf WebP (13 MB → 0,6 MB) | | 6.7 | 20:20 | 20:25 | 5 min | `docs/ANLEITUNG.md` und `docs/API.md`, README erweitert, API von Hand durchgetestet | **Etappe 6 gesamt: 31 min** (2026-09-01, 19:54 – 20:25) --- ## Nach der Abnahme (v0.7.0) | # | Start | Ende | Dauer | Arbeitsschritt | |---|---|---|---|---| | 7.1 | 20:25 | 20:50 | 25 min | Docker-Image zum ersten Mal wirklich gebaut und gestartet; zwei Fehler behoben (fehlende Prisma-Abhängigkeiten im Laufzeitimage, Schriftabruf beim Bauen), Gitea-Workflows, Erscheinungsmeldung nachgezogen | | 7.2 | 20:50 | 21:05 | 15 min | Compose-Stack von null verifiziert: Migration, erstes Konto wird Administrator, Verwaltung erreichbar | | 7.3 | 21:05 | 21:16 | 11 min | Rückfrage aus dem Betrieb umgesetzt: „hab ich" für die eigene Sammlung (Jellyfin, Plex, NAS, Blu-ray) — Schema, Logik, Oberfläche, Filter, Import/Export, API, Tests, Anleitung | **Nacharbeiten gesamt: 51 min** (2026-09-01, 20:25 – 21:16) --- ## Issue-Runde (v0.8.0) Ab hier lief die Arbeit issue-getrieben: jede Aufgabe mit eigenem Branch, Zeiterfassung in Gitea und Freigabe durch Florian. Die Zeiten unten sind die gemessenen Stopwatch-Werte, nicht die Wanduhr — dazwischen lagen Pausen. | # | Issue | Dauer | Was passiert ist | |---|---|---|---| | 8.1 | #2 Titelraster | 6 min | Titelblock auf zwei Zeilen festgenagelt; vorher und nachher vermessen | | 8.2 | #4 Standardreihenfolge | 15 min | Feld war da und wurde ausgewertet — es fehlte nur der Weg, es zu setzen | | 8.3 | #5 Gesehen zurücknehmen | 10 min | Der Knopf war ein `
`; die Gegenfunktion für Filme fehlte ganz | | 8.4 | #3 Träge Suche | 7 min | Das Ladesignal wurde erzeugt und weggeworfen; zwei Verdächtige durch Messung entlastet | | 8.5 | #6 Passkeys | 20 min | WebAuthn als dritter Weg in dieselbe Sitzung, geprüft mit virtuellem Authenticator | | 8.6 | #1 Jellyfin | 19 min | Bestand und Sichtungen über die TMDB-Kennung, Stufe 1 und 2 | **Issues gesamt: 1 h 17 min** (2026-09-01 21:22 – 2026-09-02 07:25) Dazu ohne Zeiterfassung: die Nacharbeit an `update.sh` (Rückfall auf den Container-Healthcheck), die Merkposten in `CLAUDE.md` und diese Version selbst — Changelog, Screenshots, Release. ### Was dabei auffiel 1. **Zwei eigene Vermutungen hielten der Messung nicht stand.** Bei #3 hatte ich Facetten-Abfragen und blockierende Poster als Ursachen benannt. Gemessen an 2000 Einträgen kosten die Facetten 12 ms, und bei künstlich um 1500 ms verzögerten Bildern stehen die Treffer 891 ms vor den Bildern im DOM. Beide blieben deshalb unangetastet. 2. **Ein Nebenpunkt in einem Issue war schlicht falsch.** Ich hatte bei #5 behauptet, die Einblendung biete ein wirkungsloses Zurücknehmen an — sie prüft aber längst auf `ids.length > 0`. 3. **Der Changelog zu 0.7.1 beschrieb eine Funktion, die es nicht gab.** Die Rückfallprüfung über den Container-Healthcheck stand dort, war aber nie umgesetzt. Jetzt ist sie es. 4. **Ein Abgleich mit null Treffern war kein Fehler.** Der erste Jellyfin-Lauf gegen die Beispieldaten übernahm keine einzige Sichtung — korrektes Entdoppeln, die Episoden waren im Seed längst abgehakt. 5. **Sitzungen über nacktes HTTP gehen nicht.** Das Cookie ist in der Produktion `Secure`; auf einer LAN-IP kommt man deshalb gar nicht herein, ohne Fehlermeldung. Nicht behoben, festgehalten. --- ## Zweite Issue-Runde (v0.9.0) | # | Issue | Dauer | Was passiert ist | |---|---|---|---| | 9.1 | #15 Errungenschaften | 22 min | Regelkatalog auf einem gemeinsamen Datensatz; Filmreihen über die TMDB-Zugehörigkeit statt einer gepflegten Liste | | 9.2 | #16 Titel nachladen | 15 min | Aus dem Bericht wird eine Auswahlliste; was Flimmer nicht kennt, kommt auf Wunsch aus TMDB | **Issues gesamt: 37 min** (2026-09-02, 09:47 – 11:13) Dazu ohne Zeiterfassung: zwei Issues angelegt (#15 und #16), diese Version selbst und die Nachträge an der Anleitung. ### Was dabei auffiel 1. **Ein Test hat eine Formatierungsfalle aufgedeckt.** Die Regel „zwischen drei und fünf Uhr" las die Stunde aus der formatierten Zeichenkette; auf Deutsch liefert `Intl` dafür „03 Uhr", und `Number("03 Uhr")` ist `NaN`. Das Abzeichen wäre nie vergeben worden. 2. **Ich hatte ein fragwürdiges Verhalten in einem Test festgeschrieben.** Der erste Entwurf strich auch *gescheiterte* Titel aus der Auswahlliste, und der Test hielt das fest. Erst beim Durchklicken fiel auf, wie ärgerlich das wäre — Code und Test wurden korrigiert. 3. **Ein Klickweg hat eine falsche Beschriftung gezeigt.** Eine Serie stand als „Film" in der Liste, weil der Typ aus dem Umkehrschluss „keine Episode, also Film" kam. 4. **Der Entwicklungs-Stub kann nur suchen.** Er speist sich aus dem lokalen Katalog und kann deshalb per Definition nichts liefern, was dort fehlt — der Importpfad ließ sich nur über Fixtures belegen, nicht über die Oberfläche. 5. **Zwei parallele Branches, kein Konflikt.** Beide zweigten von `main` ab und fassten dieselben drei Dateien an. Der Merge lief glatt; geprüft wurde trotzdem die Kombination auf `main`, nicht nur die einzelnen Zweige. --- ## Gesamtübersicht | Etappe | Version | Dauer | |---|---|---| | 1 — Gerüst, Branding, Docker, Schema, Auth | 0.1.0 | 38 min | | 2 — TMDB-Anbindung | 0.2.0 | 14 min | | 3 — Kern-Tracking | 0.3.0 | 24 min | | 4 — Universen | 0.4.0 | 14 min | | 5 — Dashboard, Kalender, Statistik | 0.5.0 | 15 min | | 6 — Benachrichtigungen, Sync, Import/Export, API, PWA | 0.6.0 | 31 min | | Nacharbeiten — Docker verifiziert, eigene Sammlung | 0.7.0 | 51 min | | Issue-Runde — Passkeys, Jellyfin, vier Nacharbeiten | 0.8.0 | 77 min | | Zweite Runde — Errungenschaften, Titel nachladen | 0.9.0 | 37 min | **Gesamtentwicklungszeit: 5 h 01 min** (301 min, 2026-09-01 18:09 – 2026-09-02 11:13) ### Womit die Zeit verging | Anteil | Bereich | |---|---| | ~35 min | Oberfläche und Design (Branding, Komponenten, Seiten) | | ~30 min | Domänenlogik (Tracking, Universen, Statistik, Abgleich) | | ~25 min | Schnittstellen nach außen (TMDB, REST-API, Import/Export, Benachrichtigungen) | | ~25 min | Tests — 52 Stück, die unterwegs acht echte Fehler gefunden haben | | ~15 min | Dokumentation, Screenshots, Changelog, Releases | | ~11 min | Gerüst, Docker, Datenmodell, Werkzeugkette | ### Fehler, die die Tests gefunden haben 1. `importSeries` gab veraltete Staffel- und Episodenzähler zurück. 2. Testdateien räumten sich im parallelen Lauf gegenseitig die Fixtures weg. 3. Das Monatsdiagramm blieb wegen eines Zeitzonenversatzes leer. 4. Abgeschlossene, aber weiterlaufende Serien verschwanden aus dem Kalender. 5. Poster zeigten das kaputte Bildsymbol statt der Rückfallkachel. 6. Eine `server-only`-Kette landete im Browser-Bundle und brach den Build. 7. Der SVG-Titel eines Diagramms brach die Hydration. 8. Eine Testerwartung zur Reihenfolge war falsch — nicht der Code. ### Fehler, die erst der echte Containerstart zeigte 1. Dem Laufzeitimage fehlten transitive Abhängigkeiten der Prisma-CLI, die Migration lief nicht an. Die CLI wird jetzt in einer eigenen Build-Stufe vollständig installiert. 2. npm blockiert seit Version 11 Install-Skripte; ohne Freigabe fehlte die plattformpassende Prisma-Engine. 3. `next/font/google` lud die Schrift beim Bauen herunter und ließ den Build im Container hängen. Die Schrift liegt jetzt im Repository.