In the world of software development, managing multiple GitHub accounts from a single machine is a common challenge, especially for developers who need to juggle between personal and professional projects. This guide provides a step-by-step process to help you configure multiple GitHub accounts on one computer, ensuring that you can commit to different repositories under different identities seamlessly.
Step 1: Generate SSH Keys
The first step in setting up multiple GitHub accounts is to generate SSH keys for each account. SSH keys are used to authenticate your identity when interacting with GitHub repositories securely. To generate an SSH key, follow these steps:
- Open your terminal.
- Run the following command to generate a new SSH key:
ssh-keygen -t rsa -b 4096 -C "[email protected]" -f ~/.ssh/id_work
- Repeat the process for your personal account:
ssh-keygen -t rsa -b 4096 -C "[email protected]" -f ~/.ssh/id_personal
Step 2: Add SSH Keys to GitHub Accounts
Next, add each SSH key to the corresponding GitHub account.
- Copy the public key for your primary account:
cat ~/.ssh/id_work.pub | pbcopy
- Log into your primary GitHub account, go to Settings -> SSH and GPG keys -> New SSH key, paste your key, and save it.
Here is the GitHub documentation on adding a new SSH key.
- Repeat for your secondary account using id_rsa_secondary.pub.
Step 3: Create SSH Config File
- Create a new SSH config file or edit the existing one:
vim ~/.ssh/config
- Add the following configuration:
# work account
Host account1.github.com
HostName github.com
User git
IdentityFile ~/.ssh/id_work
IdentitiesOnly yes
# personal account
Host account2.github.com
HostName github.com
User git
IdentityFile ~/.ssh/id_personal
IdentitiesOnly yes
This configuration aliases github.com to different hostnames for each account, using different SSH keys.
Step 4: Update Git Configurations
Using includeIf, you can specify different Git configurations for each account based on the directory. I recommend creating a different .gitconfig file for each account and including it conditionally based on the repository path.
I store my work repositories in ~/source/work
and personal repositories in ~/source/personal
. Here's how you can set up conditional includes:
- Create or update the global .gitconfig file
~/.gitconfig
:
[includeIf "gitdir:~/source/work/"]
path = ~/.account1.gitconfig
[includeIf "gitdir:~/source/personal/"]
path = ~/.account2.gitconfig
You can read more about the includeIf directive and gitdir glob patterns in the Git documentation.
- Create separate .gitconfig files for each account:
vim ~/.account1.gitconfig
[user]
name = Saatvik Arya
email = [email protected]
vim ~/.account2.gitconfig
[user]
name = Saatvik Arya
email = [email protected]
Step 5: Update Remote URLs
Finally, once you have organized your existing repositories into the appropriate directories, update the remote URLs to use the SSH aliases you defined in the SSH config file.
I have created this bash script to update the remote URLs for all repositories in a directory. You can customize it based on your directory structure and remote hostnames.
Update the STORES
array with the paths to your work and personal repositories, the REMOTES
array with the corresponding remote hostnames, and the CONFIG_FILE
variable with the path to your SSH config file.
update-remotes.sh
:
#!/bin/bash
# Set the directory path and SSH config file
STORES=("/Users/sarya/source/work" "/Users/sarya/source/personal")
REMOTES=("account1.github.com" "account2.github.com")
CONFIG_FILE=~/.ssh/config
# for each store
for i in "${!STORES[@]}"; do
# get the store path
STORE=${STORES[$i]}
# get the remote host
REMOTE_HOST=${REMOTES[$i]}
# Loop through each folder in the directory
for FOLDER in "$STORE"/*; do
# echo "Updating remote URL for $FOLDER"
cd "$FOLDER"
# check if the folder is a git repository
if [ ! -d ".git" ]; then
echo "Skipping $FOLDER"
continue
fi
# set of updated remotes for the repository
UPDATED_REMOTES=()
# Get the remote URLs
while read -r line; do
# Extract the remote name and URL
REMOTE_NAME=$(echo $line | awk '{print $1}')
REMOTE_URL=$(echo $line | awk '{print $2}')
# Check if the remote URL is not remote host and not already updated
if [[ $REMOTE_URL != *"$REMOTE_HOST"* ]] && [[ ! " ${UPDATED_REMOTES[@]} " =~ " ${REMOTE_NAME} " ]]; then
# update remote by replacing github.com with $REMOTE_HOST
NEW_REMOTE_URL=$(echo $REMOTE_URL | sed "s/github.com/$REMOTE_HOST/g")
# Update the remote URL
git remote set-url $REMOTE_NAME $NEW_REMOTE_URL
echo "Updated remote URL for $REMOTE_NAME to $NEW_REMOTE_URL"
# Add the remote to the updated remotes
UPDATED_REMOTES+=($REMOTE_NAME)
fi
done < <(git remote -v)
done
done
Step 6: Verify Configuration
To verify that your setup is working correctly, clone a repository from each account and make a commit to ensure that the correct identity is used.
You can also use the following commands to check the remote URLs and the user configuration for each repository:
# Check remote URLs
git remote -v
# Check user configuration
git config --show-origin --get user.email
Conclusion
The previous script can be used to update remote URLs for all repositories in a directory. For new repositories, you can specify the remote URL when cloning the repository using the SSH alias defined in the SSH config file.
Examples of using new remotes when cloning a repository:
git clone [email protected]:work/project.git
git clone [email protected]:aryasaatvik/blog.git
By following these steps, you can set up and manage multiple GitHub accounts on a single machine effectively. This configuration allows you to work on personal and professional projects seamlessly, ensuring that you commit to different repositories under different identities without any conflicts.
I hope this guide helps you streamline your workflow and manage your GitHub accounts more efficiently. Happy coding!