文章整理自TiD2019质量竞争力大会
陈磊(新奥集团中台质量总监)
《自动的自动化测试——智能化一站式API测试服务》演讲
前言
TiD2019质量竞争力大会邀请了新奥集团中台质量总监陈磊为参会者带来《自动的自动化测试智能化一站式API测试服务》精彩演讲。陈磊从智能化测试框架、智能化API测试框架打造过程、自解耦&自测试的检测装置和智能化解耦服务与智能化测试结合四方面讲述API测试服务。
智能化测试框架
智能化测试框架当今主要两种叫法,一种是AI Driven Testing,另外一种是AI for Softwaretesting。这两种叫法都是指用智能化AI的思路或者方式来推进测试的过程化进程。那么我们今天统称为AI Driven Testing,简称AI-DT。现在开发领域比较有名的aixcode,就是通过AI技术实现了人机结对编程。那么智能化的测试有什么优势和特点呢?第一点是精准度高,可以处理长时间复杂、枯燥、反复的工作,避免人工反复执行流程导致认知疲劳。第二点是能突破人的固有限制,可以完成大量用户同时进行测试的任务,也可以在短时间内执行更多的测试任务,这里面不是说的性能测试,而是更加接近于终端用户访问行文的测试。第三点是赋能测试、赋能研发,提高流水线自动化程度。第四点是具有高测试覆盖度,通过实时测试调整测试策略与基线,缩短开发周期,可以更快地交付。
智能化测试框架分为6级:
L0 原始级
L1 辅助级
L2 部分自动化级
L3 有条件的自动化级
L4 高度自动化级
L5 全量自动化级
L0
原始级
测试工程师还是在做测试用例设计、执行、回归、修复后再回归。没有专职的人写自动化的脚本。测试人员按需撰写脚本,遇到较大变更的时候还要检查脚本是否有效。
L1
辅助级
测试框架能帮助测试工程师完成一些枯燥乏味的工作,通过一些算法完善测试脚本并将测试结果发送给对应的工程师,由工程师来决策测试结果。
L2
部分自动化级
自动化测试的算法可以自我容错,不需要大量的维护工作,会按照测试用例去执行与识别,不会影响执行流程。然后它会把测试结果发送给测试工程师,由工程师决策测试。
L3
有条件的自动化级
测试工程师能建立自己的测试基线与准则,在测试过程中会定位Bug,但是不会设定Bug的优先级别。测试人员会根据工期和严重程度和对整个流程的影响定位Bug,再把它放到缺陷管理系统里。
L4
高度自动化级
系统能模拟类人的行为,进行并执行一些逻辑脚本或者业务脚本的撰写,达到一种完美的人机交互。它可以将测试结果定优先级,会根据严重程度发到测试管理系统,但不会对没有样本的做定义,还需要人类决策。
L5
全量自动化级
系统能够完成过程化的测试,了解产品的变更,知道产品的黄金流程,同时还会将问题完全反馈。测试工程师在这里仅仅做的是算法逻辑的维护、规则的维护。
目前所有的测试框架大部分都是L1级,有一小部分在向L2级发展。但是要发展到L3级及以上还需要很长时间的技术探索。接下来,陈磊给出了一些比较好的或者是比较有名的商业化的工具平台用来测试。
Testim.io通过机器学习创建、执行并且维护自动化的测试。Testim.io强度功能方面的端到端测试,用户视角的测试。这个工具可以通过不断地运行自我学习,增加测试用例的可信度和完善程度,同时也提供了通过JavaScript和HTML的方式撰写负载逻辑场景的入口。
Test.ai是一个移动端的AI-DT解决方案,通过回归测试的各种效率特性的手机,更好地分析和评价一个APP的质量。
Functionize通过机器学习创建测试(并不是创建测试脚本),并且可以在短时间内执行大量的多场景的测试,并给出深度的分析结果。
Applitools:一种自适应算法进行可视化测试,基于ML自组织,自维护testsuite,自识别有效更改,并确定bug。
Appvance.ai:实际用户映射方式,通过认知自动完成测试脚本
MABL:没有测试脚本,可与ci集成,能够自识别有效修改,不断地测试,保证可靠稳定的交付成果。MABL提供试用,访问它的网址就可以,你提交你的app,MBL会给你按约定规则发送测试报告。这个是有8个前Google工程师创建的,第一轮融资就拿到了8000万美金。这说明行业对AIDT方向的很有信息。
上面都是商业化的AI-DT平台。开源的AI-DT框架有如下:
Test.ai开发了一个appium3.0的开源插件。这是基于图像进行功能识别。这里面有一些L4级框架,例如自己提供了一些图像识别的样本库。当输入APP图标的时候,它就会通过训练找到这个模型训练结果的关键要素,识别这个图标,但有一些比较小众的图标的设计,有可能还不太容易识别。
retest开源框架是服务于WebUI的开源框架。它与L3级框架类似。WebUI脚本在页面元素做更改后,元素的定位器的ID会发生变化。执行回放脚本时,retest不会报找不到元素的错误,会给它更多的定位保障整个定位不会产生异常过程。
以上平台都是UI层的,其实还有好多平台是单元测试的。很多老师或者相关专家很早就开始研究基于静态分析的单元测试,具有很长时间的成熟度。基于文档、注释的单元测试可以生成单次脚本。还有的是基于随机的单元测试,这是出现很早的一种解决方案。最后是基于搜索的单元测试,例如活跃度比较高的EvoSuite工具。
EvoSuite是由几个大学开发维护的。它可以生成测试用例,生成mock数据。目前这个项目是由Google和Yourkit支持的,Yourkit是GDM的故障诊断工具,它提供了四种方式,第一种就是通过命令行jar包调用。还有两种是插件,Eclipse或IntelliJ IDEA这两个IDE里面的插件。最后一种是Maven plugin。这种方式使用比较多。
EvoSuite的设计师CS结构。它运行或者生成测试用例时会有消耗很多资源。目前这个框架是很常用的一个mock框架,会自动把所有的外部依赖都mock掉并生成测试用例,还会自动的mock掉所有的外部依赖。当使用这个框架生成单元测试时,它必须在项目里,而且不能生成完以后就删掉它的pom引用。它在生成的每一个case中会配另外一个脚手架文件来保证所有的用例是在它自定义的沙盒里去运行的。
但是这个工具在用的过程中会遇到的几个问题,第一个就是它运行的时候会有自己的字节码注入机制,这时如果用jcoco跟它一起运行的时候,由于EvoSuite和jcoco在生成单测或者运行单测都会启动自己的字节码注入的机制,但EvoSuite会先启动,有可能jcoco收集不到代码覆盖率,jcoco的自解码录入机制就不会起效果,也拿不到任何代码覆盖的数据。第二个是用EvoSuite去生成单测脚本时没有结果。这是因为生成过程中会在原来的代码中加入自己的自解码,超过了JVM的单个函数不能超过64K的上限。目前,除了拆分没有解决办法。
智能化API测试框架打造过程
随着微服务化和中台化的不断发展,绝大部分系统的被测件没有UI层。这就需要改变API测试这种行为或者工作模式。然而目前大多数团队人员,虽然是业务测试出身,但是存在着代码的写作能力弱或未能真正使用自动化测试等问题。
如何将好的工具、代码或框架进行熟练运用?陈磊将日常工作中的经验进行了分享。第一个是脚手架,只需要知道Java的基础便可投入脚手架新建测试工程,设计你的测试数据,写测试脚本,做一些简单的封装。第二个是类似工具的手册,手册里有一些封装和上下文获取的参数池,参数池提供的例子很多,但是照着它写一个新的接口会有不一样的地方。第三个是特殊的数据结构,用代码来撰写测试脚本。它基于前期的二叉树的结构,每个树的节点相对复杂,里面包含了名字(Name),类型(Type),左孩子指针(Leftchild),右孩子指针(Rightchild)和父亲指针(Father)。根节点Name是对应的API接口的接口名,Leftchild是基本类型参数,Rightchild是复杂类型参数,参数基本上是Java里面的整型、字符串。
以具体接口HouseHold为例陈磊简述了树的生成。这是一个复杂的JavaBean,具有两个基本类型,一个是户口地址,一个是户口属性。算法分析后生成Household接口的树形结构。第一个根节点是API的Name,类型是返回值,第一个Leftchild指向第一个基本参数,第一个Rightchild是第一个复杂类型。它的第一个基本类型的Leftchild是他的第二个基本类型的参数,但它没有Rightchild。陈磊团队通过深度优先的查找与整理和内部定义的结构,生成测试脚本。其脚本通过Class loader来识别被测接口。虽然拿不到第一层的入参参数,但是知道参数类型,不影响生成测试脚本与测试用例。每个测试用例只有两个部分,一部分是固有的逻辑,另外一部分是测试数据。
为了让测试数据简单或容易获取,提高测试工作效率。陈磊介绍道,团队在日常工作中设计了一个TDS(测试数据服务)。测试数据服务在第一次接口被配置到测试平台以后,首先需要分析入参的类型、实体与属性,如果在开始阶段不被识别时,需要测试工程师人工标记后就会生成。
TDS里面有三种类型,第一种类型是加入以前模糊测试的数据,里面引入开源工具。第二种是数据的实体类,在类里面根据业务定义大量数据实体。整个框架的主要思路来自于Facebook一个的开源框架,它提供数据实体和数据属性,在产生交互时生成给用户。还有一种是智能化的,通过对线上接口与反应器,把线上一部分流量存到大数据平台后,推动聚类分析找到一些有聚类现象的数据,再把这些数据拿到整个数据服务里。有特殊的指定需求时,需要人工配置调用模糊数据mock。
为了方便接口测试脚本和数据服务发生交互,陈磊团队模拟出HiL语言,分为有两种,一种是没有约束条件的,另一种是有约束条件的。没有约束就是产生随意的条件,而有约束条件的需要生成一个Name,要把它发给测试数据服务并返回嵌套结果,这样就可以变成程序跟程序之间的交互,来完成数据的提供。
那么,如何进行测试呢?先将被测程序放到测试平台,随后人工标记接口参数对应的实体属性,分析测试的这些入参后,通过算法和去重生成一种测试数据并匹配策略。最后调用测试执行和测试脚本分析,执行测试用例并收集整个代码包括全部分支的覆盖率,若分支没有完全被覆盖,会生成一条尽量让它去覆盖到没覆盖分支的数据。最终会将测试报告和代码覆盖报告一起发到报告的服务里,按项目维度或时间维度查看每次的测试结果。
自解耦&自测试的检测装置
随着微服务越来越多,微服务之间的依赖也越来越复杂,被测件依赖可能不稳定,测试无法进行。这样服务之间的调用要等到外部依赖稳定才能开始测试。它第一可以生成测试脚本和测试数据,第二可以做全部的外部解耦。它自己制造了一个沙盒,只测试逻辑。依据脚本生成算法,把所有的外部依赖生成一个独立运行的服务,然后将其注册到注册中心里,作为所有的外部解耦的服务。解耦首先找到被测系统,分析全部的consumer,然后获取Pom依赖,然后生成单个服务解耦jar包并在容器里运行。
当所有的外部依赖都稳定后,会替掉原来consumer,把里面所有的别名都生成新生成的别名。这样在容器里面部署完后,它是一个用自己调用方式做好的被测件,而且所有解耦的jar包的数据都来自于自己测试数据服务,相当于建立了一个沙盒机制,只是测试这次被研发去更改的系统。还包含一个Alias管理和一个集成服务,Alias主要是按项目生成一些假的别名,同时会管理和监控这些别名的心跳。集成服务让被测件和原有服务产生联系,这样会生产所有集成测试。
智能化解耦服务与智能化测试结合
目前, API会用EvoSuite做先验,然后通过自动化测试脚本和解耦服务完成解耦部署。等测试完成后把报告发到聚合报告里,最后部署集成环境人工进行测试。
大会简介
质量竞争力大会,英文名称TiD,是研发创新顶级峰会,由中关村智联软件服务业质量创新联盟主办,中国软件行业协会系统与软件过程改进分会、北京软件和信息服务业协会智能分会协办。TiD质量竞争力大会秉承追求行业高度(Top)、技术创新(innovation)、专业深度(Depth)的目标,致力于打造最具影响力的国内软件研发创新者顶级交流平台。