If your cron job runs perfectly when you execute it by hand but never fires on schedule, the problem is almost always in the environment, the cron daemon’s configuration, or the way the job is defined. This guide walks you through the most common causes and fixes, from checking the cron service to debugging environment variables and file permissions.
What You’ll Need
- Access to the server where the cron job is configured (SSH or a terminal).
- Ability to run commands with
sudoor as the user who owns the crontab (to edit system crontabs or check service logs). - A basic understanding of the command line and the cron syntax (minute, hour, day, month, weekday).
- The exact command or script path that the cron job runs.
Step-by-Step
- Verify the cron daemon is running. On most Linux systems, run
systemctl status cron(orcrondon some distros). If it’s not active, start it withsudo systemctl start cronand enable it to start on boot withsudo systemctl enable cron. On macOS, usesudo launchctl list | grep cron. - Check the crontab syntax. Run
crontab -lto list your current cron jobs. Look for errors in the time fields. A common mistake is using 24-hour time incorrectly (e.g.,20 * * * *runs at 20 minutes past every hour, not 8 PM). The format is: minute (0-59), hour (0-23), day of month (1-31), month (1-12), day of week (0-7, both 0 and 7 are Sunday). Usecrontab -eto edit and fix any issues. - Ensure the cron job is saved correctly. After editing, the crontab file is installed automatically. But if you’re using a system crontab (like
/etc/crontab), you must include the user field. For example:* * * * * root /path/to/script.sh. Missing the user field is a classic silent failure. - Test the exact command from the cron environment. Cron runs with a minimal environment (PATH is often just
/usr/bin:/bin). Runenv -i /bin/sh -c 'your_command'to simulate cron’s environment. If it fails, you need to set the full path to any executables or source your profile in the script. - Check file permissions and ownership. The script must be executable by the user running the cron job. Use
chmod +x /path/to/script.shif needed. Also, the user must have read and execute permission on the script and on any directories in its path. If the script writes to a file, the user needs write permission to that file and its directory. - Look at the cron logs. On most Linux systems, cron logs to
/var/log/syslogor/var/log/cron. Search for your job withgrep CRON /var/log/syslog. You’ll see lines likeCRON[pid]: (user) CMD (command). If you seeNo MTA installedorMailerrors, that’s just cron trying to email output; disable it by adding>/dev/null 2>&1to the end of the command. - Check if the job is actually running but failing silently. Add logging to your script:
echo "$(date) - running" >> /tmp/cron.logat the start and end. Then run the job manually and compare the log. If the log doesn’t update when scheduled, cron isn’t executing it; if it updates but the script fails, you’ll see the error. - Verify the timezone. Cron uses the system timezone, not your local time. Run
dateon the server and compare it to your expected schedule. If the server is in UTC and you’re in EST, a job set for0 9 * * *will run at 9 AM UTC, not 9 AM your time. You can change the timezone in the crontab by addingCRON_TZ=America/New_Yorkat the top (on most systems). - Check if the job is being overwritten or removed. If you have multiple crontabs (e.g., user crontab and system crontab), a job might be defined in one but not the other. Also, some deployment tools or package managers might overwrite your crontab. Check with
crontab -land also look at/etc/cron.d/and/etc/cron.daily/etc. - Test with a simple command. Create a test job that runs every minute:
* * * * * echo "test" >> /tmp/cron_test.log. Wait a minute and check if the file appears. This isolates whether cron itself is working.
Common Mistakes
- Using relative paths in the script. If your script uses
./fileordata/file, it will fail because cron’s working directory is the user’s home directory, not the script’s directory. Always use absolute paths orcdto the script’s directory at the start:cd /path/to/script && ./script.sh. - Forgetting that the script needs to be executable. A script that runs with
bash script.shmanually might not run if the shebang line is wrong or the file isn’t executable. Ensure the shebang (#!/bin/bash) is correct and the file haschmod +x. - Assuming cron uses your shell’s PATH. Cron uses a minimal PATH. If your script calls
pythonbut python is in/usr/local/bin, it won’t be found. Use the full path (/usr/local/bin/python) or set PATH at the top of the crontab:PATH=/usr/local/bin:/usr/bin:/bin. - Not escaping percent signs in the command. In a crontab, a
%is treated as a newline. If your command uses percent signs (e.g.,date +%Y), you must escape them as\%or the command will be truncated. - Using a GUI editor that adds a newline at the end. This is usually fine, but if you accidentally save the crontab with a trailing newline in the middle of a command, it can break. Use
crontab -eand check the file withcat -Ato see hidden characters.
Tips
- Always redirect output. Add
>> /var/log/myjob.log 2>&1to your cron command to capture both stdout and stderr. This way, if the job fails, you’ll have a log to inspect. - Use a wrapper script. Instead of putting a long command directly in crontab, create a script that sets up the environment (PATH, working directory, etc.) and then runs your actual job. This makes debugging much easier.
- Test with the exact same user. If the cron job runs as root, test it as root with
sudo -u root. If it runs as another user, switch to that user withsu - usernameand test there. - Check for special characters. If your command contains
>,<, or|, they are interpreted by the shell. If you need them literally, escape them or put them inside quotes. - Use a tool like
crontab.guruto verify your schedule syntax. It’s a quick way to catch mistakes like setting the hour to 24 or the minute to 60.
Troubleshooting
If you’ve followed the steps and the job still doesn’t run, try these advanced checks:
- Check for SELinux or AppArmor. On some systems, these security modules can block cron from executing certain scripts. Check the audit logs (
/var/log/audit/audit.log) or try temporarily disabling SELinux (not recommended for production) to see if it’s the cause. - Look for resource limits. Cron jobs might be killed if they exceed memory or CPU limits set in
/etc/security/limits.confor via systemd. Check the system logs for OOM (out of memory) messages. - Check if the job is being run but exiting immediately. If your script has a syntax error, it will fail silently. Run the script manually with
bash -x script.shto trace its execution and find errors. - Verify that the cron daemon is not in a broken state. Sometimes the cron service gets stuck. Restart it with
sudo systemctl restart cronand check the status again. - Check for duplicate cron entries. If you have the same job defined in multiple places (e.g., user crontab and
/etc/cron.d), they might conflict. List all cron sources:crontab -l,ls /etc/cron.d/, andcat /etc/crontab. - Use
cronnextto see the next execution time. Some systems have a tool likecronnextor you can usecrontab -l | grep 'your_job'and calculate manually. If the next time is in the past, the schedule is wrong.
Frequently Asked Questions
Why does my cron job run manually but not on schedule?
This almost always comes down to environment differences. When you run a command manually, your shell sets up PATH, working directory, and environment variables. Cron runs with a minimal environment, so commands that rely on your shell’s setup will fail. Also, the cron daemon might not be running, or the crontab syntax might be incorrect.
How do I see cron logs?
On most Linux systems, cron logs are in /var/log/syslog or /var/log/cron. Use grep CRON /var/log/syslog to see cron entries. On some systems, you may need to enable cron logging in /etc/rsyslog.conf or /etc/syslog.conf.
What does No MTA installed mean in cron logs?
MTA stands for Mail Transfer Agent. Cron tries to email the output of your job to the user. If no MTA is installed, it logs this error. It’s harmless, but you can suppress it by redirecting all output to a file or /dev/null.
How do I set the timezone for a cron job?
You can set the CRON_TZ variable at the top of your crontab. For example, CRON_TZ=America/New_York. This is supported by most modern cron implementations (Vixie cron, cronie).
Can I run a cron job every second?
No, cron’s minimum resolution is one minute. To run a job more frequently, you need to use a different tool like systemd timers or a loop in a background script.
Why does my cron job run twice?
This can happen if you have the job defined in both the user crontab and a system crontab (like /etc/cron.d). Also, if you have multiple cron daemons running (e.g., both cron and anacron), they might both execute the job. Check all cron sources and remove duplicates.
Related
Method: the standard formula for this calculation, rounded as each result states. See how the calculators work or report an error.
More cards in this drawer
- Campus Tech Innovation Hubs: What They Are
- Poco C51 Airtel Prepaid Locked Variant India?
- Jenkins vs GitHub Actions: Which CI/CD Fits Your Team?
- Turn Off Backup Encryption in iTunes?
- Shared VPS Hosting: Is It Better?
- Disk Defrag Pro: What It Does and Whether You Need It