线程组

线程组作为JMeter测试计划的核心组件之一,对于模拟并发用户的行为至关重要。线程组元件是整个测试计划的入口,所有的取样器和控制器必须放置在线程组下。

可以将线程组视为一个虚拟用户池,其中每个线程可被理解为一个虚拟用户,多个虚拟用户同时执行相同的一批任务。

在这个虚拟用户池中,每个线程之间是相互隔离且互不影响的。每个线程的执行过程中,操作的变量不会对其他线程的变量值产生影响。

线程组的关键任务之一是定义并发用户的行为,包括设置线程数、循环次数、启动延迟等关键参数。通过适当配置线程组,测试人员可以模拟多用户在系统中同时执行任务的场景,从而评估系统的性能和稳定性。

通过灵活使用setup线程组、线程组、tearDown线程组、开放模型线程组,配置前置操作、主要操作、后置操作,更能真实、详细的评估系统。

线程组分为四类:

  • 线程组
  • setUp线程组
  • tearDown线程组
  • 开放模型线程组

线程组、setUp线程组、tearDown线程组控制面板中的元素基本一致:

  • 名称、注释
  • 在取样器错误后执行的动作
  • 线程数
  • Ramp-Up时间
  • Same user on each iteration
  • 延迟创建线程直到需要(只有线程组有)
  • 调度器

开放模型线程组控制面板中的元素:

  • 名称、注释
  • 在取样器错误后执行的动作
  • 调度计划
  • 随机种子

执行顺序

在JMeter中,setUp线程组拥有最高的优先级,而tearDown线程组则具有最低的优先级。这一优先级关系可用表达式表示为:setUp线程组 > 线程组 = 开放模型线程组 > tearDown线程组

这意味着在测试计划执行过程中,setUp线程组将首先执行,其后是线程组开放模型线程组,最后执行tearDown线程组

通常情况下,setUp线程组用于在测试执行之前进行一些初始化工作,而tearDown线程组用于测试执行结束后的清理工作。

其他线程组在测试执行过程中按照它们在测试计划中的顺序执行。

示例接口代码

@ThreadGroup.route('/api/ThreadGroup/', methods=['GET', 'POST'])
def threadgroup1():
sleep(3) # 接口设置了休眠三秒,即接口在接收到请求数据三秒后,返回响应数据。
return "我是响应"

示例Jmeter脚本

  • 测试计划中,分别添加tearDown线程组、线程组、setUp线程组

  • tearDown线程组、线程组、setUp线程组下分别添加HTTP请求取样器

    名称分别为:tearDown线程组线程组setUp线程组

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup1/

    请求方式:GET

  • 测试计划下添加查看结果树

演示内容

运行,查看结果树

可以观察到在2024-04-03 15:00:07 时,setUp线程组中的取样器发送了请求。

随后,在 2024-04-03 15:00:10 时,线程组中的请求取样器也发出了请求。

最后,在 2024-04-03 15:00:13时,tearDown线程组请求取样器发出了请求。

这与接口设置的休眠时间一致,表明 JMeter 先执行setUp线程组,随后执行线程组,最后执行 tearDown线程组 。即使脚本中的顺序不是这样。

Jmeter中线程组的执行顺序可以归纳为:setUp线程组 > 线程组 > 开放模型线程组 > tearDown线程组


线程数

线程组中的线程数指的是同时运行的虚拟用户数量。这个数量决定了你的测试将模拟多少个用户同时访问目标应用程序或服务。

在JMeter的线程组配置中,你可以根据你的需求来设置线程数,通常是根据你想要模拟的用户负载量和你的系统资源来决定的。

需要注意的是,线程数设置得太高可能会导致测试机器资源不足,影响测试结果的准确性;而设置得太低可能无法模拟真实的负载情况。因此,需要根据具体情况进行合理的设置。

示例接口代码

@ThreadGroup.route('/api/ThreadGroup2/', methods=['GET', 'POST'])
def threadgroup1():
return "我是响应"

示例Jmeter脚本

  • 测试计划下,添加1个线程组

    线程数:3

  • 线程组下,添加HTTP请求取样器

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup2/

    请求方式:GET

  • 测试计划中,添加查看结果树

演示内容

运行,查看结果树

图中取样器结果中的Thread Name分别为线程组 1-1线程组 1-2线程组 1-3。这是因为线程组线程数值为3,Jmeter启功了3个线程,每个线程皆执行1次线程组

在Jmeter中1个线程就代表1个用户,现在就相当于3个用户一起执行线程组


循环次数

在JMeter中,循环次数是指每个线程(即虚拟用户)执行其测试计划的次数。这个数量决定了你的测试将模拟用户访问目标应用程序或服务的次数。

在JMeter的线程组配置中,你可以根据你的需求来设置循环次数,通常是根据你想要模拟的用户访问上限值,如抽奖次数。

需要注意的是,循环次数设置得太高,特别设置循环次数为永远,可能会导致测试机器资源不足,影响测试结果的准确性;而设置得太低可能无法达到测试要求。因此,需要根据具体情况进行合理的设置。

示例接口代码

@ThreadGroup.route('/api/ThreadGroup2/', methods=['GET', 'POST'])
def threadgroup1():
return "我是响应"

示例Jmeter脚本

  • 测试计划下,添加1个线程组

    循环次数:3

  • 线程组下,添加HTTP请求取样器

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup2/

    请求方式:GET

  • 测试计划中,添加查看结果树

演示内容

运行,查看结果树

图中取样器结果中的Thread Name皆为线程组 1-1。这是因为线程组循环次数值为3,Jmeter启功了1个线程,连续执行了3次线程组

在Jmeter中1个线程就代表1个用户,现在就相当于1个用户执行了3次线程组


取样器错误后执行的动作

在JMeter中,取样器(Sampler)是用于模拟用户请求发送到目标服务器的组件,例如HTTP请求、FTP请求等。当取样器执行过程中出现错误时,可以通过配置相应的动作来处理这些错误。以下是一些处理取样器错误时,线程组中常见方式:

  • 停止测试
  • 立即停止测试
  • 停止线程
  • 启动下一进程循环
  • 继续

通过合理配置这些错误处理方式,可以根据测试需求和场景来控制测试计划的行为,确保对错误有适当的响应和处理。


停止测试

设置取样器错误后执行的动作停止测试时,一旦任何一个取样器遇到错误,整个测试计划将会在所有当前正在执行的线程执行完毕后停止。这可以用于模拟在测试过程中发生重要错误或异常时的行为。

这种设置确保在测试执行中任何关键的错误都会导致测试的终止,以便进行及时的识别和处理。这对于模拟真实世界中的异常情况以及确保测试的准确性和可重复性都是非常重要的。

示例接口代码

@ThreadGroup.route('/api/ThreadGroup3/', methods=['GET', 'POST'])
def threadgroup3():
if request.method == 'GET': # `错误请求`立即响应
return {'code': 200}
sleep(3) # 延长非`错误请求`的请求时间
return {'code': 200} # `非错误请求`延迟响应

单线程组

示例Jmeter脚本
  • 测试计划下添加线程组

  • 线程组下添加2个HTTP 请求取样器

    名称:错误请求正确请求

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup3/

    正确请求的请求方式:POST

    错误请求的请求方式:GET

  • 错误请求取样器下添加响应断言

    值:1111

  • 测试计划中,添加查看结果树

演示内容

运行,查看结果树

图中连续请求了三次,结果是一致的。

取样器在线程组中一般是从上至下顺序执行。错误请求的结果报错后,因为设置取样器错误后执行的动作停止测试,同时没有其他正在执行的线程,Jmeter直接结束本次测试。

删除响应断言,再次运行

图中连续请求了三次,结果是一致的。

取样器在线程组中一般是从上至下顺序执行。因为错误请求的结果没有报错,会继续执行正确请求

多线程组

示例Jmeter脚本
  • 测试计划下添加2个线程组

    名称:线程组1线程组2

  • 线程组1下添加HTTP 请求取样器

    名称:错误请求

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup3/

    请求方式:GET

  • 线程组2下添加2个HTTP 请求取样器

    名称:与错误请求并行的正确请求错误请求之后的正确请求

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup3/

    请求方式:POST

  • 错误请求取样器下添加响应断言

    值:1111

  • 错误请求之后的正确请求取样器下添加固定定时器(右键取样器-添加-定时器-固定定时器)

    线程延迟:3000

  • 测试计划中,添加查看结果树

固定定时器可以延迟取样器的执行时间,设置为3秒,可以确保错误请求之后的正确请求错误请求结束后执行。

演示内容

运行,查看结果树

图中连续请求了三次,结果是一致的。

取样器在线程组中一般是从上至下顺序执行,线程组一般并发执行的。错误请求的结果报错时,与错误请求并行的正确请求也正在执行,错误请求之后的正确请求还未执行。

因为设置取样器错误后执行的动作停止测试,待与错误请求并行的正确请求结束后不会执行错误请求之后的正确请求,Jmeter直接结束本次测试。

此时,测试计划中未勾选独立运行每个线程组

