# check for authorized keys from script [SOLVED]

## Geddy Leon

How can I, using a bash script, check if a remote machine has my public key in it's authorized_keys file and print a message and exit if it doesn't.

Something like:

```

if grep "Password" in `ssh my_user@some_host.com true`

     echo "ssh keys not set up, exiting..."

     exit 1

else

     echo "log in successful, starting processing..."

     do ssh commands

     do more commands ...

     exit

fi

```

any suggestions would be great...Last edited by Geddy Leon on Sun Jan 25, 2009 6:47 pm; edited 1 time in total

----------

## timeBandit

Assuming you don't want to be prompted for passwords or passphrases: in general, you can't.

If the key is not protected by a passphrase, or you don't mind being prompted to enter the passphrase, this works:

```
result="$(ssh -oIdentityFile=/path/to/private.key user@host 'echo OK')"

if [ $? != 0 ] ; then

    echo Failed

elif [ "$result" = "OK" ] ; then

    echo Key is valid

else

    echo Denied

fi
```

Note even this is flawed: If the server is configured to allow password- and key-based authentication, it will fall back to a password prompt if the private key isn't accepted.

----------

## magic919

Take a look at Expect instead of bash scripts.  Should be able to do what you want.

----------

## Geddy Leon

Thanks for the tips.

Expect will probably work, yeah. I don't need to run an interactive session though. I just want to check whether or not I get prompted for a password. To use expect I would have to check if it's installed, emerge if not, etc... from the script.

timeBandit's script is something like I was hoping for but it still outputs "Password:" to the terminal if the public key isn't set up at the remote machine.  I was thinking the "Password:" goes to stdout or stderr or something, which can be redirected and grepped through, but apparently not. 

How does the "Password:" prompt show up on the terminal ? Does the ssh process have some other way to communicate with the terminal other than stdin, stdout, stderr ?

...

----------

## magic919

You do only need Expect on the local machine, not the remote server.

----------

## timeBandit

 *Geddy Leon wrote:*   

> I was thinking the "Password:" goes to stdout or stderr or something, which can be redirected and grepped through, but apparently not. 
> 
> How does the "Password:" prompt show up on the terminal? Does the ssh process have some other way to communicate with the terminal other than stdin, stdout, stderr?

 Yes, it opens a new file descriptor for the terminal device. No process is required to use only the standard streams to interact with the terminal, most do because it's convenient. SSH does not, specifically to prevent redirection of password/passphrase prompts. This isn't for security alone, it also keeps prompts from appearing in the redirected output of a remote command (e.g., ssh user@host "ls *.foo" >/remote-foo.lst 2>&1).

----------

## Hu

You can suppress the prompts using the BatchMode option.  Add -oBatchMode=yes to your command line.  According to man ssh_config, this disables querying for passwords/passphrases.

----------

## Geddy Leon

 *Quote:*   

> 
> 
> You can suppress the prompts using the BatchMode option. 
> 
> 

 

Excellent thanks! It also sets $? to non-zero which can be tested for.

----------

## timeBandit

 *Geddy Leon wrote:*   

>  *Quote:*   You can suppress the prompts using the BatchMode option. 
> 
>  Excellent thanks! It also sets $? to non-zero which can be tested for.

 The option disables the prompt, not the requirement. The connection will be refused if the attempt can't be authenticated by other means.

I don't see how this would help unless, again, the private key is unsecured (no passphrase). I ran a quick test of three cases you'd need to discriminate:Valid user who has an authorized, passphrase-protected key pair;Valid user with no keys, authenticated by password;Invalid user that does not exist on remote host.The first two cases fail because ssh cannot authenticate the user when prompts are suppressed. The last of course is sure to fail. In all cases, ssh exits with the same non-zero return code (255) and error message ("Permission denied (publickey,keyboard-interactive)"). This method still does not detect whether the user has an authorized key at the host.

If you think about it, this should be impossible, by design--if it's not, you have a way to probe any SSH server to identify a valid user.

Edit: Nevermind, I realized that this does work to distinguish machines that have your key from those that don't, when the key has no passphrase (which you probably wanted to avoid admitting  :Wink: ).

----------

## Geddy Leon

ok, ok, right, no passphrases...  :Wink:  BUT the script will only be run by users who are behind a firewall and employees of a company

I want to fail in all cases except when the user running the script has an account on the remote machine AND that users public key is in ~/.ssh/authorized_keys. so in my case, it works.

anyway, great tips, thanks all.

----------

