团队协作Git入门指南

4,970 阅读12分钟

前言

由于九心同学之前一直担任独立开发的职位,所以对于协作开发这块儿的技能有所欠缺,对Git命令的使用还停留在独立开发上,平常用的最多的三个命令也就:

  • git clone
  • git commit
  • git push origin master

这不,在进入新的公司以后,狂补了一波Git命令,今天我们就来聊一聊工作中的常用的Git命令。 表情

在阅读下文之前,推荐一个练习Git命令的网站(强力推荐):

Learn Git BranchingAZ

以及一些学习网站:

《Git文档》 《廖雪峰的Git教程》

目录

一、基础必读

1. Git是什么?

对于这个问题,我们可以看一下官方文档:

Git is a free and open source distributed version control system designed to handle everything from small to very large projects with speed and efficiency. Git是一个免费和开源的分布式版本控制系统,致力于高效和快速的处理任何小或者大的项目。

2. Git中的几个概念

工作区、暂存区和版本库

了解Git中的工作区和版本库很重要:

  • 工作区:简单来说,我们当前电脑能够看到的目录。
  • 版本库:使用过Git都知道里面有一个隐藏的目录 .git,这便是我们所说的版本库,其中,版本库又分为暂存区和分支。git add 命令将文件从工作目录提交到暂存区,git commit 命令将文件从暂存区提交到git仓库。
Git的过程
Git的过程

文件状态

如果我们想看一下工作区和暂存区文件的状态,可以使用命令 git status,比如我最近学习的Flutter项目:

wangjiedeMacBook-Pro:flu_pro wangjie$ git status
warning: unable to access '/Users/wangjie/.config/git/attributes': Permission denied
On branch master
Changes to be committed:
  (use "git reset HEAD <file>..." to unstage)

        new file:   lib/main.dart

Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git checkout -- <file>..." to discard changes in working directory)

        modified:   lib/HelloWorld.dart

Untracked files:
  (use "git add <file>..." to include in what will be committed)

        .metadata
        //... 省略

其中:

  • Changes to be committed:暂存区的文件。
  • Changes not staged for commit:工作区的文件,还未保存到暂存区。
  • Untracked files:指那些第一次创建,还没有加入版本更新的文件。

在 Android Studio(下称AS)中,更加方便: Git文件状态 里面有很多颜色:

  • 白色:已commit,但是没有发生变化的文件。
  • 蓝色:commit之后发生了变化
  • 原谅绿:暂存区的文件。
  • 黄色:不需要进行版本控制的文件。

分支

分支是多人协作开发中必不可少的角色,因为在我们的开发过程中,至少会有两个分支:

  • 正式版本的分支:线上代码版本保存的分支,需要稳定的运行。
  • 开发主线的分支:下个版本需求的开发分支。

除了这些分支,还可能有修复Bug的分支等。

二、基础命令

1. 暂存区相关

添加进暂存区

具体命令: 添加全部文件

git add .

如果是添加某个文件

git add <文件路径>

命令解释: 将工作区的文件添加进暂存区。

IDEA或AS: 在IDEA或者AS中,在你进行Git初始化之后,当你添加新的文件时,会有这样的提示: Git Add 也可以这样,右击文件 > 选择「Git」> 选择「Add」和「Add to .gitignore」,分别对应着添加到暂存区和配置忽略文件: Git选项 加入到暂存区意味着该文件加入到版本控制中。配置到忽略文件则意味着不会加入到版本控制。

撤销工作区的变更

这种情况可能会经常出现,你修改了某个文件的很多处代码,但是却不想挨个删除,如上代码就起作用了。

命令解释 撤销工作区的代码修改。

具体命令

git checkout -- file

注意一定要加上--,不然就会变成切换分支(下面会讲)。

IDEA或者AS AS可以很方便的查看某个文件修改了哪些代码。步骤是:选择下方「Version Control」> 选择具体的文件 > 点击 diff 查看文件的更改 有哪些差别一目了然,并且你可以点击对应的按钮撤销更改的代码 撤回更改 一不小心把git diff要进行的操作给讲了...

撤销暂存区的变更

另外一种情况是改完代码以后,如果使用了 git add,将代码提交到了暂存区,之前的命令就不管用了。

命令解释 撤销暂存区的代码修改。

具体命令

git reset HEAD file

这个命令在AS或者IDEA下使用的场景不多

2. 版本库相关

Commit代码

命令解释 将暂存区的文件添加进版本库

具体命令

git commit -m <提交描述信息>

