- Dark Mode: Hinweis auf manuellen Theme-Switch in Einstellungen
- Aufgaben/Kalender: Wiederholungen als Feature hervorgehoben
- Sicherheit: Input-Validation und parametrisierte Queries dokumentiert
- Jahreszahl auf 2025–2026 aktualisiert
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Dark Mode: Manueller Theme-Switch (System/Hell/Dunkel) in Einstellungen
mit localStorage-Persistenz und Flash-Prevention via data-theme Attribut.
RRULE UI: Wiederholungs-Formular in Aufgaben- und Kalender-Modals mit
Frequenz (Täglich/Wöchentlich/Monatlich), Intervall, Wochentag-Auswahl
und optionalem Enddatum. Backend-Routen für is_recurring/recurrence_rule
in POST/PUT erweitert. Repeat-Icon auf wiederkehrenden Einträgen.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- helmet: upgrade-insecure-requests und HSTS nur bei SESSION_SECURE=true
- Service Worker Cache-Version auf v10 hochgezählt
- Debug-Code aus router.js entfernt
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Begrüßungs-Widget mit Stats-Chips (dringende Aufgaben, heutige Termine, Mittagessen)
- Aufgaben- und Termine-Widgets mit Count-Badge im Header
- Essen-Widget als 4-Slot-Raster (Frühstück/Mittagessen/Abendessen/Snack) mit Lucide-Icons
- Notizen als Kachel-Grid statt Liste
- event-time-badge, widget__badge, greeting-chip, meal-slots, notes-grid-widget CSS
- Hover-Lift-Effekt auf Widgets (Desktop)
- Widget-Empty-States mit zentrierten Icons
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Wenn weder Cache noch Netzwerk verfügbar sind gab die Funktion undefined zurück,
was event.respondWith() als Promise-Rejection wertet und einen Network Error
im Browser erzeugt. Letzter Ausweg ist jetzt eine 503-Antwort.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- connect-sqlite3 durch eigenen BetterSQLiteStore ersetzt (sessions-Tabelle
in der bestehenden DB, keine native Kompilierung nötig)
- db.init() vor require('./auth') gezogen damit BetterSQLiteStore-Konstruktor
db.get() erfolgreich aufrufen kann
- router.js: App-Shell und pageWrapper vor module.render() in DOM einfügen
damit document.getElementById() in Seiten-Modulen funktioniert
- Seiten-Module (meals, notes, contacts, calendar, budget): _container-Referenz
eingeführt, alle document.getElementById() auf _container.querySelector() bzw.
document.querySelector() für body-Elemente umgestellt
- login.js: User-Objekt nach erfolgreichem Login an navigate() übergeben
damit auth.me()-Roundtrip entfällt
- calendar.js: /users → /auth/users korrigiert (404-Fix)
- SW-Cache v8 (erzwingt Reload aller gecachten Seiten-Module)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- lucide.min.js v0.469.0 lokal gecacht (kein unpkg-Request mehr)
- Source-Map-Referenz aus Bundle entfernt (behebt NetworkError in DevTools)
- unpkg.com aus CSP entfernt (nicht mehr benötigt)
- preconnect zu unpkg.com aus index.html entfernt
- lucide.min.js zum SW-App-Shell-Cache hinzugefügt
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Das Inline-Script in index.html für die Service-Worker-Registrierung
wurde von der Content-Security-Policy blockiert (kein 'unsafe-inline'
in script-src). Ausgelagert nach /sw-register.js ('self' erlaubt).
Außerdem: rel="preload" → rel="modulepreload" für ES-Module (korrekte
Browser-Semantik, behebt die Preload-Warnungen in der Console).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- router.js: navigateTo() existierte nicht → ReferenceError nach fehlgeschlagenem
auth.me(). Ersetzt durch navigate() + currentPath-Reset damit die Weiterleitung
nicht durch den currentPath-Guard geblockt wird.
- csrf.js: SESSION_SECURE=false wurde nicht berücksichtigt → CSRF-Cookie war über
HTTP nicht für JS lesbar → alle schreibenden API-Calls nach Login scheiterten mit 403.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Schnellstart → detaillierte 6-Schritt-Anleitung mit Erklärungen
- Schlüssel-Generierung mit openssl rand dokumentiert
- Neuer Hinweis: SESSION_SECURE=false für HTTP ohne Reverse Proxy
- Hinweis wann SESSION_SECURE wieder entfernt werden soll (nach SSL-Setup)
- Status prüfen nach Container-Start erklärt
- Konfigurationstabelle um SESSION_SECURE ergänzt
- Updates-Sektion mit Backup-Hinweis
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
SESSION_SECURE=false in .env deaktiviert das Secure-Flag für Session-
und CSRF-Cookie. Notwendig wenn die App direkt per HTTP erreichbar ist
(kein Nginx/HTTPS davor). Standard bleibt secure=true in production.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
chown im Dockerfile reicht nicht: Docker überschreibt beim Mounten eines
named Volume die Image-Permissions. Entrypoint-Script (läuft als root)
korrigiert /data-Ownership zur Laufzeit und startet dann via su-exec
als unprivilegierten node-User (korrekte Signal-Weiterleitung).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
mkdir -p /data lief als root, danach USER node — node hatte keine
Schreibrechte auf das Volume-Mountpoint. chown node:node /data vor
dem USER-Wechsel behebt den SQLITE_CANTOPEN-Fehler beim Deploy.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Interne Claude Code Instruktionsdatei — kein Inhalt für Repo-Nutzer.
Alle relevanten Informationen sind in README.md dokumentiert.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
5 Dark Mode Smartphone-Mockups (Dashboard, Aufgaben, Kalender, Einkauf,
Essensplan) mit korrekten Dark Mode Design-Tokens (#1C1C1E BG, #2C2C2E
Surface, #AEAEB2 Sekundärtext). README: Getrennte Light/Dark-Tabellen
mit je 5 Screenshots in einer Reihe.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Smartphone-Mockups für alle 5 Hauptansichten (Dashboard, Aufgaben,
Kalender, Einkauf, Essensplan) mit realistischem iPhone-Rahmen.
README um Screenshots-Sektion erweitert.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- LICENSE: MIT-Lizenz (bereits vorhanden, korrekt)
- package.json: "license": "MIT" ergänzt
- README.md: Lizenz-Badge auf MIT aktualisiert, Lizenz-Sektion angepasst
- .gitignore: .claude/ und *.txt hinzugefügt (verhindert versehentliches
Committen von Claude Code Einstellungen und Token-Textdateien)
- server/auth.js: Fail-Fast in Produktion wenn SESSION_SECRET fehlt;
Fallback-String auf 'dev-only-secret-not-for-production' umbenannt
(klarere Intention, kein bekannter Produktions-Wert im Public Repo)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Backend:
- GET /shopping — alle Listen mit item_total/item_checked Zähler
- POST/PUT/DELETE /shopping/:listId — Listen-CRUD
- GET /shopping/:listId/items — Artikel nach Supermarkt-Gang sortiert
(Obst→Backwaren→Milch→Fleisch→Tiefkühl→Getränke→Haushalt→Drogerie→Sonstiges)
Abgehakte innerhalb der Kategorie ans Ende
- POST /shopping/:listId/items — Artikel hinzufügen
- PATCH /shopping/items/:id — Artikel aktualisieren (abhaken, umbenennen)
- DELETE /shopping/items/:id — Einzelartikel löschen
- DELETE /shopping/:listId/items/checked — nur abgehakte löschen
- GET /shopping/suggestions?q= — Autocomplete aus bisherigen Einträgen
Frontend:
- Multi-Listen-Tabs (horizontal scrollbar, Artikel-Zähler im Tab)
- Quick-Add: Name + Menge + Kategorie-Dropdown in einer Zeile
- Autocomplete-Dropdown mit Tastaturnavigation (↑↓ Enter Escape)
- Optimistisches Toggle: Checkbox reagiert sofort, Rollback bei Fehler
- "Abgehakt löschen"-Button erscheint dynamisch bei checked > 0
- Listen umbenennen/löschen direkt im Header
- Kategorie-Icons (Lucide) in Gruppen-Überschriften
Tests: 17/17 bestanden (71 gesamt)
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>