How to use different accounts and SSH keys on a per-git-repo basis
If you need to use more than one git account and SSH key, you’ll quickly run into the problem of per-repository configuration.
I was recently stuck having to migrate all my work repositories to a new, work-only account (thanks to a combination of auth changes and the lack of email configuration in Bitbucket).
Previously I’d used one Bitbucket account for everything, so had never had to do per-repository authentication in git. I found most tutorials skipped some detail or other, so this is the process that worked for me including the gotchas.
Create new SSH key
I didn’t want to share an SSH key across auth boundaries so I made a new one:
Remember to set a different filename, as you probably already have
id_rsa (here we’ll make it
id_rsa_user2 and pretend the first one was
id_rsa_user1 for ease of reference). Obviously set a good password too.
As it’s a new set of keys, ensure their permissions are correct:
$ chmod 600 ~/.ssh/id_rsa_user2 $ chmod 600 ~/.ssh/id_rsa_user2.pub
Finally, add the new key to your SSH agent:
$ ssh-add ~/.ssh/id_rsa_user2
Add the new public key to Bitbucket
In this case the config URL would be
https://bitbucket.org/account/user/user2/ssh-keys/. The only real trick here is being careful you put the right key into the right account.
Create SSH host aliases
You’ll need to create an alias for each key,
Host bitbucket.org-user1 HostName bitbucket.org User git IdentityFile ~/.ssh/id_rsa_user1 Host bitbucket.org-user2 HostName bitbucket.org User git IdentityFile ~/.ssh/id_rsa_user2
user2 are the Bitbucket usernames.
If config is a new file, you’ll need to set permissions:
$ chmod 600 ~/.ssh/config
Update 2017.01.28 - if you are using OSX Sierra+ and want Keychain to manage your SSH passwords, add some extra lines:
Host bitbucket.org-user1 HostName bitbucket.org User git IdentityFile ~/.ssh/id_rsa_user1 UseKeychain yes AddKeysToAgent yes Host bitbucket.org-user2 HostName bitbucket.org User git IdentityFile ~/.ssh/id_rsa_user2 UseKeychain yes AddKeysToAgent yes
Set URLs to use the aliases
For a new checkout, just clone via the alias and your remotes will be configured for you:
$ git clone origin email@example.com:foo/foo.git
For an existing checkout, update your remote URLs. You can check these with a verbose check:
$ git remote -v origin firstname.lastname@example.org:foo/foo.git (fetch) origin email@example.com:foo/foo.git (push)
To update the URL:
$ git remote set-url origin firstname.lastname@example.org:foo/foo.git
Configure user details per repo
Updating the name is optional, but you will need to set the appropriate email in each repo:
git config user.name "User One" git config user.email email@example.com
I found non-matching emails were rejected. That is, you can't claim to be using an email address attached to a different account.
What about other git hosts?
The process is the same regardless of git host, just sub in the URL as required.
All done - each repo should now work as normal, the most obvious side effect is having to add two keys when you start your SSH agent (on OSX you won't need to worry as keychain handles that for you). This process worked for me in OSX Terminal and Windows Subsystem for Linux (WSL).
A couple of gotchas have surfaced since this was originally published:
- If you use any private packages in NPM, Bower, etc you will need to add your host alias in the relevant json files. That does mean you can't check that into source unless you have your entire team use the same alias, eg.
bitbucket.org-teamname. If your whole team needs multi-key setup this is fine, but if it's just you then it's a lot of stuffing around for everyone else. So if you're just setting out to do this you may want to set your team alias as the real hostname and your personal as the aliased hostname.
- OSX Sierra changed the way it handled SSH keys, so my note about keychain handling it is no longer accurate. You'll need to update your SSH configuration to use the proprietary
AddKeysToAgent yesoptions in each alias; and you may need to explicitly add all of your SSH keys (
ssh-add -K ~/.ssh/id_rsa && ssh-add -K ~/.ssh/id_rsa_user2etc) before it will all work. I recommend a quick google for osx sierra ssh agent to get started.