大纲
录制回放技术
微服务下的Mock技术
常见自动化测试框架
精准测试技术
一、录制回放技术
在日常的测试工作中我们或多或少总会遇到下列问题:
1)服务架构升级或重构,需要验证原始接口逻辑,对原有的一堆接口做回归
2)对于业务逻辑复杂的场景,每个迭代版本都需要大量的时间用于回归测试
3)编写自动化用例时复杂场景造数麻烦,日常自动化维护成本高
4)构造压测模拟数据麻烦…等等
那么从服务的所有环境来看,仅线上环境拥有场景丰富、数据真实、覆盖全面的条件,那么我们将线上环境的请求数据获取下来,在指定的环境中模拟用户请求基本上可解决或者优化上面的这些问题。因此有必要需要对流量回放这项技术探究一下,首先从资料总结和自身搭建讲演来讲,总结流量回放的大概流程可为:流量录制 - 数据持久化 - 回放计划 - 环境维护 - 流量回放 - 结果比对。其次,所谓工欲善其事,必先利其器,下面我们看一些常用的流量回放分类以及工具的优缺点。
根据流量录制的位置大致可分为:基于web服务器录制、基于应用层录制、基于网络协议栈录制。
Web服务器录制
方案:在服务上定制化代码
优点:请求类型比较多样
缺点:不通用,维护成本高,会占用大量线上资源
方案:在网关或基于AOP切面进行录制
优点:对代码无侵入、实现相对比较快捷简单
缺点:会占用线上部分资源、可能会对业务有影响
常用工具:Nginx插件-ngx_http_mirror_moudle、Java-sandbox
方案:直接监听网络端口,复制数据包方式录制
优点:基本对应用无影响
缺点:比较偏向底层实现成本较高
常用工具:goReplay、tcpCopy、tcpReplay
ngx_http_mirror_module
优点:
原生模块支持,在nginx 1.13.4版本后内置该模块
支持配置多份镜像放大流量
配置比较简单,nginx-server将流量复制到mirror后无交集,达到对真实流量无影响目的
缺点:
修改配置后需要执行“nginx -s reload”命令使变更生效,线上环境不建议这么做
实际业务中经由nginx转发的模块较多,无法筛选指定请求
只支持录制http流量
mirror为子请求,当mirror未结束时,主请求的内存无法释放,可导致nginx性能下降甚至阻塞
项目地址:https://github.com/session-replay-tools/tcpcopy
优点:
使用线上的真实数据
适合高并发场景
对目标服务器基本无干扰
支持复制基于TCP任意层协议的流量
缺点:
由于只做数据包复制未做流量异常鉴别,可能导致异常数据进入目标服务器
无法对应用层的数据进行筛选和修改
可能会丢失数据包导致请求丢失
项目地址:https://github.com/buger/goreplay
优点:
轻量程序基本无需配置,环境准备简单
程序资源消耗少,无侵入应用运行环境
提供不限制语言的插件机制,方便拓展
缺点:
社区版仅支持录制http协议,且与核心逻辑耦合,应用面不广泛
大公司使用少,整体成熟度不高
项目地址:https://github.com/alibaba/jvm-sandbox-repeater
优点:
通过字节码增强的方式可以直接录制Java方法、子调用
对业务代码0侵入
模块功能丰富
缺点:
对服务运行环境有一定侵入
在挂载瞬间会占用较多的机器资源,当业务量大时可能会导致服务夯住
当前功能不完善,需要代码开发能力
通过技术方案可以方便我们利用线上真实流量验证压测、自动化、回归等场景,根据自己实际的需求选择合适的工具,但一切以不影响线上服务的稳定可用为前提。也期待后续会有更多的更完善的流量回放方案
MockServer 还包括一个代理,可以检查所有被代理的流量,包括加密的 SSL 流量,并支持端口转发、Web 代理(即 HTTP 代理)、HTTPS 隧道代理(使用 HTTP CONNECT)等功能。
WireMock 是一个 Http 模拟服务,其核心是 web 服务,WireMock 可以为特定的请求(stubbing)提供固定的响应,并捕获传入的请求,以便后面校验(验证)。WireMock 可以作为第三方库在项目中使用,也可以作为单独的进程启动。
主要特性包括:
Hoverfly是一个轻量的API服务模拟工具(有时候也被称作服务虚拟化工具),可以创建应用程序依赖的API的真实模拟。Hoverfly用于创建可重复使用的虚拟服务,在CI环境中替代缓慢和不稳定的外部或第三方服务,还可以模拟网络延迟,随机故障或速率限制以测试边缘情况。此外,Hoeverfly提供多种运行模式,可以对HTTP响应进行记录,回放,修改或合成。
主要特性包括:
创建可重复使用的虚拟服务,在 CI 环境中替代缓慢和不稳定的外部或第三方服务
模拟网络延迟,随机故障或速率限制以测试边缘情况
使用多种编程语言扩展和自定义, 包括 Go,Java,Javascript,Python
导出,共享,编辑和导入 API 模拟数据
提供方便易用的命令行界面 hoverctl
Java 和 Python 的语言绑定
REST API
使用 Go 编写,轻巧,高性能,可在任何地方运行
提供多种运行模式,可以对 HTTP 响应进行记录,回放,修改或合成。
以下是 MockServer、Hoverfly 和 WireMock 之间的简要对比表格:
特性/功能 | MockServer | Hoverfly | WireMock |
---|---|---|---|
支持的协议 | HTTP, HTTPS | HTTP, HTTPS, TCP | HTTP, HTTPS, TCP, SMTP, LDAP, gRPC, WebSockets, GraphQL, SNMP, Telnet, SSH, Netconf |
动态生成响应 | 是 | 是 | 是 |
请求匹配功能 | 强大的匹配功能,包括 URL、HTTP 方法、请求头、请求体等 | 强大的匹配功能,支持 JSONPath、XPath 等 | 强大的匹配功能,支持 URL、HTTP 方法、请求头、请求体等 |
动态端口分配 | 是 | 是 | 是 |
录制和回放 | 是 | 是 | 是 |
客户端支持 | Java、JavaScript、Ruby | Java、Go、JavaScript | Java、JavaScript、Ruby、Scala、Go、Groovy |
官方文档 | MockServer 文档 | Hoverfly 文档 | WireMock 文档 |
GitHub 仓库 | MockServer GitHub | Hoverfly GitHub | WireMock GitHub |
三、常见自动化测试框架
什么是自动化测试框架?
自动化测试框架是为自动化测试脚本提供执行环境的支架。该框架为用户提供了各种优势,帮助他们有效地开发、执行和报告自动化测试脚本。它更像是一个专门为自动化组织测试而创建的系统。简而言之,我们可以说框架是各种指导方针、编码标准、概念、过程、实践、项目级别、模块化、报告机制、测试数据注入和其他支持自动化测试的元素的建设性混合。因此,用户可以在自动化应用程序时遵循这些准则,以利用各种生产结果。
这些优势可以采取不同的形式,例如易于编写脚本、可伸缩性、模块化、可理解性、过程定义、可重用性、成本、维护等。因此,为了获得这些好处,建议开发人员使用一个或多个自动化测试框架。此外,当一群开发人员在同一应用程序的不同模块上工作时,当我们想阻止每个开发人员实现自己的自动化方法时,我们需要一个统一的标准测试自动化框架。
组成框架的组件一般包括:
自动化测试框架的类型
市场上的自动化测试框架可能因支持不同的关键因素(如可重用性、易维护性等)而有所不同。如以下几种类型:
●基于模块的测试框架
●测试库架构框架
●数据驱动测试框架
●关键字驱动测试框架
●混合测试框架
●行为驱动开发框架
常见自动化测试框架
1. 单元测试框架
几乎所有的主流语言,都会有其对应的单元测试框架,下面简单介绍一下python,java,C#三种语言的常见单元测试框架
1.1 Python
python常见单元测试框架包括Unittest, PyTest
Unittest
unittest单元测试框架不仅可以适用于单元测试,还可以适用WEB自动化测试用例的开发与执行,该测试框架可组织执行测试用例,并且提供了丰富的断言方法,判断测试用例是否通过,最终生成测试结果。
unittest为python内置库,不需要单独安装(好像也和版本有关系)
PyTest
pytest是一个非常成熟的全功能的Python测试框架,主要有以下几个特点:
简单灵活,容易上手
支持参数化
能够支持简单的单元测试和复杂的功能测试,还可以用来做selenium/appnium等自动化测试、接口自动化测试(pytest+requests)
pytest不是python内置库,需要单独安装
1.2 Java
Java常见单元测试框架包括Junit、testNG
TestNG
TestNG是一个测试框架,其灵感来自JUnit和NUnit,但引入了一些新的功能,使其功能更强大,使用更方便。
TestNG是一个开源自动化测试框架;TestNG表示下一代(Next Generation的首字母)。TestNG类似于JUnit(特别是JUnit 4),但它不是JUnit框架的扩展。它的灵感来源于JUnit。它的目的是优于JUnit,尤其是在用于测试集成多类时。TestNG的创始人是Cedric Beust(塞德里克·博伊斯特)。
TestNG消除了大部分的旧框架的限制,使开发人员能够编写更加灵活和强大的测试。因为它在很大程度上借鉴了Java注解(JDK5.0引入的)来定义测试,它也可以显示如何使用这个新功能在真实的Java语言生产环境中。
1.3 C#
C#常见单元测试框架包括NUnit
2. Web自动化测试框架
Selenium
web应用程序最流行的开源测试自动化框架之一。Selenium还可以作为许多其他测试工具的基础,因为它具有跨平台和跨浏览器的功能。Selenium支持多种编程语言,如Java、C#、PHP、Python、Ruby等。它易于维护,因为它拥有最大的在线支持网络之一。Selenium可以通过广泛的库和api进行高度扩展,以满足每个人的需求和需求。Selenium是测试人员的首选,因为它可以编写更高级的测试脚本来满足各种复杂程度。它为测试编写提供了一个回放工具,无需学习特定的脚本语言。
Robot
如果是希望在测试自动化工作中使用python测试自动化框架,Robot框架是最佳选择。Robot框架基于Python,但也可以使用Jython(Java)或IronPython(.NET)。Robot框架使用关键字驱动的方法来简化测试的创建。Robot框架还可以测试MongoDB、FTP、Android、Appium等。它有许多测试库,包括Selenium WebDriver库和其他有用的工具。它有很多API来帮助它尽可能地扩展。Robot框架使用的关键字方法对于那些已经熟悉其他基于供应商的关键字驱动的测试工具的测试人员非常有用,这使得他们更容易过渡到开源。
3. 性能自动化测试框架
JMeter
JMeter是一种开源的负载测试工具,它可以模拟多种类型的负载,并测试应用程序在不同负载下的性能表现。JMeter可用于测试各种类型的应用程序,包括Web应用程序、SOAP和REST Web服务、FTP和数据库服务器等。
JMeter使用Java语言编写,可以在Windows、Linux和Mac OS X等操作系统上运行。它提供了丰富的图形化用户界面(GUI),使得用户可以轻松地创建和运行测试计划。JMeter还支持命令行模式和分布式测试,这使得用户可以在多台计算机上同时执行测试以模拟更大的负载。
JMeter支持多种类型的测试,包括负载测试、压力测试、功能测试、性能测试、并发测试和分布式测试等。用户可以通过插件扩展JMeter的功能,如增加对特定协议的支持或者添加自定义的处理器。
JMeter的主要组成部分包括测试计划、线程组、取样器、逻辑控制器、监听器和配置元件等。用户可以使用这些组件构建复杂的测试场景,并对测试结果进行分析和报告。
总之,JMeter是一款功能强大、易于使用的负载测试工具,可以帮助用户测试应用程序在不同条件下的性能表现,从而发现潜在的性能问题并进行优化。
四、精准测试技术
传统的软件测试技术主要基于测试人员对业务的理解,但由于经验与真实业务数据的差距,肯定会测试不充分,所以很多情况下,测试结果无法精确保证对软件质量的定义和判断。
精准化测试技术从字面理解,就是非常准确的测试,这意味着要用量化的数字说话。
精准化测试是一种可追溯的软件测试技术。通过构建一套计算机测试辅助分析系统,对测试过程的活动进行监控,将采集到的监控数据进行分析,得到精准的量化数据,使用这些量化数据进行质量评价,利用这些分析数据可以促进测试过程的不断完善,形成度量及分析闭环。
精准化测试的核心思想就是:使用非常精确和智能的软件来解决软件测试的问题,从根本上引领软件测试从经验型方法向技术型方法的转型。质量的评估不再靠经验,而是通过精准的数据来判定。
早在十年之前,测试行业就已经有很多人陆续投入精准化测试的技术研究。2019 年开始,精准化测试在业界大热,其中,蚂蚁金服的两位同学周为、翟帅在 MTSC 测试开发大会上分享的《进击的覆盖率 —— 实时代码染色技术》,可以说把精准化测试技术提到了一个新的高度,并迅速推动了在业界的应用普及。
百度利用覆盖率增量从回归数据中提取有效覆盖
精准定位用例数据与覆盖率关系
代码行为流建模
星云测试
有赞集成测试覆盖率统计实践
蚂蚁金服的代码实时染色
常见的调用链分析方法主要有:
基于 AST 的语法树分析
基于字节码分析
调用链的动态分析方法:
基于 gdb/jdb 的调试器分析
jvmti/jvmpi
jvm-sandbox、bytebuddy、btrace 等工具
代码覆盖率其实是一种丢失了时序结构的调用链数据。调用链的本质是一种具备调用节点顺序的列表,覆盖率则是为了方便分析把列表降级成了集合。
简单的实现精准化测试方案:
使用 SonarQube 作为覆盖率与测试用例的分析平台
使用 JaCoCo 作为代码覆盖率的分析工具
使用 JaCoCo-cli 实现对单个用例的覆盖率收集
使用 Scanner 完成覆盖率导入
调整 SonarQube 平台中覆盖率展示的信息,加入关联测试用例的展示,方便在未覆盖的代码附近可以找到最接近的测试用例
软件测试示波器
在功能测试过程中自动分析程序运行的一些数据指标,以波形的形式进行实时输出。示波器是一种实时的监控,实时的计算测试过程数据并展现。
执行一个测试用例以后,精准测试通过程序自动的记录和显示这个测试用例执行的代码。如果测试人员关注某一些代码行,它可以追溯出哪些用例在执行过程中运行过这段代码。
根据代码的变动范围来直接精确的定位需要回归的用例,这样使回归测试所需的时间更短,回归的范围更准确。
精准测试覆盖率形式多样,最高支持标准MC/DC(修订的条件/判定覆盖)的100%覆盖率要求。
根据缺陷与用例的对应关系,快速找到执行用例对应的代码行。
五、字节跳动SmartEye-智能化精准中台实践简介
字节跳动在代码覆盖率监测平台基础上,建立了 SmartEye-智能化精准中台,帮助研发团队快速定位代码变更影响域,精准推荐测试用例/自动化巡检任务,为业务减负,为研发团队提效。
用例知识库
我们前期先建设了基础代码覆盖率监测平台,收集程序运行时的动态代码覆盖率数据,以此为基础来构建用例知识库。
人工用例录制,利用内嵌到客户端的 SDK,提供 UI 界面供用户进行录制操作,同时由 SDK 内部保障录制过程中数据清理,采集,上报。用例录制结束后由 SDK 对当次录制数据进行上报,服务端实时解析,落盘用例知识库,供后续数据分析推荐,并及时给予用户录制反馈。
自动化用例录制全流程无人工干预,录制时需要以单个用例为分割,记录单条用例的代码覆盖率数据和用例的关联关系。SmartEye 结合客户端高级调试模式 SDK,使用公司基础长链接服务控制自动机架的指定设备进行用例数据的录制/停止,全流程自动化,可以以很小的成本,批量录制客户端自动化用例。
利用当前变动信息、调用链信息、覆盖率信息等基础能力,建设代码-用例的映射数据集,以索引形式存储海量用例,为测试用例推荐等上层服务产品提供数据基础。基于用例的关联方法、关联代码块、上下游调用链路以及对应覆盖率等信息,建设不同粒度不同版本的调用信息-CaseIDs 倒排索引服务,直接支撑推荐引擎的用例召回功能;此外,服务适配用例录制接口,实现了用例录制->用例信息解析->用例信息入库->索引生成的全流程自动化处理,并支持双端、人工 &&自动化用例的多维度用例独立存储。
推荐引擎
准确定位 MR 的代码变动信息及其代码调用上下游影响域,能够帮助后续精准测试准确分析与之关联的测试用例,提升测试充分性与问题拦截率。
我们利用公司 CodeGraph 平台的双端静态代码调用链分析能力与整体调用链路拓扑数据,完成基于 MR 的变动 DIFF 分析以及上下游调用链分析,并针对变动 DIFF 部分,完成代码变动率的统计。
关联用例召回与多样性平衡
基于改动影响的边界范围,召回对应方法、代码块、调用链路关联的用例集合,聚合去重后生成用例召回集合;
用例召回集合中,存在大量冗余用例。为实现向线上高频调用模块的测试倾斜,增加多样性控制逻辑。
基于对应方法 &&代码块的关联用例数、用例覆盖率以及线上热度归一化指标,生成对应方法 &&代码块的多样性控制因子,并最终将该因子作用在用例排序与推荐集生成阶段;
策略层
针对底层代码关联大量测试用例、用例路径多样性不足等导致的测试冗余问题,通过向业务侧赋能,结合业务方的先验知识体系,利用用例定向投放、底层代码规避等策略,以更加贴近业务的策略形式,在保证测试质量的同时,进一步降低测试冗余,提升测试效率。
整体方案
使用效果
目前,我们与火山客户端等研发团队一起,搭建了字节跳动精准测试平台 Cover,致力于为公司内所有产品线研发团队提供标准的精准测试解决方案,期望在保证质量的前提下为业务提效。
该平台已在火山、抖音、西瓜等团队客户端迭代流程中落地,并取得了不错的效果。其中一个典型业务线利用精准测试,在保证 100%拦截全量测试用例可发现问题的基础上,提升人效约 40%,具体数据如下:
目前,SmartEye 精准引擎每日推荐用例数 1K+,效率提升约 40%。借助 SmartEye 的能力,业务可以精确评估变更影响,清晰代码变动之后需要测试/回归的用例集。
基于 SmartEye 的精准测试,在字节跳动的落地得到了很多团队的支持,包括火山、抖音、头条、基础架构等多个研发团队,业务落地当前正在持续推进中。后续重点,我们将延伸 SmartEye 的精准能力,覆盖各种类型的测试用例与测试需求,在更大范围内成为 DevOps 基础服务,为更多的研发团队提效。
我们相信,越来越多的智能化测试工具落地,将会加速质量工程领域的变革,推动国内质量工程技术水平走到全球质量工程工业界前沿。
联系客服