Ngrinder脚本开发各细节锦集(groovy)

1、生成随机字符串(import org.apache.commons.lang.RandomStringUtils)
    数字:RandomStringUtils.randomNumeric(length);
字母:RandomStringUtils.randomAlphabetic(length);
字母加数字:RandomStringUtils.randomAlphanumeric(length);
所有ASCCII字符:RandomStringUtils.randomAscii(length);
自定义混合字符:RandomStringUtils.randomAscii(length, string);
2、生成随机数字:(import java.util.concurrent.ThreadLocalRandom;)
    数字:int random_number = ThreadLocalRandom.current().nextInt(min_num, max_num);
3、获取项目数据文件路径
    common项目:"/resources/account.txt"
maven项目:Thread.currentThread().getContextClassLoader().getResource("/account.txt").getPath();
maven项目获取文件内容:ReflectionUtils.getCallingClass(0).getResourceAsStream("/account.txt").getText("UTF-8")
4、读取文件:
    txt每行单数据:   String[] file_arrary = new File("/resources/account.txt") as String[];
String file_data = file_arrary[arrary_index]; txt每行双数据: String[] file_arrary = new File("/resources/account.txt") as String[];
String data_one = file_arrary[arrary_index].split(",")[0];
String data_two = file_arrary[arrary_index].split(",")[1];
另一种方法:
List<String> reqDataArrList = new File(dataFilePath).readLines()
String data_one = reqDataArrList.get(arrary_index).split(",")[0];
String data_two = reqDataArrList.get(arrary_index).split(",")[1]; txt每行多数据可参考双数据方法。也可以参考json方式存储:
BufferedReader txt_content=new BufferedReader(new FileReader(new File("/resources/account.txt")))
data_json = new JSONObject()
String text_line = ""
while(( text_line=txt_content.readLine())!=null){
data_json.put(text_line.split(",")[0],text_line.split(",")[1])
}
String data_one = data_json.keys[0]
String data_two = data_json.getString(data_one)
5、写入文件:
    覆盖写入:   def write = new File(file_path, file_name).newPrintWriter();
write.write(write_text);
write.flush();
write.close() 追加写入: def write = new File(file_path, file_name).newPrintWriter();
write.append(write_text);
write.flush();
write.close()
6、json文件的数据处理(import org.ngrinder.recorder.RecorderUtils)
    json文件读取:   String json_str = new File(file_path).getText("UTF-8")
def json_object = RecorderUtils.parseRequestToJson(json_str) 长度:json_object.length()
关键字:json_object.keys()
添加元素:json_object.put(name, value)
修改元素:json_object.put(name, value)
删除元素:json_object.remove(name, value)
获取对应value:json_object.getString(name)
7、字符串的处理
    字符串截取:String new_str = old_str[0..3]
字符串替换:String string = str.replace("old","new")
字符串统计:int count = string.count("char")
字符串转化:int int_num = Integer.parseInt(string)
1、设置多个请求事务(即多个test方法)
    1)设置多个静态Gtest对象:
public static GTest test1
public static GTest test2
2)实例化多个Gtest对象:
test1 = new GTest(1, "test1");
test2 = new GTest(2, "test2");
3)监听多个test请求:
test1.record(this, "test1")
test2.record(this, "test2")
4)定义多个test方法:
public void test1(){
grinder.logger.info("---ones: {}---", grinder.threadNumber+1)
}
public void test2(){
grinder.logger.info("---twos: {}---", grinder.threadNumber+1)
}
2、Ngrinder定义请求参数集:
    add方法:  List<NVPair> paramList = new ArrayList<NVPair>();
paramList.add(new NVPair("name", "value"));
paramList.add(new NVPair("name", "value"));
params = paramList.toArray(); new方法: params = [new NVPair("name", "value"), new NVPair("name", "value")];
3、Ngrinder处理日志:
    日志级别(三种常见): grinder.logger.info("----before process.----");
grinder.logger.warn("----before process.----");
grinder.logger.error("----before process.----"); 日志限定(仅打印error级别) :
1)导入依赖包
import ch.qos.logback.classic.Level;
import org.slf4j.LoggerFactory;
2)设定级别
@BeforeThread
LoggerFactory.getLogger("worker").setLevel(Level.ERROR);
3)设置打印语句
@test
grinder.logger.error("----error.----");
日志输出(输出所有进程日志):将每个agent的.ngrinder_agent/agent.conf中一项修改为agent.all_logs=true 日志打印:打印变量:grinder.logger.error("{},{}",variable1,variable2); // 换行或缩进可在""中加\n或\t
4、Ngrinder的cookie处理
    1) 登录产生cookie
@BeforeThread
login_get_cookie(); // 调用登录方法
cookies = CookieModule.listAllCookies(HTTPPluginControl.getThreadHTTPClientContext()); // 配置cookie管理器
2) 读取控制器中cookie
@Before
cookies.each { CookieModule.addCookie(it, HTTPPluginControl.getThreadHTTPClientContext()) }
5、Ngrinder请求方式:
    1)通过url加参数直接访问:
post方法: HTTPResponse result = request.POST("http://192.168.2.135:8080/blogs", params, headers)
get方法: HTTPResponse result = request.GET("http://192.168.2.135:8080/blogs", params, headers)
参数是json:设置请求头参数{"Content-Type": "application/json"}
2)通过参数化所有请求数据为json对象(导入import org.ngrinder.recorder.RecorderUtils)
HTTPResponse result = RecorderUtils.sendBy(request, req_data_json)
HTTPResponse result = RecorderUtils.sendBy(request, req_data_json)
6、Ngringer的test运行次数设定(将总运行测试次数按百分比例分配到相应test):
    1)引用依赖包:
import net.grinder.scriptengine.groovy.junit.annotation.RunRate
2)设置运行次数百分比(所有test设定的比例值不够100,那不满的部分不运行,比如设定总比80,只运行这80部分):
@RunRate(50) // 数字代表百分比
@Test
public void test1(){}
@RunRate(50) // 数字代表百分比
@Test
public void test2(){}
7、Ngringer获取设置的加压机总数、进程总数、线程总数等信息:
    int tota_agents = Integer.parseInt(grinder.getProperties().get("grinder.agents").toString()) // 设置的总加压机数
int total_processes = Integer.parseInt(grinder.properties().get("grinder.processes").toString()) // 设置的总进程数
int total_threads = Integer.parseInt(grinder.properties().get("grinder.threads").toString()) // 设置的总线程数
int total_runs = Integer.parseInt(grinder.properties().get("grinder.runs").toString()) // 设置的总运行次数(若设置的是运行时长,则得到0)
8、Ngringer获取当前运行的加压机编号、进程编号、线程编号等信息(都从0递增):
    int agent_number = grinder.agentNumber // 当前运行的加压机编号
int process_number = grinder.processNumber // 当前运行的进程编号
int thread_number = grinder.threadNumber // 当前运行的线程编号
int run_number = grinder.runNumber // 当前运行的运行次数编号
9、Ngringer获取唯一递增值方法(从1递增,不重复):
    // 传递接口参数runNumber(即def runNumber = grinder.runNumber)
private int getIncrementId(int runNumber){
// 获取压力机总数、进程总数、线程总数
int totalAgents = Integer.parseInt(grinder.getProperties().get("grinder.agents").toString())
int totalProcess = Integer.parseInt(grinder.getProperties().get("grinder.processes").toString())
int totalThreads = Integer.parseInt(grinder.getProperties().get("grinder.threads").toString()) // 获取当前压力机数、进程数、线程数
int agentNum = grinder.agentNumber
int processNum = grinder.processNumber
int threadNum = grinder.threadNumber // 获取唯一递增数id
int incrementId = agentNum * totalProcess * totalThreads + processNum * totalThreads + threadNum + totalAgents * totalProcess * totalThreads * runNumber
return incrementId
}
10、Ngringer根据唯一递增值获取参数化文件中的唯一行号:
    1)需要设置静态变量:private enum WhenOutOfValues { AbortVuser, ContinueInCycleManner, ContinueWithLastValue }
