2

I have a crontab that creates a dump of my database every night:

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

dailydump.sh contains:

#!/bin/sh

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

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

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

Permissions are:

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

Why does my cronjob not work?

I'm on a shared server without root access. There are no logs in /var/log/cron or /var/log/syslog. There is not mail in /var/mail/<user_name> or /var/spool/mail/<user_name> (in fact there is nothing at all in /var/mail/ and /var/spool/), MAILTO=my@email.com does not mail any error messages, and 1 2 * * * /path/to/your/command &>/path/to/mycommand.log does not save any log file. ps -ef | grep cron | grep -v grep? returns nothing. (See https://serverfault.com/a/449652)

The whole setup worked fine until I moved all files to a new domain and had to setup a new crontab. (Yes, I updated all paths and the database login information. I checked it multiple times, too.) I'm with the same hosting provider on the same machine, so the environment has not changed.

Any help would be greatly appreciated.


"Solution"

Okay, this is most strange. The help center of my provider says that if the script to be executed by a cronjob rests inside a password protected directory, I need to add -auth=user:password -source before the path to the script. So I added that (with the proper authentication):

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

The result was that an error message was emailed to me (so MAILTO= works), telling me /bin/sh: -=: invalid option and listing the available options. The example in the help center did not actually give a physical path (/path/to/file), but an URL (http://...), so I deleted auth and source again and saved the crontab, and now the f%§#ing cronjob runs!! 'The crontab looks exactly like it did before, char for char, but now it runs, with no apparent changes to the code.

I have no idea what the problem was, but inserting wrong code and deleting it again did the trick. o_O It appears as if the cronjob actually did run all the time (because when it doesn't, it obviously throws an error), only that it did nothing! Very mysterious. If anyone can explain that to me (in a reproducible manner), I'll offer a bounty of 200 and award it (after the necessary wait of two days).

Also, @chaos gave me another solution, completely avoiding the shell script and letting cron dump the database directly (see the comments to his answer below):

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

Just don't forget to escape the percent signs, or the script will find an "unexpected EOF".

Thank you to everyone for your help. I learned a lot again (although not what was wrong here).

  • If ps -ef | grep cron | grep -v grep is not returning anything, most probably crond is not running. – Sree Jan 7 '15 at 11:42
  • @Sree Crond is running. See my comment to the answer by "chaos" below. – user36571 Jan 7 '15 at 11:59
  • Strange. I replicated this cron on my test server (Centos 7) on a small database I have and it worked just fine. – Sree Jan 7 '15 at 12:20
  • What distro/release? Is SElinux active (and if so file type ok)? Is script ownership ok with crontab owner? – tonioc Jan 7 '15 at 12:21
  • How do I check distro/release and wether SElinux is active? – user36571 Jan 7 '15 at 12:23
0

To make sure the cron daemon is running and honouring the crontab, you could make a small test. Edit your crontab with an entry like this:

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

After a minute check the file /tmp/test. If there is no file, the daemon is most probably not running. If that's the case I would get in contact with the support of the provider.

Edit:

To determine the environment in the cron instance you that:

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

Now see the contents of the file.

  • The file is created. So the cron daemon is running. – user36571 Jan 7 '15 at 11:58
  • @what then there is something with your script. See my edit^^ – chaos Jan 7 '15 at 12:10
  • Here is the file (with private data edited): SHELL=/bin/sh PATH=/usr/bin:/bin PWD=/path/to/my/webspace [edited] SHLVL=1 HOME=/kunden/path/to/my/webspace [edited] LOGNAME=myusername [edited] _=/usr/bin/env uid=1060230(myusername[edited]) gid=600(ftpusers) groups=600(ftpusers) – user36571 Jan 7 '15 at 12:16
  • @what I assume your user for the ssh access is also myusername and has the same uid (check with the id command). You can also try the cronjob without a separate script like this: 20 3 * * * /usr/bin/mysqldump -hhost -uusername -ppassword databasename > /path/to/dumps/db_$(date +%Y%m%d).sql >/tmp/test 2>&1 and see if it works – chaos Jan 7 '15 at 12:23
  • 1
    @what I wrote it wrong sorry, I meant: 20 3 * * * /usr/bin/mysqldump -hhost -uusername -ppassword databasename > /path/to/dumps/db_$(date +%Y%m%d).sql 2>/tmp/test. the errors should be written in /tmp/test now. – chaos Jan 7 '15 at 14:40
0
  1. Execute the script directly and check if it works.
  2. Some of shell environment variables may not be available when the script is running under crontab depending on how you setup the script.

Try modifying the script to test if environment variables is the issue:

sh --login -c "/usr/bin/mysqldump -hhost -uusername -ppassword databasename > ${BASENAME} >  /path/to/LogFile.txt 2>&1"
  • Executing the script directly with sh dailydump.sh creates a database dump in the specified folder. So the script is okay. – user36571 Jan 7 '15 at 12:23

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy