Git中心式工作流程

禅あ思 2021-10-29 11:34:43 ⋅ 27 阅读

切换到分布式的版本控制系统可能会让人望而却步,不过使用即使使用Git也不用改变团队现存的工作流程,开发团队仍然可以使用跟Subersion一模一样的操作完成项目开发。

不过Git却有很多超越SVN的优点,能够增强你的开发流程。首先,Git让每个开发者拥有整个项目的本地拷贝,这个孤立的环境使开发者的能够独立地工作,不用过早关注项目的其他代码变化。开发者们能够提交代码到本地仓库,如非必要,完全可以不必花费精力考虑上游的开发。

其次,Git提供了强健的分支和合并模型,跟SVN不同,Git的分支机制保证在不同代码库之间集成代码、共享变更时是非常安全的,其机制是“fail-safe”的。

它是如何工作的

跟Subversion一样,中心式工作流程有一个中心代码仓库,其作用是作为项目代码变更的唯一入口。不过默认的开发分支名称不再是SVN里的trunk,而是master,所有的变更都会被提交到这个分支上,该流程不需要任何其它master之外的分支。

刚开始的时候,开发者“克隆”中心代码库到本地,在自己的本地项目中修改文件、提交变更,就像使用SVN一样。不过,这些新提交的变更却被存储到本地了,完全跟中心代码库隔离了。这样就开发者能够推迟同步变更到上游,直到他们认为时机合适为止。

为了发布变更到正式的项目,开发者“推送”(push)自己本地的master分支到中心代码仓库,这个操作等同于svn commit,不同的是,该操作是将原本不存在于中心master分支的本地提交记录添加到中心仓库上。

管理冲突

中心代码库代表正式的项目,应该严肃对待,它的提交历史应该正式且稳定。如果开发人员的本地提交跟中心代码库有偏离,Git将会拒绝推送这些变更,因为该行为将覆盖正式的提交内容。

在开发人员发布自己的特性代码之前,需要从中心代码或获取最新的代码记录,而且要将自己的变更rebase到这些最新的代码提交记录之前,这样做就好像是在宣告“我要把自己的变更添加到别人的工作成果之上”。操作结果是完美的线性历史,跟传统的SVN工作流一样。

如果本地变更跟上游的提交结果有直接的冲突,Git会暂停rebase操作,让开发者手动解决冲突。比较好的事Git使用git statusgit add命令完成解决冲突和产生提交的工作,经验较少的开发者能够比较容易地管理自己的合并工作。另外,如果开发者陷入非常难于解决的问题时,Git也很容易放弃整个rebase操作而让开发者进行其他尝试或寻求帮助。

示例

下面我们逐步介绍典型的小型团队如何使用这个工作流程,假设这个团队里有John和Mary两个开发人员,他们将在不同的特性上工作,最后通过中心代码库共享自己的代码。

初始化中心代码库

首先在一台服务器上创建一个中心代码库,如果是全新的项目,可以初始化空的代码仓库,否则需要从现存的Git或SVN代码库导入。

中心代码库应当是有空的代码库(不应当有工作目录),创建方法如下:

ssh user@host
git init --bare /path/to/repo.git

确保使用有效的SSH用户名、主机IP或域名,/path/to/repo.git表示代码库的位置,代码库名称后的.git扩展名表示它是一个空白的代码库。

开发人员从中心库克隆代码

中心库创建完成后,每个开发人员通过git clone命令创建本地代码拷贝:

git clone ssh://user@host/path/to/repo.git

克隆代码仓库时,Git自动添加一个被称为origin的快捷方式,它指向“父级”代码库,开发人员未来需要和它交互。

John在他自己的特性上工作

在John的本地代码库中,他可以使用标准的Git提交方式开发特性:edit、stage、commit。如果还不熟悉暂存区(stageing area)的概念,可以尝试做一次提交:

git status # View the state of the repo
git add # Stage a file
git commit # Commit a file

