CronCreate: recurring job permanently drifts after manual run overlap

Resolved 💬 2 comments Opened Apr 6, 2026 by tksohishi Closed May 17, 2026

Description

A recurring cron job created with CronCreate permanently drifts from its scheduled wall-clock time after a manual prompt overlaps with the scheduled fire time. The drift persists across all subsequent fires until the session ends.

Steps to Reproduce

  1. Create a recurring cron job: 7 8-23 * * * (fire at :07 every hour, 8am-11pm)
  2. Observe initial runs log at ~:17 (:07 + ~6 min jitter + ~4 min execution) -- this is expected
  3. At some point, send a manual prompt that overlaps with the :07 fire time (e.g., a long-running prompt active from :05 to :35)
  4. After the overlap, the cron fires late (e.g., at :35 when REPL becomes idle)
  5. From this point forward, all subsequent fires permanently shift to ~:39 instead of returning to :17

Expected Behavior

After a one-time delay (REPL busy at :07), the next hour's fire should return to wall-clock :07 + deterministic jitter. The cron expression is wall-clock based, not interval-from-last-fire.

Actual Behavior

The cron permanently adopts the delayed timing. Observed timestamps from logs:

# Before overlap (healthy, ~:17)
2026-04-04 08:17 EDT
2026-04-04 09:17 EDT
2026-04-04 10:17 EDT
2026-04-04 11:17 EDT

# Manual run overlap at 10:37
2026-04-05 10:37 EDT  <- manual run
2026-04-05 10:42 EDT  <- cron catching up

# After overlap (permanently shifted to ~:39)
2026-04-05 11:39 EDT
2026-04-05 12:39 EDT
2026-04-05 13:39 EDT
...
2026-04-06 08:39 EDT
2026-04-06 09:39 EDT
2026-04-06 10:39 EDT

The shift from :17 to :39 persists indefinitely. Recreating the cron job is the only workaround.

Environment

  • Claude Code CLI (desktop app, macOS)
  • macOS Darwin 25.3.0
  • Cron expression: 7 8-23 * * *
  • Job is session-only (not durable)

Hypothesis

The scheduler may be updating an internal "last fired" or "next fire" timestamp based on when the job actually executed rather than the original cron schedule, effectively converting wall-clock cron into interval-from-last-fire after a delayed execution.

View original on GitHub ↗

This issue has 2 comments on GitHub. Read the full discussion on GitHub ↗