【编者的话】产品的技术架构从单体服务进行微服务化改造,解决了独立构建、更新、运维等一系列问题,但这也对微服务化项目的测试提出了更高的要求和挑战。
本文将从三个方面出发,详细解读项目的微服务化改造会给测试团队带来哪些挑战,同时,测试团队对这些挑战该如何进行高效应对。
近几年互联网项目很多都有从单体服务转变成微服务化的趋势,尤其是一些架构复杂,业务比较广泛的项目,微服务化是大势所趋。微服务化可以解决独立构建、更新、运维等一系列问题,从而解放生产力,促进交付效率和质量。
目前网易云轻舟团队以 DevOps 的方式管理着 30+ 微服务,如图所示,容器服务项目微服务化特征明显、层次划分清晰:
业务的微服务化改造提升了各模块部署上线的效率,但对微服务项目的测试团队带来了新的要求和挑战。
从第一个层面来讲,线上及线下环境多样化和复杂性决定了构建部署次数的频率。好的构建、部署工具可以提高构建部署时间效率从而节约开发人员和测试人员的时间,达到快速交付的目的。因此找到好的构建、部署工具和平台的重要性和优先级都是第一位的。
另一个层面,容器化服务在提测模式,上线模式、分支管理上跟之前都有很大的不同,测试团队需要针对容器化服务特点在提测模式、分支管理、质量评价方面做出一些适配和优化,以适应容器化及微服务架构的特点,将完整的容器化持续集成流水线模式引入,以及将镜像质量评价打入元数据的实践探索。
第三个层面,微服务化的项目对测试的要求更高,具体体现在测试范围更广、测试深度也要更深。例如《 网易容器云平台的微服务化实践(一) 》文中提到的从主工程平滑拆分出用户服务的例子,一次拆分等于之前关于用户服务内部调用的流程都变成 facade + http 接口调用。也就是说接口个数会翻倍增长(内部逻辑拆分成 http 接口),分层测试的模式进一步体现出来,这样就使得测试范围更广了。其次,不同的微服务场景和特点不同,需要测试分析更加深入,测试策略更加有针对性,才能全面覆盖微服务架构下的多种服务类型。对测试人员的能力、测试平台及工具、测试效率要求都更高,在这方面的深入探索很有必要,目标是更好地进行质量 + 效率的全方位保障工作。
下面具体从这三个层面出发,来看下轻舟的测试团队该如何解决这一系列问题和挑战。
OMAD 是网易自研的一套部署管理平台。2017 年轻舟的前身——容器服务的大部分 Web 服务还是使用 OMAD 自动部署平台进行机器构建并远程部署至目标机器。
用户通过 UI 去创建部署任务,并且触发构建和部署动作完成命令下发,构建机器得到命令后按照集成模板生成工程文件,下载源码、编译并且打包上传 nos;目标机器通过 Agent 服务获取部署安装包并且替换模板属性,启动服务。
这个系统在微服务架构不明显的项目中还是比较好用的,但是一旦服务数量增长较多,或涉及到多团队多人员去同时构建部署就会暴露一些弊端。比如构建机器多任务并行时延,nos 上传和下载时延在服务数量同时构建更新时效率会变低。另外多人同时操作同一个服务的构建和部署,有可能会造成冲突导致构建失败。最重要的一点,构建部署环境强依赖于目标机上的环境配置,例如 JDK 和 Tomcat 的版本,这样在线上线下多环境复杂场景下,会导致多环境下同一服务表现有可能不一致。也由此引入了容器化服务时代。
将服务容器化需要解决两个问题:第一个问题是配置文件与代码解耦,可以使用 Docker Container 在启动的时候以 env 环境变量的方式传入,也可以将配置数据服务中心化,目前两者兼有。
第二个问题是构建出来的镜像到目标运行机器之间的传递如何来做,目前是采用网易云容器服务在线上提供的镜像仓库来存储和拉取。当然也可以直接使用 scp 等操作在构建机器上将镜像直接传到到目标机器上。
构建及部署操作分别在构建机器(可多台)以及目标机器上通过 SSH 登录 shell 命令和脚本执行的方式操作。这个阶段是本地更新时代,操作流程如下图所示。
这种方式可以解决 OMAD 时代的多任务并行阻塞问题,以及多人操作构建部署的问题(构建机器多台,即使是一台,由于是脚本化构建,完全是独立进程,互不影响;部署操作只需要更新目标机器的 pod.yaml 模板中的 image 字段即可,几乎不会造成冲突,即使冲突也可以以最近一次更新的镜像 Version 为准更新下载镜像并重新启动容器)。并且可以解决不同的目标机器上环境不同导致的服务表现不同,因为每个服务都运行在标准化的容器中,该容器预置的 Tomcat、JDK 等依赖包都是完全一样的。
在本地更新部署模式下,如果想更新环境就需要 SSH 登录到多个目标机器上更新,另外部署完的模块不能根据需要迁移目标机器,对这些问题进行改进,即转变至集群管理更新模式。所谓集群管理更新模式是指将目标机器分别独立去使用 kubelet 监控管理转变成注册到 Kubernetes Master 上去管理。在 Dashboard 上调用创建 Deployment 来启动对应微服务的部署与更新,可以可视化地查看部署进度和状态,以及可以动态的指定服务部署的目标机器,以便于一台目标机器宕机时可以快速从另外一台目标机器上拉起服务的场景。
在测试人员将线下测试环境更新到这个模式以后,测试人员普遍反馈更新操作比以前方便了。构建操作也可以省去,当开发人员在联调环境自测完毕后,测试人员直接在 Dashboard 获取到开发提测的最新镜像地址,替换镜像地址即可完成服务升级更新,可以开展测试,大大降低了测试人员重复打包、连接目标机器等繁琐的动作时间。
集群管理更新模式如下图所示:
集群管理模式在线下实验稳定后逐步升级至演练环境以及线上。但诸如 kubelet 升级或重启会导致目标机器上全部容器重启的风险等,也还需要进一步解决及评估风险。
我们针对微服务化架构本身,结合测试全流程提出了一套完整的解决方案,包含镜像提测、容器化持续集成建设及质量评价,涵盖微服务化项目从开发、提测、上线、质量归档等全部环节,力求打造质量 + 效率的全方位保障工作。
目前轻舟所有模块都由由代码发布转变为由容器发布,同时通过配置参数环境变量方式传入容器以及配置数据服务中心化等方式支持了镜像多环境发布,这样天然就带来了便利。即多个环境可以使用同一个镜像部署运行服务。测试团队综合评估效率、版本可追溯的因素,提出了镜像提测的方案。即开发人员由提交 commitid 给测试人员的方式转变为提交镜像 tag 给测试人员,一方面可以省去测试人员自己构建代码,更新环境的步骤,另一方面,通过镜像版本化管理以及新引入的质量评价打入镜像元数据等手段来归档提测后的镜像,可以快速追溯到不同质量版本的镜像记录。
代码提测模式如下:开发人员开发自测完毕后,告知测试人员 Git 提交 commitid,由测试人员构建打包,并且部署到线下环境,如果有 bug 的话,修复以后需要再次构建打包部署。并且只能往前增加逻辑,不方便回滚。一旦合入的代码想回退或者拆分就很难操作。另不方便排查引入新增的问题的提交和版本,质量评价只能按迭代而不能按提测版本,一旦有问题只能全量回退而不能回退某些特定提交。
下图为代码提测方式的流程图,黄色代表开发人员完成的内容,绿色代表测试人员所做的动作。
为了更好地追溯镜像版本的质量数据,轻舟测试团队建设了一个跟 Jira 平台打通的质量评价及归档工具,可以实现在 Jira(任务管理平台) 上评价的版本质量自动关联到特定版本的镜像元数据中并归档到镜像仓库中。根据评价的内容判断镜像是否可以满足上线标准。后续追溯历史版本也方便快捷。
质量评价打入镜像元数据与提测及上线的流程图如下所示,黄色代表开发人员完成的内容,绿色代表测试人员所做的动作,其中触发 Jenkins job 是 Jira 回调事件自动触发的,不需要人工参与:
除了提测模式转变、手工测试完然后质量评价自动打入镜像以外,我们还在线下建设了多个微服务的容器化持续集成及质量评价 Pipeline 建设。目的是为了将静态代码检查、单元测试、容器化构建部署、自动化接口测试、覆盖率统计、测试结论自动打入镜像整合成一套流程,可以满足从代码提交到自动化测试到自动发布及结论归档的全流程服务,适用于接口比较稳定、单元测试建设良好、模块依赖少的微服务模块。
目前轻舟团队已在某些独立服务模块中建设这样的全流程实践,如下所示:
当新增逻辑提交后,触发容器化持续集成全流程的启动。
最终测试人员拿到带有自动化测试通过的镜像包,可以继续进行手工测试,继而将手工验证结果通过 Jira 备注触发的方式再次构建手工测试通过的镜像 tag,以此版本镜像提供到演练环境甚至线上环境。
理想情况下,假如迭代内容经过评估后只需要完成自动化验证即可上线,可以直接略过手工测试,将自动化测试通过的镜像 tag 更新到演练环境和线上环境。这样开发人员就可以直接从代码提交到发布全流程 DevOps 化了,历史镜像版本也可追溯查看,可做到快速更新、快速回滚等操作。
轻舟项目的微服务化趋势越来越明显,对测试的深度和广度要求也提升了一个台阶。
轻舟包含微服务中,大概可以分为两类,一类是垂直业务类型,就是从上而下完全都是轻舟项目提供的应用支撑业务,例如 NSF、APM 等业务。第二类是横向业务,通过接入其他外部项目应用,或者被外部项目应用调用来提供服务,例如 网关业务。这两类微服务各有各的特点。首先来看垂直业务型的服务微服务拆分后的测试特点。
分层自动化模式:
目前在轻舟项目中已落地实践线下定时触发分层的接口维度测试,确保各个层次的服务都能按接口和逻辑维度覆盖到,接口覆盖广泛,目前已涵盖所有 http 服务模块,定时为每天一次运行。
自动化策略:接口覆盖、参数检查等可以依赖接口文档快速进行跟开发迭代同步完成,可以确保演练回归、线上回归的效率提升,以及后续迭代的回归效率。逻辑复杂的接口测试取决于接口稳定程度和重要程度后续按优先级补充进行。
端到端自动化模式:
目前已落地实践线上定时触发端到端业务测试,确保用户触发频率高的主干端到端场景能覆盖到,并及时监控,定时为每个场景每小时一次(线上目前已部署 10 个主干场景+),可以快速发现线上用户可能出现的问题。
针对垂直业务分层自动化以及端到端自动化效率显著,针对横向业务,例如网关业务这些本身不提供逻辑接口的服务来说,如何进行有效针对性的测试呢?
拿 API 网关举例,网关的主体功能及在项目中的位置如下:
如果只基于接口的测试则完全不能覆盖 API 网关本身的逻辑,并且接口本身逻辑不属于容器服务的范畴,效率不佳。在这类微服务测试中,测试人员采用 Mock 后端服务、加强独立服务逻辑测试的模式去覆盖。Mock 后的 API 网关如下所示:
API 网关中的认证服务、流控、审计功能通过模拟不同的认证方式、参数组合、场景组合、Mock 接口加压触发流控、日志检索等方式去进行测试覆盖。在单独的环境下,将大部分依赖的外部服务 Mock 掉,然后进行测试场景模拟以及自动化,在微服务化架构下,是一个测试人员必备的手段。这样可以有效排除掉由于依赖方的异常或不稳定导致的问题,能够专注于网关这个服务本身的逻辑和稳定性。
除了基础的功能和逻辑覆盖以外,测试深度不断深入也是微服务化项目的一个必然的要求。轻舟项目测试团队的测试深度挖掘包含多种工具、平台的应用以及专项测试的实践。
微服务化项目的逻辑复杂性决定了测试团队不能只专注于基本功能和逻辑的满足需求,还需要在某些极端情况下验证多个微服务之间合作是否顺畅,例如请求流量大的场景、 服务之间网络异常场景、依赖服务返回值异常的场景,这些都需要在专项测试中完成场景的分析和覆盖。在容器服务项目中,落地了多次专项的异常测试以及稳定性、性能测试。在测试过程中也发掘了不少有价值的场景和异常分支的潜在风险。同时也引入了一些工具和平台,例如性能测试工具、加压工具及平台、异常构造工具及平台、Mock 平台等。
微服务化后,由于分层测试引入的测试的自动化覆盖率要求就更高,由于专项测试需要的手段更加繁琐,自动化复杂度也变得更高,因此相应的测试执行和自动化时间如果没有更好的方法,时间势必会占用的更多。在轻舟项目中,测试人员进行了一系列的效率提升手段,以解决测试深度广度加大以后带来的工作量增加的问题。
上文提到,服务拆分以及接口分层化会导致接口成倍增长,自动化必不可少,编写自动化之前往往是在手工测试执行之后开始编写,有时候甚至等到该接口和功能上线以后再来补齐,这样会造成手工测试在多环境反复执行,因为上线前自动化代码仍然没有编写,因此会造成效率低下。在轻舟项目团队中,测试人员引入了自动化前移以及 tc 平台关联自动化的流程。
自动化前移是指:在开发提测前,测试人员拿到开发接口文档和部分设计文档后就开展自动化编写工作。基于的前提是接口文档全面无变更,这在新版 OpenAPI 模式下已经成为可以落地的现状,因为新版 OpenAPI 模式从需求提出开始就要求接口是确定的,较少变更的,也助力了自动化前移可以落地。测试人员编写大部分自动化代码后,在提测后可以使用较少的时间调试通过,并且补充少量手工测试,以完成这些接口和功能的测试任务,在代码质量达标以后上到演练环境以及线上环境可以快速的适配自动化代码的配置文件以达到快速回归的目的。这样有效的降低重复的手工多次回归工作。
tc 平台关联自动化是指:我们目前所有的执行集合都是由 tc 平台上创建并管理的,即使自动化测试在线下运行以后,仍然需要手工操作对应的测试用例置为成功状态。存在重复操作的工作量。引入 tc 关联自动化以后,通过在自动化代码 case 的元数据中加入 tc 对应用例的 id 的方式,可以将 tc 的用例跟自动化代码 case 关联起来,通过 tc 上触发自动化的回归并且同时回填测试用例的成功或失败状态,节省手工查看用例跟自动化的对应关系并且置位的操作步骤。
下图为轻舟项目中某项目大部分接口自动化以后跟 tc 相关联的执行及回填效果:
接口自动化以及逻辑自动化几乎都可以采用这种手段提高效率,但是轻舟项目还存在着一大部分关于 UI 的测试范围,比如微服务以及镜像仓库的页面也需要测试人员去例行回归。这部分的效率怎么解决呢?
轻舟项目测试团队引入了 SmartAuto 组件去进行前端自动化录制的步骤。并且将录制方式通过培训、合作调研的方式提供给前端开发人员,这样可以使得前端有样式或者逻辑变更的时候快速识别并且重新录制。
测试人员可以使用 SmartAuto 脚本一键回归各环境的前端用例。目前轻舟的前端已经有部分场景通过脚本录制的方式实现自动化,解放了一大部分测试人员回归的工作量。
轻舟测试团队引入了平台基础服务一组自研的 Mock 平台 ,在进行横向业务型微服务测试工作中,快速使用 Mock 平台去将依赖服务 Mock 掉,并完成微服务本身逻辑的测试及自动化工作。经实践,轻舟已使用 Mock 平台构造比自己使用 Moco 等 Mock Server 工具构造场景时间大概节约了 80%,在异常专项测试以及横向业务型微服务测试执行中大大提升了执行效率。
本文是《网易容器云平台的微服务化实践》系列文章之二,从三个层面讲述了目前容器服务的测试团队所做的一系列实践工作,关于容器部署模式、提测模式、容器化持续集成等活动已经在部分模块和服务中有一些落地实践,也一定程度解决了微服务化后测试团队面临的质量效率双重挑战的问题。在后续的测试工作中,需要进一步固化微服务容器化提测流程,质量元数据归档等步骤,并且推广给其他微服务化架构项目团队。在测试具体工作上引入的一些实践活动效率提升的手段也效果显著,后续需要再挖掘一些增强测试探索的理念和实践,从而为项目的质量保障工作以及打造团队影响力做出贡献。