由于这些命令仅仅创建了本地提交记录,John能够不受限制地重复这些操作而不用担心对中心库产生影响。这对大型的特性开发很有帮助,有助于将其拆分成更简单、更原子化的区块。

Mary在她自己的特性上工作

同时,Mary正在她自己的特性上进行开发,使用的也是自己的本地代码库,利用同样的edit、stage、commit操作,跟John一样,她不用关心中心代码库的事情,也不用考虑John正在做的工作,他们的本地代码库都是私有的。

John发布他自己的特性

一旦John完成了自己的特性,他应该把本地提交记录发布到中心代码仓库,以便于其他成员访问,使用git push命令完成发布:

git push origin master

origin是中心代码仓库的远程连接,是在John克隆它的时候被创建出来的,master参数告诉Git创建orginmaster分支,看起来似乎是John的本地master分支。由于中心库在John克隆后并没有任何更新,这次发布将不会导致冲突,push也如期完成自己的任务。

Mary试图发布她的特性

在John顺利地发布自己的变更到中心库后,Mary的push操作将会有什么结果呢?她也使用了同样的命令进行推送:

git push origin master

但是由于她的本地历史记录已经跟中心库发生了偏离,Git将拒绝这个请求,并提示如下信息:

error: failed to push some refs to '/path/to/repo.git'
hint: Updates were rejected because the tip of your current branch is behind
hint: its remote counterpart. Merge the remote changes (e.g. 'git pull')
hint: before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.

这就阻止了Mary覆盖中心库的正式记录,她需要把John的更新pull到自己的代码库,把这些更新集成到她自己的本地变更中,继续尝试push。

Mary rebase到John提交记录的顶端

Mary可以使用git pull命令将上游变更整合到自己的代码库中,该命令有点象SVN的update,拉取完整的上游变更到Mary的本地库,并试图整合到她的本地提交记录中:

git pull --rebase origin master

选项*--rebase让Git在同步中心库完成后将Mary的提交记录移动到master*分支的顶端,如下图所示:

如果忘记这个选项,pull操作仍然能够工作,不过当别人想要从中心库同步时,都会收到不必要的“merge commit”提示。对于这个流程来说,rebase而不是产生合并请求会更好。

Mary解决了一个合并冲突

rebase操作每执行一次,只把一个本地提交记录转移到更新过的master分支,也就是说需要一个接一个地捕捉合并冲突而不是一次性地整体解决它们,这样做有助于保持项目提交历史比较整洁,也更加容易定位bug,在必要时对项目进行回滚产生的影响也很小。

如果Mary和John工作在不相关联的特性上,rebase操作基本不会产生冲突;反之,Git将会暂停当前提交的rebase操作,并输出如下信息:

CONFLICT (content): Merge conflict in <some-file>

好消息是Git可以让任何人解决自己的合并冲突,在这个示例中,Mary运行git status命令查看问题原因,发生冲突的文件将会在Unmerged paths区域出现:

# Unmerged paths:
# (use "git reset HEAD <some-file>..." to unstage)
# (use "git add/rm <some-file>..." as appropriate to mark resolution)

# both modified: <some-file>

然后Mary可以按照自己的意愿进行修改,一旦完成,就可以暂存这些文件并让git rebase继续完成后面的工作:

git add <some-file> 
git rebase --continue

这就是全部的工作,Git将会继续处理下一个提交,并重复这个过程直到产生新的冲突。

要是你目前为止还没有任何概念,比着急,执行如下命令就能回到你运行git pull --rebase前的状态:

git rebase --abort

Mary成功发布了她的特性

在Mary完成跟中心库的同步工作后,她就能成功地发布自己的变更了:

git push origin master

何去何从

从这个过程可以看出,仅仅用Git的几个命令就能替换掉Subversion,让团队脱离SVN很不错,不过目前为止还没有真正利用上Git分布式的特点。

如果你的团队很享受中心式工作流程,不过还想简化这个过程的协作投入,绝对值得去探索一下“特性分支工作流”的好处。通过为每个特性使用独立的分支,就可以在把特性集成到正式项目之前进行深入的讨论,决策如何处理新的附加要求。


