写点什么

应用环境能力 | 阿里巴巴 DevOps 实践指南

作者:阿里云云效
  • 2022 年 3 月 10 日
  • 本文字数:4347 字

    阅读完需:约 14 分钟

应用环境能力 | 阿里巴巴DevOps实践指南


编者按:本文源自阿里云云效团队出品的《阿里巴巴 DevOps 实践指南》,扫描上方二维码或前往:https://developer.aliyun.com/topic/devops,下载完整版电子书,了解阿里十年 DevOps 实践经验。


每个软件都无法离开其依赖的运行环境。从代码的编写、调试、测试、上线、运维,每个步骤都离不开对应环境的支持。对于测试环境的争用、环境各阶段需要满足不同应用场景、软件质量的守护、成本与效率优化等诸多诉求,是环境治理和基于环境的变更交付流程规范化的原始需求。


软件行业对效率的要求是非常高的,如何能在现有条件下,提高开发测试的效率是一个很有意义的问题。而在这个问题中,环境,又是一个避不开的话题。如果每个开发都能在自己专属的环境里进行开发调试,不受外部人和物的因素干扰,自然会比较高效。然而,在微服务大行其道的今天,在同个软件模块多人多项目并行开发的情况下,为每个开发都分配一整套包含所有服务的环境,从硬件成本和维护成本上说,都不是一个明智的选择,有效的对环境进行隔离和编排,可以在保证开发效率的同时,优化硬件成本和维护成本。


软件开发通常需要经历多阶段的反复测试验证,是从无到有,从简到丰,从不稳定到稳定的一个过程。正是由于这样的特点,不同阶段中对应的环境特性也会不一样,例如最开始的开发环境,用途就是个人测试;线下集成环境,用于线下的集成测试;预发环境,用于上线前的回归测试及验收;正式环境,用于真正给用户提供服务等等。


用流程将不同的环境串联,能将原来松散凌乱的开发流程变得规范化,再加上合适的测试、验证及准入卡点等手段,实现满足准入条件(如质量标准等)才能交付下一阶段环境部署。通过系统流程化的方式引导开发者来完成安全、高效、可信的变更交付,避免交付过程无规则导致的混乱及安全隐患,同时可以让整个研发流程做到可视化、可追溯、可度量。


总而言之,基于应用环境的变更交付,需要具备两大能力:


  1. 单应用多开发者并行开发互不干扰的测试环境隔离能力

  2. 基于环境的变更交付过程规范化的流程管理能力

解决方案


在微服务架构的大背景下,服务的数量大大增加,使得原本大应用内部模块的复杂性转化为了多个小应用服务之间的调用复杂性。在实际业务场景下,一个整体业务通常会由多个小的应用服务组成,因此,在开发整体业务的过程中,通常涉及到上下游一系列的微服务应用的修改,并且在多个不同业务的开发过程中,会导致同个微服务应用有不同的服务版本,大大增加了微服务之间的联调复杂性,给开发测试过程带来了除开发业务本身外的额外成本。


如何减轻联调的系统成本,让研发专注于自身的业务,是环境治理亟待解决的问题。为了更好的支持研发工作,通过将环境进行专职分类、编排隔离域、交付过程规范化,帮助研发更高效的交付软件产品,阿里沉淀出了一系列在测试环境治理方面的最佳实践。这些实践包括:

代码变更在环境上的递进机制


环境分为两大类:线上环境和线下环境。线上环境是那些操作和数据会真正影响到实际用户服务的环境,例如预发、beta、灰度、生产等。线下环境是主要提供给研发进行开发测试的,目前按使用方式主要分为项目环境、集成环境、基础环境三大类,本篇着重介绍线下环境,其中:


  1. 项目环境:单个应用的单个开发中特性独占的环境,不受其他开发中特性的影响,也不会影响到其他环境的使用。用户可以在这个环境上进行任意的占用调试或破坏性测试。

  2. 集成环境:一个应用的多个开发中特性共享的环境。这个环境主要用来验证多开发中特性在集成以后是否会在业务上产生新的问题或是引入新的冲突。

  3. 基础环境:提供上述项目环境和集成环境的服务依赖,通过在生产环境部署后立即部署基础环境,来保证基础环境提供的服务都是最新的生产环境运行版本,从而保障上述项目环境和集成环境能够稳定的进行开发测试。



