Git协同工作流介绍
git相关的文章和教程非常多,但是系统介绍和了解工作流的人并不多,在使用过程中用错或用偏的也不少,这里分享的是,假设你已经入门的情况下,我们如何去选择适合团队需要的工作流。
git优势
这里先唠叨git的优势,对比传统的代码管理工具,git至少有以下这些优点:
- 有温度的工具:由 Git 衍生出来的 GitHub/GitLab 可以帮你很好地管理编程工作,比如GitHub包括即时通信功能,开发者可以互相审核、评论和打分。同时还包括 wiki、fork、pull request、issue……集成了与编程相关的工作,让我们的工作可以呈现在一个工作平台上,并以此来规范整个团队的工作。
- 分布式管理:你可以离线提交代码,而不用担心网络问题。
- 合并分支管理:合并分支后也能查看整个代码的变更记录
- 分支快速切换:Git 切换分支的时候通常很快,不像其他版本管理器,比如SVN,每个分支一份拷贝。
git常用命令
跳转这里查看常用命令:常用命令
这里记录自己平时经常使用的一些命令,并不是本文的重点。另外叨叨一下,有些人喜欢在集成的IDE下通过界面方式来进行操作,比如vs code或者eclipse都有傻瓜化的集成,这里推荐使用命令行操作,我觉得有如下一些优势:
- 第一、可以和IDE解耦,不用换一个IDE就要去了解对应界面的使用方法;
- 第二、命令行的操作非常快速,当然缺点是你需要记忆一些命令,但是常用的命令真心不多;
- 第三、命令行拥有界面没有的体验,比如一个简单的git status你可以查看内部更多的详情;git stash命令,可以把当前没有完成的事先暂存一下,然后去忙别的事;git cherry-pick命令可以让你有选择地合并提交。git add -p可以让你挑选改动提交。

git工作流介绍
市面上有以下几种常见的工作流:
- 中心式协同工作流【主干开发】
- 功能分支协同工作流【特性分支】
- github协同工作流
- gitlab协同工作流
- gitflow协同工作流
中心式协同工作流
这种方式等于把git当做svn适用,很多同学估计都是这么用的。这种协同方式是所有的人都在 Master 分支上共享他们的代码。
流程

这里的流程是这样的:
- 从服务器上把代码同步下来;
- 本地编码后,再add/commit到本地仓库
- 最后再push到origin master上
这里的第三步有可能出错,因为可能别人在你之前在相同地方已经提交了代码,这时候你需要先(git pull --rebase)一下,如果发现冲突,就解决冲突然后继续合并(git rebase --continue)。到这里你是否感觉和svn越来越像,每天早上过来定时的update一下,然后再编码,上传代码之前也是这样先update一下,再做上传操作?
焦油坑
这里有几个坑需要注意:
- 代码冲突:建议每天编码之前和代码上传之前不定期、频繁的进行git pull --rebase。
- 代码干扰:随着开发团队规模的扩大,可能你pull一个不可运行的代码下来(push上去的人没有用心检查是否可以编译通过),这时候你的麻烦开始产生了,你要停下手上的活,花费可能很久的时间去把代码编译通过,于是我们经常听到很多开发人员在那边互相抱怨,怎么就不能好好检查后再上传呢,还让不让人写代码,好好学习一下svn怎么用吧……
总结:
中心式的协同显然无法满足团队规模的扩展和代码的干扰冲突,而且产品上线后,master的BUG会直接影响生产环境,也就说master其实是不稳定的,而用不稳定的主干直接和生产环境挂钩,后果可想而知。所以该流程不适用产品线迭代开发和持续更新,如果你只有1-2个开发人员那就罢了,否则一般不建议使用这种方式,接下来就要介绍如何去避免上面的这些焦油坑,也就是我们的功能分支协同工作流上场了。
功能分支协同工作流
上面的那种方式有一个问题,就是大家都在一个主干上开发程序,对于小团队或是小项目你可以这么干,但是对比较大的项目或是人比较多的团队,这么干就会有很多问题。最大的问题就是代码可能干扰太严重。尤其是,我们想安安静静地开发一个功能时,我们想把各个功能的代码变动隔离开来,同时各个功能又会有多个开发人员在开发。
这时,我们不想让各个功能的开发人员都在 Master 分支上共享他们的代码。我们想要的协同方式是这样的:同时开发一个功能的开发人员可以分享各自的代码,但是不会把代码分享给开发其他功能的开发人员,直到整个功能开发完毕后,才会分享给其他的开发人员(也就是进入主干分支),接下来就是我们的功能分支上场了。
流程:

