一台电脑两个github账号问题

一台电脑两个github账号问题

提交项目到github示例

这是一个从初始化一个git项目到提交到github的实例演示

# 创建一个learn-git文件夹并进入该文件夹
mkdir ~/Code/learn-git && cd ~/Code/learn-git

# 在learn-git文件夹内执行git初始化(会在learn-git文件夹下生成一个名为“.git”的隐藏文件夹)
git init

# 在learn-git文件夹下添加一个文件
echo "This is a test!" > test.txt

# 把test.txt文件添加到git暂存区
git add test.txt

# 把该文件提交到本地仓库
git commit -m "first commit"

# 添加远程仓库地址(在github创建“learn-git”项目,得到这个地址)
git remote add origin https://github.com/zhangsan/learn-git.git

# push到远程仓库(-u把origin设置为上游)
git push -u origin main

在2021年8月13日之前,在你执行git push -u origin main这句推送代码命令时,它会弹出让你输入github的账号密码,验证通过后才能上传。

然后输出以下内容(事实上这个并不会发生,原因往下看)

枚举对象中: 3, 完成.
对象计数中: 100% (3/3), 完成.
写入对象中: 100% (3/3), 227 字节 | 227.00 KiB/s, 完成.
总共 3(差异 0),复用 0(差异 0),包复用 0
To https://github.com/zhangsan/learn-git.git
* [new branch] main -> main
分支 ‘main’ 设置为跟踪来自 ‘origin’ 的远程分支 ‘main’。

但是很遗憾,即使你输入正确的账号密码,它也不会上传,而是会出现以下提示

remote: Support for password authentication was removed on August 13, 2021.

出现上述提示的原因,是因为github在2021年8月13日移除了对账号密码的支持,理由是安全性不高,所以从这一天开始,github就无法通过账号密码来认证上传代码了。

在github添加公钥

github禁止了账号密码后,只能通过公私钥对来认证了,也就是说,https协议的github仓库链接,你只能用来下载代码,如果你想上传代码,必须使用ssh协议的链接

创建公私钥对:
首先要创建一对公私钥对,我相信能研究本文的同学肯定都已经有公私钥对了,在你电脑的~/.ssh/文件夹下,应该是会有一个“id_rsa”(私钥)和“id_rsa.pub”(公钥)。

如果没有,请用以下命令创建(运行后无论提示什么,一路按回车即可)

ssh-keygen -t rsa -b 4096 -f ~/.ssh/id_rsa_4096 -C "abc123@gmail.com"

注:记得把“abc123@gmail.com”换成你的邮箱,不是必须要github登录邮箱,它只是个标记而已,不会用于验证邮箱。

以上命令最终会在你的~/.ssh/文件夹下生成两个文件: id_rsa_4096和id_rsa_4096.pub。

其中带.pub结尾的就是公钥(pub是public的意思),我们需要把公钥添加到github中,这样github就能通过公钥来与我们本地的私钥来加密传输数据了(公钥加密的数据只有对应的私钥能解,私钥签名的数据只有公钥验证数据是否被篡改)。


把公钥添加到github:
登录github后,点击右上角头像→Settings→点击左侧边栏的“SSH and GPG keys”→点击右侧的“New SSH Key”

把前面生成的公钥“id_rsa_4096.pub”中的内容复制粘贴到下边框中,如果是mac,用以下命令就可以直接复制到剪贴板了,文件都不需要打开

cat ~/.ssh/id_rsa_4096.pub | pbcopy

添加完成后,在你电脑客户端运行以下命令

ssh -T git@github.com

如果一切正常,它会输出以下内容,告诉你你已成功被认证

Hi xxx! You’ve successfully authenticated, but GitHub does not provide shell access.


关于前面的ssh命令的解释
我们知道ssh user@host是可以登录一台服务器的,比如ssh zhangsan@192.168.1.2,但为什么ssh -T git@github.com不会登录呢?因为-T

ssh有-t-T选项,这两个t都是Terminal(终端,在这里指伪终端,pseudo terminal)的意思,在命令(不止是ssh命令)中经常有一个不成文的规则,当两个选项相同,一个大写,一个小写时,一般小写表示“是”,而大写正好相反,表示“否”,所在在这里,这个大写的-T表示不分配伪终端,当我们用ssh登录Linux远程主机时,它都会让我们输入账号密码,我们输入账号密码后,就“登录”进去了,这个其实就是分配了一个“伪终端”,而我们通过ssh连接github、gitee等,其实是没有权限操作它的服务器的,所以它也不可能给我们分配终端的,所以需要用-T来指定不分配伪终端。

假如不用-T或用-t(默认就是-t),也就是你希望github服务器给你分配伪终端,它会输出如下提示,当然是不可能给你提供终端的啦,毕竟人家又不是给你用服务器

PTY allocation request failed on channel 0

通过公私钥对来上传

通过公私钥上传,必须使用ssh协议地址,而不能是https协议地址,因为公私钥上传本质上就是ssh传输,当然就得用ssh协议地址了。

在github创建一个仓库后,我们可以选择是用HTTPS还是SSH地址

从上图中可以看到,SSH地址是git@github.com开头的,其实它就是user@host,本质上就相当于github的服务器上创建了一个名为“git”的用户,然后你使用这个用户来向github服务器通过ssh协议传输数据。

