为什么我的 cronjob 不执行我的 shell 脚本?

为什么我的 cronjob 不执行我的 shell 脚本?

我有一个 crontab,每天晚上都会创建数据库转储:

20 3 * * * /path/to/dailydump.sh

dailydump.sh包含:

#!/bin/sh

DATENAME=`date +%Y%m%d`

BASENAME="/path/to/dumps/db_${DATENAME}.sql"

/usr/bin/mysqldump -hhost -uusername -ppassword databasename > ${BASENAME}

权限是:

-rwx---r-x 1 ... dailydump.sh
drwxr-xrwx 2 ... dumps

为什么我的 cronjob 不起作用?

我在没有 root 访问权限的共享服务器上。没有登录/var/log/cron/var/log/syslog/var/mail/<user_name>或中没有邮件(事实上,和/var/spool/mail/<user_name>中根本没有任何内容),不邮寄任何错误消息,也不保存任何日志文件。什么也不返回。 (看/var/mail//var/spool/[email protected]1 2 * * * /path/to/your/command &>/path/to/mycommand.logps -ef | grep cron | grep -v grep?https://serverfault.com/a/449652

整个设置工作正常,直到我将所有文件移至新域并必须设置新的 crontab。 (是的,我更新了所有路径和数据库登录信息。我也检查了多次。)我在同一台计算机上使用相同的托管提供商,因此环境没有改变。

任何帮助将不胜感激。


“解决方案”

好吧,这是最奇怪的。我的提供商的帮助中心说,如果 cronjob 执行的脚本位于受密码保护的目录中,我需要-auth=user:password -source在脚本的路径之前添加。所以我添加了这一点(通过正确的身份验证):

20 3 * * * -auth=user:password -source /path/to/dailydump.sh

结果是通过电子邮件向我发送了一条错误消息(如此MAILTO=有效),告诉我/bin/sh: -=: invalid option并列出可用的选项。帮助中心的例子实际上并没有给出物理路径(/path/to/file),而是一个URL(http://...),所以我再次删除authsource保存了crontab,并且现在该死的 cronjob 运行了!“crontab 看起来和以前一模一样,一个字符接着一个字符,但现在它运行了,代码没有明显的变化。

我不知道问题是什么,但插入错误的代码并再次删除它就成功了。 o_O 看起来好像 cronjob 实际上做过一直运行(因为当它不运行时,它显然会抛出错误),只是它什么也没做!非常神秘。如果有人能向我解释这一点(以可重现的方式),我将提供 200 的赏金并奖励它(在必要的两天等待后)。

另外,@chaos 给了我另一个解决方案,完全避免了 shell 脚本并让 cron 直接转储数据库(请参阅下面对他的答案的评论):

20 3 * * * /usr/bin/mysqldump -hhost -uusername -ppassword 数据库名 > /path/to/dumps/db_$(date +\%Y\%m\%d).sql

只是不要忘记转义百分号,否则脚本会发现“意外的 EOF”。

感谢大家的帮助。我又学到了很多东西(虽然不是这里出了什么问题)。

答案1

为了确保cron守护进程正在运行并遵守crontab,您可以进行一个小测试。crontab使用如下条目编辑您的:

* * * * * /bin/date >>/tmp/test

一分钟后检查文件 /tmp/test.txt如果没有文件,则守护进程很可能没有运行。如果是这种情况,我会联系提供商的支持人员。

编辑:

要确定 cron 实例中的环境,您需要:

* * * * * /usr/bin/id >>/tmp/test
* * * * * /usr/bin/env >>/tmp/test

现在查看文件的内容。

答案2

  1. 直接执行脚本并检查是否有效。
  2. 当脚本在 crontab 下运行时,某些 shell 环境变量可能不可用,具体取决于您设置脚本的方式。

尝试修改脚本来测试环境变量是否是问题所在:

sh --login -c "/usr/bin/mysqldump -hhost -uusername -ppassword databasename > ${BASENAME} >  /path/to/LogFile.txt 2>&1"

相关内容