How to use SSH private key to log in without entering passphrase every time on Mac OS X Lion?

I use Mac OS X Lion and login remote hosts via SSH every day. Despite the fact that I use SSH key pair for remote authentication and I don't need to motorize every host's login phrase, it is still very annoying that the terminal asks for the passphrase for accessing my SSH private key.

For security reason, I think, a passphrase for accessing SSH private key is must-needed. Is there a way that makes the terminal to ask for the phrase exactly only one time at start up, then memorize it, and automatically using my private key in later SSH sessions?

There is a script called keychain which works fine on Gentoo Linux. But I never figure it out on Mac OS X Lion. What's more, there are so many intimidating terms, such as ssh-agent, ssh-add. After reading various materials about those SSH toolkits and doing some frustrated experiments, I got more confused.

Therefore, I came to StackExchange, looking for some advice about the following questions.

  1. What are ssh-agent, ssh-add, keychain, Keychain Access.app and how they interact with each other?
  2. How can I enter the passphrase for my SSH private key once at login, and use it freely at later SSH session creation?
  3. Errr... What's wrong with Keychain Access.app? It does not store the SSH phrase like it did before.

I list what I've done here. Hopefully there are clues about the steps I missed.

Step 1. Create an SSH key pair on my Mac.

$ ssh-keygen -t rsa -C "[email protected]"
# Set a passphrase for accessing the private key.

Step 2. Copy my SSH public key to remote host. To take an example, I copy the key to localhost, Mac.

$ ssh-copy-id USER@localhost
# Enter the login password for USER at localhost, not my SSH passphrase

Step 3. Then try to connect to the remote host (localhost here), via SSH key pair authentication.

$ ssh USER@locahost
Enter passphrase for key '/Users/YOUR_ACCOUNT/.ssh/id_rsa': 
# Enter my SSH passphrase, not the login password.

Step 4. Logout from the remote host and try to connect to it again. Damn it, the terminal asks for the SSH phrase again.

A frequently asked question is that "Does ssh-agent work well on your Mac?". Frankly speaking, I have no idea what's going on these things. Here show some running results.

$ echo $SSH_AUTH_SOCK
/tmp/launch-M48niA/Listeners
$ echo $SSH_AUTH_PID
(EMPTY)
$ ssh-add -l
Could not open a connection to your authentication agent.
$ ssh-agent
SSH_AUTH_SOCK=/tmp/ssh-Z54zXukQiP/agent.26769; export SSH_AUTH_SOCK;
SSH_AGENT_PID=26770; export SSH_AGENT_PID;
echo Agent pid 26770;
$ ssh-add -l
Could not open a connection to your authentication agent.
$ echo $SSH_AUTH_SOCK
/tmp/launch-M48niA/Listeners
$ echo $SSH_AUTH_PID
(STILL EMPTY)
$ ssh-agent  # Oh no, anther ssh-agent with different PID
SSH_AUTH_SOCK=/tmp/ssh-cx0B4FUX8B/agent.26898; export SSH_AUTH_SOCK;
SSH_AGENT_PID=26899; export SSH_AGENT_PID;
echo Agent pid 26899;
$ ps -e | grep -i ssh
26769 ??         0:00.03 ssh-agent
26899 ??         0:00.02 ssh-agent

Any feedback is welcomed. Thanks!


ssh-agent is the piece that you want to get working, as it does exactly what you're asking about. The agent runs as a daemon, and when you "add" a private key to it, it remembers that key and automatically provides it to the remote sshd during the initial connection. (ssh-add is simply the command you run to manually add a private key to ssh-agent).

In OS X, as of Leopard, you shouldn't ever have to run ssh-agent or ssh-add manually. It should "just happen" when you attempt to connect to a server. Once per key, it will prompt you with a UI password dialog, which (among other things) will allow you to automatically add the key to the ssh-agent so you never get prompted again.

This is handled by having a launchd configuration that listens for connections on the $SSH_AUTH_SOCK socket, and automatically launches ssh-agent when it first needs to; after that, ssh-agent prompts you for credentials only when it needs to open a new key.

If that's not working, make sure you have the correct launchd configuration file present:

