FilmAPI è l'API REST del sistema CineBase, sviluppata con ASP.NET Core 10 Minimal API. Espone circa 80 endpoint sotto il namespace /api e gestisce l'intera logica di business: catalogo film, programmazione, ticketing, pagamenti, autenticazione e amministrazione.
backend/FilmAPI/
├── Program.cs (entry point, configurazione)
├── FilmAPI.csproj (target net10.0)
├── Data/
│ ├── FilmDbContext.cs (EF Core DbContext, 27 DbSet)
│ ├── DatabaseBootstrap.cs (migrazioni + seed bootstrap)
│ └── Migrations/ (18 migrazioni)
├── Endpoints/ (minimal API endpoint groups)
│ ├── AuthEndpoints.cs (/api/auth/*)
│ ├── FilmsEndpoints.cs (/api/films/*)
│ ├── CinemasEndpoints.cs (/api/cinemas/*)
│ ├── ShowsEndpoints.cs (/api/shows/*)
│ ├── CheckoutEndpoints.cs (/api/checkout/*)
│ ├── ProgrammazioneEndpoints.cs
│ ├── SaleEndpoints.cs
│ ├── RegistiEndpoints.cs
│ ├── CategorieEndpoints.cs
│ ├── MediaEndpoints.cs
│ ├── ProfiloEndpoints.cs
│ ├── AdminUtentiEndpoints.cs
│ ├── CreditoEndpoints.cs
│ ├── ValidazioneBigliettiEndpoints.cs
│ ├── ShowCancellationEndpoints.cs
│ ├── AdminSettingsEndpoints.cs
│ ├── DashboardStatsEndpoints.cs
│ └── TmdbEndpoints.cs
├── Services/ (logica di business, ~30 servizi)
│ ├── AuthService.cs
│ ├── ExternalAuthService.cs
│ ├── CheckoutService.cs
│ ├── SeatHoldService.cs
│ ├── PagamentoService.cs
│ ├── StripeGateway.cs
│ ├── ShowCancellationService.cs
│ ├── EmailService.cs
│ ├── PdfService.cs
│ ├── CatalogLifecycleService.cs
│ └── ...
├── Model/ (37 classi entità)
│ ├── User.cs
│ ├── Film.cs
│ ├── Cinema.cs
│ ├── Show.cs
│ ├── Ordine.cs
│ ├── Biglietto.cs
│ └── ...
├── DTO/ (Data Transfer Objects)
└── Services/
├── AuthCookieService.cs (gestione cookie HTTP-only)
├── RefreshTokenProtector.cs (hashing token SHA256)
└── FrontendEnvironment.cs (URL building e CORS)
Il Program.cs segue una sequenza di bootstrap ben definita:
- Ambiente: Carica variabili da
.env(DotNetEnv), costruisce connessione MySQL/MariaDB da variabili d'ambiente - Servizi: Registra ~30 servizi scoped, 3 hosted service, client HTTP per OAuth, TMDB client
- Sicurezza: Configura JWT Bearer, policy di autorizzazione, rate limiting, CORS
- Pipeline: Aggiunge middleware CORS, RateLimiter, Authentication, Authorization, StaticFiles
- Endpoint: Mappa gruppi sotto
/api+ callback OAuth a root + webhook Stripe a root - Bootstrap: Esegue
DatabaseBootstrap.BootstrapAsync()(migrazioni EF Core + DataSeeder) - Lifecycle: Promuove film
InArrivoaInCartellone, pubblica show pianificati
Il backend è self-bootstrapping: all'avvio esegue MigrateAsync() per applicare le migrazioni EF Core e DataSeeder.SeedAsync() per popolare i dati di base (admin user). L'health endpoint /api/health/ready restituisce 200 solo quando il DB è raggiungibile e il bootstrap è completato, permettendo agli orchestrator (Docker Compose, ACA) di attendere la piena operatività.
| Variabile | Default | Descrizione |
|---|---|---|
DB_HOST |
localhost |
Host MariaDB |
DB_PORT |
3306 |
Porta MariaDB |
DB_NAME |
film-api-db |
Nome database |
DB_USER |
root |
Utente DB |
DB_PASSWORD |
root |
Password DB |
JWT_SECRET |
obbligatorio | Chiave firma JWT (min 32 byte) |
JWT_ISSUER |
CineBaseAPI |
Issuer JWT |
JWT_AUDIENCE |
CineBaseWeb |
Audience JWT |
SMTP_HOST |
localhost |
Server SMTP |
SMTP_PORT |
587 |
Porta SMTP |
STRIPE_SECRET_API_KEY |
(vuoto) | Chiave segreta Stripe |
CORS_ALLOWED_ORIGINS |
http://localhost:5001 |
Origini consentite |
FRONTEND_PUBLIC_BASE_URL |
http://localhost:5001 |
URL pubblico frontend |
GOOGLE_OAUTH_CLIENT_ID |
(vuoto) | Client ID Google OAuth |
MICROSOFT_OAUTH_CLIENT_ID |
(vuoto) | Client ID Microsoft OAuth |
| Policy | Ruoli |
|---|---|
Authenticated |
Qualsiasi utente autenticato |
AdminOnly |
Solo Admin (ruolo 2) |
PowerUserOrAdmin |
PowerUser (1) o Admin (2) |
CinemaStaffOrPowerUserOrAdmin |
CinemaStaff (3), PowerUser (1), Admin (2) |
GlobalBackoffice |
PowerUser (1) o Admin (2) |
Il ruolo CinemaStaff è un ruolo con scope limitato: può gestire solo i cinema a cui è assegnato (validazione biglietti, ricariche credito, gestione show).
Il rate limiter usa builder.Configuration (non Environment.GetEnvironmentVariable diretto) per permettere override per-test senza mutare stato globale. La configurazione è centralizzata in Program.cs con due policy:
| Policy | Algoritmo | Partition | Limite | Finestra | Segmenti | Endpoint |
|---|---|---|---|---|---|---|
LoginRateLimit |
SlidingWindow | `{IP} | {SHA256(email)}` | 10 tentativi | 60s | 4 (15s) |
ForgotPasswordRateLimit |
FixedWindow | `{IP} | {SHA256(email)}` | 3 tentativi | 300s | — |
- Partition composita: l'email è estratta dal body JSON da un middleware asincrono (
ReadToEndAsync) prima diUseRateLimiter(). Email diverse sullo stesso IP = contatori indipendenti. - IP reale da header
X-Forwarded-For(primo IP), fallbackconnection.RemoteIpAddress. - Fallback anonimo: se il body non ha campo
email, partition{IP}|__anon__con limiti ridotti (5 login, 1 forgot). - Risposta 429: JSON
{"message":"Troppi tentativi..."}con headerRetry-Afterdinamico daMetadataName.RetryAfter. - Configurazione: variabili
LOGIN_RATE_LIMIT_PERMITS,LOGIN_RATE_LIMIT_WINDOW_SECONDS,FORGOT_PASSWORD_RATE_LIMIT_PERMITS,FORGOT_PASSWORD_RATE_LIMIT_WINDOW_SECONDS.
7 test case dedicati in RateLimiterIntegrationTests.cs coprono tutti gli scenari (RL1-RL7). Usano TightRateLimitWebApplicationFactory (derivata da CustomWebApplicationFactory, non-sealed) con configurazione in-memory per evitare interferenze tra classi di test parallele.
Tutti i DateTime sono serializzati in formato UTC. Due converter personalizzati (UtcDateTimeJsonConverter, NullableUtcDateTimeJsonConverter) garantiscono che il suffisso Z sia sempre presente, evitando ambiguità di timezone.
RefreshTokenCleanupService— Elimina periodicamente i refresh token scaduti o revocati dal database (intervallo configurabile, default 30 minuti)ExpiredHoldCleanupService— Rilascia i posti in hold scaduti (intervallo configurabile, default 5 minuti)CatalogLifecycleHostedService— Promuove automaticamente i film conDataRilascioraggiunta daInArrivoaInCartellonee pubblica gli show conPublishAtUtcscaduto (intervallo configurabile)
Il progetto di test (tests/backend/FilmAPI.Tests) contiene 639 test (xUnit) che coprono l'intera API, con test di integrazione che usano un database in-memory o un MariaDB dedicato.