zoukankan      html  css  js  c++  java
  • Git Flow工作流程

    背景

    在多组员,多项目等环境进行协同工作时,如果没有统一规范、统一流程,则会导致额外的工作量,甚至会做无用功。所以要减少版本冲突,减轻不必要的工作,就需要规范化的工作流程。

    总则

    -统一使用Git作为版本控制的主要工具。
    -统一使用GitFlow流程管理控制版本。

    提交的准则

    1.除了源码相关的东西之外,其他build产生的东西(如:maven的target文件夹,.idea文件夹等),均不能提交进入源码仓库,添加到.gitignore文件中忽略掉。
    2.撰写规范的提交说明。一份好的提交说明可以帮助协作者更轻松更有效地配合工作。
    3.要严格按照我们指定的流程切换到指定分支,开发相应的功能。

    分支简述

    我们使用的分支流程:

     
    主要分支简述
    • 天蓝色圆点所在的线为我们源码的主线(master)。主分支,产品的功能全部实现后,最终在master分支对外发布。
    • 天蓝色方形指向的节点就是每一个发布版本的标签(tag)。
    • 紫色圆点所在的线为主要分支线(develop)。开发分支,基于master分支克隆,产品的编码工作在此分支进行。
    • 橙色圆点所在的线为新功能开发分支线(feature)。功能特征分支,基于develop分支克隆,主要用于多人协助开发场景或探索性功能验证场景,功能开发完毕后合并到develop分支。feature分支可创建多个,属于临时分支,目的实现后可删除分支。
    • 绿色圆点所在的线为新版本发布线(release)。测试分支,基于delevop分支克隆,产品编码工作完成后,发布到本分支测试,测试过程中发现的小bug直接在本分支进行修复,修复完成后合并到develop分支。本分支属于临时分支,目的实现后可删除分支。
    • 红色圆点所在的线为发布版本bug修复线(hotfix)。Bug修复分支,基于master分支或发布的里程碑Tag克隆,主要用于修复对外发布的分支,收到客户的Bug反馈后,在此分支进行修复,修复完毕后分别合并到develop分支和master分支。本分支属于临时分支,目的实现后可删除分支。

    主分支说明

    代替原来的单个主线(master),我们使用两个分支来记录源码轨迹:
    1.原来的master分支用来记录官方发布轨迹;
    2.新的develop分支是一个集成分支,用来记录开发新功能的轨迹。

     
    Master与Develop分支

    除了master主线和develop主分支线,其他的分支都是临时的分支,有一定的生命周期的,其余的工作流程分支都是围绕这两个分支之间的区别进行的。

    其他分支说明

    -新功能分支(Feature Branches)

    每一个新的功能都应该创建一个独立的分支,从develop分支中派生出来。当功能完成后,要合并(merged)回develop分支,合并后它的生命周期就结束。新功能分支不会与master分支有直接的交汇。如图:

     
    Feature Branches

    注意:对于所有意图和目的,新功能分支会合并到develop分支。但是,这个Gitflow工作流不会在此结束。

    -发布分支(Release Branches)

    一旦开发的功能已经满足发布条件(或预定发布日期接近),应该合并所有满足发布条件的新功能分支到develop分支中,然后,开出一个发布分支(Release),开始准备一个发布版本。在这个分支上,不能再添加新的功能,只有bug修复和该版本为导向的任务。一旦到了发布日期,Release就要合并回master发布,并且,打出版本标签。另外,还需要合并回develop分支。

     
    Release Branches

    使用一个专门的分支来准备发布版本,使得一个团队能对当前版本进行抛光,而另一个团队继续为下一个版本的功能做准备。它还创造了良好定义的发展阶段(例如,很容易说,“本周我们正在准备4.0版”,而且真实地看到它在库中的结构)。

    -维护分支(Maintenance Branches)

    维护分支也就是线上bug修复分支,使用来快速修复生产环境的紧急问题。

     
    Maintenance Branches

    这个分支是唯一一个开放过程中直接从master分支派生来的分支。快速的修复问题后,它应该被合并回master和develop(或者当前发布分支),然后,master分支需要打一个版本标签。

    一个专门的错误修复开发线,可以让团队在不等待下一个发布周期,导致中断工作流程情况下解决问题。可以将维护分支当做主要的问题修复分支,与master并行。

    命名约定

    -主分支名称:master
    -主开发分支名称:develop
    -标签(tag)名称:v*.RELEASE,其中”*“ 为版本号,“RELEASE”大写,如:v1.0.0.RELEASE
    -新功能开发分支名称:feature-*or feature/*,其中“*” 为新功能简述,如:feature-item-activity-list
    -发布分支名称:release-*or release/*,其中*为版本号,“release”小写,如:release-1.0.0
    -master的bug修复分支名称:hotfix-*or hotfix/*,其中*为bug简述,如:hotfix/item-update-bug

    工作流程

    下面具体演示如何使用工作流来管理版本发布周期。假设我们已经存在或创建了一个源码中央存储仓库。

    工作流的基础

    创建develop分支

     
    Create Develop Branch

    -项目负责人在本地master基础上创建一个develop分支,然后,推送到服务器;

    git branch develop
    git push -u origin develop

    -其他开发人员,需要克隆develop中央仓库的源码,创建一个develop的轨迹版本;如果,已经克隆过该项目,则,不需要执行以下第一条命令。

    git clone git@github.org:search-cloud/demo.git
    git checkout -b develop origin/develop

    develop这个分支将包含项目的完整历史记录,而master将包含缩略版本。

    ** 假设开始以下所有的流程之前,都已经创建好develop分支。**

    新功能开发流程

    1.新建feature分支

     
    Create Feature Branch

    基于develop分支创建新功能分支:

    git checkout -b feature/demo develop

    推送到远程仓库,共享:

    git push

    所有开发此新功能的人员,都在此分支上开发提交代码。

    git status
    git add
    git commit -m "Add some-file."

    2.完成新功能开发(合并feature分支到develop)

     
    Merge Feature to Develop

    当确定新功能开发完成,且联调测试通过,并且新功能负责人已经得到合并feature分支到develop分支的允许;这样才能合并feature分支到develop。

    git pull origin develop
    git checkout develop
    git merge feature/demo
    git push
    git branch -d feature/demo

    第一条命令是确保在合并新功能之前,develop分支是最新的。

    注意:

    -新功能分支,永远不要直接合并到master分支。
    -合并可能会有冲突,应该谨慎处理冲突。

    3.在测试环境发布develop分支代码(提交测试)

    线上版本发布流程

    1.从develop中创建准备发布的release分支

     
    Create Release Branch

    当主测试流程完成,源码已经趋近于稳定状态,应该准备一个发布版本,确立版本号:

    git checkout -b release-0.1.0 develop

    推送到远程仓库共享:

    git push

    这个分支是清理准备发布、 整体回归测试、 更新文档,和做其他任何系统即将发布的事情。

    2.继续抛光改bug
    3.release分支合并到master发布

     
    Merge Release to Master and Develop

    一旦已经满足发布条件(或已经到了预定发布日期),应该把release分支合并到master分支和develop分支中,然后,使用master发布新版本。合并release分支到develop分支是很重要的,要让release上修改的东西能在后续的开发分支中生效。

    git checkout master
    git merge release-0.1.0
    git push

    4.release分支合并到develop

    git checkout develop
    git merge release-0.1.0
    git push
    git branch -d release-0.1.0

    5.打标签

    Release分支在功能开发分支(develop)和公共发布版(master)中,充当一个缓冲的作用。每当有源码合并到master中的时候,应该在master上打一个标签,以便后续跟踪查阅。

    git tag -a 0.1.0.RELEASE -m "Initial public release" master
    git push --tags

    线上Bug修复流程

    当终端用户,反馈系统有bug时,为了处理bug,需要从master中创建出保养分支;等到bug修复完成,需要合并回master:

    1.创建hotfix分支

    git checkout -b issue-#001 master

    2.修改bug Fix the bug
    3.完成修复,合并到master发布

     
    Merge hotfix to Master
    git checkout master
    git merge issue-#001
    git push

    4.打标签

    git tag -a 0.1.1.RELEASE -m "Initial public release" master
    git push --tags

    5.合并到develop

    git checkout develop
    git merge issue-#001
    git push

     新功能开发工作流

    切换到本地仓库工作区

    cd /home/timerhunter/workspace

    从远程仓库克隆代码到本地仓库

    git clone https://xxxx@localhost:8443/r/valve/V5-Lora.$git

    基于master分支,创建develop分支

    /* 切换到master分支 */
    git checkout master
    /* 基于master分支克隆develop分支,并在克隆完毕后直接跳转到develop分支 */
    git checkout -b develop
    /* 推送develop分支到远程仓库 */
    git push origin develop

    注:编码工作主要在develop分支,master分支主要用来发布稳定版本

    在本地仓库的开发流程

    完成一个功能点或者一天的工作结束时,将代码提交到本地仓库

    /* 提交修改到缓冲区 */
    git add .
    /* 提交修改到本地仓库 */
    /* 如果是修复的BUG,应该在修改说明的最开始添加Bug#ID,多个Bug用逗号分隔,例如Bug#002,003 */
    /* 如果是完成了一个指派的任务,应该在修改说明的最开始添加Task#TaskID,例如Task#165 */
    git commit -m "Bug#123 修改说明"
    /* 每完成一个功能点可以对代码进行打包 */
    git tag -m "简要说明增加/修复/删除了什么功能" v0.0.0.170718

    注:不是每一个Tag都需要提交到远程仓库,比如可以在完成一个功能点的编码工作后未编译就打一个包,仅存储于本地仓库,在编译成功&测试通过后,再打一个新的Tag包(里程碑Tag包),仅将里程碑Tag包推送到远程仓库

    推送代码到远程仓库

    当完成一个功能点或阶段工作时,将代码推送到远程仓库develop分支

    /* 执行代码拉取操作,防止代码冲突 */
    git pull
    /* 解决代码冲突后,推送代码到远程仓库*/
    git push origin develop

    注:禁止将未编译或编译不通过的代码提交到远程仓库,如果编码工作进行未完成可以提交到本地仓库中,等待该功能点全部实现后再将代码推送到远程仓库中。

    将代码发布到测试分支

    阶段性的开发工作已完成,启动小批量测试工作,将代码发布到测试分支release

    git checkout develop
    git checkout -b release
    git push origin release

    测试工程师提交Bug后修复

    从远程仓库拉取代码

    /* 克隆仓库 */
    git clone https://admin@192.168.1.88:8443/r/admin/test.$git
    /* 查看远程仓库分支情况:克隆仓库时只能克隆master分支,因此需要拉取指定分支,我们使用$git branch -r查看远程分支情况 */
    git branch -r
    origin/HEAD -> origin/master
    origin/dev
    origin/master
    origin/release
    /* 拉取测试分支 */
    git checkout -b release origin/release
    • 修复流程同#2.4,#2.5;
    • 注意在$git commit时的修复说明中添加Bug#BugID关键字
    • 完成一个Bug修复或完成阶段性工作后,将代码推送到远程分支

    测试工作完成后,合并代码到develop分支

    /* 切换到develop分支 */
    git checkout develop
    /* 执行合并操作,将release分支代码合并到develop分支 */
    git merge release
    /* 如果合并报错,则解决冲突,冲突解决后继续再次执行合并 */

    开发工作和测试工作都完毕后,发布时将develop分支合并到主线

    git checkout master
    git merge develop

    阶段开发完毕,打一个里程碑Tag包

    /* 创建里程碑Tag */
    git tag -m "Task#003 v1.0.0 首版发布" v1.0.0.170718
    /* 推送里程碑Tag到远程仓库 */
    git push origin v1.0.0.170718

    发布后的产品Bug修复工作流

    查找里程碑Tag

    /* 查询里程碑及其提交说明 */
    git tag -n1 -l v*

    基于里程碑Tag创建分支

    /* git checkout -b [创建的分支名称] [里程碑Tag名称] */
    git checkout -b bugfix-v1.0.0.170718 v1.0.0.170718

    修复代码后可以查询修改过的地方

    git diff

    修复完毕后分别合并到develop分支和master分支

    /* 合并到develop */
    git checkout develop
    git merge hotfix-v1.0.0.170718
    /* 提交到远程仓库develop分支 */
    git push origin develop
    /* 合并到master:如果随下一个版本再发布,可不用合并至master分支 */
    git checkout master
    git merge develop
    /* 提交到远程仓库master分支 */
    git push origin master

    创建新的里程碑Tag

    git tag -m "Bug#002 修复某某Bug" v1.0.1.170719
    /* 推送到远程仓库 */
    git push origin v1.0.1.170719

    删除bugfix分支

    /* 删除本地分支-$git branch -d [本地分支名]*/
    git branch -d bugfix-v1.0.0.170718
    /* 删除远程分支-$git push origin :[远程分支名]*/
    git push origin :bugfix-v1.0.0.170718

    日常开发过程中常用操作

    提交后发现丢了几个文件没有提交

    /* 正常提交 */
    git commit -m "发布v1.0"
    /* 发现丢了修改记录,重新添加 */
    git add CHANGELOG.md
    /* 重新提交,仍以"发布v1.0的名义提交",最终只有一个提交*/
    git commit --amend

    撤销上一次的提交,但是保留暂存区和当前修改不变

    /* 正常提交 */
    git commit -m "发布v1.0"
    /* 将会撤销“发布v1.0”的提交,但是保留暂存区和当前目录中文件的修改 */
    git reset --soft HEAD~

    撤销上一次的提交和暂存区修改,仅保留当前修改不变

    /* 正常提交 */
    git commit -m "发布v1.0"
    /* 将会撤销“发布v1.0”的提交,但是保留暂存区和当前目录中文件的修改 */
    git reset --mixed HEAD~

    撤销上一次的提交,并丢弃所有修改,包括暂存区和当前目录中的修改,整体回档到上上次的提交

    /* 正常提交 */
    git commit -m "发布v1.0"
    /* 将会撤销“发布v1.0”的提交,但是保留暂存区和当前目录中文件的修改 */
    git reset --hard HEAD~

    撤销暂存区和当前目录下所有文件的修改,整体回档到上一次提交

    注意:此操作非常危险,会丢失所有修改,直接整体回档到指定的版本,谨慎使用

    /* 正常提交 */
    git commit -m "发布v1.0"
    /* 修改多个文件 */
    /* 添加到暂存区 */
    git add .
    /* 撤销暂存区和本地目录下所有文件的修改,并整体回档到上一次提交的状态 */
    git reset --hard HEAD
    /* 可以修改HEAD为SHA-1值回档到任意版本 */
    /* 使用git log查看每次提交的SHA-1值,可以仅指定前7位 */
    git reset --hard 745d8cd

    将文件提交到暂存区后撤回

    在对文件执行git add操作后,重新撤回

    /* 添加文件到暂存区 */
    git add README
    /* 将文件从暂存区撤回 */
    git reset HEAD README

    撤销对文件的修改

    在对文件进行修改后,发现思路不对,需要将文件恢复至原有状态

    /* 撤销对CHANGELOG.md文件的修改,请注意这是一个危险的命令,
    * 对指定文件的修改都会被取消,会还原成上次提交的样子 */
    git checkout -- CHANGELOG.md
  • 相关阅读:
    Linux下svn服务器搭建
    mybatis-generator自动生成代码插件使用详解
    java中Class.forName("xxx")和ClassLoader().loadClass("xxx")的区别
    ExecutorService中submit()和execute()的区别
    Redis学习总结(1)——数据持久化
    Java内存模型及性能优化
    (转)Lock和synchronized比较详解
    SpringBoot中获取spring.profiles.active
    SpringBoot添加拦截器
    SpringBoot与Kafka集成
  • 原文地址:https://www.cnblogs.com/zhuochong/p/10148163.html
Copyright © 2011-2022 走看看