Linux command to wait for a SSH server to be up

Solution 1:

I don't have a host that I can ssh to and control whether it's up or not, but this should work:

while ! ssh <ip>
do
    echo "Trying again..."
done

Or a shell script that is more explicit:

#!/bin/sh

ssh $1
while test $? -gt 0
do
   sleep 5 # highly recommended - if it's in your local network, it can try an awful lot pretty quick...
   echo "Trying again..."
   ssh $1
done

Save it as (say) waitforssh.sh and then call it with sh waitforssh.sh 192.168.2.38

Solution 2:

Something simple like this does the job, waiting 5 seconds between attempts and discarding STDERR

until ssh <host> 2> /dev/null
  do
    sleep 5
  done

Solution 3:

The ssh command can be given a command to perform on the remote machine as the last paramater. So call ssh $MACHINE echo in a loop. On success it returns 0 in $?, on failure 255. You must of course use paswordless authentication with certificates.

Solution 4:

Well, I'm not sure what you mean by to be up, but what about:

$ ping host.com | grep --line-buffered "bytes from" | head -1 && ssh host.com

First command ping | ... | head -1 waits for server to sent single ping reply and exists. Then ssh comes into play. Be aware that grep can buffer output, so this is what --line-buffered is for.

You can wrap this command with bash function to use it exactly the way you've described.

$ waitfor() { ping $1 | grep --line-buffered "bytes from" | head -1 }
$ waitfor server.com && ssh server.com

Solution 5:

function hurryup () { 
    until ssh -o ConnectTimeout=2 "$1"@"$2"
        do sleep 1
    done
}
hurryup root "10.10.0.3"

-o ConnectTimeout=2 is a slightly hacky way of getting around not responding to network packets, reporting ssh: connect to host 10.10.0.3 port 22: Operation timed out until it's responsive.

Then, when the host responding to network packets, the 1 second sleep with happen in-between ssh: connect to host 10.10.0.3 port 22: Connection refused as we wait for ssh to come up.