动画模型 git commit 输入git commit之后,沙盒模型中发生了什么?其实就是生成了一个新的版本记录:

IDEA或者AS 我一般针对对应的需求,新建一个Change List,具体过程如下是:

选中「Version Control」 > 选择某个 Change List > 右击弹出选择框 > 选择「New Changelist」 新建Changelist 如需 commit,选择上图「Commit」,输入 Commit Message 即可 Commit弹出框

撤销提交

常见场景是你使用了 git commit 提交了代码,但是还没提交到远程分支,随后你很快发现了这次提交会带来重大问题,于是你想撤销这次提交。

命令解释 在没有上传到远程分支时,进行版本库的撤销。

具体命令

git reset HEAD~1

HEAD 代表当前的头结点,HEAD~1 代表当前节点的前一个节点,后面解释。

动画模型 Reset版本库.gif

IDEA或者AS 在 AS 中,先打开到版本提交历史 Reset操作 比如我想回退到 first commit 的那个版本 > 选中右击 > 选择【Reset Current Branch to Here...】,之后弹出一个弹出框 Reset选项 四个选项的区别:

  • Soft:当前的文件不变(但是你可以根据git diff查到文件发生了哪些变化),暂存区的提交记录也会被保留。
  • MIxed:当前文件不变,暂存区提交记录不会被保留。
  • Hard:当前文件回退到选择的版本,任何当前的改变都不会被保存下来,慎用。
  • Keep:当你工作区或者暂存区有改变的时候,类似于处理冲突的情形,可手动选择要保存哪些内容。

查看改动

人又不是机器,忘记自己改了哪些东西也是常有的事儿。

命令介绍 比较当前工作区和上一个版本的差异

在不输入文件路径的情况下,默认比较的是当前工作区和上一个版本的区别,并且命令行会告诉你什么类的变化是什么样的。内容我就不罗列了。

IDEA或者AS 已介绍,不再赘述~

3. Branch

查看分支

具体命令

git branch

命令介绍 查看本地分支

命令结果 查看分支

IDEA或者AS 点击右下角红色部分即可展示本地分支和远程分支,并且可以切换分支。 AS查看分支

创建分支

命令介绍 创建一个分支。

具体命令

git branch <name>

必须加上分支名。

动画效果 创建分支

IDEA或者AS 跟分支查看的按钮在同一处,点击「New Branch」完成。

切换分支

命令介绍 切换分支

具体命令

git checkout <name>
git checkout -b <name>

第一个命令是切换分支,第二个命令是创建并切换分支,git checkout 也可以用来撤回工作区的修改,大家注意区分。

动画效果 切换分支 图片中不仅仅是切换分支,切换完以后,还进行了一次提交,至此,两个分支就不在同一个版本了。

IDEA或者AS 同查看分支一样 查看并切换 如果想查看当前各个分支所对应的版本,点击「Version Control」> 再点击「log」。 查看日志

合并分支

下一个版本的代码迭代完毕,准备上线,这时你就可以合并分支。

命令介绍 合并分支。

具体命令

git merge <name>

动画效果 Merge分支 可以看到,在 C2C3 的版本下面,合并生成了一个新的版本 C4master 分支直接指向了 C4

除了 git merge 外,还有一个合并分支的命令,我们看看这两者有什么区别。

具体命令

git rebase <分支名>

动画效果 Rebase分支 可以看到,当前分支 bugFix 指向的版本 C3失踪了,而在 master 分支下面生成了一个 C3',虽然看不出 C3' 是由原来的 C2C3 合并的,但新的提交记录更加线性和简洁。

git mergegit rebase 两种动画效果可以得出:

  • Merge:保留之前的提交顺序。
  • Rebase:得到的提交历史更加线性,看着更加简洁。大部分团队的选择。

IDEA或者AS 选中右下角「git:分支名」> 选中具体分支 > 选择Rebase或者Merge Rebase or Merge

三、远程命令

1. 更新代码

团队协作时每次要上传代码之前记得拉取最新代码。

命令介绍 拉取最新代码

具体命令

git pull <origin> <local分支名>

这里的 origin 是我们远程分支的别名,是可以自己定义的,通常我们使用 git remote add <origin> <远程仓库地址> 来添加。

动画效果 Pull远程仓库 可以看到,远程的代码被拉下来以后,如果你的代码已经提交过,它会先 merge 代码,之后再将当前分支切换到最新的版本。

IDEA或者AS 这是 「VCS」>「Git」>「Remotes」下远程仓库的记录: 远程仓库地址 你可以选择左下角的添加按钮手动添加。

