See also the GitHub SSH Key Guide.
Generate your key:
ssh-keygen -t rsa -b 4096 -C "<your email address>"
You can leave the password field blank, but I recommend setting one (you can save it in your OS Keychain anyway).
This will generate two files. The public key is at
~/.ssh/id_rsa.pub. This is
what you share with other people. You should never give anyone else your private
key, which is
These are a new type of key that is shorter but harder to crack that the older
rsa format. Older machine might not understand them though, so you might want to
rsa key as a backup.
Copying these keys is much nicer though, so worth using them where possible.
ssh-keygen -t ed25519 -C "<your email address>"
Your public key will look like this, don't worry, it's still secure enough.
ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIDsiCLI9WWTrSd4MDUpSM35f44HPKYaV96e8WGyjgDzQ email@example.com
Add your key to the ssh keychain
ssh-add with the path to the private key you created, then enter your password.
Add your public key to GitHub
Copy the public key to your clipboard, and then paste it into any site
cat ~/.ssh/id_rsa.pub | pbcopy open https://github.com/settings/keys
cat ~/.ssh/id_rsa.pub | xclip -selection clipboard xdg-open https://github.com/settings/keys
Now paste in the key that the previous command copied to your keyboard.
Repeat for any other site that needs your ssh keys (like Gitlab, GitHub Enterprise, or Bitbucket).
Put your public key on remote machines
If you want to ssh into machines, it's much easier to authenticate via key rather than via password. To set up your account on that machine for remote access do:
# ssh-copy-id takes the same arguments as ssh, including `-i ~/.ssh/other_key` # in case you chose a different name. # <machine> can be a hostname (foo.bar.com) or an IP address. ssh-copy-id <remoteuser>@<machine>
This just appends your
id_rsa.pub to the
~/.ssh/authorized_keys file on the
remote machine. You can paste it in manually if you want.
If you run
ssh <remoteuser>@<machine>, you should now connect without having
to type your password (if
<remoteuser> equals the output of
uname, then you
can omit the
If it doesn't work:
Make sure permissions are set directly on both local and remote machines. Try running the following on both machines:
# Only you should be able to write to your home directory. chmod go-w ~ # No-one else should be able to write to anything in ~/.ssh. chmod -R go-w ~/.ssh # No-one else should be able to read your private keys. chmod go-r ~/.ssh/* # Optionally allow others to see your public key and config: chmod go+r ~/.ssh/*.pub ~/.ssh/config
If you get a password prompt, try manually specifying the path to the private
ssh -i ~/.ssh/id_rsa <remoteuser>@<machine>. Make sure you're using
the right remote username (and that you can
If you don't get a password prompt you probably can't access the machine.
Setting up an ssh config
So now you can be lazy and not type your password. But machine names are long and annoying, and often you have a different username, or a different private key, and typing it all is a drag.
Say you have a group of machines you frequently ssh into called
foo2-bar.xxx.com etc. You might have a different username
on those machines too. Instead of typing
ssh firstname.lastname@example.org every
time, you can just add this to your ssh config:
Host 1 2 3 4 5 6 7 8 9 # %h gets replaced with the Host string above. HostName foo%h-bar.xxx.com User remoteuser
And now you just type
ssh 2 etc.
Now you find that you keep getting pesky messages every time you connect to a new machine asking if you want to add the RSA key to the trusted list, and you have to type yes.
Or you find that some machines close the connection if you don't type anything for a couple of minutes.
Or you want to set a default key for all machines that isn't
You just add this to the beginning of your ssh config:
# Defaults for all hosts Host * # Consider getting a shiny modern key. IdentityFile ~/.ssh/id_ed25519 # Backup key for older machines (ssh tries each one). IdentityFile ~/.ssh/id_rsa # Automatically accepts the "do you accept this RSA key" prompt. StrictHostKeyChecking=no # Don't close the connection if you are idle for a while. ServerAliveInterval 120 # Use a different default user for sshing. User gib # Tells ssh to ignore the following option if ssh is too old to understand it. IgnoreUnknown AddKeysToAgent # Automatically run the ssh-add command if it's not already in the ssh keyring. AddKeysToAgent yes
These generic rules can be overwritten by more specific ones you define below.
The next level
alias s=ssh in my dotfiles.
Check out the ssh and ssh-config man pages for more useful stuff.