git 入门教程之协同开发

前面咱们已经介绍过远程仓库的相关概念,不过那时并无深刻探讨,只是讲解了如何建立远程仓库以及推送最新工做成果到远程仓库,实际上远程仓库对于团队协同开发很重要,不只仅是团队协同开发的基础,也是代码备份的保障手段,如今咱们先简单回忆下相关概念,以便为接下来的协同开发作好铺垫!html

远程仓库和远程分支

远程仓库

远程仓库其实并不复杂,实际上只是本地电脑上的本地仓库在另外一台远程电脑的备份而已.git

相对本地仓库来讲远程电脑上的版本库天然就是远程仓库,远程仓库使得咱们的版本库更加安全,毕竟远程电脑可不是通常的电脑,出错的几率比咱们平时工做所使用的电脑几率要小得多,这样一来即便不当心丢失了本地仓库的所有数据,只要远程仓库没有丢失,那咱们就能够经过远程仓库从新取回最新数据!github

还有一点,远程仓库让代码社交化,由于你们有了一致途径来访问远程仓库,团队也好或者陌生人也罢,只有你愿意,他们就能够获取远程仓库的最新代码并参与开发,这也是 github 的一大亮点!安全

远程分支

回顾好远程仓库的概念后,咱们再来说一下本地仓库的远程分支是什么意思?app

当前你正在工做的电脑上存储的是本地仓库,若是没有远程仓库的支持,只能一我的鼓捣,别人没法共享你的工做成果,如今加入了团队开发流程,天然再也不一我的独自开发,须要和团队其余人协同开发,共享开发成果.fetch

因此本地仓库必然保存着远程仓库的基本信息,只有区分好本身的工做成果公共成果,才能不乱套,又能作到信息及时共享.网站

实际上,在项目初期刚刚拷贝远程仓库(git clone)时,git 已经默认在本地仓库建立一个远程分支(origin/master),本地修改提交首先都是在本地仓库完成的,好比 git add,git commit 等命令,若是须要发布你的工做成果,那么就须要使用 git push origin <branch> 命令推送到远程仓库,这里的 origin 指的就是远程仓库名称(由于最初你们都是先从远程仓库克隆下来的,因此远程仓库存储的项目至关于原始项目,故而叫origin).spa

git clone 命令帮助本地仓库的 master 分支和远程仓库的 master 分支创建了关联,通常称远程仓库名称为 origin.code

git-clone.png

查看远程仓库信息 : git remotegit remote -v

# 查看远程仓库名称
$ git remote
origin

# 查看远程仓库详情 : 拉取和推送连接
$ git remote -v
origin  git@github.com:snowdreams1006/git-demo.git (fetch)
origin  git@github.com:snowdreams1006/git-demo.git (push)
$

本地分支推送到远程仓库 : git push origin <branch>

本地仓库和远程仓库的分支理论上应该一一对应,本地仓库的主干分支叫作 master ,而远程仓库也有相应的分支叫作 master ,这种映射关系是使用 git clone 命令时默认生成的,也是推荐的作法.htm

通常来讲,本地仓库的分支推送到远程仓库指的就是推送到远程仓库同名的分支上,例如 git push origin master 意思是: 推将本地仓库的 master 分支推送到远程仓库的 master分支,固然你也能够推送其余分支到相应的远程分支上.

按照以前约定的分支管理策略来讲,master 分支用于生产环境部署,dev 分支用于收集开发成果,feature 分支用于开发具体功能分支,既然如此,那这些本地分支哪些须要同步推送到远程仓库就比较清晰了!

  • 推送本地 master 分支到远程仓库的 master 分支 : git push origin master
  • 推送本地 dev 分支到元层仓库的 dev 分支 : git push origin dev
# 查看当前分支 : `master` 主分支
$ git branch
  dev
* master
  snow

# 推送本地 `master` 分支到远程仓库 `origin` 上相应的 `master` 分支 
$ git push origin master
Counting objects: 15, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (15/15), done.
Writing objects: 100% (15/15), 1.31 KiB | 1.31 MiB/s, done.
Total 15 (delta 9), reused 0 (delta 0)
remote: Resolving deltas: 100% (9/9), completed with 3 local objects.
To github.com:snowdreams1006/git-demo.git
   e60c8ad..dcce09c  master -> master
