优雅的处理多个git账户

352 阅读3分钟

本文记录的是mac系统

场景

相信大家在git的使用中肯定会遇到一个问题,就是本机维护多个git账号(主要是不同邮箱)。

假设我现在有两个账号:

第一个qq邮箱是我个人的账号,用于GitHub、Gitee

第二个是公司邮箱,用于工作

在使用方面,比如git的pull、push等常用操作,即使是多个用户,只要配置好ssh,然后在各个仓库的用户设置中,设置好就能够正常使用

包括我在内,估计很多人都是直接设置全局的git用户信息去使用的

 git config --global --unset user.email
 git config --global --unset user.name

虽然git能够正常使用,但是大家有没有发现,这个操作是设置了全局的邮箱和用户名,然后当你clone一个项目时,如果没有给这个项目配置local的用户信息,那么当你操作git的时候就会取全局的那个配置,如果全局也有没有配置,就提示你要设置

假设你全局配置的是公司邮箱,这个时候你想弄个小东西,然后在GitHub上面创建了仓库,一顿操作之后push代码,结果你会发现,提交commit的那个人,并不是你的GitHub账号。其实影响最大的案例是,你给某个很多star的开源项目提了pr,作者也合并了,心想着

image-20221113172453331

结果发现commit的人都不是你的GitHub账号😂

解决

其实这个问题很简单,上面也有提到,就是clone了项目之后,配置一下当前项目的git用户信息(local)

假设我clone了一个公司的test项目,那么我就

 cd test
 git config user.email "gauharchan@edu.cn"
 git config user.name "gauhar chan"

so easy是不是,但是每次这样是不是有点繁琐呢

优雅地解决

我们最终想要的,就是在clone项目后,执行上面的三句终端命令,所以我们可以写一个shell脚本来执行,具体代码请看注释

 # 确保脚本抛出遇到的错误
 set -e
 # 克隆项目到当前终端目标路径
 git clone $1
 # 获取到 项目名.git
 first=${1##*/}
 # 获取到项目名
 project_name=${first%*.git}
 # 进入项目路径
 cd $project_name
 # 设置local信息
 git config user.email "gauharchan@edu.cn"
 git config user.name "gauhar chan"
 ​
 echo 'local信息设置成功'
 # http://patorjk.com/software/taag/#p=display&h=3&v=3&f=Ogre&t=hongdu
 echo '
          _____                   _____                   _____                   _____                   _____                   _____          
         /\    \                 /\    \                 /\    \                 /\    \                 /\    \                 /\    \         
        /::\    \               /::\    \               /::\____\               /::\____\               /::\    \               /::\    \        
       /::::\    \             /::::\    \             /:::/    /              /:::/    /              /::::\    \             /::::\    \       
      /::::::\    \           /::::::\    \           /:::/    /              /:::/    /              /::::::\    \           /::::::\    \      
     /:::/\:::\    \         /:::/\:::\    \         /:::/    /              /:::/    /              /:::/\:::\    \         /:::/\:::\    \     
    /:::/  \:::\    \       /:::/__\:::\    \       /:::/    /              /:::/____/              /:::/__\:::\    \       /:::/__\:::\    \    
   /:::/    \:::\    \     /::::\   \:::\    \     /:::/    /              /::::\    \             /::::\   \:::\    \     /::::\   \:::\    \   
  /:::/    / \:::\    \   /::::::\   \:::\    \   /:::/    /      _____   /::::::\    \   _____   /::::::\   \:::\    \   /::::::\   \:::\    \  
 /:::/    /   \:::\ ___\ /:::/\:::\   \:::\    \ /:::/____/      /\    \ /:::/\:::\    \ /\    \ /:::/\:::\   \:::\    \ /:::/\:::\   \:::\____\ 
/:::/____/  ___\:::|    /:::/  \:::\   \:::\____|:::|    /      /::\____/:::/  \:::\    /::\____/:::/  \:::\   \:::\____/:::/  \:::\   \:::|    |
\:::\    \ /\  /:::|____\::/    \:::\  /:::/    |:::|____\     /:::/    \::/    \:::\  /:::/    \::/    \:::\  /:::/    \::/   |::::\  /:::|____|
 \:::\    /::\ \::/    / \/____/ \:::\/:::/    / \:::\    \   /:::/    / \/____/ \:::\/:::/    / \/____/ \:::\/:::/    / \/____|:::::\/:::/    / 
  \:::\   \:::\ \/____/           \::::::/    /   \:::\    \ /:::/    /           \::::::/    /           \::::::/    /        |:::::::::/    /  
   \:::\   \:::\____\              \::::/    /     \:::\    /:::/    /             \::::/    /             \::::/    /         |::|\::::/    /   
    \:::\  /:::/    /              /:::/    /       \:::\__/:::/    /              /:::/    /              /:::/    /          |::| \::/____/    
     \:::\/:::/    /              /:::/    /         \::::::::/    /              /:::/    /              /:::/    /           |::|  ~|          
      \::::::/    /              /:::/    /           \::::::/    /              /:::/    /              /:::/    /            |::|   |          
       \::::/    /              /:::/    /             \::::/    /              /:::/    /              /:::/    /             \::|   |          
        \::/____/               \::/    /               \::/____/               \::/    /               \::/    /               \:|   |          
                                 \/____/                 ~~                      \/____/                 \/____/                 \|___|          
                                                                                                                                                 
'

上面的代码是不是很简单,由于我是个shell小白,所以上面获取项目名的操作很下饭,假设我们的git地址是git@xxx/test.git

first=${1##*/}这个代码的意思是截取/的右边字符串,所以得到test.git并赋值给first这个变量

接着project_name=${first%*.git}是获取.git的左边,最终我们得到了project_name这个变量

echo是在终端输出东西,我在最后打印了一个立体字,上面的网址就是一个在线生成shell 打印立体字母的网站

配置alias

现在呢,shell文件我们写好了,那要怎么执行呢?

 sh 上面的文件路径 项目ssh克隆地址

项目ssh克隆地址对应的就是上面代码中的$1变量,shell是根据顺序来获取的,$0是文件路径

zsh在配置文件中,用户可以自定义alias去更加方便的执行命令

我把上面的文件放到了.ssh文件夹中,命名为clone.sh,这里存储了ssh公钥等等的东西,放在一起以后不怕忘记,当然你可以随意放,执行命令的时候改一改就行

所以我们目前的命令是

 sh ~/.ssh/clone.sh

打开终端,执行

 open ~/.zshrc 

此时会打开一个文件编辑器,找一行,添加下面代码并保存。alias后面的是命令名称,自己取一个

 alias htclone='sh ~/.ssh/clone.sh'

然后重新加载zsh配置

 source ~/.zshrc 

大功告成,假设我们clone一个项目'git@192.168.7.7:gauhar/test.git';htclone是配置的alias命令名称

htclone git@192.168.7.7:gauhar/test.git

对了,我配置了全局的用户是我的个人账号,所以公司的项目用htclone命令,其他就正常git clone