Skip to content

feat(security): require JWT authentication on the Viron API (#149)#150

Merged
dmccoystephenson merged 1 commit into
mainfrom
fix/149-jwt-authentication
Jun 14, 2026
Merged

feat(security): require JWT authentication on the Viron API (#149)#150
dmccoystephenson merged 1 commit into
mainfrom
fix/149-jwt-authentication

Conversation

@dmccoystephenson

Copy link
Copy Markdown
Member

Summary

Closes #149. Viron exposed every endpoint unauthenticated over plain HTTP — an open read/write API to world state — contradicting the architecture (RFC 0001), which specifies JWT auth for all services. This adds JWT bearer-token authentication that validates tokens issued by UserAuth.

  • SecurityConfig — a stateless Spring Security filter chain. All endpoints require a valid Authorization: Bearer <token> except /actuator/health and the OpenAPI/Swagger docs. The JwtDecoder mirrors UserAuth's own JwtConfig (HMAC HS256/384/512 with a shared secret + issuer validation), so a token minted by UserAuth validates here with no network call (fast, fits Viron's hot path).
  • Configapp.jwt.secret (${JWT_SECRET}), app.jwt.issuer (default userauth), app.jwt.algorithm (default HS256).
  • Tests — new SecurityConfigTest (unauthenticated → 401; health public); the five controller tests run as @WithMockUser.

Validation

  • Full suite green: 228 tests, 0 failures via ./mvnw test under JDK 21 (the CI command). Includes the new auth tests and all existing tests.

⚠️ Operational / breaking — please review before merge

  • Breaking: every caller must now send a bearer token; previously-anonymous callers get 401.
  • New required env var: JWT_SECRET (no default — the app fails fast without it) and it must match UserAuth's JWT_SECRET (≥ 32 bytes for HS256). JWT_ISSUER/JWT_ALGORITHM default to userauth/HS256.
  • HTTPS is assumed at the gateway, consistent with the other services (this PR adds the auth layer, not TLS termination).

Left for your review rather than auto-merged, given the breaking behavior and the new operational requirement.

Possible follow-ups (not in this PR)

  • Revocation-aware validation (calling UserAuth GET /session/validate) if you want logged-out tokens rejected before expiry — local HS256 validation was chosen for performance.
  • Documenting JWT_SECRET in the README / a .env.example (Viron currently has neither).

Closes #149

Opened by Claude on behalf of Daniel Stephenson; verified with ./mvnw test (228 passing) under JDK 21.

Viron previously exposed every endpoint unauthenticated over plain HTTP,
contradicting the architecture (RFC 0001), which specifies JWT auth for all
services. Add JWT bearer-token authentication that validates tokens issued by
the UserAuth service.

- SecurityConfig: stateless filter chain requiring a valid bearer token on all
  endpoints except actuator health and the OpenAPI/Swagger docs. The JwtDecoder
  mirrors UserAuth's JwtConfig (HMAC HS256/384/512 with a shared secret, issuer
  validation), so UserAuth-minted tokens validate here with no network call.
- New config: app.jwt.secret (${JWT_SECRET}, required, >= 32 bytes for HS256),
  app.jwt.issuer (default userauth), app.jwt.algorithm (default HS256).
- Tests: new SecurityConfigTest (unauthenticated -> 401, health public); the
  five controller tests run as @WithMockUser. Full suite: 228 passing under
  JDK 21 (./mvnw test).

BREAKING: callers must now send `Authorization: Bearer <token>`; the app
requires JWT_SECRET (matching UserAuth's) to start. HTTPS is expected at the
gateway, as for the other services.

Closes #149

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@dmccoystephenson dmccoystephenson merged commit 1418052 into main Jun 14, 2026
1 check passed
@dmccoystephenson dmccoystephenson deleted the fix/149-jwt-authentication branch June 14, 2026 03:34
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Endpoints are unauthenticated over plain HTTP; RFC 0001 specifies JWT auth over HTTPS

1 participant