cron 任务不执行怎么排查修复?
cron 不跑的排查顺序:crond 服务在不在 → cron 日志看有没有触发 → 时间格式与全角字符 → 环境变量/PATH 差异 → 脚本权限与 shebang。本文给出逐步排查法。
排查六步,命中率从高到低:①cron 服务在跑吗(systemctl status cron);②看日志确认触发没(grep CRON /var/log/syslog);③手动跑一遍命令(排除脚本本身问题);④检查 PATH 与环境变量差异(cron 环境极简);⑤查时间格式与不可见字符;⑥看脚本权限与解释器。
① cron 服务状态
systemctl status cron # Debian/Ubuntu;RHEL 系是 crond
sudo systemctl start cron && sudo systemctl enable cron
② 看 cron 日志确认触发
grep CRON /var/log/syslog # Debian/Ubuntu
grep CROND /var/log/cron # RHEL/CentOS
journalctl -u cron --since today
- 日志里有执行记录但没看到效果 → 任务跑了但失败,去④
- 日志里根本没有 → 没触发,去⑤查格式
③ 手动跑一遍
把任务命令原样在终端执行。能跑≠cron 里能跑(环境不同),但不能跑=cron 里肯定不能跑。
④ 环境差异(最高频根因)
cron 的环境变量极简:没有你的 PATH、没有 .bashrc 里的 alias/export。
# 在 crontab 顶部显式设 PATH
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
任务里:命令用绝对路径(/usr/bin/python3 而不是 python3),脚本内同理。
⑤ 格式与隐藏字符
- 五段时间是否合法(
crontab -l复核) - 从文档复制的全角空格/星号:
crontab -l | cat -A现形 - 行尾换行、
%未转义(cron 里 % 表示换行,写\%)
⑥ 权限与解释器
ls -l /app/jobs/job.sh # 有执行位吗(x)
head -1 /app/jobs/job.sh # shebang 正确吗(#!/bin/bash)
输出要接住
*/10 * * * * /app/jobs/job.sh >> /var/log/job.log 2>&1
没重定向的输出默认走邮件,没装 MTA 就丢了——错误永远看不见。
观测云对照
cron 监控的平台化解法。 任务日志统一采集到观测云后,配监控器做"预期时间窗无成功日志即告警"+错误关键字告警,cron 失效从"几天后有人发现"变成"当周期就通知"。
常见问题(FAQ)
Q:手动能跑 cron 里不行,九成是什么原因?
A:环境变量。在任务开头加一行 * * * * * env > /tmp/cron-env.txt,对比终端里的 env 输出找差异。
Q:容器里的 cron 不跑?
A:容器里 cron 可能没前台运行或根本没装;详见本系列容器 cron 篇。K8s 用 CronJob。
Q:任务跑了一半被杀了?
A:查内存(OOM Killer,dmesg 可见)与执行时长(下个周期叠加),长任务加锁防重入(flock)。