$

git-branch-remote-github.png

正常来讲,本地仓库的 master 分支应该领先远程仓库 origin 上的 master 分支若干个版本.

git-branch-remote-commit.png

一旦咱们已经将本地分支上的工做成果推送到远程仓库上相应分支时,本地仓库和远程仓库这时候就保持一致了.

$ git status
On branch master
Your branch is up to date with 'origin/master'.

nothing to commit, working tree clean
$

git-branch-remote-master.png

远程仓库下载到本地分支 : git fetch

远程仓库的操做能够简单概括为两部分: 上传和下载.

本地仓库推送到远程仓库是上传,而远程仓库拉取到本地仓库就是下载.

团队多人协做开发时,你们都会按期或不按期往 masterdev 等分支上推送各自的更改,相应的咱们就须要下载别人的最新工做成果.

如今模拟其余伙伴正在往 master 分支上推送更改,最好在另外一个电脑另外一个帐户,固然模拟的话也能够是同一个电脑下其余目录,或者最简单的方式,直接登陆 github 更改 master 分支上某个文件内容,简单起见,咱们采用最后一种方式.

其余伙伴已往远程仓库上的 master 分支提交了新的版本: 建立 git-remote.txt 文件

git-branch-remote-new-commit.png

如今咱们想要下载其余人的最新工做成果,接下来让咱们看看本地仓库的 master 还能和远程仓库的 master 分支保持一致吗?

git-branch-remote-fetch.png

# 下载远程仓库的 `master` 分支
$ git fetch origin master
remote: Enumerating objects: 4, done.
remote: Counting objects: 100% (4/4), done.
remote: Compressing objects: 100% (2/2), done.
remote: Total 3 (delta 0), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (3/3), done.
From github.com:snowdreams1006/git-demo
 * branch            master     -> FETCH_HEAD
   dcce09c..10942ff  master     -> origin/master
$

git-branch-remote-fetch-master.png

执行 git fetch 命令后,远程仓库上的最新提交记录已经下载到本地仓库,同时更新了本地仓库的远程分支origin/master ,值得注意的是本地仓库的 master 分支并无更新!

那你可能会有疑问了,我想要的结果是下载其余人的最新工做成果,怎么我本地仓库的 master 分支并无更新呢?

# 查看工做区
$ ls
LICENSE     README.md   test.txt

# 查看版本库状态
$ git status
On branch master
Your branch is behind 'origin/master' by 1 commit, and can be fast-forwarded.
  (use "git pull" to update your local branch)

nothing to commit, working tree clean
$

既然 git fetch 并无更新本地仓库的 master 分支,那它到底作了哪些工做呢?

git fetch 会作的事情

实际上, git fetch 完成了仅有的可是很重要的两步操做:

  • 从远程仓库下载本地仓库中缺失的提交记录
  • 更新本地仓库的远程分支(好比origin/master)

经过上述两步操做完成的效果是: 将本地仓库中的远程分支更新成了远程仓库相应分支最新的状态.

远程分支其实是反映了远程仓库在你最后一次与它通讯时的状态,而git fetch 就是你与远程仓库通讯的方式了!

git fetch 不会作的事情

git fetch 并不会改变你本地仓库的状态,因此也就不会更新你的 master分支,天然也不会修改你磁盘上的文件.

理解这一点很重要,由于许多开发人员误觉得执行了 git fetch 之后,他们本地仓库就与远程仓库同步了.

实际上它可能已经将进行这一操做所需的全部数据都下载了下来,可是并无修改你本地的文件.

既然本地仓库的远程分支已更新,那么想要更新本地仓库的 master 分支该如何作呢?很简单,能够 git merge 啊!

远程仓库更新到本地分支 : git pull

其实经过 git fetch 命令咱们已经下载了远程仓库的最新版本,只不过尚未合并到本地仓库而已,如何合并分支相信你们已经轻车熟路了,有不少方法:

  • git merge origin/master
  • git rebase origin/master
  • git cherry-pick origin/master

实际上,先抓取更新(git fetch)再合并(git merge)这个流程很经常使用,所以 git 是有专门的命令来完成这两步操做的,这就是拉取更新git pull --- 恰好与推送更新 git push 相反!

