mirror of
https://github.com/azaion/satellite-provider.git
synced 2026-06-22 15:11:13 +00:00
[AZ-494] Enable JWT iss/aud validation with fail-fast startup
Option B per user decision: production ships with empty Jwt.Issuer / Jwt.Audience in appsettings.json so the API process refuses to start unless JWT_ISSUER + JWT_AUDIENCE env vars are supplied. Development ships with grep-friendly DEV-ONLY- placeholders so local + docker flows keep working unchanged. AuthenticationServiceCollectionExtensions flips ValidateIssuer + ValidateAudience to true and wires ValidIssuer / ValidAudience via a new ResolveRequiredOrThrow helper that all three required values (secret, iss, aud) now share. JwtTokenFactory.Create + CreateExpired gain optional iss / aud parameters (default null) so existing call sites compile unchanged. JwtTestHelpers adds MintAuthenticated / MintExpired wrappers that resolve iss + aud from env, plus ResolveIssuerOrThrow / ResolveAudienceOrThrow. PerfBootstrap.MintToken + Program.cs JWT bootstrap migrated to the new surface so the perf harness and the integration runner both validate against the same contract. Adds 4 fail-fast unit tests (missing/empty issuer + audience), 2 negative integration scenarios (WrongIssuer_Returns401, WrongAudience_Returns401), and re-tags every existing integration mint site via MintAuthenticated. Compose, .env.example, run-tests.sh, run-performance-tests.sh all load + export JWT_ISSUER + JWT_AUDIENCE alongside JWT_SECRET. Resolves F-AUTH-2 (security_report.md + owasp_review.md). AC-7 (cross-repo suite/_docs/10_auth.md write) deferred — outside this workspace; tracked in deploy_cycle2.md R3 follow-up. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -53,7 +53,7 @@ Cycle 1's A01 / A07 verdicts were `N/A (with caveat)` because the service shippe
|
||||
| A04 | Cryptographic Failures | N/A | **PASS** | HS256 token validation uses `Microsoft.IdentityModel`'s `SymmetricSecurityKey` with `RequireSignedTokens = true` and `RequireExpirationTime = true`. The `alg=none` bypass is blocked by `RequireSignedTokens`; algorithm-confusion is bounded because only one signing key is registered. Secret length ≥ 32 bytes enforced at startup. |
|
||||
| A05 | Injection | PASS | **PASS** | No new SQL / shell / template surfaces. The new JSON parse (`PermissionsAuthorizationHandler`) runs on signature-validated token bytes — see F-UAV-2 disposition. |
|
||||
| A06 | Insecure Design | FAIL (S3, S4, I3) | **FAIL** (+ F-AUTH-3, F-UAV-3) | Rate limiting still absent (now also a 401-flood vector). UAV reject reasons disclose gate structure — accepted UX trade-off, flagged for operator awareness. |
|
||||
| A07 | Identification & Authentication Failures | N/A (with caveat) | **PASS_WITH_WARNINGS** (+ F-AUTH-2) | HS256 with secret ≥ 32 bytes; lifetime + signature validation; ClockSkew = 30 s. **Warning**: `ValidateIssuer = false`, `ValidateAudience = false` per the suite contract — any service that holds `JWT_SECRET` can mint tokens accepted here. Track until admin team defines `iss`/`aud`. No token revocation list — leaked tokens stay valid until `exp`. |
|
||||
| A07 | Identification & Authentication Failures | N/A (with caveat) | **PASS_WITH_WARNINGS** → **PASS_WITH_WARNINGS** (cycle 3: F-AUTH-2 resolved by AZ-494) | HS256 with secret ≥ 32 bytes; lifetime + signature validation; ClockSkew = 30 s. **Cycle 3 (AZ-494)**: `ValidateIssuer` / `ValidateAudience` now `true`; values sourced from `JWT_ISSUER` / `JWT_AUDIENCE` env vars with fail-fast contract. Production iss/aud values are admin-team-confirmed at deploy time. Remaining warning: no token revocation list — leaked tokens stay valid until `exp`. |
|
||||
| A08 | Software or Data Integrity Failures | PASS | **PASS** | AZ-488 file-first-then-row write order documented; same migration / CI discipline as cycle 1. |
|
||||
| A09 | Security Logging Failures | PASS_WITH_WARNINGS (I4) | **PASS_WITH_WARNINGS** (unchanged) | No new logging changes; 401 responses are not currently aggregated for alerting (out of scope for internal service). |
|
||||
| A10 | Mishandling of Exceptional Conditions | PASS | **PASS** | UAV decode failures wrapped in scoped `try/catch` for `UnknownImageFormatException` / `InvalidImageContentException` — produce structured `INVALID_FORMAT` rejects, no stack-trace leak. SEC-11 test verifies reject details have no path / exception-type leakage.
|
||||
@@ -68,5 +68,6 @@ Cycle 1's A01 / A07 verdicts were `N/A (with caveat)` because the service shippe
|
||||
| A03 | F-DEPS-UAV — ImageSharp decode exposure widened | Medium | Phase 1 |
|
||||
| A06 | F-AUTH-3 — rate-limit gap now also covers 401 floods | Low (recurrence of I3) | Phase 2 |
|
||||
| A06 | F-UAV-3 — reject reasons disclose gate structure | Informational (accepted) | Phase 2 |
|
||||
| A07 | F-AUTH-2 — `iss`/`aud` not validated; no revocation list | Medium | Phase 2 |
|
||||
| A07 | F-AUTH-2 — `iss`/`aud` not validated | Medium → **Resolved cycle 3 (AZ-494)** | n/a |
|
||||
| A07 | No token revocation list (residual after AZ-494) | Low | Phase 2 — out of scope until requirement emerges |
|
||||
| (claim handler) | F-UAV-2 — `JsonDocument.Parse` on token claim values | Low | Phase 2 |
|
||||
|
||||
Reference in New Issue
Block a user