Cron is the Unix scheduler that runs commands on a schedule. It powers everything from database backups and log rotation to deployment pipelines and report generation. The syntax looks cryptic at first, but once you understand the five fields, you can write any schedule from memory.
The Five-Field Format
Every cron expression has five fields separated by spaces:
┌───────────── minute (0–59)
│ ┌───────────── hour (0–23)
│ │ ┌───────────── day of month (1–31)
│ │ │ ┌───────────── month (1–12)
│ │ │ │ ┌───────────── day of week (0–7, 0 and 7 are Sunday)
│ │ │ │ │
* * * * * command to run
* means "every valid value" for that field.
Special Characters
| Character | Meaning | Example |
|-----------|---------|---------|
| * | Any value | * * * * * = every minute |
| , | List of values | 1,15,30 = at 1st, 15th, and 30th |
| - | Range of values | 9-17 = 9am through 5pm |
| / | Step/interval | */15 = every 15 units |
Common Cron Schedules
Every minute
* * * * *
Use this for high-frequency health checks or queues that need near-real-time processing.
Every 15 minutes
*/15 * * * *
Every hour, on the hour
0 * * * *
Every day at midnight
0 0 * * *
Every day at 6:30 AM
30 6 * * *
Every weekday (Monday–Friday) at 9 AM
0 9 * * 1-5
Every Monday at 8 AM
0 8 * * 1
First day of every month at midnight
0 0 1 * *
Every 6 hours
0 */6 * * *
Runs at 00:00, 06:00, 12:00, 18:00.
Twice a day (9 AM and 6 PM)
0 9,18 * * *
Every Sunday at 2 AM (weekly backup)
0 2 * * 0
Last minute of every year
59 23 31 12 *
Month and Day Name Aliases
Most cron implementations accept three-letter names:
# Month names
0 0 * Jan * = January
0 0 * Feb * = February
0 0 * Dec * = December
# Day names
0 9 * * Mon = Monday
0 9 * * Fri = Friday
0 9 * * Mon-Fri = weekdays
Special Strings (Non-Standard but Widely Supported)
Many modern schedulers accept these shortcuts:
| String | Equivalent | Meaning |
|--------|-----------|---------|
| @yearly | 0 0 1 1 * | Once a year, Jan 1st midnight |
| @monthly | 0 0 1 * * | Once a month, 1st day midnight |
| @weekly | 0 0 * * 0 | Once a week, Sunday midnight |
| @daily | 0 0 * * * | Once a day at midnight |
| @hourly | 0 * * * * | Once an hour |
| @reboot | — | Once at startup |
Real-World Examples
Database backup every night at 2 AM:
0 2 * * * /usr/local/bin/pg_dump mydb > /backups/mydb-$(date +\%Y\%m\%d).sql
Clean temp files every Sunday at 3 AM:
0 3 * * 0 find /tmp -type f -mtime +7 -delete
Restart an app every day at midnight:
0 0 * * * /usr/bin/systemctl restart myapp
Send a report on the first of every month:
0 9 1 * * /usr/local/bin/send-monthly-report.sh
Check disk space every 5 minutes:
*/5 * * * * /usr/local/bin/check-disk.sh
The Crontab File
To edit your system crontab:
# Edit crontab for current user
crontab -e
# List current crontabs
crontab -l
# Remove all crontabs for current user
crontab -r
# Edit crontab for a specific user (requires sudo)
sudo crontab -u www-data -e
System-wide cron files live in /etc/cron.d/, /etc/cron.daily/, /etc/cron.weekly/, /etc/cron.monthly/.
Cron in Cloud & Modern Environments
GitHub Actions:
on:
schedule:
- cron: '0 6 * * 1-5' # 6 AM weekdays UTC
AWS EventBridge (uses cron or rate expressions):
cron(0 6 ? * MON-FRI *) # Same schedule in AWS format
rate(15 minutes) # Simpler rate expression
Vercel Cron Jobs (in vercel.json):
{
"crons": [{
"path": "/api/daily-cleanup",
"schedule": "0 2 * * *"
}]
}
Kubernetes CronJob:
spec:
schedule: "0 2 * * *"
A Note on Timezones
Cron runs in the server's local timezone by default. This causes bugs when servers run UTC but your business logic uses a local timezone.
On Linux, you can set the timezone per crontab:
CRON_TZ=America/New_York
0 9 * * * /usr/local/bin/send-report.sh
In cloud services (GitHub Actions, AWS EventBridge), cron always runs in UTC. Calculate your local time → UTC offset before setting the schedule.
Test Cron Expressions Without Waiting
Use our free Cron Expression Tester to see exactly when your cron job will next fire — and the 10 upcoming trigger times — without waiting for the actual time to arrive.
Summary
- Cron expressions have 5 fields: minute, hour, day-of-month, month, day-of-week
*= any,,= list,-= range,/= step@daily,@weekly,@monthlyare convenient shortcuts- Always specify timezone explicitly when running time-sensitive jobs
- Test your cron expression before deploying — a misconfigured cron can run every minute or never
References & Credits
- crontab(5) Linux man page — Linux man-pages project
- crontab(1) — vixie-cron — the original cron implementation by Paul Vixie
- GitHub Actions: Scheduled Workflows — GitHub Docs
- AWS EventBridge Cron Expressions — AWS Documentation
- Vercel Cron Jobs — Vercel Documentation
- cronstrue — Brady Holt, the open-source library used to translate cron expressions to human-readable text on WeHelpDevs