测试效率提升之精准测试

1技术背景

每一次底层服务的变动都牵动着QA同学的神经(这次又改了啥?),咨询开发当前版本影响到哪些接口或功能点时,通常得到的回答是就改了一点点或者变动挺大,建议全部回归测试。是否有一种更精确、可量化的方式来度量是改了“一点点”还是“亿点点”呢?基于此我们做了“精准测试”的尝试。

2精准测试架构

在做测试效率提升时,我们发现一种可以让代码“讲话”的测试流程,可以为QA提供指引,让测试策略更透明、更精准的测试手段,对于这种测试手段方式我们称之为精准测试。

我们希望精准测试可以全流程、一站式的为我们提供项目内、项目间的调用关系,指导QA的测试方向,基于此我们前期给出了精准测试的架构图如下:

image

结合网易传媒项目的特点,目前精准测试的最终技术选型为java-callgraph+全链路(网易传媒项目线上问题的追溯定位平台)+Neo4j+jenkins+overmind(测试流程平台),其中overmind触发jenkins的job进行提测版本和master分支的代码diff,最后将提测版本影响的接口邮件给业务测试同学。

3精准测试框架详解

3.1 java-callgraph

在精准测试中,如何获取方法与方法之间的调用链路呢?我们引入开源框架java-callgraph,该工具可以通过静态或动态方式获取java项目的方法调用关系图。java-callgraph的开源地址:https://github.com/gousiosg/java-callgraph。

image

编****译

java-callgraph工具用maven构建的,安装maven并使用mvn install进行打包,打包后再target目录下会生成3个jar包:

javacg-0.1-SNAPSHOT.jar:静态和动态调用图生成的标准jar

javacg-0.1-SNAPSHOT-static.jar:静态调用图生成器

javacg-0.1-SNAPSHOT-dycg-agent.jar:动态调用图生成器

静态执行

java -jar javacg-0.1-SNAPSHOT-static.jar lib1.jar lib2.jar…。其中lib1.jar lib2.jar…为要执行的项目jar包,除了可以直接解析jar包,还可以解析war包。

生成调用****链路树

M:class1:(arg_types) (typeofcall)class2:(arg_types)表示class1的method1调用了class2中的method2

3.2 javassist

获取到Method-Method调用关系后,我们还需要获取项目中每个URL路径与其对应的方法。那么如何拿到Spring MVC中所有RequestMapping以及对应方法和参数呢?

  • 通过传媒微服务调用框架dsf获取:暂不支持
  • 开启mapping端点:springboot项目可用,不够通用
  • 业务方新增mapping接口

Spring MVC框架已提供了获取RequestMapping信息的类方法,获取参数类型可以引用javassit类库。


private String getMethodParams(String className,String methodName){ 

    StringBuilder result = new StringBuilder();    try{        ClassPool pool = ClassPool.getDefault();        ClassClassPath classPath = new ClassClassPath(this.getClass());        pool.insertClassPath(classPath);        CtMethod cm = pool.getMethod(className, methodName);        // 使用javaassist的反射方法获取方法的参数名        MethodInfo methodInfo = cm.getMethodInfo();        CodeAttribute codeAttribute = methodInfo.getCodeAttribute();        LocalVariableAttribute attr = (LocalVariableAttribute) codeAttribute.getAttribute(LocalVariableAttribute.tag);        result.append(cm.getName()).append("(");        ………..        CtClass[] pTypes = cm.getParameterTypes();        String[] paramNames = new String[pTypes.length];        ……….    }catch(Exception e){        e.printStackTrace();}    return result.toString();}

3.3 Neo4j

获取到数据后,如何存储数据可以方便我们回溯查找呢?RDBMS数据库不太方便表示

非结构化连接数据,而且即使将此类数据存储到RDBMS数据库中,检索或遍历性能也会较差。但图形DBMS存储这种连接数据非常简便,将数据作为节点存储在内部,通过关系连接相邻节点,这样检索或遍历是非常快的。

Neo4j是一个世界领先的开源图形数据库,图形数据库数据模型主要包括节点、关系和属性3类构建块,其中圆圈表示节点,箭头表示关系且关系是有方向性的。我们可以用Properties(键值对)来表示Node数据如下所示。

{        "name":"/api/v1/elephant/cindex/batch/xxInterface.do",        "project": "elephant"}

image

同时Neo4j提供了Cypher查询图形数据,Cypher是描述性的图形查询语言、语法简单,功能强大。Cypher提供了“模式”查询方式,模式的格式是:使用()标识节点,使用[]标识关系。查询模式包括节点模式、关系模式、关联节点模式和变长路径模式,精准测试常用后两种。

4精准测试实战

目前传媒后台的重要项目已基本全接入了精准测试,以跟贴项目展开精准测试的执行流程如下图所示:

image

4.1 Jenkins配置Job

  • 新建job

  • 配置jar路径、maps接口、分支名

image

  • 配置job触发器

image

  • 配置解析和邮件发精准测试报告脚本

image

write2neo4j-new.sh脚本主要用来解析节点和关系;getInterface接口解决了从Neo4j数据库中如何根据A方法查询出影响的接口。

举个栗子,通过代码diff已知当前提测版本影响了A方法,可以通过Neo4j的关联节点查询模式查出A方法影响的接口,具体查询语句如下

MATCH ownership = shortestPath((a:InterfaceNode)-[*0..]->(b:MethodNode{name:"A"})) WHERE NOT()-[:has]->(a) RETURN head(nodes(ownership)).name AS interface

checkLog.py脚本用处理日志格式;sendEmail.py用于发送精准测试定制化测试报告。

4.2 基准Job增加跟贴项目

image

4.3 git配置webhook

在跟贴项目git上配置webhook,当有分支代码合入master时触发基准job,将Neo4j库中跟贴的数据完全删除后重新解析master分支,将最新数据入图库以便有效校正数据库数据。

image

4.4 mapping接口

业务提供mapping接口,通过该接口可以获取接口和接口方法的对应关系

**4.**5 精准测试接入overmind

image

4.6 精准测试报告通知

image

5未来规划

5.1 项目间服务调用拓扑图

传媒大部分项目已接入全链路,全链路平台可以实时获取到业务上报的服务调用和响应情况,dsf根据上报的数据画出每次请求的服务调用拓扑图。基于全链路的最终定位和精准测试的需求,dsf开发团队已经支持通过url搜索出服务调用链路图。目前具体项目间url的调用关系目前还在完善中,后续会根据指挥官提供的api将项目间接口调用链路入图库以便完善精准测试。

image

5.2 支持根据接口优先级返回数据

一个大版本的提测可能会影响到非常多的方法或接口,如果精准测试报告中只是统一给出所有受影响的接口会导致看起来比较混乱。将受影响的接口按优先级进行分类,对业务测试同学展开测试工作会更加友好。

6小结目前精准测试已经在测试组内积极进行推广,使用方积极反馈了一些问题并提出了新需求,我们会不断优化精准测试流程,切实有效的为业务测试同学提供指引。

服务推荐

参与评论 您还未登录,请先 登录 后发表或查看评论
©️2022 CSDN 皮肤主题:深蓝海洋 设计师:CSDN官方博客 返回首页
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值