IReplayCache Interface
Remembers the identifiers of single-use tokens so a second presentation of the same one can be told from the first. Every JWT profile that forbids replay needs this and needs it in the same shape - a DPoP proof (RFC 9449 Section 11.1), a client assertion (RFC 7523 Section 3) and a Security Event Token (RFC 8417 Section 2.2) differ in what they call the identifier and how long it stays interesting, never in the question they ask of the cache.
public interface IReplayCacheDerived
↳ ReplayCacheBase
Remarks
The contract is reserve-and-check in one call, so a caller cannot read, decide and write in
three steps that another caller slips between. Whether the reservation is strictly atomic is
the implementation's promise, not this interface's: the shipped
DistributedReplayCache rides IDistributedCache, which exposes only Get
and Set, so its answer is probabilistic within one cache round trip. A deployment that needs
strict single-use takes a backend-native primitive behind this same interface, which is what
ReplayCacheBase is for: it holds everything around the primitive and leaves the
primitive itself to a subclass - Redis SET NX PX, SQL
INSERT ... ON CONFLICT DO NOTHING, and their equivalents.
Methods
IReplayCache.TryReserveAsync(string, DateTimeOffset, CancellationToken) Method
Reserves an identifier, answering whether this is its first sighting.
System.Threading.Tasks.Task<bool> TryReserveAsync(string identifier, System.DateTimeOffset expiresAt, System.Threading.CancellationToken cancellationToken=default(System.Threading.CancellationToken));Parameters
identifier System.String
What identifies the token. A profile whose identifier is unique only within a scope composes that scope into the value it passes - a SET's "jti" is unique per event feed (RFC 8417 Section 2.2), so its receiver reserves the issuer and the identifier together.
expiresAt System.DateTimeOffset
When the identifier stops being worth remembering, which is the last moment a replay of this token could still pass the caller's own freshness checks. Forgetting earlier would let that token replay; the implementation is free to remember longer.
cancellationToken System.Threading.CancellationToken
Cancels the cache round trip.
Returns
System.Threading.Tasks.Task<System.Boolean>
True when the identifier was newly reserved and the token is therefore fresh; false when
it was already there, which is a replay.