美文网首页
Avatar--行走的接口自动化框架 (支持 dubbo、htt

Avatar--行走的接口自动化框架 (支持 dubbo、htt

作者: 测试在路上 | 来源:发表于2020-06-13 02:44 被阅读0次

    自评:

    读了@孙高飞大佬的文章后,知道我这篇文章没有成为精华帖的原因了,因为浮于表面,深度不够。需要反省了

    背景

    因一直从事服务端测试,在人员极速减少的情况下,故开发了一套提升效率的接口自动化框架,用于提升测试效率。

    github源码地址:

    https://testerhome.com/opensource_projects/avatar

    该框架功能完善和性能优化将会一直在路上。

    1、Avatar框架图

    废话不多说,框架支持功能和依赖见下图:

    image

    2、已实现功能及报告展示

    目前可测试dubbo、http/https、mysql
    邮件报告内容如下:

    image

    附件内容如下:

    image

    3、Avatar代码结构图

    废话不多说,框架代码结构及说明见下图:

    image

    4、详细功能及使用说明

    4.1 dubbo接口测试

    4.1.1 pom.xml中添加dubbo provider的maven库

    image

    示例:

    <!-- maven仓库配置 -->
        <distributionManagement>
            <snapshotRepository>
                <id>xxxx-snapshot</id>
                <name>xxxx Snapshot</name>
                <url>http://maven.xxxx.cn/nexus/</url>
            </snapshotRepository>
                    <repository>
                <id>xxxx-release</id>
                <name>xxx Release</name>
                <url>http://maven.xxxx.cn/content/repositories/</url>
            </repository>
        </distributionManagement>
        <!-- 仓库地址配置,可以放置到maven工具的conf目录setting.xml进行全局配置 -->
        <repositories>
            <repository>
                <id>xxxx-public</id>
                <name>xxxx-public</name>
                <releases>
                </releases>
                <snapshots>
                </snapshots>
                <url>http://maven.xxxx.cn/nexus/content/</url>
            </repository>
                    <repository>
                    ......
                    </repository>
        </repositories>
    

    4.1.2 dubbo-config.xml中配置zookeeper和dubbo接口

    image

    示例:

    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
           xmlns:dubbo="http://code.alibabatech.com/schema/dubbo"
           xmlns:p="http://www.springframework.org/schema/p"
           xsi:schemaLocation="http://www.springframework.org/schema/beans
           http://www.springframework.org/schema/beans/spring-beans.xsd
           http://code.alibabatech.com/schema/dubbo
           http://code.alibabatech.com/schema/dubbo/dubbo.xsd">
    
        <dubbo:application name="demo-consumer"/>
    
        <!-- zookeeper地址配置 -->
        <dubbo:registry address="zookeeper://10.110.112.119:2181" />
    
        <!-- id定义为接口名,version需要和开发核实当前的接口version -->
        <dubbo:reference id="IPromiseForOrderService" interface="com.order.promise.api.IPromiseForOrderService" version="1.0" check="true"/>
        <dubbo:reference id="OrderStatusService" interface="com.order.status.flow.service.OrderStatusService" version="1.2" check="true"/>
    </beans>
    

    4.1.3 导入dubbo接口参数化文件

    image

    dubbo参数化文件内容如下:

    image

    4.1.4 编写测试用例

    image
    public class TestIPromiseForOrderService {
    
        //不需要修改:固定值变量
        private static final String FILE_PATH = "/src/test/TestCaseExcelData/dubbo/";  //文件路径
        public static final ApplicationContext CONTEXT = new ClassPathXmlApplicationContext("dubbo-config.xml");
        private GetTestCaseExcel excelData;
    
    
        //1、fileName是dubbo接口的包名, caseName是dubbo接口名
        private String fileName = "com.order.promise.api"; //dubbo接口的包名作为文件名,不包含文件后缀.xls
        private String caseName = "IPromiseForOrderService"; //dubbo接口名作为sheet名
    
    
        //2、request随着dubbo接口的不同,需要定义指定类型
        private FreeStockForOrderParam requestParam = new FreeStockForOrderParam();
    
    
        //3、新建dubbo的消费者对象,需要修改类名
        private IPromiseForOrderService ClassConsumer = (IPromiseForOrderService) CONTEXT.getBean(caseName);
    
    
        //不需要修改: 从excel文件中读取数据,不需要修改
        @DataProvider
        public Object[][] Numbers() throws BiffException, IOException {
            excelData = new GetTestCaseExcel(FILE_PATH, fileName, caseName);
            return excelData.getExcelData();
        }
    
        //不需要修改:dubbo接口访问Provider
        @Test(dataProvider = "Numbers")
        public void test(HashMap<String, String> data) {
    
            //4、从excel中取出各项参数
            String orderNo = data.get("orderNo");
            String operater = data.get("operater");
            String channel = data.get("channel");
            String operateId = data.get("operateId");
            String version = PromiseVersion.V_1_0_0.getVersion();
            String status = data.get("Status");
            String message = data.get("Message");
            String Result = data.get("Result");
    
            //5、将请求参数导入对象requestParam中
            requestParam.setOrderNo(orderNo);
            requestParam.setOperater(operater);
            requestParam.setChannel(channel);
            requestParam.setOperateId(operateId);
            requestParam.setVersion(version);
    
            //6、定义dubbo接口请求参数,修改类名
            RestRequest<FreeStockForOrderParam> request = new RestRequest<FreeStockForOrderParam>();
    
            //不需要修改:向生产者发送请求
            request.setRequest(requestParam);
    
            //7、修改dubbo接口方法名 和 responseData类型
            RestResponse responseData = ClassConsumer.freeSaleStock(request);
    
            //8、自定义log记录内容及校验数据(根据responseData来判断dubbo接口是否请求成功)
            if (responseData!=null) {
                String responseStatus = responseData.getStatus().toString();
                String responseMessage = responseData.getMessage().toString();
                if (responseStatus.equals(status) && responseMessage.equals(message)) {
                    Reporter.log("期望的Status:" + status + ",期望的Message:" + message + "\n" + "实际的Status:" + responseStatus + ",实际的Message:" + responseMessage);
                    System.out.println("期望的Status:" + status + ",期望的Message:" + message + "\n" + "实际的Status:" + responseStatus + ",实际的Message:" + responseMessage);
                    Assert.assertTrue(true);
    
                } else {
                    Reporter.log("期望的Status:" + status + ",期望的Message:" + message + "\n" + "实际的Status:" + responseStatus + ",实际的Message:" + responseMessage);
                    System.out.println("期望的Status:" + status + ",期望的Message:" + message + "\n" + "实际的Status:" + responseStatus + ",实际的Message:" + responseMessage);
                    Assert.assertTrue(false);
    
                }
            } else {
                Reporter.log("responseData为空");
                Assert.assertTrue(false);
            }
    
        }
    }
    

    4.1.5 将dubbo测试类添加到测试类列表中

    配置文件路径:

    image

    配置内容:

    image

    测试结果展示:

    image

    4.2 http接口测试

    4.2.1 导入http/https接口参数化文件

    导入路径:

    image

    参数化文件格式:

    image

    http测试用例路径:

    image

    4.2.2 参数化文件http接口测试类编写

    Java代码如下:

    public class testExampleForJmeterData {
        String filePath = "/src/test/TestCaseExcelData/http/";  //文件路径
        String fileName = "testcase"; //文件名,不包含文件后缀.xls
        String caseName = "testcase"; //sheet名
        public HttpJmeterExcelData httpJmeterExcelDatademo;
        public testExampleForJmeterData() throws IOException, BiffException {
            httpJmeterExcelDatademo = new HttpJmeterExcelData(filePath,fileName,caseName);
        }
    
        @DataProvider
        public Object[][] Numbers() throws BiffException, IOException {
            return httpJmeterExcelDatademo.Numbers();
        }
    
        @Test(dataProvider = "Numbers")
        public void test(HashMap<String, String> data) throws IOException, BiffException {
            httpJmeterExcelDatademo.test(data);
        }
    }
    

    4.2.3 自定义http/https接口Get测试类编写

    代码如下:

    public class testExampleForGet {
        private Map<String,String> headerMap = new HashMap<String,String>(); //Map<String,String> headerMap,为header列表
        private String url = ""; //String url为post请求的url
        private List<String> responseDataList = new LinkedList<>(); //断言list,元素为String类型
        private String httpStatus = "";
        private String hostIP = "";
        private String hostName = "mcart-go.lemall.com";
    
        @Test
        public void DoGetTest() throws Exception {
            headerMap.put("User-Agent", "smatisance");
            headerMap.put("Content-type", "application/x-www-form-urlencoded;charset:UTF-8");
            headerMap.put("cookie", "ssouid=2126407; sso_tk=102XXXO0EZzx5TDSj2oFRbam2avyAm3El7RLin1zm28Aaipj2SlKPxORcufgm1O5EyBfhFbP2PDbcm4");
    
            hostIP =  new GetHostIp(hostName).getHostIP();  //从host参数化文件中读取HOST IP
    //        System.out.println("===================" + hostIP);
    
            // http/https的URL       
            url = "https://mcart-go.com/api/query/viewCart.jsonp?provinceId=10602&cityId=10048&callback=Zepto1503543771015";
    
            // 添加需要校验的response data
            responseDataList.add("Hellosabiasnas");
            responseDataList.add("lizhen");
            responseDataList.add("bvghkl");
    
            //添加需要校验的http 状态码
            httpStatus = "200";
    
            //调用http请求类进行测试
            HttpGetTest httpGetTest = new HttpGetTest(headerMap, url, responseDataList, httpStatus, hostIP);
    
         //    用例成功与否判断     
        try {
                if(httpGetTest.isRequestSuccessful()) {
                    Reporter.log("ResponseStatus: " + httpGetTest.getHttpStatus());
                    Reporter.log("ResponseHeader: " + httpGetTest.getResponseHeader());
                    Reporter.log("ResponseData: " + httpGetTest.getResponseBody());
    
                    System.out.println("ResponseData: " + httpGetTest.getResponseBody());
                    Assert.assertTrue(true);
                } else {
                    Reporter.log("ResponseStatus: " + httpGetTest.getHttpStatus());
                    Reporter.log("ResponseHeader: " + httpGetTest.getResponseHeader());
                    Reporter.log("ResponseData: " + httpGetTest.getResponseBody());
    
                    System.out.println("ResponseData: " + httpGetTest.getResponseBody());
                    Assert.assertTrue(false);
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
    

    4.2.4 自定义http/https接口Post测试类编写

    代码如下:

    public class testExampleForPost {
        private Map<String,String> paramMap = new HashMap<String,String>();  //Map<String,String> paramMap,为post请求的参数列表
        private Map<String,String> headerMap = new HashMap<String,String>(); //Map<String,String> headerMap,为header列表
        private String url = ""; //String url为post请求的url
        private List<String> responseDataList = new LinkedList<>(); //断言list,元素为String类型
        private String httpStatus = "";
        private String hostIP = "";
        private String hostName = "mproduct-go.lemall.com";
    
        @Test
        public void DoPostTest() throws Exception {
            //request Body
            paramMap.put("params","{\"mobileHead\":{\"equipment\":{\"devHwVersion\":\"SM919\",\"channelId\":\"2003\"},\"other\"}}");
    
            //request header
            headerMap.put("cookie", "ssouid=24707; sso_tk=102XXXO0EZ2Mfdim38Aaipj2SlKPxORcufgm1O5EyBfhFbP2PDbcm4");
            headerMap.put("mEncodeMethod", "none");
            headerMap.put("User-Agent", "android-phone;21;zh_CN");
    
            //从host ip参数化文件中获取hostname对应的host ip
            hostIP =  new GetHostIp(hostName).getHostIP();
    
            //post请求的URL
            url = "https://mproduct-go.com:443/api/query/v2/getProDetail.json?sso_tk=102XXXO0EZ2Mfdim38Aaipj2SlKPxORcufgm1O5EyBfhFbP2PDbcm4";
    
            //需要校验的response data
            responseDataList.add("message\":\"服务调用成功\"");
    
            //需要校验的http状态码
            httpStatus = "200";
    
            //调用http post请求类
            HttpPostTest httpPostTest = new HttpPostTest(paramMap, headerMap, url, responseDataList, httpStatus, hostIP);
    
            //用例成功与否判断
            try {
                if(httpPostTest.isRequestSuccessful()) {
                    Reporter.log("ResponseStatus: " + httpPostTest.getHttpStatus());
                    System.out.println("ResponseStatus: " + httpPostTest.getHttpStatus());
                    System.out.println("ResponseHeader: " + httpPostTest.getResponseHeader());
                    System.out.println("ResponseData: " + httpPostTest.getResponseBody());
                    Assert.assertTrue(true);
                } else {
                    Reporter.log("Status: " + httpPostTest.httpPostRequest().getStatusLine().getStatusCode());
                    Reporter.log("Message: " + httpPostTest.httpPostRequest().getEntity().getContent());
                    System.out.println("ResponseStatus: " + httpPostTest.getHttpStatus());
                    System.out.println("ResponseHeader: " + httpPostTest.getResponseHeader());
                    System.out.println("ResponseData: " + httpPostTest.getResponseBody());
                    Assert.assertTrue(false);
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
    

    4.3 mysql测试

    mysql测试用例类路径:

    image

    4.3.1 mysql测试用例类编写

    代码如下:

    public class SqlTest {
        //jdbc路径
        private String DBurl = "jdbc:mysql://127.0.0.1/test";
        //jdbc驱动
        private String JdbcName = "com.mysql.jdbc.Driver";
        //mysql用户名
        private String UserName = "root";
        //密码
        private String PassWord = "root";
    
        private SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");//设置日期格式
        String strDate = df.format(new Date());
    
        //要执行的sql语句,支持增删改查
        private String sql = "INSERT INTO runoob_tbl1  (runoob_title, runoob_author, submission_date) VALUES (\"Memcached\", \"Memcached.com\", '" + strDate + "')";
    
        //sql请求、执行,并判断用例成功与否
        @Test
        public void SqlTest() {
            DBHelper dbHelper = new DBHelper(DBurl, JdbcName, UserName, PassWord, sql);
    
            if(dbHelper.isRequestSuccessful()) {
                Reporter.log("sql执行成功");
                Assert.assertTrue(true);
            } else {
                Reporter.log("sql执行失败");
                Assert.assertTrue(false);
            }
        }
    }
    

    4.4 HOST IP设置

    4.4.1 host文件导入

    host文件导入路径:

    image

    host文件格式:

    image

    4.4.2 待测试环境配置

    配置文件路径:

    image

    配置方式:

    image

    4.5 报警邮件配置

    4.5.1 报警邮件发送方配置

    配置文件路径:

    image

    配置文件内容:

    image

    4.5.2 报警邮件接收方配置

    配置文件路径:

    image

    配置文件格式:

    image

    相关文章

      网友评论

          本文标题:Avatar--行走的接口自动化框架 (支持 dubbo、htt

          本文链接:https://www.haomeiwen.com/subject/zyezaxtx.html