# 拉取最新版本
$ git pull
Updating dcce09c..10942ff
Fast-forward
 git-remote.txt | 1 +
 1 file changed, 1 insertion(+)
 create mode 100644 git-remote.txt

# 查看版本库状态
$ git status
On branch master
Your branch is up to date with 'origin/master'.

nothing to commit, working tree clean

# 查看工做区内容: 文件已更新
$ ls
LICENSE     README.md   git-remote.txt  test.txt
$

git-branch-remote-pull.gif

团队协做

掌握了远程仓库和远程分支的相关概念后,如今开始真正模拟团队协做开发了,为了简单起见,仍然以直接操做 github 上的 master 分支为例说明如何协同开发.

(1). 其余人已往远程仓库推送2个版本

git-branch-remote-teamworks.png

(2). 你正在本地仓库提交1个版本

$ echo "learn teamwork" >> test.txt
$ git commit -am "learn teamwork"
[master f971647] learn teamwork
 1 file changed, 1 insertion(+)
$

git-branch-remote-teamwork-local-commit.png

(3). 你推送到远程仓库前先拉取最新版本

# 拉取最新版本,并尝试合并
$ git pull
remote: Enumerating objects: 8, done.
remote: Counting objects: 100% (8/8), done.
remote: Compressing objects: 100% (5/5), done.
remote: Total 6 (delta 0), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (6/6), done.
From github.com:snowdreams1006/git-demo
   10942ff..612e08a  master     -> origin/master
Merge made by the 'recursive' strategy.
 git-remote.txt | 2 ++
 1 file changed, 2 insertions(+)

# 查看版本库状态
$ git status
On branch master
Your branch is ahead of 'origin/master' by 2 commits.
  (use "git push" to publish your local commits)

nothing to commit, working tree clean

# 查看其余人工做成果
$ cat git-remote.txt
git remote
git clone
git commit -am "fake second teamwork"

# 查看本身即将推送的工做成果
$ cat test.txt
add test.txt
see https://snowdreams1006.github.io/git/usage/remote-repository.html
learn git branch
see https://snowdreams1006.github.io/git/usage/branch-overview.html
git commit c1
git commit c2 and c3
git checkout -b dev
fast forward not recommend
Happy coding
learn git stash
learn git rebase
learn teamwork
$

git-branch-remote-teamwork-pull.png

(4). 你将本地仓库更改内容推送到远程仓库

# 推送到远程仓库
$ git push origin master
Counting objects: 5, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (5/5), done.
Writing objects: 100% (5/5), 564 bytes | 564.00 KiB/s, done.
Total 5 (delta 3), reused 0 (delta 0)
remote: Resolving deltas: 100% (3/3), completed with 3 local objects.
To github.com:snowdreams1006/git-demo.git
   612e08a..8fe5aba  master -> master
$

如今前往 github 网站确认咱们已经推送成功,咱们的工做成果和其余人的工做成果同时存在于远程仓库中,这样就完成了一次团队协同开发的案例.

git-branch-remote-teamwork-myself.png

git-branch-remote-teamwork-push.png

如今简单回顾一下整个协同开发流程:

  1. 其余人先于咱们提交2个版本
  2. 咱们本地提交1个版本
  3. 本地版本推送前拉取远程仓库
  4. 本地仓库推送到远程仓库

git-branch-remote-teamwork.gif

小结

  • 查看远程仓库信息: git remote -v
  • 本地仓库推送到远程仓库: git push origin <branch>
  • 远程仓库抓取到本地仓库: git fetch
  • 远程仓库拉取到本地仓库: git pull 至关于 git fetchgit merge
  • 本地建立和远程仓库一致的分支: git checkout -b <branch> origin/<branch>,本地和远程分支名称最好一直,好比本地 master 和 远程 origin/master,本地 dev 和远程 origin/dev
  • 本地分支和远程分支创建关联: git branch --set-upstream <branch> origin/<branch> ,足够任性的话,本地 dev 能够关联远程 remote-dev 等,不过建议名称最好一致.
  • 团队协同开发时,不只平时要按期拉取(git pull),推送到远程仓库前更应先拉取(git pull)再推送(git push),如出现冲突,解决冲突后再推送.
相关文章
相关标签/搜索