昨天朋友问我Jmeter怎么把数据库查询结果与接口响应JSON报文做对比。(第一段是记录自己的探索过程,读者可以直接跳至第二段)
我当时想法是
第一步:搞定接口参数
1. 正则匹配接口响应的JSON内容。匹配-1,匹配所有符合内容 (分别匹配ID 和 NAME的值)
2. 取ID,作为ForEach控制器的控制参数。(ID_1, ID_2, ID_3 .. 有多少会循环几次)
3. 其他变量用${__counter(TRUE,)}计数器来拼接。例如${__V(NAME_${__counter(TRUE,)})}(取得NAME_1, NAME_2... ForEach循环几次,就取几个)
第二步:搞定数据库值
1. JDBC PostProcessor 后置处理器,将查询结果保存为 (id_1, id_2 ... name_1, name_2 ...的形式)
第三步:断言
1.使用java请求。ResultData参数 添加接口返回的 id 和 name
2.为java请求添加相应断言,在断言中添加 数据库的ID 和 NAME
朋友说这不是他想要的。他想在一个断言里判断。但是因为json里内容是不固定的,所以响应断言肯定无法满足。
昨天回到家想了一下,觉得Beanshell断言应该可以。
实际上确实可以,还很简单!
我的思路是:
第一步:接口参数直接使用HTTP请求的响应内容,JMeter内置了获取当前请求响应的方法prev.getResponseDataAsString()
第二步:数据库逃不掉的,老老实实赋字段名
第三步:Beanshell断言
1. for循环, i = 1,vars.get("id_" + i) 拼接变量名 获得基础填充内容 "{\"id\":" + id + ",\"latitude\":" + latitude + ",\"longitude\":" + longitude + ",\"name\":\"" + name + "\"}"
2. 拼接首位JSON格式,获得完整JSON报文
3. equals() 判断 2个字符串
另外Jmeter中的BeanShell中,好像不能使用String.format()。我查了一下,暂时没有这块儿资料。如果有的话,拼接部分就方便很多了。
最后附上Beanshell断言完整代码
int M = ${id_#};
int i;
String Str = "";
String id = "";
String latitude = "";
String longitude = "";
String name = "";
Str = "{\"data\":[";
for(i = 1; i <= M; i++){
id = vars.get("id_" + i);
latitude = vars.get("latitude_" + i);
longitude = vars.get("longitude_" + i);
name = vars.get("name_" + i);
Str = Str + "{\"id\":" + id + ",\"latitude\":" + latitude + ",\"longitude\":" + longitude + ",\"name\":\"" + name + "\"}";
if (i != M){
Str = Str + ",";
}
}
Str = Str + "],\"message\":\"\",\"result\":0}";
System.out.println("数据库内容: \n" + Str);
//prev.getResponseDataAsString是Jmeter提供的方法,可以调取上次请求的响应字符串
response = prev.getResponseDataAsString();
System.out.println("响应内容: \n" + response);
if(Str == ""){
Failure = true;
FailureMessage = "连接数据库失败或者数据库内没有历史数据!";
//对比数据库内容和响应内容,私用euqals方法判断是否一致
}else if(response.equals(Str) == false){
//把断言失败置为真
Failure = true;
String Msg = "与数据库内容不匹配!\n";
FailureMessage = Msg + "数据库内容: \n" + Str + "\n" + "响应内容: \n" + response;
}
最后总结一下用到的Jmeter内置方法:
vars.get() #获取JMeter中的变量
prev.getResponseDataAsString() #获取当前请求的响应结果
Failure、FailureMessage 是Beanshell断言特有的参数,用于指定断言失败。
完整的Jmeter内置方法请参考这位大佬的博文
http://www.cnblogs.com/puresoul/p/4915350.html
解决问题过程中参考了这位大佬的博文,利用gson包直接对比json报文。(但我没实现,只是使用了他的部分java代码)
http://blog.csdn.net/drico1986/article/details/53021071