流程上,从拉取特性分支开始,自动分配项目环境,在特性分支线下测试基本完成后,将项目环境转为集成环境,同其他特性分支一起测试,在集成环境测试通过后,部署至线上环境,最后在特性分支合并至主干后,用最新的生产版本更新基础环境。

编排隔离域


随着业务的不断增长,当前的测试环境需要支持数万开发工程师的同时使用,对于某些核心业务,有数百个开发中的业务特性同时进行开发测试,而大部分的业务特性都涉及到多个不同微服务的修改,如何保证多个并行业务之间能相互独立,不会相互影响?解决方案是隔离。将同个业务特性的多个不同微服务的环境圈定为一个隔离域,保证相关调用在隔离域内进行,这样就能隔绝其他的业务特性提供的服务对这个业务特性开发测试的干扰,在用户看起来,这个业务特性仿佛拥有了一套完整的环境。


然而,在微服务大行其道的今天,一个业务特性的运行通常依赖着许许多多其他的服务,如果每个隔离域内都将这些服务全部部署作为支撑,是一件成本非常高的事情。我们的解决方案是共享。从路由维度出发,所有隔离域共享基础环境,而保留隔离域自身的项目和集成环境,来达到尽可能的复用公共服务的目的,大量减少了资源成本和环境维护成本。



如图,项目环境 1 的用户和项目环境 2 用户分别拉起隔离域进行联调,相互之间流量隔离互不干扰,隔离域不存在的服务都复用基础环境进行服务兜底,待特性开发分支经过集成、预发验证并发布生产环境后,会自动更新基础环境的基线版本,所以基础环境会持续保持跟生产环境相同的稳定版本,以提供稳定的支撑服务。

基础环境建设


微服务架构场景下从端发起的一次调用,会涉及到调用链路上多个应用提供的服务,但在实际的开发联调中,一条链路上只有少部分的应用需要变更,如果面向开发者需要拉起整个链路进行开发联调,那么会带来低效和成本的问题,所以其中非变更应用可以采用基础环境作为服务支撑。如何保证基础环境的稳定可用就是隔离环境建设的重点。为了保证基础环境的可用性,主要做了三方面的工作:


  1. 降低接入基础环境成本:创建环境通常是一个比较让开发头疼的工作,通常涉及到上下游一系列配置工作,例如修改发布流程、增加 Dockerfile、下发环境隔离文件、准备测试域名、申请相应资源等,为了实现基础环境解决方案的落地,需要实现批量的基础环境搭建,过程中需要具备用户一键搭建基础环境及相应配套的能力,降低基础环境的接入成本。

  2. 代码层面保证服务稳定:基础环境只部署最新的主干代码版本,而且通过系统流程保证每当线上部署完成,发布特性分支代码合入主干分支后,将基线版本自动部署到基础环境,用户无法直接部署开发中的特性到基础环境上,从代码版本管理层面来保证基础环境服务的稳定性。

  3. 可持续流量与自愈、监控保障:为了保证基础环境稳定服务的可持续性,基础环境需要稳定的全链路测试流量及监控,实时监测基础环境的可用性,在发现基础环境服务不可用时,首先通过无人值守的系统手段自愈,如果还是不可用,通过自动工单机制通知并跟踪基础环境的恢复进程。

基于环境的交付流程


从拉取变更代码特性分支,到最终特性分支交付正式发布大致分为几个阶段:创建变更特性分支、变更特性分支功能开发、分支功能调试及自动化验证、多分支集成验证、准入卡点、提交预发验证、正式发布上线(如下图所示)。



其中预发准入卡点是为了保障达到一定质量要求的代码才能进入预发验收,把低质量的代码拦在测试环境持续验证,而自动部署环境则是为了减轻准入卡点给开发者带来的负担,通过自动化手段来对特性分支代码持续验证,收集并沉淀质量数据,为准入卡点提供判断依据。

自动部署环境