2)传递接口参数fileDataList(即def fileDataList = new File(dataFilePath).readLines())
private int getLineNum(def fileDataList) {
// 获取当前运行数、数据读取行数、数据最大行数
int counter = getIncrementId(grinder.runNumber)
int lineNum = counter + 1
int maxLineNum = fileDataList.size() - 1 // 读取最大值的判断处理
WhenOutOfValues outHandler = WhenOutOfValues.AbortVuser
if (lineNum > maxLineNum) {
if(outHandler.equals(WhenOutOfValues.AbortVuser)) {
lineNum = maxLineNum //grinder.stopThisWorkerThread()
} else if (outHandler.equals(WhenOutOfValues.ContinueInCycleManner)) {
lineNum = (lineNum - 1) % maxLineNum + 1
} else if (outHandler.equals(WhenOutOfValues.ContinueWithLastValue)) {
lineNum = maxLineNum
}
}
return lineNum
}
11、Ngrinder日志输出配置的测试信息:(import java.text.SimpleDateFormat)
    public static String getTestInfo(){
String time_string = ""
// 获取压测时设置的进程总数、线程总数、运行次数并在log中打印
int all_process = grinder.getProperties().getInt("grinder.processes", 1) // 设置的总进程数
int all_threads = grinder.getProperties().getInt("grinder.threads", 1) // 设置的总线程数
int all_runs = grinder.getProperties().getInt("grinder.runs", 1) // 设置的总运行次数(若设置的是运行时长,则得到0)
int all_duration = grinder.getProperties().getLong("grinder.duration", 1) // 设置的总运行时长(若设置的是运行次数,则得到0)
// 格式化时间毫秒输出(输出格式00:00:00)
SimpleDateFormat formatter = new SimpleDateFormat("HH:mm:ss")
formatter.setTimeZone(TimeZone.getTimeZone("GMT+00:00"))
String all_duration_str = formatter.format(all_duration)
if (all_duration_str.equals("00:00:00"))
time_string = "Test information: the processes is "+all_process+", the threads is "+all_threads+", the run count is "+all_runs+"."
else
time_string = "Test information: the processes is "+all_process+", the threads is "+all_threads+", the run time is "+all_duration_str+"."
return time_string
}
12、Ngrinder打印所有的配置信息
        String property = grinder.getProperties();
grinder.logger.info("------- {}", property) ;
13、Ngrinder获取请求返回值:
        HTTPResponse result = request.POST("http://192.168.2.135:8080/blogs", params, headers)
返回的文本:grinder.logger.info("----{}----", result.getText()) // 或者result.text
返回的状态码:grinder.logger.info("----{}----", result.getStatusCode()) // 或者result.statusCode
返回的url:grinder.logger.info("----{}----", result.getEffectiveURI())
返回的请求头所有参数:grinder.logger.info("---\n{}---", result)
返回的请求头某参数:grinder.logger.info("----{}---- ", result.getHeader("Content-type"))
14、Ngrinder返回值的匹配:
匹配状态码:assertThat(result.getStatusCode(), is(200))
匹配包含文本:assertThat(result.getText(), containsString("success"))
15、Ngrinder获取所有虚拟用户数:
public int getVusers() {
int totalAgents = Integer.parseInt(grinder.getProperties().get("grinder.agents").toString());
int totalProcesses = Integer.parseInt(grinder.getProperties().get("grinder.processes").toString());
int totalThreads = Integer.parseInt(grinder.getProperties().get("grinder.threads").toString());
int vusers = totalAgents * totalProcesses * totalThreads;
return vusers;
}
16、Ngrinder的断言和error日志输出
if (result.statusCode == 301 || result.statusCode == 302) {
grinder.logger.error("Possible error: {} expected: <200> but was: <{}>.",result.getEffectiveURI(),result.statusCode);
} else {
assertEquals((String)result.getEffectiveURI(), result.statusCode, 200)
assertThat((String)result.getEffectiveURI(), result.statusCode, is(200))
}

  

参考文档:

  1、https://testerhome.com/topics/17585?locale=zh-CN

  2、https://my.oschina.net/aub/blog/858483

  3、https://blog.csdn.net/u013512987/article/details/81776845

  4、https://www.cnblogs.com/zjsupermanblog/archive/2017/08/18/7390980.html

  5、https://www.cnblogs.com/lindows/p/10517839.html

  6、https://www.cnblogs.com/zhongyehai/p/10386478.html

