Y2Z/monolith · error
Time went backwards
Error message
Time went backwards
What it means
This panic comes from an `.expect()` on `SystemTime::now().duration_since(UNIX_EPOCH)` inside `is_expired` in src/cookies.rs. `duration_since` returns `Err` if the system clock is set before the Unix epoch (1970-01-01), so the library panics instead of guessing an expiry. It means the OS clock is wrong, not that the cookie or session is invalid.
Source
Thrown at src/cookies.rs:29
pub name: String,
pub value: String,
}
#[derive(Debug)]
pub enum CookieFileContentsParseError {
InvalidHeader,
}
impl Cookie {
pub fn is_expired(&self) -> bool {
if self.expires == 0 {
return false; // Session, never expires
}
let start = SystemTime::now();
let since_the_epoch = start
.duration_since(UNIX_EPOCH)
.expect("Time went backwards");
self.expires < since_the_epoch.as_secs()
}
pub fn matches_url(&self, url: &str) -> bool {
match Url::parse(url) {
Ok(url) => {
// Check protocol scheme
match url.scheme() {
"http" => {
if self.https_only {
return false;
}
}
"https" => {}
_ => {
// Should never match URLs of protocols other than HTTP(S)
return false;View on GitHub (pinned to a6fc8d0095)
Solutions
- Fix the system clock: enable NTP or systemd-timesyncd so the time is after 1970.
- Check container/VM time sync: ensure the host clock is correct and RTC/hwclock is set before running the app.
- Patch or wrap `is_expired` to treat `duration_since` failure as 'not expired' (return false) instead of panicking.
- File an upstream issue so the library replaces `.expect()` with graceful handling of pre-epoch clocks.
Example fix
// before
let since_the_epoch = start
.duration_since(UNIX_EPOCH)
.expect("Time went backwards");
// after
let since_the_epoch = start
.duration_since(UNIX_EPOCH)
.unwrap_or_default(); // pre-epoch clock: treat as t=0 (nothing expired) Defensive patterns
Strategy: validation
Validate before calling
fn system_clock_is_sane() -> bool {
SystemTime::now()
.duration_since(UNIX_EPOCH)
.map(|d| d.as_secs() > 1_600_000_000) // roughly after Sep 2020
.unwrap_or(false)
}
// call before request handling; if false, resync clock via NTP Prevention
- Enable NTP/time sync on hosts, containers and VMs before running the app.
- In ephemeral containers, wait for clock sync (or check `timedatectl`) before issuing requests.
- Add a startup assertion that the clock is after a plausible recent date.
- Wrap library calls that may panic in `std::panic::catch_unwind` for batch resilience.
When it happens
Trigger: Calling `is_expired` (directly or via cookie/session checks during request handling) while the system clock is set earlier than 1970-01-01T00:00:00Z, so `duration_since(UNIX_EPOCH)` yields `Err(SystemTimeError)`.
Common situations: Containers/VMs with no RTC whose clock starts at or before the epoch, bare-metal devices booting with a reset CMOS battery, embedded systems without NTP sync, clock drift after restore from a snapshot.
Related errors
- unable to serialize DOM into buffer
- Unable to serialize DOM into buffer
- Failed to initialize HTTP client
- unable to read file
- could not prepare output
AI-assisted analysis of Y2Z/monolith@a6fc8d0095 (2026-09-05).
Data as JSON: /api/errors/c85c11b26524fe8a.
Report an issue: GitHub.