Git 多账户管理
当你有多个 GitHub 账号时,推送代码后可能会遇到马赛克砖不会被点亮的问题。
这是因为,在本地仓库 commit 的时候,会记录user.name
和 user.email
。
push 代码到 GitHub 后,平台会对比 user.email
和你在平台保留的邮箱地址。
邮箱一致,这就是你提交的代码,马赛克砖可以被点亮。
邮箱不一致,则不行。
所以,你可以通过简单的在平台上添加邮箱地址,保证和本地 git 设置的 user.email
一致。
但在仓库的
Insights
页中,Contributor 仍然不是你当前的 GitHub 账号,而是和邮箱对应的你另一个账号。
或者,
你可以在不同的代码仓库中使用不同的用户信息。
Git 多个用户信息配置
alias <命令名>='git config --local user.name <名字> && git config --local user.email <邮箱地址>'
把上面这段命令保存在 bash 文件中,每次执行定义的命令,就可以快速的在仓库中修改用户信息。
执行 git config --local
命令会在当前仓库的 .git/config
中保存用户信息。
确保在 commit 之前,仓库的用户信息设置正确,就可以控制仓库中 commit 的用户信息。
为了进一步区分,不仅是对不同的仓库使用不同的用户信息,还可以使用不同的远程仓库。
当你给第二个 GitHub 账号配置 SSH keys
时,可能会被拒绝,因为一个公钥只能用于一个 GitHub 账号。
创建多个密钥文件
使用 ssh-keygen -t rsa
生成密钥文件时,会要求输入文件名。我们可以通过指定不同的文件名,来生成多个密钥文件。
比如,在拥有 ~/.ssh/id_rsa
的情况下,可以再生成一个 ~/.ssh/second_id_rsa
密钥文件。
这时,我们拥有两个不同的密钥文件:
~/.ssh/id_rsa
~/.ssh/second_id_rsa
为了使用这些密钥,我们需要用 ssh-agent
注册它们。
ssh-add ~/.ssh/id_rsa
ssh-add ~/.ssh/second_id_rsa
我们可以将这两个密钥文件,用于不同的 GitHub 账号,添加到 SSH keys 中,从而实现一台主机绑定多个 GitHub 账号。
虽然我们已经有了多个密钥文件,也都分别添加到不同的 GitHub 账号中了,但你仍然会遇到问题。
在往 GitHub 推送代码的时候,系统该如何选择密钥呢?
SSH配置文件
SSH 配置文件为 ~/.ssh/config
,如果有,直接编辑它,没有则创建。
Host first.github.com
HostName github.com
User first
IdentityFile ~/.ssh/id_rsa
Host second.github.com
HostName github.com
User second
IdentityFile ~/.ssh/second_id_rsa
使用 ssh git@first.github.com
和 ssh git@second.github.com
查看是否拥有两个 GitHub 账户的访问权。
成功的话,就可以使用密钥文件访问远程仓库,推送、拉取代码。
SSH 客服端根据地址来判断使用哪个密钥文件,@后面的部分匹配 config 中的 Host 字段。
最后,为本地仓库添加远程仓库地址时,需要对地址根据上面的配置修改。
比如我有一个 git@github.com:username/Hello-World.git
的仓库,如果该 GitHub 账号使用的是 second_id_rsa
密钥,需要将地址修改为 git@second.github.com:username/Hello-World.git
@和:之间的部分为配置文件中,Host字段的值。
如果出现了 kex_exchange_identification: Connection closed by remote
报错,尝试在配置文件中添加 Port 443
,并将 HostName 字段修改为 ssh.github.com
修改全部 Commit 的用户名和邮箱
首先修改该仓库的用户名和邮箱,然后在仓库根目录执行下面脚本,运行前保证工作区和暂存区修改都已提交。
#!/bin/sh
git filter-branch --env-filter '
OLD_EMAIL="fphd_xian_lufei@fphd"
CORRECT_NAME="sy-records"
CORRECT_EMAIL="52o@qq52o.cn"
if [ "$GIT_COMMITTER_EMAIL" = "$OLD_EMAIL" ]
then
export GIT_COMMITTER_NAME="$CORRECT_NAME"
export GIT_COMMITTER_EMAIL="$CORRECT_EMAIL"
fi
if [ "$GIT_AUTHOR_EMAIL" = "$OLD_EMAIL" ]
then
export GIT_AUTHOR_NAME="$CORRECT_NAME"
export GIT_AUTHOR_EMAIL="$CORRECT_EMAIL"
fi
' --tag-name-filter cat -- --branches --tags
执行前,修改脚本中的旧邮箱和修改后的用户名和邮箱
若执行失败,使用以下命令
git filter-branch -f --index-filter 'git rm --cached --ignore-unmatch Rakefile' HEAD
References
[1] Bivil M Jacob, How to manage multiple GitHub accounts on a single machine with SSH keys
[2] 沈唁, 修改Git全部Commit提交记录的用户名Name和邮箱Email