现在我们可以来解决本文开头上传不了的问题。

首先要把github仓库链接改为git协议的

git remote set-url origin git@github.com:xiebruce/learn-git.git

然后再来push,就能正常push了

git push -u origin main

两个github账号问题

了解了前面的知识,现在终于来到本文的主题了,这里虽然举例了两个账号问题,但3个以上也是一样的方法,另外也不一定要是github,gitee等也是相同的原理。

我们来看看git协议的github仓库链接,在本例中,其实“xiebruce”就是github的用户名,通过这个用户名,github完全可以知道这是在上传到哪个用户下的哪个项目中

git@github.com:xiebruce/learn-git.git

所以一台电脑两个github账号的问题按道理是不存在的。但实际上,由于github不允许添加相同的公钥,所以如果你用相同的公钥去另一个账号添加公钥,它会报公钥已经添加(已存在),反正就是无法添加成功(没有显示出来)。

如果公钥没有添加成功就执行push操作,就会报以下错误

ERROR: Repository not found.
fatal: Could not read from remote repository.

Please make sure you have the correct access rights
and the repository exists.


再创建一个公私钥对:
由于github不允许两个账号添加相同的公钥,我们必须再创建一对新的公私钥对,才能把新的公钥添加到另一个github账号上

ssh-keygen -t rsa -b 4096 -f ~/.ssh/id_rsa_4096_02 -C "abc123@gmail.com"

注:记得把“abc123@gmail.com”换成你的邮箱,不是必须要github登录邮箱,它只是个标记而已,不会用于验证邮箱。

创建成功后,还是按前面说的方法把创建的公钥的内容添加到另一个github账号中。

然后就能git push了吗?当然不能!因为公私钥认证,需要私钥对应公钥,默认的私钥名称就是id_rsa,所以当你只有一个默认私钥的时候,不需要指定,ssh协议会自动读取~/.ssh/id_rsa这个私钥来与github中添加的公钥作为一对来进行数据加密传输。

但是现在不同了,现在你有两个账号,假设之前那个账号还是会自动使用~/.ssh/id_rsa私钥,那新的账号呢?它是不可能会自动使用你的新私钥的,因为你的新私钥不是默认名称,它还是会找默认名称的私钥,也就是原来的私钥,这样一来跟你在github另一个账号上添加的公钥根本就对不上,自然也就不可能传输数据了。

于是你可能会想,它默认会使用~/.ssh/id_rsa私钥,我们不能让它“不默认”吗?我们指定让它使用哪个私钥不就行了吗?对!确实是可以指定使用哪个私钥的。

由于这本质上是ssh传输,所以我们指定私钥是在ssh的配置文件中指定的,ssh的默认配置文件是~/.ssh/config

添加以下配置

# 个人github
Host personal
    HostName github.com
    PreferredAuthentications publickey
    User git
    IdentityFile ~/.ssh/id_rsa
    IdentitiesOnly yes

# 工作github
Host work
    HostName github.com
    PreferredAuthentications publickey
    User git
    IdentityFile ~/.ssh/id_rsa_4096
    IdentitiesOnly yes

如上所示,两段配置只有两个值不同,HostIdentityFile,Host指是上传的地址(对于ssh user@192.168.1.2来说,“192.168.1.2”就是Host值),只不过这个值可以用ip也可以用域名,也可以完全不是域名,总之就是一个标识,用于区分用。

我们前面的git仓库链接是这样的

git@github.com:xiebruce/learn-git.git

现在改了Host值,就要变成这样

git@personal:xiebruce/learn-git.git

当我们push数据时,“personal”会匹配上~/.ssh/config中的Host personal,匹配上就会读取它下边的配置,最终又用回真正的HostName,即“github.com”。

而work也一样,work的写成这样,那么匹配上Host work后,它也会用它下边的配置,发现没,此时它的IdentityFile指向的私钥地址就不是前面那个了,而是我们新生成的

git@work:zhangsan/learn-git.git

所以,通过这种在~/.ssh/config文件中添加配置,手动指定使用哪个私钥来配合github上添加的公钥的方法,就可以达到“同一台电脑用两个github账号”的方法。

两个github账号用户名问题

如果你按以上的方法,确实可以使用两个账号了,但是用户名却是相同的,因为它默认会使用你github配置文件(~/.gitconfig)中的用户名,注意这个用户名不是github登录用户名,而是git commit要显示是谁提交的,这个“谁”就是我说的用户名。

git commit提交用户的用户名,可以通过以下命令设置,但这样设置的是全局的

git config --global user.name 用户名
git config --global user.email 邮箱

由于全局只能有一个用户名,所以如果你希望两个github账号中的项目git commit的用户名不一样,你可以对项目进行单独设置

git config --local user.name 用户名
git config --local user.email 邮箱
打赏
订阅评论
提醒
guest

此站点使用Akismet来减少垃圾评论。了解我们如何处理您的评论数据

0 评论
内联反馈
查看所有评论
0
希望看到您的想法,请您发表评论x

扫码在手机查看
iPhone请用自带相机扫
安卓用UC/QQ浏览器扫

一台电脑两个github账号问题