626

I have a private key protected with a password to access a server via SSH.

I have 2 linux (ubuntu 10.04) machines and the behavior of ssh-add command is different in both of them.

In one machine, once I use "ssh-add .ssh/identity" and entered my password, the key was added permanently, i.e., every time I shutdown the computer and login again, the key is already added.

In the other one, I have to add the key every time I login.

As far as I remember, I did the same thing on both. The only difference is that the key was created on the one that is added permanently.

Does anyone know how to add it permanently to the other machine as well?

Randomize
  • 8,651
  • 18
  • 78
  • 133
duduklein
  • 10,014
  • 11
  • 44
  • 55
  • 1
    the agent should be temporary only; but it is possible you have the ssh-add command somewhere in ~/.bashrc or so on one of the both machines – mirek Oct 25 '18 at 11:24
  • This command worked for me ssh-add --apple-use-keychain ~/.ssh/id_rsa – Vansuita Jr. Dec 19 '22 at 12:41
  • That's what worked for Ubuntu 22.04.2. No password needed after reboots. `cp key.pub ~/.ssh cp key ~/.ssh chmod 600 ~/.ssh/key.pub chmod 600 ~/.ssh/key` – oginski May 17 '23 at 09:13

13 Answers13

903

A solution would be to force the key files to be kept permanently, by adding them in your ~/.ssh/config file:

IdentityFile ~/.ssh/gitHubKey
IdentityFile ~/.ssh/id_rsa_buhlServer

If you do not have a 'config' file in the ~/.ssh directory, then you should create one. It does not need root rights, so simply:

nano ~/.ssh/config

...and enter the lines above as per your requirements.

For this to work the file needs to have chmod 600. You can use the command chmod 600 ~/.ssh/config.

If you want all users on the computer to use the key put these lines into /etc/ssh/ssh_config and the key in a folder accessible to all.

Additionally if you want to set the key specific to one host, you can do the following in your ~/.ssh/config :

Host github.com
    User git
    IdentityFile ~/.ssh/githubKey

This has the advantage when you have many identities that a server doesn't reject you because you tried the wrong identities first. Only the specific identity will be tried.

daminetreg
  • 9,724
  • 1
  • 23
  • 15
  • 103
    Permissions on the config file should be 600. ```chmod 600 config``` – generalopinion May 01 '14 at 05:39
  • 11
    I have to put in my password for every push, fetch, or clone with this, how do I avoid that? – Asaf Jul 10 '14 at 09:33
  • 9
    Use instead `ssh-add ~/.ssh/gitHubKey`, it will remember your key passphrase. The solution I proposed was to set it permanently across reboots. – daminetreg Jul 10 '14 at 14:35
  • 46
    This answer is so good that ssh-add shouldn't exist. Who wants to have a command that "temporarily" fixes a problem and breaks unexpectedly when you can just edit a config file permanently. – RussellStewart Aug 18 '14 at 18:55
  • 2
    The problem is with this kind of config, if you don't do it in .ssh/config for a specific Host, you'll get all key tried against all server each time. – daminetreg Aug 19 '14 at 05:42
  • 6
    This solution is not using the ssh-agent. - Is there a difference? Yeah, you can't forward they identity via agent-forwarding. – Robert Siemer Nov 06 '14 at 19:08
  • @daminetreg How will it know which key to send to which server? For example, if I have key1<>server1 and key2<>server2, and both are set in ~/.ssh/config.. will it try both keys when connecting? If yes, isn't it a security issue? – MZHm Jul 26 '16 at 11:00
  • As mentioned in the reply, if you use the second way which is host specific the key won't be tried on other hosts than the one specified with HostName. But with the first solution proposed the key will be tried on each host. But it's not an issue as the key is used to encrypt a random challenge message from the server, if the server is able to decrypt it with the public key previously uploaded, then it will let you log in. So that an attacker could make a plain-text attack on your key, you should log-in **alot** to other servers so that they might begin inducing your key. – daminetreg Aug 08 '16 at 14:06
  • 2
    You can clone with @github.com if you put this in your config file: `Host github.com` – timblack1 Dec 22 '17 at 04:41
  • this worked on mac os sierra too – user1735921 Oct 29 '18 at 07:27
  • 1
    If the config file change starts "Host github.com", then you don't need the "HostName" line, and you no longer need to clone using just "github", you can use the regular clone url including "github,com". – Jonathan Hartley May 30 '19 at 16:44
  • Thanks @JonathanHartley , did it always work or is it an improvement of modern ssh versions ? – daminetreg Jun 04 '19 at 06:03
  • Hi. I don't know. – Jonathan Hartley Jun 04 '19 at 12:44
  • Test your connection with `ssh -T git@github.com` – UdaraWanasinghe Aug 25 '21 at 07:44
  • certainly one of the best answers on the whole site! – Fattie Jun 09 '22 at 13:48
  • what is the `~/.ssh/config` for? – Charlie Parker Jun 13 '22 at 18:31
  • @CharlieParker what do you mean ? `~/.ssh/config` is the user-specific SSH client config file. ~ is the home directory of the user and ssh on windows should also look in the user directory for a config as in $HOME/.ssh/config – daminetreg Jun 13 '22 at 22:07
  • Is it me or does this not actually answer the question? The question is how to permanently ssh-add, which would load the key in the agent, which means the key could also be forwarded. With this solution, at least on my computer, the key only works locally. Been running in circles because of this. – SFG Jun 23 '22 at 09:34
