[Issue #181] Compare certificate expiration timestamps in UTC - #269
Merged
jsf9k merged 6 commits intoJun 24, 2026
Merged
Conversation
Signed-off-by: Arpit Jain <arpitjain099@gmail.com>
arpitjain099
requested review from
IanLee1521,
dav3r,
felddy,
jsf9k and
mcdonnnj
as code owners
June 24, 2026 01:14
jsf9k
approved these changes
Jun 24, 2026
Contributor
There was a problem hiding this comment.
Pull request overview
This PR addresses Issue #181 by making certificate-expiration evaluation consistent with SSLyze’s UTC-based timestamps, avoiding timezone-dependent drift when comparing certificate validity.
Changes:
- Adds a
certificate_is_expired()helper that compares certificate “not valid after” timestamps in UTC. - Updates
https_check()to compute a single UTCnowvalue and reuse it for leaf/chain expiry checks. - Adds unit tests covering UTC-aware and naive timestamp handling, and bumps the package version.
Reviewed changes
Copilot reviewed 3 out of 3 changed files in this pull request and generated 3 comments.
| File | Description |
|---|---|
src/pshtt/pshtt.py |
Introduces UTC-based expiry helper and uses a single now_utc for consistent comparisons in https_check(). |
tests/test_pshtt.py |
Adds unit tests for UTC-aware vs naive certificate timestamp handling. |
src/pshtt/_version.py |
Bumps module version to 0.7.5. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
not_valid_after is typically the last valid moment; once now == not_valid_after the certificate should be considered expired. Using a strict < comparison can produce off-by-one-second results vs the common not_after <= now semantics (and the query in Issue #181). Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
In the former, test the cases where not_valid_after_utc is TZ-aware and naive. In the latter, test the cases where not_valid_after is TZ-aware and naive.
This makes the TZ code handle the case where not_valid_after_utc is present but is a naive timestamp. I'm not sure if that ever happens, but now if it does we are covered.
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.
Fixes #181
I tracked this down to how expiration is compared in
https_check: we compare certificate timestamps against local naive time, while SSLyze data is UTC-based. That can drift by timezone and produce inconsistent expired/not-expired results.This change adds a small helper (
certificate_is_expired) and uses one UTCnowvalue for both leaf and chain certificate checks. It prefersnot_valid_after_utcwhen available and falls back to treating naive timestamps as UTC for older certificate objects.I also added unit coverage for both paths in
tests/test_pshtt.py.What I ran locally:
python3 -m py_compile src/pshtt/pshtt.py tests/test_pshtt.pycertificate_is_expired(UTC-aware and naive fallback cases)I could not run
pyteston this macOS environment becausesslyzepullsnassland fails to import with_SSLv2_methodmissing. So I validated the helper behavior directly and left the new unit tests for CI.