Replace IsAdmin with role-based admin

Switch user admin handling from an AppUser boolean to ASP.NET Identity roles. Removed AppUser.IsAdmin and related configuration/model entries; added migration ReplaceIsAdminWithRoles to copy Users.IsAdmin=true into a persistent admin role and drop the IsAdmin column. CurrentUserResponse now exposes roles (string[]), AuthController returns ordered roles from UserManager, and IdentitySeedService now ensures the admin role exists and assigns/creates an initial admin user in that role. Program.cs registers an Admin-only policy (PolicyNames/RoleNames), adjusts cookie auth events to return 401/403 for API requests, and wires up authorization. Frontend updated to use roles: authSession normalizes roles, adds hasRole and ROLE_ADMIN, router and layout support meta.requiredRoles, and new Forbidden and AdminUsers pages/route are added. codexInfo.md updated to reflect the migration to role-based auth.
This commit is contained in:
Jonas
2026-04-20 19:57:49 +02:00
parent bd261b6868
commit b2984fcf1a
19 changed files with 813 additions and 39 deletions
+6 -2
View File
@@ -91,11 +91,11 @@ Ich baue alleine neben meiner Ausbildung eine einfache self-hosted Web-App für
- Swagger/OpenAPI ist im Backend nur im Development-Modus aktiv (`/swagger`).
- Frontend-Build (`npm run build` im `GUI`-Projekt) schreibt direkt nach `API/wwwroot`; das Backend liefert die SPA und statische Assets aus.
- Backend nutzt jetzt PostgreSQL über `ConnectionStrings:Postgres` mit EF Core (`ApplicationDbContext`) und führt Migrationen beim Start automatisch aus.
- Backend nutzt ASP.NET Identity mit `AppUser` (Guid-Key, `IsAdmin`, `IsActive`, `MustChangePassword`, `CreatedAt`, `UpdatedAt`) über PostgreSQL.
- Backend nutzt ASP.NET Identity mit `AppUser` (Guid-Key, `IsActive`, `MustChangePassword`, `CreatedAt`, `UpdatedAt`) über PostgreSQL; Admin-Rechte laufen über Rollen (`admin`) statt User-Flag.
- `ApplicationDbContext` basiert auf `IdentityDbContext`; Identity-Tabellen sind auf `Users`, `Roles`, `UserRoles`, `UserClaims`, `UserLogins`, `RoleClaims` und `UserTokens` gemappt.
- Migration `InitIdentity` (`API/Migrations/20260418192723_InitIdentity.cs`) erstellt das Identity-Schema und wird beim Start automatisch angewendet.
- Temporäre Test-Entity und Test-CRUD-Endpunkt (`api/test-items`) wurden wieder entfernt.
- Nach den Migrationen wird per `IdentitySeedService` ein initialer Admin angelegt, falls noch kein Admin existiert.
- Nach den Migrationen wird per `IdentitySeedService` die Rolle `admin` sichergestellt und einem initialen Admin-Account zugewiesen, falls noch kein Admin in dieser Rolle existiert.
- Für lokale Entwicklung liegt unter `API/Dev/docker-compose.yml` ein Stack mit PostgreSQL (`localhost:5432`) und pgAdmin (`localhost:5050`).
- API lädt optional `API/appsettings.custom.json`; wenn vorhanden, überschreibt sie Werte aus `appsettings.json`.
- `API/appsettings.custom.json` ist in `.gitignore` hinterlegt, damit lokale Konfigurationswerte nicht versehentlich committed werden.
@@ -170,3 +170,7 @@ Ich baue alleine neben meiner Ausbildung eine einfache self-hosted Web-App für
- `GUI/src/Layout.vue` Brand-Navigation nachgeschärft: `navigateToBrandTarget()` löst bei Klick zuerst die Session via `fetchCurrentUser()` auf (falls lokal noch `null`) und verhindert dadurch Fehlnavigation auf `Welcome`; Mobile-Account-Menütext auf `Zum Dashboard` vereinheitlicht.
- Neuer globaler Skill `codexinfo-komprimieren` unter `C:/Users/famil/.codex/skills/codexinfo-komprimieren` erstellt; er liest `codexInfo.md`, verdichtet `Änderungen durch Codex` auf drei Kernzeilen und enthält ein Hilfsskript zum robusten Abschnitts-Update.
- `GUI/src/routes/404NotFound.vue` erweitert: Seite ermittelt beim Laden den Login-Status über `fetchCurrentUser()`, setzt CTA/Icon dynamisch auf `Zum Dashboard` oder `Zur Startseite` und leitet nach kurzer Verzögerung automatisch auf das passende Ziel weiter.
- Rollenbasiertes Auth-Modell umgesetzt: `IsAdmin` aus `AppUser`/Konfiguration entfernt, neue Rolle-Konstante `admin` eingeführt und Admin-Prüfungen auf Policy/Rollen (`API/Security/*`, `Authorize(Policy = admin-only)`) umgestellt.
- Neue Migration `ReplaceIsAdminWithRoles` (`API/Migrations/20260420174609_ReplaceIsAdminWithRoles.cs`) ergänzt: migriert bestehende `Users.IsAdmin = true` idempotent in `UserRoles` (`admin`) und entfernt anschließend die Spalte `IsAdmin`.
- `GET /auth/me` liefert jetzt `roles: string[]` statt `isAdmin`; `GUI/src/services/authSession.ts` wurde auf Rollen normalisiert und um `hasRole()` ergänzt.
- Frontend-Autorisierung erweitert: Router unterstützt `meta.requiredRoles`, neue 403-Seite `GUI/src/routes/Forbidden.vue` und admin-spezifische Route `GUI/src/routes/admin/AdminUsers.vue` werden nur für Rolle `admin` zugänglich/angezeigt.