3.5 持续交付
Martin Fowler是这么描述持续交付的:“持续交付是一种软件开发实践,令软件可随时发布上线……为此需要持续地集成软件开发成果,构建可执行程序,并运行自动化测试以发现问题,进而把可执行程序逐步推送到越来越像生产环境的各个测试环境中(并测试),以保证它最终可以在生产环境中运行。”[7]
Jez Humble是这么描述持续交付的:“持续交付是一种能力,能够让各类变更(如新特性、配置变更、缺陷修复、尝试性内容等)以安全、快速、可持续的方式交付到生产环境中或用户手上。”[8]
更详细的介绍,请参考2010年出版的《持续交付:发布可靠软件的系统方法》一书。
3.5.1 包括所有质量验证工作
持续交付是持续集成的扩展。首先是扩展到所有质量验证工作:持续集成主要关注的是频繁地把各个改动汇聚在一起,发现并修复其质量上的问题。其中发现并修复问题所采用的主要是不需要测试环境的手段,比如构建、代码扫描、单元测试等。然而,发现问题的方法可不止这些,还需要到各个测试环境中进行其他各类测试。持续交付希望这些需要测试环境的测试也能够比较频繁地发生。
为什么要让这些测试比较频繁地发生呢?理由跟为什么要持续集成差不多。
前面提到,越早发现问题,越容易修复问题。而构建、代码扫描、单元测试并不能发现所有的问题,还有不同模块间配合的问题、环境配置的问题等有待早点发现,以便早点修复。
前面提到,集成后可以工作的代码,有利于跟踪进度和提供对进度的感知。而经过了部署和更多测试的代码,质量更高,更接近可发布状态,因此能更好地提供对进度的感知。
前面提到,越是频繁地集成,越是有利于产品早点发布上线。而频繁地部署测试环境并测试,亦有利于从需求提出到发布上线整体时间的缩短。于是用户可以更早地将产品用起来,更快地给出反馈。
为了让这些测试能比较频繁地发生,我们需要把以下事情做好。
• 前面提到的版本控制、自动化、过程可视化、加速也要被应用到部署和随后的测试中。比如把自动化应用到测试环境部署中,实现测试环境的自动化部署。
• 一旦涉及测试环境特别是类似于生产环境的测试环境,对环境的管理其实相当不简单。比如如何管理环境中的各种配置及其变更,以及数据库表结构和内容的变更等。这些是从持续集成扩展到持续交付后增加的很大一摊子事情。
• 持续集成中的构建、代码扫描、单元测试,与持续交付中增加的部署测试环境,以及测试环境中的各种测试,虽然都要频繁地做,但是频繁的程度是不一样的。对于那些执行速度快、“性价比”高的测试,则应该很频繁地做,比如每当集成分支收到提交的代码改动后就做;而对于那些比较耗时费力的测试,就不用那么频繁地做了。所以需要自动化流程(比如流水线)支持这样的模式:不同的阶段有不同的频率,还要保证能衔接在一起。
3.5.2 比较频繁地发布上线
持续交付是除了将持续集成扩展到所有质量验证工作,还从集成测试扩展到了发布上线,旨在让发布上线成为一件轻松、容易的事情,可以一键搞定:想发布时,一下子就能发布上去。这样就可以适度频繁地发布上线。
为此需要:
• 将自动化和自助化部署到生产环境,将整个自动化流程延伸到发布上线。如果测试环境已经自动化了,这一步也不难。
• 将生产环境及其组成部分管理起来。如果测试环境已经实现管理,这一步也不难。
以上是持续交付的全部内容:基于持续集成,让所有质量验证工作都适度频繁地进行,并且让发布上线能一键搞定,以进一步缩短软件交付所需的时间,适度频繁地发布上线。
3.5.3 持续部署
我们还常听到一个词,与持续交付相关,它就是“持续部署”。这里的“部署”指的是生产环境部署。
Martin Fowler是这么描述持续部署的:“持续部署意味着每个通过部署流水线的变更都被自动地部署到生产环境中,于是每天都会有若干次生产环境部署。”[9]
更详细的介绍,请参考《持续交付:发布可靠软件的系统方法》一书。
持续交付是指适度频繁地发布上线。而持续部署则基于此更进一步,频繁到每当一个版本通过测试时,就立刻自动把它部署到生产环境中。
持续交付并不排斥人工测试,只要它不过于庞大和笨重,不会让测试的频率变得太低就行。然而,持续部署对此的要求要高得多,它要求测试做到完全的自动化。
显然,完全的自动化测试以及更频繁的生产环境部署,能进一步缩短从需求提出到发布上线进而得到用户反馈的整体时间,这是持续部署的主要收益。不过,显然实现持续部署要比实现持续交付困难得多。持续部署是持续交付的极端情况,当然也可以说是将持续交付做到了极致。