勾选独立运行每个线程组,再次运行

图中连续运行了5次,但是结果不符合预期。预期结果应该是不会执行线程组2,但是执行了。应该是Jmeter的一个BUG(或许是独立运行每个线程组的问题)。读者请谨慎使用。


立即停止测试

设置取样器错误后执行的动作立即停止测试时,当取样器在执行过程中遇到错误时,JMeter会立即停止当前运行的测试,不再执行任何后续的请求或操作。

这有助于保护应用程序免受可能导致问题的异常或错误的影响,并确保测试结果的准确性。

这种设置对于测试场景中的稳定性和可靠性非常重要,特别是在模拟并发用户或大负载情况下,能够及时发现问题并停止测试,有助于减少潜在的影响和损害。

示例接口代码

@ThreadGroup.route('/api/ThreadGroup3/', methods=['GET', 'POST'])
def threadgroup3():
if request.method == 'GET': # `错误请求`立即响应
return {'code': 200}
sleep(3) # 延长非`错误请求`的请求时间
return {'code': 200} # `非错误请求`延迟响应

单线程组

示例Jmeter脚本
  • 测试计划下添加线程组

  • 线程组下添加2个HTTP 请求取样器

    名称:错误请求正确请求

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup3/

    正确请求的请求方式:POST

    错误请求的请求方式:GET

  • 错误请求取样器下添加响应断言

    值:1111

  • 测试计划中,添加查看结果树

演示内容

运行,查看结果树

图中连续请求了三次,结果是一致的。

取样器在线程组中一般是从上至下顺序执行。错误请求的结果报错后,因为设置取样器错误后执行的动作立即停止测试,Jmeter直接结束本次测试。

删除响应断言,再次运行

图中连续请求了三次,结果是一致的。

取样器在线程组中一般是从上至下顺序执行。因为错误请求的结果没有报错,会继续执行正确请求

多线程组

示例Jmeter脚本
  • 测试计划下添加2个线程组

    名称:线程组1线程组2

  • 线程组1下添加HTTP 请求取样器

    名称:错误请求

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup3/

    请求方式:GET

  • 线程组2下添加2个HTTP 请求取样器

    名称:与错误请求并行的正确请求错误请求之后的正确请求

    请求地址:HTTP://127.0.0.1:5000/api/ThreadGroup3/

    请求方式:POST

  • 错误请求取样器下添加响应断言

    值:1111

  • 错误请求之后的正确请求取样器下添加固定定时器(右键取样器-添加-定时器-固定定时器)

    线程延迟:3000

  • 测试计划中,添加查看结果树

固定定时器可以延迟取样器的执行时间,设置为3秒,可以确保错误请求之后的正确请求错误请求结束后执行。

演示内容

运行,查看结果树

图中连续请求了三次,结果是一致的。

取样器在线程组中一般是从上至下顺序执行,线程组一般并发执行的。错误请求的结果报错时,与错误请求并行的正确请求也正在执行,错误请求之后的正确请求还未执行。

因为设置取样器错误后执行的动作立即停止测试,不会等待与错误请求并行的正确请求结束,Jmeter会直接结束本次测试,因此与错误请求并行的正确请求的响应结果提示 Socket 关闭异常。

此时,测试计划中未勾选独立运行每个线程组

勾选独立运行每个线程组,再次运行

图中连续运行了2次,但是结果不符合预期。预期结果应该是不会执行线程组2,但是执行了。应该是Jmeter的一个BUG(或许是独立运行每个线程组的问题)。读者请谨慎使用。

提示

本文示例接口源代码可从前言中下载。


