Files
2026-06-11 00:24:17 +02:00

233 lines
6.5 KiB
Markdown
Raw Permalink Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# DotNetAngular
Full-Stack Webanwendung mit **ASP.NET Core (.NET 10)** und **Angular 21**, basierend auf **Clean Architecture** mit **PostgreSQL** als Datenbank.
---
## Architektur
```
src/
├── API # ASP.NET Core Web API (Controller, Middleware, Swagger)
├── Application # Anwendungslogik (Services, DTOs, Validatoren)
├── Domain # Entitäten, Repository-Interfaces, Value Objects
└── Infrastructure # EF Core DbContext, Repositories, Migrations
tests/
├── Application.UnitTest # xUnit-Unit-Tests
└── Application.FunctionalTest # xUnit-Funktionstests
```
### Patterns
- **Clean Architecture** mit 4 Schichten (API → Application → Domain ← Infrastructure)
- **Repository & Unit of Work** Pattern
- **Result Pattern** für explizite Erfolgs-/Fehlerrückgaben (keine Exceptions für Flow-Control)
- **FluentValidation** für Request-Validierung
- **JWT-Authentifizierung** mit Refresh-Token
- **Role-Based Access Control** (SuperAdmin, Admin, User)
---
## Technologien
| Bereich | Technologie | Version |
|---|---|---|
| **Backend** | ASP.NET Core | .NET 10 |
| **ORM** | Entity Framework Core | 10.0.7 |
| **Datenbank** | PostgreSQL (Npgsql) | 10.0.1 |
| **Auth** | JWT Bearer (System.IdentityModel.Tokens.Jwt) | 8.18.0 |
| **Validierung** | FluentValidation | 12.1.1 |
| **E-Mail** | MailKit / MimeKit | 4.16.0 |
| **API-Dokumentation** | Swagger (Swashbuckle) | 10.1.7 |
| **Frontend** | Angular (Standalone Components) | 21.2 |
| **UI-Framework** | Bootstrap + Bootstrap Icons | 5.3.8 / 1.13.1 |
| **JWT Frontend** | @auth0/angular-jwt | 5.2.0 |
| **Tests Backend** | xUnit v3 | 3.2.2 |
| **Tests Frontend** | Karma + Jasmine | 6.4 / 5.2 |
---
## Features
- **Registrierung & Login** mit JWT-Token (Access + Refresh Token)
- **Passwort-Reset** per E-Mail (MailKit, HTML-Template)
- **Rollensystem**: SuperAdmin, Admin, User
- **Benutzerverwaltung**: CRUD, Rollenzuweisung/-entzug
- **Paginierte Benutzerliste**
- **Dark Mode**
- **Toast-Benachrichtigungen**
- **Route-Guards** (Authenticated, Admin, Guest)
- **Token-Interceptor** mit automatischem Refresh bei 401
---
## Voraussetzungen
- [.NET 10 SDK](https://dotnet.microsoft.com/en-us/download/dotnet/10.0)
- [Node.js (LTS)](https://nodejs.org/) (≥18)
- [Angular CLI](https://angular.dev/tools/cli)
- PostgreSQL (lokal oder per Docker)
- Ein Chrome/Chromium für Headless-Tests
---
## Setup
### 1. Repository klonen
```bash
git clone <repo-url>
cd DotNetAngular
```
### 2. Angular-Abhängigkeiten installieren
```bash
cd src/ClientApp
npm install
cd ../..
```
### 3. Datenbank konfigurieren
Die Verbindungsdaten werden über **User Secrets** gesetzt:
```bash
cd src/API
dotnet user-secrets set "PostgreSqlSettings:Password" "<dein-passwort>"
dotnet user-secrets set "PostgreSqlSettings:Host" "localhost"
dotnet user-secrets set "EmailSettings:From" "deine-email@gmail.com"
dotnet user-secrets set "EmailSettings:Password" "<app-passwort>"
```
> Standard-Datenbank: `template_db`, Standard-User: `natlinux` (aus `appsettings.json`).
### 4. Datenbank erstellen
```bash
dotnet ef database update
```
> `dotnet-ef` ist als lokales Tool in `dotnet-tools.json` definiert.
### 5. Anwendung starten
**Mit Angular-Dev-Proxy (empfohlen):**
```bash
cd src/API
dotnet run --launch-profile Angular_dev
```
- Angular Frontend: [http://localhost:44492](http://localhost:44492)
- API (direkt): [http://localhost:5184](http://localhost:5184) / [https://localhost:7091](https://localhost:7091)
**Nur API mit Swagger:**
```bash
dotnet run --launch-profile swagger_dev
```
- Swagger UI: [https://localhost:7091/swagger](https://localhost:7091/swagger)
---
## Tests
**Status:** 76 .NET-Tests + 132 Angular-Tests — alle grün.
### Backend (xUnit)
```bash
# Alle Tests
dotnet test
# Nur Unit-Tests
dotnet test tests/Application.UnitTest
# Nur Funktionstests
dotnet test tests/Application.FunctionalTest
```
Getestete Komponenten: `Result`/`PagedResult` (Edge Cases), `JwtService` (Token-Generierung, Refresh-Validierung), `EmailService` (SMTP-Interaktion), `AuthenticationService`.
### Frontend (Karma + Jasmine)
```bash
cd src/ClientApp
# Interaktiv (Browser)
npm test
# Headless CI
npm run test:ci
# Mit Coverage
npm run test:coverage
# Report: src/ClientApp/coverage/index.html
```
```bash
# Headless (benötigt Chromium-Pfad)
CHROME_BIN=/usr/bin/chromium npx ng test --no-watch --browsers=ChromeHeadless
```
Getestete Komponenten: `tokenInterceptor` (401-Refresh-Flow), `HeaderComponent` (Logout/Rolle/Username), `authService` (HTTP-Login/Register/Renew), `DarkModeService` (localStorage-Persistenz), `ToastComponent` (Auto-Dismiss), `PopupModalComponent` (Inputs/Outputs), `ForgetPasswordPopupComponent` (Close/Error/Success).
---
## NPM-Skripte (Frontend)
| Befehl | Beschreibung |
|---|---|
| `npm start` | `ng serve --port 44492` |
| `npm run build` | Produktions-Build |
| `npm test` | Tests (Watch-Modus) |
| `npm run test:ci` | Headless CI-Tests |
| `npm run test:coverage` | Tests mit Coverage |
| `npm run watch` | Dev-Build mit Watch |
---
## API-Endpunkte
Basis: `http://localhost:5184/api` (Dev) / `https://localhost:7091/api`
### Auth (`/api/auth`)
| Methode | Pfad | Auth | Beschreibung |
|---|---|---|---|
| POST | `/register` | - | Benutzer registrieren |
| POST | `/login` | - | Login (gibt JWT + Refresh-Token) |
| POST | `/refresh-token` | - | Access-Token erneuern |
| POST | `/send-reset-email/{email}` | - | Passwort-Reset-Mail senden |
| POST | `/reset-password` | - | Passwort zurücksetzen |
### User (`/api/user`)
| Methode | Pfad | Auth | Beschreibung |
|---|---|---|---|
| GET | `/` | Admin/SuperAdmin | Paginierte Benutzerliste |
| GET | `/{id}` | Authenticated | Benutzer per ID |
| PUT | `/` | Authenticated | Benutzer aktualisieren |
| DELETE | `/{id}` | Authenticated | Benutzer löschen (außer sich selbst) |
| POST | `/assign-role` | SuperAdmin | Rolle zuweisen |
| DELETE | `/revoke-role` | SuperAdmin | Rolle entziehen |
---
## Standard-Rollen
| Rolle | ID | Berechtigungen |
|---|---|---|
| SuperAdmin | 1 | Vollzugriff, Rollenverwaltung |
| Admin | 2 | Benutzerliste, Dashboard |
| User | 3 | Eigenes Dashboard, Profil bearbeiten |
Seed-Daten: SuperAdmin (ID 1) und Admin (ID 2) werden automatisch angelegt.
---
## Hinweise
- Der JWT-Secret-Key in `appsettings.json` ist ein Platzhalter und sollte in Produktion überschrieben werden (z.B. über User Secrets, Umgebungsvariablen oder `appsettings.Production.json`).
- E-Mail-Versand verwendet Gmail SMTP es wird ein [App-Passwort](https://support.google.com/accounts/answer/185833) benötigt.