Ngrinder脚本开发各细节锦集(groovy)的更多相关文章

  1. 2020 python web开发就业要求锦集

    郑州 Python程序员 河南三融云合信息技术有限公司 6-8k·12薪 7个工作日内反馈 郑州 1个月前 本科及以上2年以上语言不限年龄不限 微信扫码分享 收藏 Python程序员 河南三融云合信息 ...

  2. ios开发经典语录锦集

    原文链接: iPhone开发经典语录集锦 前言:iPhone是个极具艺术性的平台,相信大家在开发过程中一定有很多感触,希望能写出来一起交流,所以开了这个帖子,以后还会维护. 如果大家和我一样有感触的话 ...

  3. 基于Groovy搭建Ngrinder脚本调试环境

    介绍 最近公司搭建了一套压力测试平台,引用的是开源的项目 Ngrinder,做了二次开发,在脚本管理方面,去掉官方的SVN,引用的是Git,其他就是做了熔断处理等. 对技术一向充满热情的我,必须先来拥 ...

  4. Nifi组件脚本开发—ExecuteScript 使用指南(三)

    上一篇:Nifi组件脚本开发-ExecuteScript 使用指南(二) Part 3 - 高级特征 本系列的前两篇文章涵盖了 flow file 的基本操作, 如读写属性和内容, 以及使用" ...

  5. CMD命令锦集

    虽然随着计算机产业的发展,Windows 操作系统的应用越来越广泛,DOS 面临着被淘汰的命运,但是因为它运行安全.稳定,有的用户还在使用,所以一般Windows 的各种版本都与其兼容,用户可以在Wi ...

  6. ubuntu16.04安装cuda8.0试错锦集

    ubuntu16.04安装cuda8.0试错锦集 参考文献: [http://www.jianshu.com/p/35c7fde85968] [http://blog.csdn.net/sinat_1 ...

  7. Linux系统命令与脚本开发

    系统命令 # cat EFO cat >> file << EOF neirong EOF # 清空 >file 清空文件 [root@Poppy conf]# sed ...

  8. redis 锦集

    redis 锦集url:http://blog.csdn.net/lqadam/article/category/7479450 1. redis 排序 2.redis 慢查询.位数组和事务 3.re ...

  9. Nifi组件脚本开发—ExecuteScript 使用指南(二)

    Part 2 - FlowFile I/O 和 Error Handling flow File的IO NiFi 的 Flow files 由两个主要部件组成:attributes 和 content ...

随机推荐

  1. Windows+Nginx+Tomcat整合的安装与配置学习笔记

    以下全部是nginx在window7下运行的: nginx学习总结: 我的是放在F盘 1.启动:F:\nginx-1.10.2\nginx-1.10.2>start nginx.exe(找到相应 ...

  2. Python3简易接口自动化测试框架设计与实现(上)

    目录 1.开发环境 2.用到的模块 3.框架设计 3.1.流程 3.2.项目结构 5.日志打印 6.接口请求类封装 接口开发请参考:使用Django开发简单接口:文章增删改查 1.开发环境 操作系统: ...

  3. centos redis自启动

    #!/bin/sh # chkconfig: 2345 90 10 # description: Redis is a persistent key-value database # Simple R ...

  4. Web自动化测试中的接口测试

    1.2.3 接口可测性分析 接口显而易见要比UI简单的都,只需要知道协议和参数即可完成一次请求,从自动化测试实施难易程度来看,有以下几个特征: 1)驱动执行接口的自动化成本不高:HTTP,RPC,SO ...

  5. 使用Gallery制作图片浏览器

    MainActivity.class public class MainActivity extends AppCompatActivity implements AdapterView.OnItem ...

  6. C++第四次作业--继承与派生

    C++ 继承 面向对象程序设计中最重要的一个概念是继承.继承允许我们依据另一个类来定义一个类,这使得创建和维护一个应用程序变得更容易.这样做,也达到了重用代码功能和提高执行效率的效果. 当创建一个类时 ...

  7. 使用IDA Pro逆向C++程序

    使用IDA Pro逆向C++程序 附:中科院李_硕博 : IDA用来做二进制分析还是很强大的 .lib程序是不是很容易分析出源码? 这个得看编译选项是怎么设置的 如果没混淆 没太过优化 大体能恢复源码 ...

  8. Angular与Vue

    最近在考虑对前端js框架的选择 根据前人的总结,就总结一下 Angular与Vue 的特点与区别 速度/性能 虽然 Angular 和 Vue 都提供了很高的性能,但由于 Vue 的虚拟 DOM 实现 ...

  9. React组件:拖拽布局Dragact v0.1.6 发布

    仓库地址:Dragact爽滑的拖拽组件 大家好,新年已经过去,大家又投入了繁忙的工作当中,由于我在国外,因此压根儿没有休息... 少说废话,上周一周的时间里,我陆陆续续的为Dragact组件进行了一系 ...

  10. 面向对象(oop)特征

    上课时老师不止一次和我们说过,面向对象是Java基础的重中之重!!所以一定要扎实基本功,代码都是呆子活,重要的是思想! 一般来说oop的三大特性是:封装.继承和多态,上次笔者看到有把抽象也归类其中,不 ...