这里的流程是这样的:
- 切割开发分支:从git服务器上clone一份代码下来,并在本地切割出一个分支(git checkout -b jackyfei_dev);
- 编码提交:在分支下进行本地编码,后进行git add和git commit;
- 合并分支:切换到master分支(git checkout master),合并jackyfei_dev分支(git merge jackyfei_dev);
- 推送到服务器:最后push到服务器(git push -u origin master),注意这里推送后不会把分支一起推送到服务器,如果要推送分支上去可以使用命令:git push origin jackyfei_dev;
- 代码重审或代码测试[可选步骤]:代码审查人员或代码测试人员在你的分支上审查或测试通过后,在服务器端进行合并操作。该步骤根据团队大小进行选择,非必做项。
- 删除分支[可选步骤]:这里有点阅后即焚的感觉(git branch -d jackyfei_dev),当然你不删除也无妨,后续可以继续使用。
切割分支:

合并分支:

推送分支:

注意事项
- 删除分支:如果你在还没合并分支的时候,就要进行分支删除操作,git会有一个提示不能删除的操作,如果有重要的代码没有合并,建议不要-D强制删除。
- 分支冲突:在合并的过程会出现冲突,如下图所示,这时候需要手动解决冲突,方式和svn一样。手动合并后,再git add/git commit就可以了。
- 版本同步:这里的master和线上的版本保持同步,所以master必须尽量保证是干净的,稳定的,一般不要轻易去动他。


焦油坑
这里和注意事项不同,罗列的是该协作方式的缺陷:
- 线上出现BUG,本地分支正开发到一半,还没经过测试,无法进行发布,这时该如何解决?
- master无法保证一定是纯净的,因为每个人都可以merge上去
总结:
我们可以看到,其实,这种开发也是以服务器为中心的开发,还不是 Git 分布式开发,它只不过是用分支来完成代码改动的隔离。这里隔离的内容不叫项目而是小功能,这符合了产品快速迭代的需求。
如果团队规模不大,采用这种分支协同反而可能增加不必要的工作,所以要根据团队规模和现实当中的问题进行选型,一般团队超过两个人以上,而且线上环境频繁变更导致经常性的出现不稳定的异常,这种协同方式还是挺不错的。这里要思考的是,如果线上出了问题,本地开发一半无法进行发布的问题该如何处理呢?
GitFlow协同工作流
针对功能分支工作流的不足,GitFlow出现了,该工作流总共有5个分支,而其中的master和developer两个分支需要长期维护,其他的分支都是可以随时“阅后即焚”的。
流程

