持续交付实践:如何通过自动化流水线加快软件交付速度

SEO 摘要: 本文介绍持续交付如何通过自动化流水线提升软件交付速度,并在加快发布节奏的同时降低部署风险。文章重点讨论持续改进、软件交付自动化、流水线工具、部署安全机制、生产前测试、生产中验证和发布时机控制,帮助团队在保证质量和可用性的前提下提升交付效率。

持续交付实践:如何通过自动化流水线加快软件交付速度

简介

持续改进与软件自动化:持续交付的起点

十多年前,海外某些大型科技公司曾启动过一个项目,目的是了解团队将一个想法转化为高质量生产系统的速度究竟有多快。在这个项目中,团队对软件交付吞吐量进行了度量,希望借此提升执行速度。

研究发现,从代码提交到进入生产环境,平均需要 16 天。一个团队通常会先提出一个想法,然后大约用一天半的时间编写代码,将这个想法付诸实现。构建和部署新代码所需的时间不到一小时。真正耗时的是之后大约 14 天:团队需要等待有人开始构建、执行部署并运行测试。

项目结束时,团队建议对代码提交之后的流程进行自动化改造,以提高执行速度。这样做的目标,是在保持甚至提升质量的同时,消除流程中的等待和延迟。这也是持续交付实践的核心价值:通过自动化流程缩短从代码提交到生产发布的周期,同时降低人为操作带来的风险。

这一建议的核心,是一项以提升执行速度为目标的持续改进计划。对于海外某些大型科技公司而言,提升执行速度也符合其内部强调的“高标准”工程原则。这一原则要求团队设定严格标准、不断提高标准,并持续交付高质量的产品、服务和流程。类似原则也描述了这些公司如何开展业务、领导者如何带领团队,以及团队如何始终坚持以客户为中心做出决策。

为了提升软件工程师的工作效率,这些公司构建了一系列内部软件开发工具。例如,它们曾创建一套集中托管的构建系统,该系统会在服务器上执行一系列命令,生成可部署的构建产物。不过,早期的构建系统并不会监听源代码变更,也不会自动启动构建。它们还拥有一套内部部署系统。启动部署时,相关人员需要将构建产物上传到该系统。

随着业界开始关注持续交付,团队受到启发,构建了内部流水线系统,用来在构建系统和部署系统之间实现软件交付流程自动化。对于希望进一步提升研发效能的团队来说,也可以借助 PingCode 这类智能化研发管理工具,将团队目标、客户反馈、需求清理、评审排期、开发、测试、发布上线和 Wiki 知识沉淀串联起来,并打通研发工具链,让持续交付过程中的数据能够更顺畅地流转。

流水线:持续交付与持续部署工具

团队首先启动了一个试点计划,对少数团队的软件交付流程进行自动化改造。试点完成时,主要试点团队已经将从代码提交到生产发布的总时间缩短了 90%。

这个项目验证了流水线的价值。流水线是一种让团队定义软件发布全过程的方式,团队可以在其中描述将软件交付给客户所需的所有步骤。流水线的第一步是生成构建产物。随后,流水线会让该构建产物依次经过一系列步骤,直到最终发布给所有客户。

使用流水线的目的,是降低新代码变更对客户造成负面影响的风险。流水线中的每一个步骤,都应该进一步证明构建产物没有缺陷。如果缺陷最终影响到生产环境,团队也希望能够尽快让生产环境恢复正常状态。

流水线上线之初,只能为每个应用程序建模一个发布流程。这一限制反而推动了团队发布流程的一致化、标准化和精简化,从而降低了缺陷风险。在转向使用流水线之前,团队通常会在修复错误和发布主要功能时使用不同的发布流程。

当其他团队看到试点团队通过自动化交付取得成功后,也开始将自己原本手动管理的发布流程迁移到流水线中,从而提升流程一致性。过去采用多种发布流程的团队,现在拥有了一个所有人都可以使用的标准流程。此外,当团队成员把发布流程迁移到工具中时,往往也会重新审视原有方法,并寻找简化流程的机会。

流水线团队的年度目标,是让产品使用量达到“用户愿意自发采用”的程度。换言之,他们需要打造出足够优秀的产品,让人们主动选择使用它。

