Why ssh fails from crontab but succedes when executed from a command line? Why ssh fails from crontab but succedes when executed from a command line? unix unix

Why ssh fails from crontab but succedes when executed from a command line?


keychain

solves this in a painless way. It's in the repos for Debian/Ubuntu:

sudo apt-get install keychain

and perhaps for many other distros (it looks like it originated from Gentoo).

This program will start an ssh-agent if none is running, and provide shell scripts that can be sourced and connect the current shell to this particular ssh-agent.

For bash, with a private key named id_rsa, add the following to your .profile:

keychain --nogui id_rsa

This will start an ssh-agent and add the id_rsa key on the first login after reboot. If the key is passphrase-protected, it will also ask for the passphrase. No need to use unprotected keys anymore! For subsequent logins, it will recognize the agent and not ask for a passphrase again.

Also, add the following as a last line of your .bashrc:

. ~/.keychain/$HOSTNAME-sh

This will let the shell know where to reach the SSH agent managed by keychain. Make sure that .bashrc is sourced from .profile.

However, it seems that cron jobs still don't see this. As a remedy, include the line above in the crontab, just before your actual command:

* * * * * . ~/.keychain/$HOSTNAME-sh; your-actual-command


I am guessing that normally when you ssh from your local machine to the machine running crond, your private key is loaded in ssh-agent and forwarded over the connection. So when you execute the command from the command line, it finds your private key in ssh-agent and uses it to log in to the remote machine.

When crond executes the command, it does not have access to ssh-agent, so cannot use your private key.

You will have to create a new private key for root on the machine running crond, and copy the public part of it to the appropriate authorized_keys file on the remote machine that you want crond to log in to.


Don't expose your SSH keys without passphrase. Use ssh-cron instead, which allows you to schedule tasks using SSH agents.