0

On my local machine, I have two keys:

~/.ssh/id_rsa
~/.ssh/old/id_rsa/

On the remote machine (me@example.com) I have only ~/.ssh/old/id_rsa, already in authorized_keys. Is there a single line I can run to use ~/.ssh/old/id_rsa to log into the remote machine and add ~/.ssh/id_rsa to the authorized keys file?

I'm doing this from Git Bash when I attempt ssh-copy-id "me@example.com -i ~/.ssh/old/id_rsa" it seems to interpret the whole string me@example.com -i ~/.ssh/old/id_rsa as the domain name rather than the domain plus options for the SSH connection, giving this error:

/usr/bin/ssh-copy-id: ERROR: ssh: Could not resolve hostname example.com -i ~/.ssh/old/id_rsa: Name or service not known

This is an extension of Easiest way to copy ssh keys to another machine?

3 Answers3

1

This appends the key to authorized keys:

cat ~/.ssh/id_rsa.pub | ssh me@example.com -o "IdentitiesOnly=yes" -i ~/.ssh/old/id_rsa 'cat >> ~/.ssh/authorized_keys && echo "Key copied"'

I still feel there must be a better solution. But all the effort to do this passwordless feels a little silly. I have passwords on my keys now, so I'm running ssh-add ~/.ssh/old/id_rsa just to prove I don't have to type a password for the command itself.

But indeed, this command DID work for me without typing any password.

This answer borrows from another answer on IdentitiesOnly

1

Although this works, I'm not entirely sure why the -f option is needed:

ssh-copy-id -f -o IdentityFile=~/.ssh/old/id_rsa -i ~/.ssh/id_rsa me@example.com

Trying to run the same command without the -f option results in:

/usr/bin/ssh-copy-id: WARNING: All keys were skipped because they already exist on the remote system.

But this is 100% untrue, as ~/.ssh/id_rsa.pub was freshly generated, and sure enough, listing the keys stored in ~/.ssh/authorized_keys on the server before (and after) running the command only showed the key stored in ~/.ssh/old/id_rsa.pub.

Subsequently running the command including the -f option correctly results in ~/.ssh/id_rsa.pub being added to ~/.ssh/authorized_keys on the server, with no duplication of any sort.

Either I'm missing something (likely) or this is a bug, I'm not sure which one is it.

Another way:

ssh-copy-id -i ~/.ssh/id_rsa me@example.com

Or, if the old key is not loaded into the SSH agent anymore (and you can't / don't want to use password authentication to push the new key):

ssh-add ~/.ssh/old/id_rsa/ && ssh-copy-id -i ~/.ssh/id_rsa me@example.com && ssh-add -d ~/.ssh/old/id_rsa/ me@example.com

Which will load the old key into the SSH agent before attempting to push the new key, and remove the key from SSH the agent right after the new key has been pushed.

Addressing why your command didn't work:

From man ssh-copy-id:

SYNOPSIS
       ssh-copy-id  [-f]  [-n]  [-s]  [-x]  [-i  [identity_file]]  [-p   port]
                   [-o ssh_option] [-t target_path] [user@]hostname
       ssh-copy-id -h | -?

Which highlights the main issue with your command: -i and [user@]hostname are positional, i.e. you must pass -i before [user@]hostname.

Additionally your attempt:

ssh-copy-id "me@example.com -i ~/.ssh/old/id_rsa"

is quoting the destination and the identity file as a single string; this prevents them from being recognized as separate options, and me@example.com -i ~/.ssh/old/id_rsa are being interpreted as a single argument, leading to the error you experienced:

/usr/bin/ssh-copy-id: ERROR: ssh: Could not resolve hostname example.com -i ~/.ssh/old/id_rsa: Name or service not known

(not to mention the double quotes would have prevented ~ from expanding anyways).

All you need to do is to unquote what you have and switch the order of the arguments:

ssh-copy-id -i ~/.ssh/id_rsa me@example.com
kos
  • 41,268
0

If you want to replace your server's current 'authorized_keys' file with the contents of your new public key you can use SCP to copy it to your server:

use your old id_rsa to login and replace the old public key with your new one:

scp -i </path/to/old/id_rsa> </path/to/new/id_rsa.pub> you@example.com:~/.ssh/authorized_keys 

This will overwrite your current 'authorized_keys' file on your server, allowing only connections authenticated with your new key pair as the consequence.

Make sure only your user can read the 'authorized_keys' file on your server, because wrong permissions can cause trouble when trying to log in:

chown username:username ~/.ssh/authorized_keys
chmod 400 ~/.ssh/authorized_keys

Correct me if I'm wrong but that's the way I would do it.