团队统计了使用流水线将软件部署到生产环境的团队数量,并按照流水线的自动化程度对这些团队进行分类。团队的目标,是使用流水线发布软件,并逐步实现发布流程的完全自动化。不过,他们也注意到,在某些组织中,如果质量评估方式不够合理,可能会促使团队在没有任何测试的情况下,直接采用自动化发布流程。

“多少测试才算足够?”这个问题没有统一答案。它要求团队理解自己所处的运行环境。为了应对这一问题,海外某些公司采用了另一条工程原则:主人翁精神。该原则要求团队从长远角度思考,不会为了短期业绩牺牲长期价值。

软件团队会为测试设定很高标准,并为此投入大量精力。因为团队知道,拥有一款产品,就意味着要为该产品中任何缺陷造成的后果负责。如果问题影响到了客户,拥有该服务的小型工程团队就需要负责处理问题,并实时完成修复。

提升执行速度与响应生产问题之间存在天然张力。正是这种张力,推动团队投入足够多的测试。不过,过度投资测试也未必是好事,因为这可能让团队的发展速度落后于竞争对手。因此,团队一直努力改进软件发布流程,同时避免让发布流程本身成为业务发展的阻碍。

这些团队面临的另一个问题是,各团队之间并没有充分共享软件发布的最佳实践。组织鼓励小型工程团队独立自主地工作,这意味着工程师需要自行解决部署问题。当他们找到能够满足软件发布需求的解决方案时,会通过电子邮件、运营会议和其他沟通渠道,将相关技术分享给其他工程师。

但这种沟通方式存在两个问题。首先,这些渠道本质上是“尽力而为”式的沟通渠道,并不能确保所有人都能学到新技术。其次,领导者虽然会鼓励下属团队采用新的最佳实践,却无法判断团队是否已经做好了真正落地这些最佳实践的准备。在涉及多团队协作、发布排期、任务跟踪、文档沉淀和审批流转的场景中,团队也可以使用 Worktile 这类通用项目协作系统,将任务、项目、文档、日历、甘特图和审批流程集中管理,减少最佳实践推广过程中的信息断层。

团队意识到,需要让所有工程师都能接触到已经沉淀下来的最佳实践,同时也需要让领导者能够识别哪些流水线需要重点关注。

解决方案是,将最佳实践检查直接加入到构建和发布软件所使用的工具中,把最佳实践学习机制化。团队也非常重视一点:某个组织的最佳实践未必适合另一个组织。因此,系统允许不同组织根据自身实际情况配置这些检查。

组织级别的最佳实践检查,让领导者可以根据业务需求调整发布流程。如果领导者希望鼓励或强制团队采用新的最佳实践,可以先在工程师日常使用的工具中添加警告信息。通过在工具中展示消息,可以有效确保团队成员了解新的最佳实践,以及这项最佳实践何时会生效。

实践表明,给团队留出时间学习和讨论新的最佳实践,可以帮助组织检验并改进这些实践。这最终提升了最佳实践本身的质量,也让它们更容易获得工程社区的认可。

团队还系统性地识别需要推行的最佳实践。一个由资深工程师组成的小组列出了导致发布失败的常见原因,并确定了确保发布正常进行所需的步骤。随后,团队基于这份列表构建了一组最佳实践检查。

在这个过程中,团队意识到,虽然大家都希望新的软件版本能够快速、轻松地交付给客户,并且不降低系统可用性,但仍然应该把可用性放在第一位,其次才是速度。这样才能让工程师在安全可靠的前提下,更轻松地完成交付。

持续交付如何降低缺陷影响客户的风险

发布流程,包括流水线和部署系统,都必须被设计成能够尽早识别缺陷,并防止缺陷影响客户。为此,团队需要确保发布流程配置正确,同时确保构建产物能够按预期运行。

部署安全机制

部署安全机制是最基础的部署测试形式,用于确保新部署的构建产物能够正常启动并响应请求。

作为部署后流程的一部分,团队会运行快速检查,确保新部署的构建产物已经启动,并且能够正常处理流量。例如,可以使用部署配置文件中的生命周期事件钩子触发简单脚本,用于停止、启动和验证部署。