171

I solved that problem on macOS 10.10 by the -K flag in the ssh-add command:

ssh-add -K ~/.ssh/your_private_key

For macOS 10.12 and later you need to additionally edit your ssh config as described here: https://github.com/jirsbek/SSH-keys-in-macOS-Sierra-keychain

2023 Update

On newer versions on macOS, you have to use the --apple-use-keychain flag instead of -K, since -K is deprecated:

ssh-add --apple-use-keychain ~/.ssh/your_private_key
Roj
  • 995
  • 1
  • 8
  • 22
totas
  • 10,288
  • 6
  • 35
  • 32
130

This didn't answer the same issue for me under Mac OS X Lion. I ended up adding:

ssh-add ~/.ssh/id_rsa &>/dev/null

To my .zshrc (but .profile would be fine too), which seems to have fixed it.

(As suggested here: http://geek.michaelgrace.org/2011/09/permanently-add-ssh-key-ssh-add/ )

Aaron
  • 3,726
  • 2
  • 26
  • 23
  • 9
    This is I think better than the solution I proposed, because ssh-add uses an authentication agent which can remember the passphrase of a protected private key, so that you don't need to type it each time you try to authenticate. Another advantage of the solution you propose is that if you have alot of key, the ssh client won't propose keys irrelevant for the server you try to connect to, indeed it will provide only the keys which are for this server, and won't lead to the server refusing the connection because of MaxAuthTries being reached, while trying all the keys listed in ssh/config. – daminetreg Aug 23 '12 at 23:04
  • 1
    Thanks @daminetreg. My particular problem was needing to access gitosis on a development machine without transferring my private key to it. This solution (along with adding `ForwardAgent yes` to my `.ssh/config`) solved that issue fantastically. As it turns out, it could just be `ssh-add &>/dev/null` as the default behavior of `ssh-add` appears to be to add the keys it finds in your `.ssh` folder. – Aaron Aug 24 '12 at 13:43
  • 1
    My understanding is that there is a -K switch in Mac OS: http://stackoverflow.com/questions/1909651/svnssh-not-having-to-do-ssh-add-every-time-mac-os – Nicu Tofan Jun 12 '14 at 07:34
  • 3
    @TNick `-K` adds keys to OS X's keychain, which OS X GUIs use to authenticate to foreign servers. The poster in that Q is connecting through an SSH Tunnel, but is still just connecting to a remote server. **A**-[SSH Tunnel]->B The case I'm in is I am on a remote server but want authentication to be against credentials on my home system. A <-[Auth]-**B**-[Connect]->C So `-K` doesn't actually help, but is a great solution for the other Q. – Aaron Jun 12 '14 at 16:04
  • what is the equivalent command for linux or ubuntu? I get `unknown option -- K` (I admit I'm not sure why I even need to do this...) – Charlie Parker Jun 13 '22 at 18:04
58

Just add the keychain, as referenced in Ubuntu Quick Tips https://help.ubuntu.com/community/QuickTips

What

Instead of constantly starting up ssh-agent and ssh-add, it is possible to use keychain to manage your ssh keys. To install keychain, you can just click here, or use Synaptic to do the job or apt-get from the command line.

Command line

Another way to install the file is to open the terminal (Application->Accessories->Terminal) and type:

sudo apt-get install keychain

Edit File

You then should add the following lines to your ${HOME}/.bashrc or /etc/bash.bashrc:

keychain id_rsa id_dsa
. ~/.keychain/`uname -n`-sh
Christian Saiki
  • 1,568
  • 15
  • 22
  • 1
    What exactly does the second command do, out of curiosity? this just opens the permissions to the current user? – Vincent Buscarello Oct 24 '18 at 17:03
  • 2
    This `.` is an alias for `source` – Brad Solomon Jan 24 '19 at 23:08
  • Is the steps enough? Why the file ~/.keychain/`uname -n`-sh exists ? – Victor Choy Jun 05 '21 at 07:16
  • 2
    what's `id_dsa` ? I've searched this page and only seen this mentioned in this answer and [another](https://stackoverflow.com/a/35176183/227926) but not in the [original question](https://stackoverflow.com/questions/3466626/how-to-permanently-add-a-private-key-with-ssh-add-on-ubuntu). Is this just another key like `id_rsa` because 2 keys are being setup? – therobyouknow Dec 16 '21 at 15:08
  • When using this method, on opening a first terminal I'm asked for my passphrase. – therobyouknow Dec 16 '21 at 15:44
  • 3
    I am curious if keychain saves the ssh key passphrase and how does it do that. Where are these passphrases saved? – Sudhir Singh Khanger Feb 06 '22 at 03:53
  • what is the equivalent command for linux or ubuntu? I get `unknown option -- K` (I admit I'm not sure why I even need to do this...) – Charlie Parker Jun 13 '22 at 18:04
  • In case anyone is wondering, replace id_rsa with the name of your private key file. And remove the second id_rsa. – Amarghosh Apr 28 '23 at 11:04
22

I had the same issue on Ubuntu 16.04: some keys were added permanently, for others I had to execute ssh-add on every session. I found out that the keys which were added permanently had both private and public key located in ~/.ssh and the keys which were forgotten on every session had only private keys in ~/.ssh dir. So solution is simple: you should copy both private and public key to ~/.ssh before executing ssh-add.

P.S.: As far as I understand from Gnome wiki my method works thanks to gnome-keyring tool which is part of the Gnome Desktop Environment. Therefore my method should probably work only if you use Gnome or Gnome-based DE.

NShiny
  • 1,046
  • 1
  • 10
  • 19
  • 8
    Underrated answer. This solved my problem without needing additional scripts or packages after searching for two hours. – etagenklo Jan 16 '19 at 09:38
  • Flarkin fabulous! Great detective work. I don't think I would have figured this out. – nicorellius Sep 20 '19 at 20:10
  • 1
    For me this was the solution too! You do not need any other software or installations or configuration. Just put both keys in. – Andreas Dec 28 '20 at 15:40
  • Although this might work I would suggest that putting the public and private key in the same place is a very bad idea - it's like leaving the keys in the car – Oly Dungey Dec 14 '21 at 17:07
  • 1
    This worked for me. @OliverDungey I would agree and disagree. At the end of the day unless you are storing the private key off the computer (say a flash drive) since it is in your directory another sudo user / root could access the file no matter where it is with the find command. If you are the only one on the system and have a strong password I don't see this as a risk. – Charles Ludlow Dec 27 '21 at 09:00
  • This worked for me on Ubuntu 20.04 and 22.04. GREAT – Sasquatch Oct 31 '22 at 17:57
20

I tried @Aaron's solution and it didn't quite work for me, because it would re-add my keys every time I opened a new tab in my terminal. So I modified it a bit(note that most of my keys are also password-protected so I can't just send the output to /dev/null):

added_keys=`ssh-add -l`

if [ ! $(echo $added_keys | grep -o -e my_key) ]; then
    ssh-add "$HOME/.ssh/my_key"
fi

What this does is that it checks the output of ssh-add -l(which lists all keys that have been added) for a specific key and if it doesn't find it, then it adds it with ssh-add.

Now the first time I open my terminal I'm asked for the passwords for my private keys and I'm not asked again until I reboot(or logout - I haven't checked) my computer.

Since I have a bunch of keys I store the output of ssh-add -l in a variable to improve performance(at least I guess it improves performance :) )

PS: I'm on linux and this code went to my ~/.bashrc file - if you are on Mac OS X, then I assume you should add it to .zshrc or .profile

EDIT: As pointed out by @Aaron in the comments, the .zshrc file is used from the zsh shell - so if you're not using that(if you're not sure, then most likely, you're using bash instead), this code should go to your .bashrc file.

Nikola Ivanov Nikolov
  • 5,022
  • 1
  • 26
  • 27
  • 3
    `.zshrc` is for the `zsh` shell, which I use instead of `bash`. If you're using `bash` on Mac OS X (the default), it would be `.bashrc` there as well. – Aaron May 28 '14 at 19:28
  • 1
    After `ssh-add -l` return code `echo $?` can be used to decide whether to add key or not. Im my linux machine with bash, the `ssh-add -l` won't output the key filename. Return code always works. – Bharat G Nov 17 '15 at 03:00
14

In my case the solution was:

Permissions on the config file should be 600. chmod 600 config

As mentioned in the comments above by generalopinion

No need to touch the config file contents.

erezmta
  • 157
  • 1
  • 3
6

I run Ubuntu using two id_rsa key's. (one personal one for work). ssh-add would remember one key (personal one) and forget the company one every time.

Checking out the difference between the two I saw my personal key had 400 rights while the company one had 600 rights. (had u+w). Removing the user write right from the company key (u-w or set to 400) fixed my problem. ssh-add now remembers both keys.

Fholst
  • 304
  • 3
  • 6
4

On Ubuntu 14.04 (maybe earlier, maybe still) you don't even need the console:

  • start seahorse or launch that thing you find searching for "key"
  • create an SSH key there (or import one)
    • no need to leave the passphrase empty
    • it is offered to you to even push the public key to a server (or more)
  • you will end up with an ssh-agent running and this key loaded, but locked
  • using ssh will pickup the identity (i.e. key) through the agent
  • on first use during the session, the passphrase will be checked
    • and you have the option to automatically unlock the key on login
    • this means the login auth will be used to wrap the passphrase of the key
  • note: if you want to forward your identity (i.e. agent-forwarding) invoke your ssh with -A or make that the default
    • otherwise you can't authenticate with that key on a machine you login to later to a third machine
Robert Siemer
  • 32,405
  • 11
  • 84
  • 94
4

Adding the following lines in "~/.bashrc" solved the issue for me. I'm using Ubuntu 14.04 desktop.

eval `gnome-keyring-daemon --start`
USERNAME="reynold"
export SSH_AUTH_SOCK="$(ls /run/user/$(id -u $USERNAME)/keyring*/ssh|head -1)"
export SSH_AGENT_PID="$(pgrep gnome-keyring)"
reynoldpj
  • 79
  • 6
4

This worked for me.

ssh-agent /bin/sh
ssh-add /path/to/your/key
Jaseem Abbas
  • 5,028
  • 6
  • 48
  • 73
4

For those that use Fish shell you can use the following function then call it in ~/.config/fish/config.fish or in a separate configuration file in ~/.config/fish/conf.d/loadsshkeys.fish. It will load all keys that start with id_rsa into the ssh-agent.

# Load all ssh keys that start with "id_rsa"
function loadsshkeys
  set added_keys (ssh-add -l)
   for key in (find ~/.ssh/ -not -name "*.pub" -a -iname "id_rsa*")
    if test ! (echo $added_keys | grep -o -e $key)
      ssh-add "$key"
    end
  end
end

# Call the function to run it.
loadsshkeys

If you want to have the ssh-agent auto started when you open a terminal you can use danhper/fish-ssh-agent to do this.

frederickjh
  • 1,739
  • 1
  • 11
  • 10
3

very simple ^_^ two steps

1.yum install keychain

2.add code below to .bash_profile

/usr/bin/keychain $HOME/.ssh/id_dsa
source $HOME/.keychain/$HOSTNAME-sh
LawrenceLi
  • 407
  • 5
  • 9