Common cron mistakes
Cron is reliable, which means when a job fires at the wrong time the cause is almost always the expression or the environment, not the scheduler. A handful of mistakes account for most of the surprises, and all of them are easy to avoid once you have seen them.
The day-of-month and day-of-week trap
This is the one that catches nearly everyone. When both the day of month and the day of week fields are set to something other than *, cron treats them as an OR, not an AND. The job runs when either condition matches.
0 0 13 * 5
You might read this as "midnight on Friday the 13th." It actually means "midnight on the 13th of any month, and also midnight on every Friday." If you need a true AND, you cannot express it in the day fields alone. The usual fix is to schedule on one field and add a guard in the job script, for example checking the date before doing the work.
Server timezone assumptions
A cron line has no timezone of its own. It runs in whatever timezone the cron daemon uses, which is often UTC on a server even when you are sitting in a different zone.
0 9 * * *is 9am, but 9am where the server thinks it is.- Daylight saving shifts can cause a job to run twice or be skipped around the changeover.
Decide explicitly what zone you mean and set CRON_TZ or the service's timezone setting rather than assuming. The details of how daylight saving interacts with schedules are covered in cron timezones and DST.
Overlapping long jobs
Cron starts a job on schedule whether or not the previous run has finished. A task set to run every five minutes that sometimes takes seven will start piling up, and before long you have many copies competing for the same resources.
Protect against it with a lock:
*/5 * * * * flock -n /tmp/myjob.lock /usr/local/bin/myjob
flock -n skips the run if the lock is already held, so a slow run never stacks on top of itself.
The missing minute field
Cron expects exactly five fields. If you write what looks like a four field line, every field shifts left and the schedule is wrong.
# wrong: meant 2am daily, only four fields
0 2 * *
# right
0 2 * * *
A missing field usually produces a parse error, but a subtly wrong one, such as pasting a six field expression into a five field crontab, can run silently at the wrong time. Count the fields before you save.
Check before you commit
The safest habit is to confirm what an expression means before it goes live. The Cron Generator shows a plain English reading and the next scheduled runs, so you can catch an OR trap or a shifted field immediately. It works entirely in your browser, so nothing you type is sent anywhere.
Most cron failures come down to these four. Read the day fields carefully, pin down your timezone, guard against overlap, and count your fields. If you want a refresher on the syntax itself, see cron special characters explained.