团队还会检查当前是否拥有足够的容量来处理客户流量。某些部署系统中会提供类似“最少健康主机数”的机制,用于确保始终保留足够容量为客户提供服务。

最后,如果部署引擎检测到故障,系统应当回滚变更,从而尽可能缩短客户感知到缺陷的时间。

生产前测试

海外某些公司的一项最佳实践,是将单元测试、集成测试和生产前测试自动化,并将这些测试加入流水线。团队通常会坚持执行负载测试和安全测试,也倾向于将这些测试纳入流水线。

这里的单元测试,指的是所有可能需要在构建机器上执行的测试,包括代码格式检查、代码覆盖率检查和代码复杂度测试等。集成测试则包括所有端到端测试,例如故障注入测试、自动化浏览器测试等。关于单元测试和集成测试,已经有很多优秀文章进行了详细介绍,这里不再赘述。

单元测试和集成测试的目标,是验证构建产物的行为是否正确实现了相应功能。验证越充分,缺陷暴露给客户的风险就越低。为了缩短产品交付给客户的时间,团队会尽力在发布流程中尽早发现缺陷。通常,这意味着测试规模越小、运行速度越快,就越能更早获得关于变更问题的反馈。

在海外某些公司的工程实践中,还会使用一种称为生产前测试的技术。在变更部署到生产环境之前,生产前环境是最后一道测试关口。生产前环境使用系统的生产配置,因此其行为与生产系统非常接近。

这种方法有两个好处。首先,生产前环境会测试生产配置,确保服务能够正确连接所有生产资源,包括生产数据存储。其次,它可以确保系统能够与其依赖的生产服务 API 正确交互。

生产前环境仅限拥有该服务的团队使用,绝不会承载客户流量。运行生产前测试,可以有效验证相同代码和配置是否能够在生产环境中正确运行。

生产中验证

当团队向客户发布代码时,不会一次性向所有客户发布。一次性向所有客户发布代码,会让代码缺陷的影响范围变得过大。

因此,团队会采用将变更部署到单元的方式。这里的单元,是指服务的一个完全独立实例。当团队把变更部署到第一个单元,并让第一批客户接触到它时,会非常谨慎。团队只会让少量客户看到新的变更,并收集关于新代码是否正常运行的反馈。

团队会监控金丝雀部署后服务产生的错误数量。如果错误率上升,就会自动回滚变更。例如,在继续部署之前,团队可能要求结果中出现数千个正常数据点,并且没有异常数据点。

如果自动化测试缺少某些使用场景,问题就可能变得更加复杂。团队会努力通过结构化、可重复的测试捕获所有错误,包括自动化测试和手动测试。但即使竭尽所能,也难免会有一些缺陷漏网。

为了检验测试是否足够有效,团队会让生产环境中的新变更保留一段固定时间,并观察非团队成员是否会发现问题。团队曾花费大量时间讨论:变更是否只应该先停留在生产环境中,或者在金丝雀部署之后,应该等待多久再部署到其余部署组。

许多团队最终决定,在进行常规部署之前,除了等待收集足够的正常数据点,还要额外等待一段固定时间。流水线中的等待时间高度依赖团队。有些团队会等待数小时,另一些团队则只等待几分钟。缺陷影响越大、修复问题所需时间越长,发布流程就应该越慢。

当第一个单元中的发布表现良好后,团队会让越来越多的客户接触到新的代码变更,直到最终完成全量发布。和金丝雀部署类似,团队会先确认第一个新单元的部署情况良好,然后再部署到下一个单元。

随着团队对构建产物的信心逐步增强,验证代码变更所需的时间也会随之减少。由此形成了一种发布模式:目标是尽可能缩短从代码提交到第一个生产客户接触到变更之间的时间;但进入生产环境后,团队会逐步、谨慎地将新代码发布给更多客户,并在扩大部署范围的同时增强对变更的信心。

为了确保生产系统持续满足客户需求,团队会在系统上生成合成流量。如果服务无法正常运行,团队需要及时获得反馈,因此通常至少每分钟运行一次合成测试。合成测试的目标,是确保运行中的流程都能正常工作,并且所有依赖项都经过测试。通常,这意味着需要测试所有面向公众的 API。

