crontab任务不执行的首要原因是crond服务未运行,其次为语法错误、环境变量缺失、路径不正确、权限不足、日志未重定向、PAM访问限制及特殊字符未转义;需按服务状态→语法→环境→权限→日志顺序排查。

crontab 任务不执行,90% 是环境、权限或日志缺失导致的静默失败,不是脚本写错了。
crond 服务没运行,所有任务都白配
再正确的 crontab -e 配置,也敌不过 crond(RHEL/CentOS)或 cron(Ubuntu/Debian)没在跑。
- 查状态:
sudo systemctl status cron(Debian/Ubuntu)或sudo systemctl status crond(RHEL/CentOS) - 如果显示
inactive (dead),立刻启动:sudo systemctl start cron - 顺手设开机自启:
sudo systemctl enable cron - 注意:某些最小化安装系统默认不装
cron,得先sudo apt install cron或sudo yum install cronie
crontab -l 看不到任务,说明根本没写进去
用 vi 编辑时按了 :q!、Esc :q 或编辑器崩溃,都会导致 crontab -e 的修改未保存。
- 务必执行
crontab -l确认内容已生效——别信“我刚保存了” - 检查时间字段顺序:必须是
分 时 日 月 周,比如0 2 * * 1表示每周一凌晨 2 点 - 行尾不能有空格,
#后所有内容都被当注释,哪怕写在时间字段后面也会整行失效 - 用
crontab.guru粘贴表达式验证语义,避免0 0 * * 7这种周日写成 7(应为 0)的低级错误
脚本能手动跑,cron 里就失败,大概率是环境变量或路径问题
cron 默认只用 /bin/sh,PATH 极窄(通常只有 /usr/bin:/bin),不读 ~/.bashrc,不认识 ~,也不加载任何 profile。
- 在
crontab文件最开头显式声明变量:PART=/usr/local/bin:/usr/bin:/bin<br>SHELL=/bin/bash<br>HOME=/home/username
- 脚本中所有命令用绝对路径:
/usr/bin/python3而非python3;用which python3查真实路径 - 脚本第一行加
#!/bin/bash,开头加cd "$(dirname "$0")" || exit 1切工作目录,避免相对路径失效 - 测试 cron 环境:运行
env -i /bin/bash -l -c 'echo $PATH; which python3',对比你手动执行时的输出
没日志,等于蒙眼排错
cron 默认把 stdout/stderr 发邮件到 /var/spool/mail/$USER,但多数服务器没配邮件服务,结果就是输出彻底消失。
- 给每条任务加重定向:
0 3 * * * /path/to/script.sh >> /tmp/script.log 2>&1 -
2>&1必须写在>>或>之后,顺序错了就只重定向 stdout,stderr 仍丢弃 - 查系统级日志:
sudo grep CRON /var/log/syslog(Ubuntu/Debian)或sudo journalctl -u crond -n 50 --no-pager(RHEL/CentOS) - 临时加一行测试日志:
* * * * * echo "test $(date)" >> /tmp/cron-test.log 2>&1,5 秒后看文件有没有新增内容
真正难排查的,往往不是“完全不触发”,而是“触发了但中途失败”,比如 Python 脚本因 JAVA_HOME 缺失退出、curl 因证书路径不对被 kill、或 SELinux 拦截了网络调用——这些都不会报错到终端,只会在重定向日志里留一行 exit code 1。所以,加日志不是可选项,是必选项。


