下拉代码就更加简单了,点击右上角的按钮,第一次下拉的时候会生成一个弹窗 下拉代码 左边的 Update Type 就不多介绍,右边的 Clean working tree before update 有两个选项,第二个并不是 Git 中的,并且 IDEA 也说了以后会去除,我们就无需了解了,选择 Using Stash 就对了。

Using Stash对应着 Git 命令中的 git stash,因为合并两个分支前需要提交改动的代码,但我们当前的开发还没有完毕,不想无缘无故的进行一次提交从而脏了我们的提交记录,这时就可以使用git stash,它会先将工作区的代码暂存好,之后清空工作区的代码,合并远程分支的代码,最后再将工作区的代码恢复。

处理冲突 但凡是协作开发,在工作合理分配的情况下偶尔也会出现冲突,选用《关于Android Studio使用Git的总结》中的图片,当出现冲突时,会出现如下弹框 出现冲突 除非明确的知道使用谁的代码,一般我们会点「Merge...」,之后会出现另外一个弹框 解决冲突 从图中可以很清晰的看出,弹框分为左中有三块:

  • 左:本地代码
  • 中:合并的结果
  • 右:远程的代码

如果想选择左边的代码,点击左边「>>」按钮,不想选择点「x」按钮,确定好代码以后点击右下角的「Apply」按钮。

2. 上传代码

除了下载最新的代码,我们还需要将自己改动的代码上传。

命令介绍 上传最新的代码。

具体命令

git push <origin> <本地分支名>

动画效果 Push远程仓库 左边是本地分支,右边是远程分支。

IDEA或者AS 正常我们在 commit 代码的时候,可以选择 Commit and Push,也就是提交代码的时候附带 Push提交选择Push 如果你不想在 Commit 的时候进行 Push,也可以选择在菜单栏中的「VCS」选择单独 Push

3.远程进阶

在上面的推送命令中,默认了远程仓库的分支和当前的分支名一致,比如 git push origin master,本地分支名和远程分支的名称都为 master,那如果不一致呢?

具体命令

git push <origin> <本地分支:远程分支>

更新的命令也是如此

git push <origin> <远程分支:本地分支>

直接看可能有点抽象,我们直接看图。

动画效果 Push进阶 这次试用了相对引用,即 foo^ 指向 foo 分支指向的版本的上一个版本,所以远程仓库 master 分支也只更新到了 foo 分支指向版本的上一个版本。

进阶命令

1. 相对引用

使用 Hash 值指定版本并不总是很方便,比如你想将版本 revert 到上个版本,你得先查一下版本的 Hash 值,之后再去使用这个 Hash 值去 revert,显然这样的方式并不优雅。

上一个版本

命令介绍 指定当前版本的上一个版本。

具体命令

HEAD^
分支^
Hash值^

这里使用 HEAD、分支和 Hash 值都可以,只要能确定版本库即可。

比如上一个版本的代码代码出现 bug 了,我想在 master 分支上一个版本的基础上对代码进行修改,我可以输入 git checkout -b bugfix master^

动画效果 上一个版本 这是一个分离 HEAD 的命令,将 HEAD 分离到当前 master 分支指向版本的上一个版本。

上N个版本

命令介绍 回退到指定版本的前N个版本。

具体命令

HEAD~2
分支~n
Hash值~n

其他和上一个命令相似,不再赘述。

追加更新

你刚提交了一笔代码,突然发现了一个错误,这时你肯定不想为此再创建一个提交。

命令介绍 更新上次 commit 的代码,避免再次生成一个 commit 记录。

具体命令

git commit --amend

动画效果 更新提交 可以从动图中看到,原先的版本库 C2 消失了,取而代之的是 C2',它们两个其实是一个版本,对应的 id 是同一个。

IDEA或者AS As中的amend 选中「Amend commit」,至于「Sign-off commit」,平常基本用不着。

总结

以上的命令已经可以胜任平时的开发,而对于一些复杂的命令,使用的时候再查。如果你有一些经常使用的命令,也欢迎在评论区补充。

进入新公司已经一个月了,终于恢复到了自己的节奏,以后就可以正常输出文章啦。 攻击力+300.jpg

广告

我是九心,新晋互联网码农,如果想要进阶和了解更多的干货,欢迎关注我的公众号接收到的我的最新文章。 公众号

引用文章:

《🛠Git 常用操作总结》
《关于Android Studio使用Git的总结》
《廖雪峰的Git教程》