控制软件发布时机

为了控制软件发布的安全性,团队会建立一套机制,用于控制变更在流水线中的推进速度。常见做法包括使用指标、时间窗口和安全检查来控制软件发布时机。

流水线可以配置为:当指标变化触发告警时,阻止继续部署。流水线中包含大量指标,并且会针对系统、单元、可用区、区域的运行状况,以及几乎所有关键维度设置告警。当关键指标触发告警时,流水线可以暂停部署代码。

不过,有时团队需要部署修复程序,以解决正在触发告警的系统问题。在这种情况下,团队可以对告警阻断进行豁免,以允许变更继续在流水线中推进。

流水线也支持指定时间窗口,只允许变更在特定时段内向前推进。团队可以通过设置时间窗口,限制变更发布给客户的时间。某些海外云服务团队通常倾向于在有足够人员能够快速响应并缓解部署问题时发布软件。因此,这类团队通常会设置时间窗口,使部署只在工作时间内进行。

其他团队则更愿意在客户流量较低时发布软件。如果确有必要,也可以对这些时间窗口进行豁免。

团队还可以根据构建产物的内容暂停流水线。例如,流水线可以阻止包含已知错误软件包或特定 Git 引用的构建产物继续发布。当团队发现某个软件包变更导致性能下降时,就可以使用这一能力。如果只是从软件包仓库中删除该软件包,那么已经包含这个缺陷包的流水线仍然可能继续将错误变更部署给客户。

如何通过持续交付加快软件交付速度

实践表明,各团队普遍非常希望实现自动化。工程团队始终专注于构建功能并发布给客户,目标是提升客户体验和业务价值。持续交付让这一目标变得可持续。

自动化替代了繁琐、易出错且耗时的手动工作,为工程师节省了大量时间。事实也证明,持续部署有助于提升质量。自动化让团队能够更频繁地发布变更,并且通常一次只发布一个变更,从而更容易识别回归问题。

在采用新系统时,大多数团队成员通常都了解需要测试的范围,因此手动测试的难度相对较低。但随着系统日益复杂、团队成员不断变化,自动化就变得越来越重要。

工程团队希望系统尽可能实现自动化。这样一来,团队就可以把精力集中在为客户创造更多价值上,而不是花时间手动管理将变更发布给客户的流程。

多年来,海外某些大型科技公司一直在推进持续改进计划,重点关注向客户发布软件的速度和安全性。持续改进并不是一开始就具备本文提到的所有风险检查和测试。相反,团队是在长期实践中逐步发明并完善识别风险、降低风险的方法。

持续改进计划通常由组织中不同层级的业务领导者负责。业务领导者可以调整软件发布流程,以平衡风险和业务影响。有些持续改进计划会跨多个部门运行;也有一些规模较小的组织,会由其领导者自行推动改进计划。

团队知道,规则总会存在例外。因此,系统需要提供选择性退出机制,以免降低那些需要永久或临时例外团队的速度。归根结底,团队需要对自己软件的行为负责,也需要负责在软件发布流程中投入适当精力。

团队通常从分析问题根因开始,解决问题,并持续迭代。为了让这项工作可持续,需要逐步推进,并随着时间不断改进。

最初开始使用流水线时,许多团队并不确定持续部署是否真的可行。为了帮助团队接纳这一方式,组织鼓励团队先把当前发布流程编码到流水线中,包括手动步骤在内的所有内容。对许多团队来说,流水线最初只是发布流程的可视化界面,并不会自动将构建产物推进到下一阶段。

随着团队信心增强,他们逐渐在流水线的不同阶段启用自动化,直到最终淘汰流水线中需要手动触发的步骤。

再看今天。如今,许多成熟工程团队在编写新代码时,就会以完全自动化为目标。对这些团队而言,自动化是持续发展业务的关键路径。

文章包含AI辅助创作:持续交付实践:如何通过自动化流水线加快软件交付速度,发布者:shang,转载请注明出处:https://worktile.com/kb/p/3974733

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
shang的头像shang

发表回复

登录后才能评论
注册PingCode 在线客服
站长微信
站长微信
电话联系

400-800-1024

工作日9:30-21:00在线

分享本页
返回顶部