当用户通过系统创建特性分支时,会自动为用户的新创建分支申请一个项目环境,该项目环境的配置与基础环境相同,并自动进行资源分配、部署操作。同时,这个项目环境的调用和消息同其他环境相互隔离,它的服务并不会影响到其他环境的调用。


每当用户所创建的特性分支提交了新的代码,都会自动触发系统去进行一次部署及自动化测试验证,通过持续的变更提交+反馈,缩短特性分支变更缺陷的反馈周期,帮助开发尽早修复代码缺陷。

分支版本准入卡点


在研发交付的过程中,通过开放配置流程的能力,可以让业务方灵活的根据业务需要,配置所需的流程步骤,通过流水线步骤的自动推进,完成从测试到上线的整个交付过程。流水线是由一个个组件组成的,每个流水线都可以串联一到多个组件,在阿里巴巴的最佳实践中,在某些环境的部署组件后配置代码质量管控的组件,可以让环境在部署后,马上自动触发测试组件,来验证最新的部署版本是否符合质量要求,从而倒推出最新变化的代码是否符合质量要求。


使用中,为了保证线上环境的安全和稳定,在提交预发环境集成部署之前,会判断所要发布的分支的最新版本是否都通过了准入质量要求,没有达到质量要求的代码变更会被拦在测试环境继续修复验证以保障生产环境的安全。

环境与测试技术的结合


自动化测试一直作为有效的验证手段被广泛使用,然而,在实际使用过程中,用户对于自动化测试用例的诟病并不少,例如:


  1. 测试用例本身有问题,而不是被测试的代码有问题,导致花费了大量时间排查后,在确定本身代码没有问题,才能反查测试用例的正确性,排查成本较高。

  2. 破窗效应明显,一个开发的懒惰导致测试用例失败,其他开发人员并没有足够的动力将测试用例修复,同时由于他人的原因导致测试用例无法通过,也就降低了自身对测试用例的要求,几次下来就会导致测试用例的情况越来越糟糕。

  3. 责任排查难,大多数测试用例只会告诉你这次失败还是成功,但是无法关联比较多次测试用例之间的代码变动情况,当测试用例失败时,用户并不知道上次测试用例成功到这次测试用例失败之间,变动的是哪些代码,带来高昂的定位成本。


针对这样的情况,我们需要从更高纬度的视角去关联代码版本与测试用例,主要分为两点:


  1. 常态化代码主干测试用例回归:在每天夜里系统自动根据主干代码创建应用环境并隔离、部署,然后跑对应的测试用例,由于是主干代码,因此受到的代码干扰较小,如果通过,表示该测试用例有效释放环境,如果不通过,则保留现场,并自动创建发送消息到用例负责人。通过常态化的跑测试,能对比上一天的结果来快速定位问题,并能保证“测试用例本身有问题”时能尽快得到解决。

  2. 测试用例对比迅速定位代码:系统将每次跑测试用例的各个分支代码版本、集成分支代码版本都保存下来并进行关联,当测试用例失败时,能直接定位到上次这些分支测试通过时候的代码版本,将提交记录直接展示给用户,帮助用户定位测试用例失败的原因。


上述过程需要结合环境的一键拉起和流量隔离能力,通过这两点措施,可以让测试用例失败时做到结果可对比、原因可回溯,防止测试用例失败的破窗效应出现。

总结


应用环境解决方案并不仅仅是将应用的开发环境、基础环境搭建起来即可,还涉及到环境的稳定性如何保证,基于环境如何规范变更的流程,基于环境如何提升开发效率等等。环境治理需要站在更高的角度,综合看待上述问题,否则就会陷入环境问题年年治理、年年被吐槽的怪圈。



发布于: 刚刚阅读数: 2
用户头像

云效,云原生时代一站式BizDevOps平台 2021.11.05 加入

云效,云原生时代一站式BizDevOps平台,支持公共云、专有云和混合云多种部署形态,通过云原生新技术和研发新模式,助力创新创业和数字化转型企业快速实现研发敏捷和组织敏捷,打造“双敏”组织,实现 10 倍效能提升

评论

发布
暂无评论
应用环境能力 | 阿里巴巴DevOps实践指南_阿里巴巴_阿里云云效_InfoQ写作平台