Cron, time zones and daylight saving time
Updated 25 September 2026
Cron is simple — until a job runs an hour late, twice, or not at all. Almost always the cause is time zones or daylight saving.
Cron uses the server's clock
A classic crontab follows the system time zone of the machine it runs on. Cloud servers and containers usually run in UTC, so 0 9 * * * is 09:00 UTC —
10:00 or 11:00 in Brussels depending on the season. Check with date or timedatectl. Other schedulers have their own rules: GitHub Actions always uses UTC;
Kubernetes CronJobs support a timeZone field; systemd timers accept a zone per timer. The crontab generator previews run times in any zone.
Daylight saving: gaps and repeats
- Spring forward — on the last Sunday of March (Europe), 02:00–02:59 doesn't exist. A job at 02:30 has no matching moment. Depending on the cron implementation it's skipped or run just after 03:00.
- Fall back — in October, 02:00–02:59 happens twice. Some implementations run a 02:30 job once, some twice.
- Jobs every few minutes are affected too: expect a one-hour gap or overlap in the logs.
Rules that avoid surprises
- Run servers in UTC and convert schedules deliberately.
- If a job must run in local time, avoid 01:00–03:00 (in the US, 01:00–02:59).
- Make jobs idempotent — safe to run twice — and guard against overlaps with
flock -n /tmp/job.lock command. - Log start and end times in UTC with the offset, so incidents can be reconstructed.
For converting individual timestamps between zones and formats, use the Unix timestamp converter.