# Kontoverwaltung für DAK-Mitarbeiter — Design **Datum:** 2026-02-26 **Status:** Genehmigt ## Zusammenfassung Neue Kontoverwaltungsseite (`/account`) für alle authentifizierten User. Tab-basiertes Layout mit drei Bereichen: Profil, Sicherheit und Zwei-Faktor-Authentifizierung. Sidebar-Eintrag "Kontoverwaltung" für alle User sichtbar. ## Route & Navigation - Route: `/account` (innerhalb `ProtectedRoute`/`AppLayout`) - Seite: `AccountPage.tsx` - Sidebar: "Kontoverwaltung" mit `UserCog`-Icon, sichtbar für alle authentifizierten User - Position: unterhalb der Main-Navigation, oberhalb der Admin-Sektion - Header-Dropdown: Link "Konto verwalten" als Quick-Access ## Tab-Struktur ### Tab 1 — Profil | Feld | Typ | Bemerkung | |------|-----|-----------| | Profilbild | Avatar-Upload (Drag & Drop / Klick) | Max 2MB, JPG/PNG, `/uploads/avatars/{user_id}_{timestamp}.{ext}` | | Vorname | Text-Input | `first_name`, neu | | Nachname | Text-Input | `last_name`, neu | | Anzeigename | Text-Input | `display_name`, auto-generiert aus Vor+Nachname, überschreibbar | | Benutzername | Text-Input | `username`, bestehend | | E-Mail | Text-Input | `email`, bestehend | Speichern-Button am Ende. Erfolgsmeldung nach Speichern. ### Tab 2 — Sicherheit | Bereich | Funktion | |---------|----------| | Passwort ändern | Aktuelles Passwort, Neues Passwort, Bestätigung. Min 8 Zeichen. Nutzt `POST /api/auth/change-password` | | Aktive Sessions | Info: Letzter Login-Zeitpunkt (`last_login`) | ### Tab 3 — Zwei-Faktor-Authentifizierung | Status | Anzeige | |--------|---------| | Deaktiviert | Erklärungs-Text + "2FA aktivieren"-Button → Setup-Flow | | Setup-Flow | QR-Code → Authenticator scannen → Bestätigungscode eingeben | | Aktiviert | Status-Badge "Aktiv" + "2FA deaktivieren"-Button (Passwort-Bestätigung) | ## Backend-Erweiterungen ### Neue Felder im User-Model (Alembic-Migration) - `first_name: Optional[str]` (max 100) - `last_name: Optional[str]` (max 100) - `display_name: Optional[str]` (max 200) - `avatar_url: Optional[str]` (max 500) ### Neue Endpoints | Methode | Pfad | Beschreibung | |---------|------|-------------| | PUT | `/api/auth/profile` | Eigene Profildaten ändern | | POST | `/api/auth/avatar` | Profilbild hochladen (multipart) | | DELETE | `/api/auth/avatar` | Profilbild löschen | | DELETE | `/api/auth/mfa` | MFA selbst deaktivieren (Passwort nötig) | | DELETE | `/api/admin/users/{id}/mfa` | MFA durch Admin zurücksetzen | ### Avatar-Speicherung - Verzeichnis: `backend/uploads/avatars/` - Dateiname: `{user_id}_{timestamp}.{ext}` - StaticFiles Mount: `/uploads/` - Max 2MB, nur JPG/PNG ## Datenfluss ### Profil speichern ``` React Hook Form + Zod → PUT /api/auth/profile → Uniqueness-Check → DB Update → re-fetch /api/auth/me → AuthContext aktualisiert ``` ### Avatar hochladen ``` File-Input → POST /api/auth/avatar (multipart) → Validierung (Typ/Größe) → Speicherung → DB avatar_url Update → Avatar in Header/Sidebar aktualisiert ``` ### 2FA aktivieren ``` POST /api/auth/mfa/setup → QR-Code anzeigen → User gibt Code ein → POST /api/auth/mfa/verify → mfa_enabled = true ``` ### 2FA deaktivieren ``` Dialog: Passwort eingeben → DELETE /api/auth/mfa → mfa_enabled = false ``` ## Fehlerbehandlung - E-Mail/Username vergeben → 409 Conflict → Fehlermeldung am Feld - Falsches Passwort → 401 → Fehlermeldung - Ungültiger MFA-Code → 400 → "Code ungültig" - Avatar zu groß / falsches Format → Client-Validierung + Backend-Fallback