/System/Library/LaunchAgents/org.openbsd.ssh-agent.plist

If it's still not working for you for some reason, here's the "old" way of getting things running by hand:

http://timesinker.blogspot.com/2007/08/getting-ssh-agent-going-on-mac-osx.html

There is also this application, which I have stopped using since Leopard came out but basically did the same thing in previous versions of Mac OS X:

http://www.sshkeychain.org/


During the process of resolving the "problem", I've googled some related topics and write down some notes about how ssh-agent, ssh-add, keychain, KeyChain Access.app work. It finally turns out that this issue is not a problem at all, instead the issue is all about me, and so called ssh-login-without-asking-passphrase-every-time works perfectly on Mac out of box.

However, this process gains me some experiences. I write down my notes here in hope that they help someone confusing about those terms.

Two password terms:

  • passphrase refers to the required phrase when accessing your SSH private key.
  • password refers to the required phrase to log in to your Mac.

Now I can figure out what these toolkits do, that is, ssh-agent, ssh-add, keychain, Keychain Access.app on Mac.

  • ssh-agent is the critical service to enable using SSH private key without typing SSH passphrase. ssh-agent works in this way. First it stores, or cache, your SSH private key in main memory. Then at a later time in this session when your SSH private SSH key is needed for remote authentication, ssh-agent will find your private key in main memory and hand it to the remote process. The only chance you are asked to type your SSH passphrase is when your private key is added by ssh-agent initially.
  • ssh-add is part of ssh-agent collection, which helps to manage your SSH keys in ssh-agent. We use ssh-add command to list, add, remove private keys in ssh-agent's keyring. Then ssh-add communicates with ssh-agent service to fulfill the tasks.
  • keychain is script to find ssh-agent service (if not exist, start a new one) and call ssh-add to add SSH private keys. keychain has a simple and straight-forward idea, working fine on Linux where ssh-agent usually doesn't automatically start up.
  • Keychain Access.app seems to be the most complicated component. It is Mac OS X's universal token storage service. It stores various of tokens, such as passwords, certs, et al, and serves as an token agent for those apps that request the tokens. In our SSH private key case, first it grasps the request for accessing SSH private key and pops up a window to ask you to store the SSH passphrase, which is a kind of token, into Keychain Access.app's keyring. Then next time when you are to use private keys for authentication, Keychain Access.app pops up a window again, asking whether granting the privilege. After getting a big yes, keychain Access.app adds your private key into ssh-agent's storage.

Two things deserve your attention:

  1. Mac OS X Lion automatically starts a ssh-agent service at start up, listening on a socket under /tmp.
  2. Keychain Access.app stores your SSH passphrase, so it can add your private key into ssh-agent without interrupting you. Yes, no need to type your SSH phrase, but need to type your Mac account's login password for granting privilege when creating this entry for the first time.

So, in summary, SSH-login-without-asking-passphrase should work on Mac OS X out of box.


In case other solutions here don't work for people, the following worked for me.

For each and every private key in your ~/.ssh directory, make sure that the corresponding public key is also present. Make sure the public key is named exactly the same as the private key but with .pub at the end. If you already had an appropriate public key, try regenerating it.

If you need to recreate the public keys, you can do so easily:-

ssh-keygen -y -f ~/.ssh/my_key > ~/.ssh/my_key.pub

replacing my_key with whatever your key is called.

After that, MacOS remembers the key passphrase in keychain as it should.

Note - entering the passphrase and saving it the keychain is now a one time only action (not once per login session as OP wanted), but assuming login to the mac in question is password protected, then your passphrase is protected by that login password. Also, this solution makes no sense to me... a public key shouldn't be required in addition to the private key, but for some reason MacOSX requires it.

(originally from answer to a similar question on Apple Stack Exchange)


The one thing I rarely find mentioned regarding configuring the ~/.ssh folder is restricting the directory permissions.

To enable ssh to avoid asking for the password I've always had to set the user's home directory permissions to 700, and the ~/.ssh folder permissions to 700 as well.

Otherwise it continues to ask me for a password even when I have all of the keys generated and copied correctly. An error message gets generated in the authentication logs but this is invisible to the end user for the most part.