这里的流程是这样的:
- Feature 分支:也就是功能分支,用于开发功能,其对应的是开发环境,可以“阅后即焚”。
- Developer 分支:是开发分支,一旦功能开发完成,就向Developer 分支合并,合并完成后,删除功能分支。这个分支对应的是集成测试环境。
- Release 分支:当 Developer 分支测试达到可以发布状态时,开出一个 Release 分支来,然后做发布前的准备工作。这个分支对应的是预发环境。之所以需要这个 Release 分支,是我们的开发可以继续向前,不会因为要发布而被 block 住而不能提交。一旦 Release 分支上的代码达到可以上线的状态,那么需要把 Release 分支向 Master 分支和 Developer 分支同时合并,以保证代码的一致性。然后再把 Release 分支删除掉。
- Hotfix 分支:是用于处理生产线上代码的 Bug-fix,每个线上代码的 Bug-fix 都需要开一个 Hotfix 分支,完成后,向 Developer 分支和 Master 分支上合并。合并完成后,删除 Hotfix 分支。
- Master 分支:也就是主干分支,用作发布环境,上面的每一次提交都是可以发布到线上环境的。
主要事项
- 我们需要长期维护 Master 和 Developer 两个分支。
- Release 和 Hotfix 分支需要同时向两个分支作合并。所以,如果没有一个好的工具来支撑的话,这会因为我们可能会忘了做一些操作而导致代码不一致。
- GitFlow 协同虽然工作流比较重。但是它几乎可以应对所有公司的各种开发流程,包括瀑布模型,或是快速迭代模型。
焦油坑
- 分支太多,所以会出现 git log 混乱的局面。
- 在开发得足够快的时候,你会觉得同时维护 Master 和 Developer 两个分支是很太无聊,因为大部分情况下两者都是一样的。
- 管理变得非常复杂。尤其当你想回滚某些人的提交时,你就会发现这事似乎有点儿不好干了。
- 工作过程中,你会来来回回地切换工作的分支,有时候一不小心没有切换,就提交到了不正确的分支上,你还要回滚和重新提交等等。
GitHub Flow
流程
除非你是开源项目或者有购买github企业版,否则一般企业不会把核心代码托管在公共的github上面。

- 开发人员都把github上的代码 fork 到自己的代码仓库中。
- 开发容易代码库有两个远程仓库,一个是自己fork的库,一个是官方的库。
- 开发人员在本地建“功能分支”,在这个分支上做代码开发。
- 开发完成后,功能分支被 push 到开发人员自己的代码仓库中。
- 然后,向“官方库”发起 pull request,并做 Code Review。
- 一旦通过,就向官方库进行合并。
焦油坑
- GitHub Flow 这种玩法虽然变得很简单,但是没能把我们的代码和运行环境给联系在一起。
GitLab Flow
流程

以上是引入环境分支流程:
- 从master分支拉取一个预发布环境分支
- 从预发布环境分支拉取一个生产环境分支
流程虽然简单,但是增加分支后都是工作量,如果有很好的引入CI/CD,其实这一步也是多余的。以上主要是针对2C的互联网业务,2B的要看情况来处理,实时性没有那么强。

以上是引入版本分支流程:
对于版本和代码分支的问题,我觉得这应该是有意义的,但是,最好不要维护太多的版本,版本应该是短暂的,等新的版本发布时,老的版本就应该删除掉了。
总结
总之,GitFlow大而全,但是很重;中心式协同流简单但扩展性不好;功能分支和GitHub协同流轻量灵活(无须关注环境和多版本),适应性强大(既能适应快速开发和迭代,也适应CI/CD),个人倾向使用这功能分支协同工作流。当然没有一招鲜吃遍天的银弹,具体选择什么协作流程还是要具体分析,比如GitFlow的这种流程,可以考虑把Release分支裁剪掉,保证轻量化的同时,也能满足实际流程的需要;中心式的流程增加版本分支,也能很好的管理产品的版本代码。
当我们把精力放在软件架构和开发流程优化上,我们的git协同流会变得更加简单,所以与其熟练玩弄git协同流,不如放心思放在架构和开发流程的优化上,这才有事倍功半的效果。最后附上对比图,供你选择和参考,如果你们的团队有更好的用法,请多赐教。

