00.79.10
@ExperimentalJSentinelApi
(own soak window); the Etappe-1 stable JWT / OAuth2 / OIDC surfaces are
unchanged. The current release is 00.79.41.Release date: 2026-06-27 Previous release: 00.79.00 Maven coordinates (parent):
com.svenruppert.jsentinel:jSentinel-parent:00.79.10Full changelog: GitHub release v00.79.10
Three security blocks, building on the Etappe-1 vendor profiles + Stable-API promotion.
Replay-protection stores
Two persistence-neutral SPIs in jSentinel-core: JtiStore (single-use
jti — backs DPoP-proof and logout-token replay protection) and
NonceStore (per-request-key, single-use, TTL-checked). InMemoryJtiStore
is a bounded sliding window that, on overflow, evicts the soonest-to-expire
entry — never the least-recently-used (an LRU policy would let an attacker
flood the store to evict a victim’s still-live jti and replay a captured
proof; same class as the 00.75.20 R012 fix). Single-JVM defaults; a multi-node
deployment plugs a shared store.
DPoP — sender-constrained tokens (RFC 9449)
New opt-in module jSentinel-dpop:
DpopProofGeneratorsigns an outbounddpop+jwtproof (embedded public JWK;jti/htm/htu/iat, plusathwhen bound to an access token).NimbusDpopProofValidatorverifies the signature against the embedded key, enforces an algorithm allow-list (rejectsnone/ private / symmetric header keys), checkshtm/htu(normalised) /iatfreshness (too-old and future rejected) /ath(constant-time), and enforces single-usejtivia theJtiStore. It returns the RFC 7638 key thumbprint so the caller can bind a DPoP-confirmed access token (cnf.jkt). The thumbprint is computed before thejtiis recorded, so a failure can’t consume a one-timejti.- Sealed, leak-free
DpopValidationError(proof-malformed/signature-invalid/htm-mismatch/htu-mismatch/proof-expired/replay/ath-mismatch); aDpopKeyStoreSPI holds per-target signing keys.
OIDC logout-hardening
Back-Channel + Front-Channel Logout 1.0 (API in jSentinel-core, impls in
jSentinel-identity-oidc):
DefaultLogoutTokenValidatorcomposes aJwtValidatorand adds the §2.4 checks: the back-channel-logouteventsmember required,noncemust be absent (stops an ID token being replayed as a logout token),sub/sidpresent,jtirequired + single-use viaJtiStore.BackChannelLogoutReceiveris pure token-in / outcome-out — it dereferences no URL from the token, so no SSRF (§2.6) — and terminates RP sessions via aSessionRegistrySPI.FrontChannelLogoutEndpointchecksissagainst the trusted issuer first — a forged issuer is a silent no-op (no spoofed force-logout).
Exit-review
A two-pronged adversarial review fixed three findings before ship: LRU→soonest-
to-expire eviction (R-EXIT-1), thumbprint-before-jti (R-EXIT-2), and jti
now required on logout tokens (R-EXIT-3). No mocks — DPoP round-trips run
real RSA/EC Nimbus signing; logout tests use real RSA-signed logout tokens.
jSentinel-dpop first PIT pass: 63 % (57/91).
Migration
None. Additive. Add jSentinel-dpop to sign/validate DPoP proofs; wire
BackChannelLogoutReceiver behind your backchannel_logout_uri. Just bump the
version to 00.79.10.