Set up SSH for your GitHub accounts
Categories: Git Shell Tutorial
November 17, 2021
Introduction
Few weeks ago when I needed to work on something that I stored in another github account, I came across the issue of managing multiple github accounts. After some digging I notice that many articles are only giving instructions, but hardly any explanations. So here I intend to provide the most up-to-date information, and explain “why” so you understand the purpose of each step. This series will answer the following questions:
- How to set up multiple github accounts in one computer?
- Some terms mentioned in this series of articles: SSH, SSH-agent, SSH-Identiy, … What are these and why do we need to use them?
- How to generate SSH keys?
- How to set up global account? How to switch when you want to use another one?
- I want to set a default account for one path that applies to all sub-directories. How do I do that?
- I want to set up account individually for each project/directory. How do I do that?
- My github repo is private. How to make sure I can interact with that repo?
Let’s jump right in. As the first article of this series, I’ll explain the steps to set up SSH with different github accounts first, and explain what SSH is. I’ll put the nuances associated with these setups in the later posts.
In the following examples, I’ll assume we work with the following two accounts:
- personal github: gh-personal; personal@abc.com –> let’s assume you want your personal account to be the global setting, and only use office account for certain directories.
- office github: gh-office; office@abc.com
Note that git account and github account are two different things. You can link them with email address, but not the user name.
Step 1: Generate new SSH keys
There are different encryption algorithms you can use to generate SSH keys. GitHub Docs recommend using ed25519 for highest security, although a lot of the articles on this topic still use rsa 4096. At the moment Github still supports RSA keys that used SHA-2 signature algorithm, but DSA key will not be supported after March 2022.
SSH keys are usually stored in home directory, under .ssh/
.
In mac, go to terminal, then type the following to go to .ssh/
folder:
cd ~/.ssh
Once you are in /.ssh
folder, you can type in ls
to view all the files in that folder. If you don’t see a file called ssh.config
, you probably haven’t configured any SSH keys yet. So let’s create it by typing in the following command, and associated it with your personal email:
ssh-keygen -t ed25519 -C "personal@abc.com" -f "github-personal-key"
Note here the -f ...
part is to name the key, which is optional, but recommended if you have more than one account. Now, system will prompt you to type in a password. This password is not your github account password, it is a password to protect the key.
Now let’s do the same for your office account:
ssh-keygen -t ed25519 -C "office@abc.com" -f "github-office-key"
To check if you now have two sets of keys, us the “list all” command ls -al
to show all files in that folder. Note that SSH-keys are generated in pairs. So you should see the keys with the names that you gave, as well as the suffix indicating whether it is a public key (with .pub
as suffix) or private key (no suffix) returned in terminal like this:
Step 2: Add key to SSH-agent
This step is optional. SSH-agent manages your passphrases, so adding SSH keys (private key) to SSH-agent saves you the hussle of having to re-enter passphrase every time you use SSH key.
Still in the ~/.ssh
directory, let’s start SSH-agent:
eval "$(ssh-agent -s)"
First, check if your SSH-agent already have any private key added:
ssh-add -L
If it says “The agent has no identities”, that means no private key is added to ssh agent yet. If there’s something prompt, meaning there are existing identities. We can remove them:
ssh-add -D
Then add your newly generated private keys to SSH-agent. Note that here the “-K” is to add passphrase to Keychain (for Mac users). If you do not wish to add it to Keychain, just skip the “-K” part.
ssh-add -K github-personal-key
When you add key to SSH-agent, you will be prompted to enter passphrase. Do the same thing for another account. If successful, terminal will return “Identity added: github-public-key ( personal@abc.com)”.
If you have multiple github accounts, and want to add all the keys to SSH-agent in one go, use ssh-add
. For demonstration purpose, let’s only add the personal account key for now.
Now if we call ssh-add -L
again, we should see both keys, with the coresponding email in the end. That means the keys are now added to SSH Agent.
Step 3: Modify SSH config
In this step, we will finally add the keys to config file to specify what keys to look for when using different hosts. If there’s no config
file in your ~/.ssh
folder, we can create one by typing in command touch config
. If you want to create a config file and enter the edit mode at the same time, use nano config
.
Then, put the following in your config file:
# This first part is for git to authenticate yor personal github account
Host github-personal # or whatever name you want to use to call your personal github account. It does NOT need to be the same as your github handle. Although some articles recommend the "github.com-{user-handle}" format
HostName github.com # this is the address of the host that you want to connect. in this case, it's github.com
UseKeychain yes # only for macOS users. If you want to keep the passphrase in Keychain, add this line. Otherwise don't include this line
User git # because you are allowing git to authenticate github
IdentityFile ~/.ssh/github-personal-key # this tells SSH-agent which key it should use to authenticate the specified host, so it NEEDS to be the same key you created for your personal github account
IdentitiesOnly yes # this is optional. It is recommended when you have many different accounts and keys, as SSH-agent iterates over all the keys and try with each one. Specifying identity saves the searching process
# leave a blank line so SSH-agent knows the following section is for a different account, and add your 2nd account here:
Host github-office
UseKeychain yes
HostName github.com
User git
IdentityFile ~/.ssh/github-office-key
IdentitiesOnly yes
Step 4: Add public key to GitHub
To build a connection between your local git accounts and remote GitHub accounts via SSH, you will need to give the public key to GitHub.
GitHub Docs explained this step very clearly, so just follow that along.
After adding your public key to your GitHub account, you want to test the connection. But first, authenticate this action. Note that in
GitHub Docs, only the git@github.com
is authenticated, which will be only for your global account. Because we are dealing with multiple accounts, we need to authenticate each account separately.
Still in ~/.ssh
folder, use the following command:
ssh -T github-account-personal # this should be the same as the Host alias that you just put in ssh config file
If the connection is succesfully authenticated, terminal will tell you (rather excited): “Hi gh-personal (your personal github handle)! You’ve succesfully authenticated, but GitHub does not provide shell access.”. Do the same for your office account.
Step 5: Test connection
Clone from a public repo
Here we can explore a few scenarios The first scenario is probably the most common one, clone from a public repo. When a repo is public, everyone can clone it.
First, create a directory where you want to store the cloned repo. Assume it’s under ~/test
. Navigate to that directory, and let’s clone a GitHub’s public repo
Spoon-Knife. On the repo page, you’ll see the green “Code” button on the upper right. Under “SSH”, copy the address.
In the ~/test
directory, type in the following command:
git clone git@github.com:octocat/Spoon-Knife.git
Notice here the actual command is only git clone
, and the address following would be the url you just copied. You should have no problem cloning the repo, and you’ll see a new folder called “Spoon-Knife” under your ~/test
directory.
We can do a bit of digging. Navigate to the Spoon-Knife
folder, in terminal, type in the following command:
nano .git/config
This is to go to the folder .git
and open the file config
. .git
is a system file so usually it is hidden. You will see something like this:
Look! The same address you just used to clone the repo is under [remote "origin"]
. Make a note of that as we’ll see something different next. Let’s return to ~/test
directory, and delete this “Spoon-Knife” folder:
rm -r Spoon-Knife
Now let’s clone this repo again. Only this time, we’ll specify which key we want to use to connect with the host. We can try the personal key. Remember in Step 4 we specified configuration for each github account, and the host alias for personal github account is github-personal
, which is associated with the key github-personal-key
, which is then associated with personal email address “
personal@abc.com”. To use this account to clone, type the following in terminal:
git clone git@github-personal:octocat/Spoon-Knife.git
note that the only difference from last attempt is what’s in between the at sign “@” and semicolon “:”. This part is the Host alias, and now we replaced it with our personal host. The repo is successfully cloned, but with a minor difference. Just like what we did in last attempt, let’s open up the config file and take a look again nano Spoon-Knife/.git/config
. You’ll notice that under section [remote "origin"]
, the url is different.
Clone from a private repo
When clone from a private repo, you need to make sure to use the right host alias, which will use the correct private key to authenticate the connection. For instance, you created a private repo called “privateRepo-personal” in your personal github account, when clone, the url will look like this:
git clone git@github-personal:gh-personal/privateRepo-personal
Note here the naming for the url follows:
git@<your-host-alias-for-github-account>:<your-github-username>/<your-repo-name>
If you put “github-office” as the host alias, you won’t be able to clone, as it is not the right connection (the private key the host uses does not match the public key you give to your personal github account).
Having the right host alias is important, because when you need to push, make sure the host alias is authenticated and has the right to write (the host alias will refer to the private key to build the connection, and if the corresponding public key is given to the repo’s GitHub account, the connection can be successfully authenticated, meaning you will be able to make commits to that repo.
In the next post, I’ll explain how to set up git account, specify default git account for a specific directory, and what can you change in git config file.