Cherry Pick

一套代码,多个平台,git工作流

2018/11/6 by DKZ

在老东家那里遇到了这个问题,我们有一个面向企业的产品,这个产品要加入不同客户的定制。为满足日后产品升级的需要,这些定制都被写在了同一个工程里,这些定制的逻辑不能被良好的拆分出来,导致代码越来越臃肿,变得难以维护。

开始觉得是我们自己产品的问题,在尝试改进这个产品的时候始终没有解决这个问题。我觉的可能是我们的工作流程和管理出了问题,首先不同的项目肯定要再拆分到不同工程中去,由于我们当时是瀑布式的开发,各个项目组各自为阵,最终这些分开的工程都没有办法合并在一起,不得不重新整理一个基版。

这个基板中还是存在定制的部分,用 if else 的方式分开来,总之想要将它拆分开来,就需要添加日后的升级和维护的成本,而不拆开导致了代码逻辑复杂臃肿开发起来很难受,新来的同事和外包的同事难以上手。

当时公司面临从甲方到乙方的角色转变,在产品尚未成熟和稳定的情况下,接了很多项目和定制的开发,走了一些弯路。在我任职期间这个问题没有得到解决,但我们已经开始针对开发的流程做出调整,逐步从瀑布改为可以快速迭代的敏捷开发模式。

辞职之后,在自己的独立游戏项目《山海》中同样出现了相似的问题。倒不是因为有定制开发的问题,而是因为《山海》要在不同的平台上线,虽然是基于egret引擎打包,但在不同的平台上有一些差异化的部分,诸如底层socketio通信,微信分享二维码,iOS端消息通知等。

由于也是摸着石头过河,这个项目经常重构,进行了多次架构调整。有了之前的教训,这个项目很早就分出了三个工程降低逻辑的复杂性,iOS工程和微信工程是从Web版本上fork而来,在Web版本的基础上改了对应的底层接口,分离了一部分差异化的部分。

对应的基本功能开发完毕后,这个游戏还在不断的升级和迭代。这个时候就面临同一个功能要在不同的工程上开发多次问题,要手动把代码粘过来十分麻烦。直接 merge 每次需要处理太多差异部分的冲突,我开始尝试使用 cherry pick 代替 merge 的开发模式。

                V2.3    V2.4   V2.5  V2.6
Web    +--------+-------+------+-----+      master
            +---+-------+------+-----+----+ dev
             fork     
             |  |       
        +---------------+------+------+     web master
             |  |       |    cherry pick
             |  |       |      |     |
Wechat       |  +-------+------+-----+      master
             |  +-----------------------+   dev
             |  |       |      |     |
iOS          +----------+------+-----+      master
             +------------------------+     dev

首先要在Wechat和iOS工程上 add remote 指向Web工程,将Web工程的master分支拉下来,这样就可以在这两个工程里cherry-pick Web工程里的commit了。

不同平台的定制在对应的dev上开发直接合并到对应master上,功能开发步骤如下

  1. 在 Web 工程 dev 分支上进行新功能的开发与测试。
  2. 将dev内容merge到master上,发布web版本
  3. 在其他两个工程上将web master拉下来
  4. cherry pick web master 上这个功能的 commit hash
  5. 处理冲突
  6. cherry pick continue

基本解决了这个问题吧。在快速迭代的情况下,可以保证多个平台代码的同步。目前只在个人的小项目中使用过不知道在多人大型项目中会不会有问题。