关注领取运维自学路线资料 | 进百人交流群
你在日常使用Linux系统中的Crontab定时任务时,是否遇到过Crontab定时执行和手动执行Shell脚本的结果不一致问题?
你可能会说手动执行Shell脚本(如:bash test.sh)成功了,创建Crontab定时任务执行肯定也可以成功的啊!!
没错一般情况下是这样的,还有很大一部分情况是有问题的。今天,就来认识一下Crontab定时执行和手动执行Shell脚本有啥区别?

手动执行输出$PATH变量和 Crontab 定时执行输出$PATH变量的值是不一样的。如图:

/etc/profile、~/.bash_profile、~/.bashrc等配置文件,包含了完整的环境变量(如PATH、JAVA_HOME、PYTHONPATH等),所有命令(如python、mysql、docker)都能找到对应的执行路径。PATH 通常只有 /usr/bin:/bin,不会加载用户的 bash 配置文件。如果脚本中使用了非系统默认路径的命令(非系统自带命令需单独安装的命令,比如/usr/local/bin/python3),手动执行能找到,但 crontab 会提示 “命令未找到”。处理方法:
/usr/local/bin/python3 代替 python3,用 /usr/bin/mysql 代替 mysql。命令绝对路径,可通过which命令获取。$PATH变量,可以先手动执行echo $PATH得到完整变量值。如图:
手动执行:脚本的工作目录是你执行脚本时所在的目录(比如你在 /home/yourname/scripts 下执行 ./test.sh,工作目录就是这个路径)。
crontab 执行:默认工作目录是执行用户的家目录(比如 root 的家目录是 /root,普通用户是 /home/yourname)。如果脚本中使用相对路径(比如 ./data.txt),手动执行能找到文件,但 crontab 会在错误的目录下查找,导致 “文件不存在”。
处理方法:
在脚本开头切换到脚本所在的工作目录,如:
#!/bin/bash# 切换到脚本所在目录(解决相对路径问题)cd $(dirname $0) || exit 1# 此时./data.txt就会指向脚本目录下的data.txtcat ./data.txt手动执行:脚本以当前登录用户(比如 root、yourname)的权限运行,继承了该用户的所有权限(如访问 /home/yourname 下的文件、读写特定目录)。
crontab 执行:
.ssh 密钥)。处理方法:
执行crontab -u root -l命令检查哪个用户创建了 crontab 定时任务。知道用户后,便于我们查看权限问题。

手动执行:脚本的输出(stdout)、错误(stderr)会直接显示在终端上,输入(stdin)也能从终端获取。
crontab 执行:默认没有终端,stdout/stderr 如果不重定向,会被邮件发送给用户(通常未配置邮件,导致输出丢失);如果脚本需要交互输入(比如密码),crontab 执行会直接卡住失败。
处理方法:
在 crontab 中重定向脚本的输出和错误到日志文件,方便排查问题,示例 crontab 配置:
# 每分钟执行脚本,输出和错误都写入日志* * * * * /home/yourname/scripts/test.sh >> /home/yourname/scripts/test.log 2>&1手动执行:使用系统当前的时区(比如 CST)。
crontab:部分系统中 crontab 的时区可能与系统时区不一致(比如 UTC),导致定时任务执行时间偏离预期。
关注领取运维自学路线资料 | 进百人交流群

个人博客:博客介绍
进百人交流群(推荐vx群聊):运维交流/商务合作,集合