Jmeter线程组-上的更多相关文章

  1. 【转】关于JMeter线程组中线程数,Ramp-Up Period,循环次数之间的设置概念

    关于JMeter线程组中线程数,Ramp-Up Period,循环次数之间的设置概念 笔者是个刚刚踏入压力测试领域不到2个月的小菜,这里分享一下线程组中3个参数之间关系的个人见解,不喜请!喷!,望大家 ...

  2. 关于JMeter线程组中线程数,Ramp-Up Period,循环次数之间的设置概念

    关于JMeter线程组中线程数,Ramp-Up Period,循环次数之间的设置概念 笔者是个刚刚踏入压力测试领域不到2个月的小菜,这里分享一下线程组中3个参数之间关系的个人见解,不喜请!喷!,望大家 ...

  3. JMeter线程组编辑区揭秘

    线程组编辑区如下: 有点复杂,但是慢慢看下来,还是比较容易理解. Name 带有业务含义的名字. Comments 线程组的备注说明. Action to be taken after a Sampl ...

  4. Jmeter线程组间传递参数

    现在做测试和以前不太一样了,以前只要站在一个用户的角度做端到端的UI测试就可以了,现在不会做接口测试,出去都不好意思和别人打招呼.那提到接口测试,就不得不提一下接口测试利器Jmeter,大家也都知道, ...

  5. Jmeter线程组设置

    添加线程组:右键测试计划->添加->Threads->线程组 左侧树形标签栏中,显示标签信息. 选中线程组,右侧内容栏中显示线程组的相关信息. 名称:可以给线程组设置一个个性化的命名 ...

  6. jmeter线程组之间传递参数

    JMeter 变量作用域局限于所属线程.这样设计是经过深思熟虑的,目的是让测试线程能够独立运转.有时候用户可能需要在不同线程间(可能属于同一个线程组,也可能不属于同一个线程组)传递变量. 其中一种方法 ...

  7. JMeter 线程组之ConcurrencyThreadGroup介绍

    线程组之ConcurrencyThreadGroup by:授客 QQ:1033553122 测试环境 apache-jmeter-3.2 jmeter-plugins-manager-1.3.jar ...

  8. JMeter 线程组之Stepping Thread Group插件介绍

    线程组之Stepping Thread Group插件介绍   by:授客 QQ:1033553122 测试环境 apache-jmeter-2.13   插件: https://jmeter-plu ...

  9. jmeter线程组之间传参

    背景介绍: 使用jmeter做登录和搜索接口的测试: 登录接口请求头为:Content-Type: application/x-www-form-urlencoded; charset=UTF-8 搜 ...

  10. jmeter线程组介绍

    Jmeter中的测试计划是一直有的,但可以在右侧修改名字,要开始做具体测试设计前,都需要在测试计划下边添加一个线程组,添加路径为鼠标捕获测试计划后,点击鼠标右键->添加->Threads( ...

随机推荐

  1. Flask遇到的坑及解决办法

    flask_script 在使用第三方包flask_script时,报一下错误 ModuleNotFoundError: No module named 'flask._compat' 问题时flas ...

  2. 【Azure 应用服务】如何查看App Service中的私网IP地址?

    问题描述 在使用App Service服务时,可以通过Azure 门户中的属性功能查看出站IP列表. 如果把App Service与虚拟网络(VNET)集成后,它就可以直接访问虚拟网络内部资源,那么如 ...

  3. C++异常的基本概念与用法

    //异常的概念/*抛出异常后必须要捕获,否则终止程序(到最外层后会交给main管理,main的行为就是终止) try{}内写可能会抛出异常的代码.catch(类型){处理} 写异常类型和异常处理 抛出 ...

  4. SpringCloud Hystrix断路器的基本使用

    官网资料: https://github.com/Netflix/Hystrix/wiki/How-To-Use 1. 服务雪崩 分布式系统面临的问题 复杂分布式体系结构中的应用程序有数十个依赖关系, ...

  5. OpenCV开发笔记(七十六):相机标定(一):识别棋盘并绘制角点

    前言   知道图像畸变矫映射的原理之后,那么如何得到相机的内参是矫正的第一步,内参决定了内参矩阵(中心点.焦距等),用内参矩阵才能计算出投影矩阵,从而将原本畸变的图像矫正为平面投影图像.  本篇描述了 ...

  6. 图片动态操作,利用SeekBar控制属性示例,适配屏幕解决方案

    需求为,让图片适配屏幕大小,并且可以用一个滑块来控制图片的旋转,用一个滑块来控制图片大小,核心语法思路,控制图片的大小, 核心语法为:mImageView.setLayoutParams(new Li ...

  7. offline RL | D4RL:最常用的 offline 数据集之一

    pdf:https://arxiv.org/pdf/2004.07219.pdf html:https://ar5iv.labs.arxiv.org/html/2004.07219 GitHub:ht ...

  8. 从零开始学Spring Boot系列-集成mybatis

    在Spring Boot的应用开发中,MyBatis是一个非常流行的持久层框架,它支持定制化SQL.存储过程以及高级映射.在本篇文章中,我们将学习如何在Spring Boot项目中集成MyBatis, ...

  9. be动词 系动词 连缀动词 Linking Verb

    be动词 系动词 连缀动词 Linking Verb be 原型 am 第一人称单数形式 is 第三人称单数形式 are 第二人称单数和复数形式 been 过去分词 being 现在分词 was 第一 ...

  10. Spring Boot学习日记15

    使用thymeleaf <!DOCTYPE html> <html lang="en" xmlns:th="http://www.thymeleaf.o ...