Cron Expression Builder

Build, validate and decode cron expressions. See next run times, a 7-day schedule grid, and copy-ready snippets for GitHub Actions, Kubernetes, and Vercel Cron.

Build a Cron Schedule

Minute
0
Hour
9
Day (month)
*
Month
*
Day (week)
1-5
Human-readable
At 09:00, on Mon, Tue, Wed, Thu, Fri

Next 7 days — schedule grid

Day0003060912151821
Sun 24
Mon 25
Tue 26
Wed 27
Thu 28
Fri 29
Sat 30
Fires this hour
No fire

Next 6 runs (local time)

Mon, 25 May 2026, 09:00 UTC
in 20h 28m
Tue, 26 May 2026, 09:00 UTC
in 1d 20h
Wed, 27 May 2026, 09:00 UTC
in 2d 20h
Thu, 28 May 2026, 09:00 UTC
in 3d 20h
Fri, 29 May 2026, 09:00 UTC
in 4d 20h
Mon, 01 Jun 2026, 09:00 UTC
in 7d 20h

Describe in English → cron

Try phrases like "every weekday at 9am", "first day of every month", "every 15 minutes", "saturday and sunday at noon".

Copy for…

Presets

Syntax Reference

FieldAllowedExamples
Minute0–590, */5, 15-45
Hour0–230, 9, */6, 8-17
Day (month)1–311, 15, 28-31
Month1–121, JAN, */3, 3-6
Day (week)0–60=Sun, 1-5, MON-FRI
* — any value
*/n — every nth value
a-b — range
a,b,c — list of values

Cron syntax explained: the 5 fields

A standard Unix cron expression is five space-separated fields read left to right: minute (0–59), hour (0–23), day of the month (1–31), month (1–12 or JAN–DEC), and day of the week (0–6 where 0 is Sunday, or SUN–SAT). Each field accepts a fixed number, a comma-separated list, a range, an asterisk for "any", or a step value like */n. The expression matches a particular minute if every field matches that minute's timestamp. One important edge case: when both day-of-month and day-of-week are restricted, classic Unix cron treats them as an OR — the job fires if either field matches. This tool uses the same convention, which is also what Vixie cron, GitHub Actions and Vercel use.

Common cron patterns and what they mean

* * * * * fires every single minute — useful for tests, dangerous in production. */5 * * * * is the bread-and-butter polling schedule: every five minutes, on the dot. 0 * * * * means "at minute zero of every hour" — so 13:00, 14:00, 15:00 and so on. 0 9 * * 1-5 is a working-hours classic: 9am Monday through Friday. 0 0 1 * * runs once a month at midnight on the first. 0 0 * * 0 is a weekly Sunday-midnight digest. 0 3 * * * is the canonical "quiet hours" slot — 3am every day, when nobody is awake to argue with your maintenance window. If you ever see something like 0 0 28-31 * *, it's a workaround for "last day of the month" in standard cron, since Unix cron has no L token.

Standard cron vs Quartz vs cron with seconds

Three flavours of cron syntax dominate the wild. Standard Unix cron (5 fields, minute precision) is what crontab, GitHub Actions, Kubernetes CronJob, Vercel Cron, and most serverless schedulers use. Quartz (Java, Spring, Hangfire, AWS EventBridge in some configurations) adds a leading seconds field and a trailing year field for 6 or 7 total, and introduces extras like L (last), W (nearest weekday), and# (nth occurrence). Cron-with-seconds sits in between: 6 fields, starting with seconds — used by Cron4j and some background-job libraries. Pasting a 6-field Quartz expression into a 5-field scheduler will silently misalign every value, so always confirm which dialect your platform expects before copying.

Cron pitfalls: timezone, DST, missed runs, overlap

Cron looks deterministic, but four things bite people in production. First, timezone: most managed schedulers (GitHub Actions, Vercel Cron, AWS EventBridge defaults) interpret your expression in UTC, not your local time. A 0 9 * * 1-5 intended as "9am London" will fire at 10am London in winter and 9am London in summer if you forget to set the timezone explicitly. Second, DST: when the clock jumps forward, expressions targeting the skipped hour never fire that day; when it falls back, they may fire twice. Schedulers handle this differently, so check your platform's docs. Third, missed runs: if the host is down at the firing minute, classic cron simply skips that run — only some schedulers (anacron, systemd timers with Persistent=true) catch up. Fourth, overlap: cron will start a new instance at the next firing minute even if the previous one is still running. Wrap your job in a lock (flock, Redis SETNX, or framework-level concurrency controls) if it isn't safely re-entrant.

Frequently Asked Questions

Find this useful?

These tools are free and ad-free. Support the project!

Buy me a coffee

Related Tools