Git协同工作流介绍的更多相关文章
- 【Slickflow学习】.NET开源工作流介绍、下载(一)
第一次自己写博客文章,大家多多指教.写博客主要记录一下学习的过程,给初学者提供下参考,也留给自己做备忘. Slickflow .NET开源工作流-介绍 这里摘录Slickflow官网的介绍: Slic ...
- 通达OA 小飞鱼开发培训第四讲 工作流介绍(图文)
本次课程主要解说了OA工作流相关内容,有些涉及到工作流的程序开发假设对工作流不熟悉也是有非常大难度,因此在这里进行了内容补充. 1.工作流介绍
- 【git】------git的基本介绍及linux的基本命令------【巷子】
001.git简介 git是一款开源的分布式版本控制工具 在世界上所有的分布式版本控制工具中,git是最快.最简单.最流行的 git的起源 作者是Linux之父:Linus Benedict Torv ...
- git 工作流介绍
GIT Git工作流你可以理解为工作中团队成员遵守的一种代码管理方案,在Git中有以下几种工作流方案作为方案指导: 集中式工作流 功能开发工作流 Gitflow工作流 Forking工作流 下面针对性 ...
- Git flow 工作流与规范
概述 简版图: PS. 可能用到的命令: 1.从指定 commit拉出新分支 git checkout commitId -b 本地新branchName git checkout 9fbc3d0 ...
- git flow工作流
https://github.com/xirong/my-git/blob/master/git-workflow-tutorial.md 说明: 个人在学习Git工作流的过程中,从原有的 SVN 模 ...
- git的基本介绍和使用
前言:从事iOS开发一年多以来,一直使用svn管理源代码.对svn的特点和弊端已经深有体会.前些天双十二前后,项目工期紧张到爆,起早贪黑的加班,可谓披星戴月,这还不止,回到家中还要疯狂的敲代码.那么问 ...
- 转载:CODE CSDN Git 配制方法介绍
以前一直使用Github,最近看到CSDN出了CODE代码托管功能,由于国内的阿里云服务器很稳定,而且不会被国 墙,所以果断的迁移了,下面就简单的介绍一下CODE的配置使用.其实CSDN的code 何 ...
- git的基础介绍和使用
git工作原理 git的工作原理还是比较简单的,当我们创建了本地代码仓库后,会在本地代码仓库的根目录中生成一个.git的隐藏文件. .git为一个文件目录,又叫做版本库.在本地代码仓库文件夹中,除.g ...
随机推荐
- 在Linux上安装Python3
1. 安装依赖环境 # yum -y install zlib-devel bzip2-devel openssl-devel ncurses-devel sqlite-devel readline- ...
- 高性能网络IO模型
同步阻塞式IO开发简单,但在处理IO密集的并发任务时,非常浪费CPU资源,性能低:并且,当一个进程(线程)含有多个套接字上时,同步阻塞式IO会带来问题:因为同步阻塞式IO只支持进程(线程)阻塞在一个套 ...
- scrapy安装过程问题解决、新建项目、调试断点
一.安装问题 1. 下载速度太慢 使用国外源,下载速度很慢,可以考虑使用豆瓣的镜像下载 pip install -i https://pypi.douban.com/simple/ scrapy 2. ...
- Cookie、Session、jsp、EL、JSTL
会话技术 Cookie Session 从访问一个站点,到关闭不继续访问 称为一次会话过程.会话技术就是记录本次会话中客户端的状态与数据的. 会话技术分为cookie.session. cooki ...
- 杨老师课堂_Java核心技术下之控制台模拟记事本案例
预览效果图: 背景介绍: 编写一个模拟记事本的程序通过在控制台输入指令,实现在本地新建文件打开文件和修改文件等功能. 要求在程序中: 用户输入指令1代表"新建文件",此时可以从控制 ...
- @Scheduled cron表达式
一.Cron详解: Cron表达式是一个字符串,字符串以5或6个空格隔开,分为6或7个域,每一个域代表一个含义,Cron有如下两种语法格式: 1.Seconds Minutes Hours Dayof ...
- PAT1077: Kuchiguse
1077. Kuchiguse (20) 时间限制 100 ms 内存限制 65536 kB 代码长度限制 16000 B 判题程序 Standard 作者 HOU, Qiming The Japan ...
- SSH整合配置文件概括
配置方式一:struts.xml, applicationContext.xml(hibernate.cfg.xml配置信息写入spring配置文件中) (版本号, struts2:2.3.15; s ...
- Tiny4412 烧写uboot到emmc步骤
将uboot写入emmc,并通过EMMC驱动,不在只用SD卡启动 烧写uboot的之前用如下命令查看EMMC卡信息及分区信息: mmcinfo 0: 查看mmc卡信息, 0表示SD卡:1表示emmc卡 ...
- ARM-Linux中断系统
1.前言 了解Linux中断子系统,同时也需要了解ARM体系结构中断处理流程:在熟悉整个软硬件架构和流程基础上,才能对流程进行细化,然后找出问题的瓶颈.<2. 梳理中断处理子系统> 但是所 ...