Repository navigation
fix: Take related timestamps from a single clock read - #144
Merged
patchandthat merged 2 commits intoOct 29, 2026
Merged
Conversation
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
oleks9o6
marked this pull request as ready for review
October 28, 2026 13:11
patchandthat
self-requested a review
October 29, 2026 11:04
patchandthat
approved these changes
Oct 29, 2026
patchandthat
left a comment
Collaborator
There was a problem hiding this comment.
Looks good, thanks
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Description
Values that describe the same moment now come from one clock read, so they can't drift apart when a second ticks over between reads.
TokenExtensions.CreateJwtPayload:nbfandexp, the case in Time drift in nbf/exp claims #133, where a token could live one second longer than its lifetime.DefaultTokenService: theiatclaim andCreationTimeof identity and access tokens.ServerSessionTicketStore: a session'sCreatedandRenewedwhen the ticket has noIssuedUtc, for new and overwritten sessions.SecretValidator: the expired and current secret lists read the clock once per secret, so a secret expiring between reads ended up in neither list.DistributedDeviceFlowThrottlingService: the stored last-seen time, the polling comparison and the cache entry's expiry.Closes #133
Type of change
Does this PR introduce a breaking change?
Does the change cause a breaking change to any of the following?
Testing
Each change has a unit test with
FakeTimeProvider.AutoAdvanceAmountset, so every clock read moves time on by a second. All seven fail with separate reads and pass with one. The full unit and integration suites pass.LLM Usage
The
src/changes are written by me. The tests were drafted with Claude and reviewed by me.Other context
Checked and left as they are, because the reads are separate checks or separate operations: the two authorization code expiry checks in
TokenRequestValidator, themax_ageand user SSO lifetime checks, PAR storage and validation, refresh token creation, validation and update, and consent and interaction messages.Not changed here:
iatinDefaultBackChannelLogoutService, whilenbfandexpcome later fromCreateJwtPayload. Aligning them would mean takingnbfandexpfromtoken.CreationTime, which changes tokens created without one, so I've left that to you.DateTime.UtcNowinstead of theTimeProvider. That's a different problem from the drift here, so it has its own issue, Some code readsDateTime.UtcNowinstead of theTimeProvider#145.🤖 Generated with Claude Code