全部评论: 0

    我有话说:

    Git特性分支工作流程

    Git特性分支工作流程

    Git典型工作流程介绍

    Git典型工作流程介绍

    交叉型工作流程

    交叉型工作流程跟前面讨论过的流程相比大不相同,不再使用单一的服务器端中心代码仓库,而是给每个开发人员一个服务器端的代码仓库,也就是说每个开发人员都有两个Git仓库:私人的本地仓库和公共的服务器端仓库

    Gitflow工作流程

    Gitflow工作流程来源于Vincent Driessen的网站nvie。 这个工作流程围绕项目发布定义了一个严格的模型,它比特性分支工作流程复杂很多,为更大型的项目提供了强劲的管理框架。 本流程

    Git 2.29稳定版发布,实验性支持更安全的SHA-256

    Git 2.29 稳定版已发布。此前发布的多个版本都在为将 Git 使用的安全哈希算法从 SHA-1 迁移至 SHA-256 做准备,2.29 版本终于实验性支持 SHA-256,可用于提升代码仓库

    Gitlab Flow

    基于GIT分支的开发流程层出不穷,Gitlab也不甘人后,提出了围绕GitLab的开发协作流程模型。

    最全Mac工具

      MacTool Mac 开源免费工具汇总, 只罗列开源好用的。更全列表请参考awesome-mac 必备 Homebrew - 体验通过命令行安装 Mac 软件的工具(大部分是

    工具集001

      1.  Google项目管理工具 Tables   2. 终端 taskwarrior --- TODO List Taskwarrior is

    Git托管平台的拉取请求

    拉取请求是Bitbucket的一个特性(经调查,Gitlab、Github都支持这个特性),可以让开发人员的协作更加容易,他们提供了一个友好的网页界面让开发者在集成代码到正式库之前对其进行讨论。 Bibucket Github Gitlab ...

    WeCMDB 1.5.5 版本发布,可视化的集中配置数据中心

    WeCMDB简介 WeCMDB是集中配置数据中心,管理IT各层面组件及组件关系信息。同时与自动化运维管理工具紧密相联,支持运维管理工具流程的运作,发挥配置信息的价值,同时依赖这些工具流程保证数据

    Netbox 2.9.10 发布,IP 地址与数据中心管理工具

    NetBox 是一个 IP 地址管理(IP address management,IPAM)和数据中心基础设施管理(data center infrastructure management

    Netbox 2.11.1 发布,IP 地址与数据中心管理工具

    NetBox 是一个 IP 地址管理(IP address management,IPAM)和数据中心基础设施管理(data center infrastructure management

    WeCube 2.7.0 版本发布,一站架构和运维管理工具

    WeCube简介 微众银行在分布式架构实践的过程中,发现将银行核心系统构建于分布式架构之上,会遇到一些与传统单体应用不同的痛点(例如,服务器增多,部署难度大;调用链长,全链路跟踪困难; 系统复杂,问题定位时间长等),在逐步解决这些痛点的过程中,总...

    代码评审流程(摘要)

    代码评审流程(摘要)

    Martian-cloud 4.0,跟注册中心拜拜了,基于传染机制的分布式组件诞生

    这次真的要跟注册中心讲拜拜了,微服务不再需要占用一套注册中心集群了,大大节约了运维成本 更新点如下 丢弃了一开始的【生产者-&gt;注册中心-&gt;消费者】模型 采用传染机制,实现服务的发现与

    工具集002

      文件对比 https://www.diffchecker.com/excel-diff 快速找出类似文件的不同之处。  

    Git 2.30.1 发布

    Git 2.30.1 已经发布,此版本主要用于合并 “master” 上累积的修补程序,以准备仍与 2.30.x 相关的 2.31 版本发布。 部分更新内容 修复了 "git fetch

    Spring 5 的 WebFlux 响应开发示例

    Spring 5 已经大力支持了响应开发模式,引入的响应框架叫做 Spring WebFlux。