Article

JMeter 压力测试

更新于:2026-07-13

第一章:JMeter 概述与环境搭建

1.1 什么是 JMeter

概念名称说明注意事项
Apache JMeter开源的Java桌面应用程序,用于性能测试和功能测试,支持负载和压力测试。需要Java环境运行,不适用于UI功能测试,专注于接口/服务层性能验证。
性能测试模拟多用户并发访问系统,评估系统在高负载下的响应能力、稳定性和资源消耗。测试结果受网络、服务器配置、脚本设计等多因素影响,需控制变量进行对比分析。
开源免费JMeter由Apache基金会维护,完全免费,社区活跃,插件丰富。使用第三方插件时需注意版本兼容性和安全性。

1.2 JMeter 的核心功能与应用场景

功能/场景名称说明注意事项
负载测试模拟真实用户行为,测试系统在正常或峰值负载下的表现。应结合业务场景设计合理的用户行为模型和数据量。
压力测试持续增加负载直至系统崩溃,找出系统瓶颈和最大承载能力。需监控服务器资源(CPU、内存、I/O),避免生产环境误用导致服务中断。
接口功能测试支持HTTP、HTTPS、REST、SOAP、JDBC、FTP、JMS等多种协议的功能验证。可替代Postman进行批量接口测试,但不适合复杂UI交互测试。
分布式测试支持主从架构,通过多台机器协同发起请求,突破单机资源限制。主控机与从机需网络互通,时间同步,版本一致。
自动化集成可与CI/CD工具(如Jenkins)集成,实现自动化性能回归测试。建议使用非GUI模式运行(-n -t -l),避免图形界面资源开销。

1.3 JMeter 安装与运行环境配置(Windows/Linux/Mac)

步骤名称操作细节注意事项
安装Java环境安装JDK 8或以上版本,设置JAVA_HOME环境变量,并加入系统PATHJMeter基于Java开发,必须先安装JDK,推荐使用LTS版本(如JDK 8、11、17)。
下载JMeter从Apache官网(https://jmeter.apache.org/download_jmeter.cgi)下载最新稳定版。建议下载二进制包(.zip或.tar.gz),避免源码包需编译。
解压安装包将下载的压缩包解压到指定目录(如C:\jmeter/opt/jmeter)。路径中避免空格或中文字符,防止启动异常。
验证安装进入bin目录,运行jmeter.bat(Windows)或jmeter(Linux/Mac)启动程序。若无法启动,检查Java是否正确安装,或尝试运行jmeter -v查看版本信息。
设置JVM参数(可选)修改jmeter.batjmeter文件中的JVM参数(如-Xms512m -Xmx2g)以优化内存使用。大并发测试时建议调大堆内存,避免OutOfMemoryError

1.4 JMeter 目录结构与核心组件简介

目录/文件名称说明注意事项
bin/存放启动脚本和配置文件,如jmeter.batjmeterjmeter.properties等。所有运行相关的脚本和配置都在此目录,是日常操作重点。
docs/官方API文档和用户手册。可离线查阅,适合深入学习。
examples/提供各种测试计划示例(.jmx文件)。初学者可参考示例学习脚本编写。
lib/存放核心库(ext/)和插件库(junit/)。第三方插件通常放入lib/ext目录,重启后生效。
printable_docs/可打印的用户手册PDF文件。包含完整用户指南,适合系统学习。
core components核心组件:线程组、取样器、监听器、断言、定时器、逻辑控制器等。理解各组件作用是构建测试脚本的基础。

1.5 启动与界面概览

操作名称操作细节注意事项
启动JMeter进入bin目录,双击jmeter.bat(Windows)或执行./jmeter(Linux/Mac)。首次启动可能较慢,因需加载GUI和类库。
主界面组成左侧树形结构显示测试计划元素,右侧为属性配置面板。所有操作均通过右键菜单添加元件。
新建测试计划右键”Test Plan” → Add → Threads (Users) → Thread Group 开始构建脚本。每个.jmx文件对应一个测试计划,建议命名清晰。
保存测试计划File → Save Test Plan As… 保存为.jmx格式文件。建议定期保存,避免意外丢失。
退出JMeterFile → Exit 或关闭主窗口。若有未保存更改,会提示是否保存。

第二章:JMeter 测试计划基础

2.1 测试计划(Test Plan)的概念与作用

概念名称说明注意事项
测试计划(Test Plan)JMeter中最顶层的容器,包含所有测试组件(线程组、取样器、监听器等)。每个.jmx文件只能有一个测试计划,是执行的入口。
元件执行顺序按树形结构自上而下执行,同级元件按添加顺序执行。控制器内部的元件受其逻辑控制(如循环、条件等)。
函数与变量支持支持内置函数(如${__Random})和用户定义变量,在整个计划中共享。变量名避免使用保留字(如ThreadNameSTARTTIME等)。
运行模式选择支持GUI模式(调试用)和非GUI模式(-n -t xxx.jmx -l result.jtl,用于执行)。生产压测务必使用非GUI模式,减少资源消耗。
类路径引用可通过”Add directory or jar to classpath”引入外部Java库。添加后需重启JMeter才能生效。

2.2 线程组(Thread Group)的创建与配置

参数名称语法/取值示例用途说明注意事项
Number of Threads (users)100并发用户数,即模拟的虚拟用户数量。数值过大可能导致本机资源耗尽,建议分布式测试。
Ramp-up Period (seconds)10启动所有线程所需时间,线程均匀启动。若设为0,则所有线程同时启动;建议设置合理爬升时间模拟真实场景。
Loop Count1, 5, 或勾选”Forever”每个线程执行取样器的次数。配合调度器可实现定时任务。
Delay Thread creation until needed勾选/不勾选延迟创建线程,按需启动。节省内存资源,尤其在大并发但低频率场景下有效。
Scheduler勾选后可设置启动/停止时间、持续时间控制测试执行的时间窗口。常用于定时压测,如每天凌晨执行性能回归。
Duration (seconds)600测试持续运行时间(秒)。与Loop Count结合使用,优先级高于循环次数。
Startup delay (seconds)30延迟启动时间(秒)。可用于等待系统预热或与其他任务协调。

2.3 取样器(Sampler)简介与 HTTP 请求示例

HTTP Request

参数语法/配置示例说明
Protocolhttp / https指定通信协议
Server Name or IPexample.com目标服务器地址
Path/api/login请求路径
MethodGET / POST请求方法

注意:POST请求需在”Parameters”或”Body Data”中填写数据,注意Content-Type匹配。

其他取样器

取样器名称语法/配置示例用途说明注意事项
JDBC RequestVariable Name: jdbc1, Query: SELECT * FROM users执行数据库SQL查询。需提前在JMeter中添加JDBC驱动jar包,并配置JDBC Connection Configuration。
FTP RequestServer: ftp.example.com, Remote File: /test.txt上传或下载FTP文件。适用于文件传输性能测试。
TCP SamplerServer Name or IP: 192.168.1.1, Port Number: 8080发送原始TCP数据包。用于测试非HTTP协议的服务。
SMTP SamplerServer: smtp.gmail.com, To: user@example.com发送邮件测试。可用于验证邮件服务性能。
HTTP Request Defaults可设置默认协议、服务器、端口、编码等为所有HTTP请求提供默认值,减少重复配置。优先级低于具体HTTP Request中的配置。

2.4 逻辑控制器(Logic Controllers)初步认识

控制器名称语法/使用方式用途说明注意事项
Simple Controller无参数,仅用于组织取样器对取样器进行逻辑分组,无执行逻辑控制。仅用于结构化脚本,不影响执行流程。
Loop ControllerLoop Count: 5 或 Infinite让子元素循环执行指定次数。常用于模拟重复操作,如连续刷新页面。
Once Only Controller无参数线程中仅执行一次,即使在外层循环中。适用于登录操作等只需执行一次的场景。
If ControllerCondition: ${age} > 18根据条件判断是否执行子元素。条件表达式支持JavaScript、Jexl3或默认语言,需注意语法差异。
While ControllerCondition: ${counter} < 10当条件为真时持续执行子元素。需确保条件最终能为假,避免死循环。
Foreach ControllerInput Variable Prefix: user, Output Variable: name遍历变量集合,依次赋值并执行子元素。常用于处理CSV或正则提取的多个值。
Transaction ControllerGenerate parent sample 勾选/不勾选将多个请求合并为一个事务,统计总耗时。勾选”Generate parent”后会在聚合报告中显示事务整体性能。

2.5 监听器(Listeners)查看测试结果

监听器名称语法/配置方式用途说明注意事项
View Results Tree无特殊配置,直接添加查看每个请求的请求头、响应数据、断言结果等。仅用于调试,GUI模式下大数据量会导致内存溢出。
View Results in Table无配置以表格形式展示请求结果(URL、响应时间、状态等)。比树形视图更节省资源,适合中等数据量查看。
Summary Report无配置显示每个请求的统计摘要:平均响应时间、TPS、错误率等。常用于分析关键指标,支持导出数据。
Aggregate Report无配置聚合报告,提供更详细的统计信息(中位数、90%行等)。是性能分析的核心监听器之一。
Graph Results可设置X轴(样本数)、Y轴(响应时间)以折线图展示响应时间变化趋势。可直观发现性能波动,但大数据量下图形可能卡顿。
jp@gc - Bytes Throughput Over Time需安装插件展示吞吐量随时间变化曲线。属于JMeter Plugins Manager扩展,需额外安装。
Save Responses to a file设置保存路径将响应结果保存到文件,用于后续分析。可指定保存成功/失败的响应,注意磁盘空间。

第三章:核心组件详解

3.1 线程组类型与参数详解(普通/Setup/Teardown线程组)

线程组类型语法/参数说明用途说明注意事项
Thread Group(普通)Number of Threads, Ramp-up, Loop Count, Scheduler主要用于执行核心业务逻辑的并发测试。所有取样器通常放在该线程组下,是性能测试的主体。
setUp Thread Group配置方式同普通线程组在所有线程组运行前执行,用于初始化操作。常用于准备测试数据、登录获取Token、预热缓存等前置任务。
tearDown Thread Group配置方式同普通线程组在所有线程组运行后执行,用于清理工作。常用于登出、删除测试数据、关闭连接等收尾操作。

执行顺序:setUp Thread Group → Thread Group(s) → tearDown Thread Group

注意:即使tearDown中配置了大量线程,也必须等待所有普通线程组完成后再执行。

3.2 HTTP 请求取样器配置详解

参数名称语法/示例值用途说明注意事项
NameLogin Request标识请求名称,便于识别建议命名清晰,反映业务含义。
Protocolhttp / https指定通信协议HTTPS会自动使用443端口,无需手动填写。
Server Name or IPapi.example.com目标服务器地址可使用变量(如${host})实现参数化。
Port Number8080服务端口若为默认端口(HTTP:80, HTTPS:443),可留空。
MethodGET, POST, PUT, DELETE, PATCH请求方法根据接口文档选择正确方法。
Path/user/login请求路径不包含域名和协议,可拼接参数或使用”Parameters”选项卡。
Content encodingUTF-8, GBK请求体编码格式影响中文参数传输,需与服务器一致。
ParametersKey: username, Value: test, Encode: √表单参数(application/x-www-form-urlencoded勾选Encode可自动URL编码。
Body Data{"username":"test","password":"123"}原始请求体(如JSON)用于POST/PUT请求,需配合Header Manager设置Content-Type为application/json
Files UploadFile Path: C:\file.txt, Param Name: file, MIME Type: text/plain文件上传配置MIME Type需正确填写,否则服务器可能拒绝。
Use multipart/form-data for POST勾选启用multipart格式上传文件或表单文件上传时必须勾选。

3.3 参数化实现方式:用户定义变量、CSV 数据文件设置

用户定义变量(User Defined Variables)

概念名称说明注意事项
定义方式在”User Defined Variables”中添加Name=Value对变量在测试计划启动时初始化,不可动态修改。
引用语法${variable_name}所有组件均可引用,作用域为整个测试计划。
初始化时机测试计划启动前一次性赋值不适用于运行时变化的值(如时间戳、随机数)。

CSV Data Set Config

参数名称语法/示例值用途说明注意事项
FilenameC:\data\users.csvCSV文件路径支持相对路径(相对于.jmx文件),建议使用变量统一管理路径。
Variable Namesusername,password定义列对应的变量名,逗号分隔必须与CSV内容列数一致,否则报错。
Delimiter,字段分隔符默认为逗号,若为TSV可改为\t
Allow quoted data?True / False是否允许字段包含引号通常为True。
Recycle on EOF?True到达文件末尾是否循环设为True可实现多轮测试数据复用。
Stop thread on EOF?False到达文件末尾是否停止线程若Recycle为False且Stop为True,则线程读完即停止。
Sharing modeAll threads / Current thread only变量共享模式All threads表示所有线程共享同一数据流;Current thread表示各线程独立读取。

3.4 断言(Assertions)类型与使用场景

断言类型配置说明用途说明注意事项
Response AssertionApply to: Main sample, Pattern: 200, success, ${expected_msg}验证响应文本或响应码是否符合预期。支持字符串、正则、相等、包含等多种模式。
Duration AssertionDuration in milliseconds: 2000验证响应时间不超过指定阈值。用于性能验证,超时则断言失败。
Size AssertionSize to Assert: 1024, Type: response bytes验证响应体大小(字节)是否符合要求。可用于检查资源是否完整加载。
JSON AssertionAssert JSON Path exists: $.data.id, Expected value: 123验证JSON响应中特定路径存在且值正确。需掌握JSON Path语法,是接口测试常用断言。
XML Assertion无配置,自动验证响应是否为合法XML检查响应是否为格式正确的XML。常用于SOAP接口测试。
HTML AssertionTidy warnings, Fatal errors 等选项验证HTML响应的合法性可检测HTML语法错误,适合Web页面测试。
MD5Hex AssertionMD5 hash: abc123def456验证响应体的MD5值是否匹配用于验证文件或资源完整性。

3.5 定时器(Timers)控制请求节奏

定时器类型配置说明用途说明注意事项
Constant TimerThread delay (milliseconds): 1000每个请求后固定延迟1秒。最简单定时器,模拟用户思考时间。
Gaussian Random TimerConstant Delay Offset: 500, Deviation: 200在基础延迟上加高斯随机波动。更真实模拟用户行为,避免请求过于规律。
Uniform Random TimerConstant Delay: 1000, Random Delay Range: 500延迟 = 固定值 + [-范围, +范围] 的随机值。生成均匀分布的延迟。
Synchronizing TimerNumber of Simulated Users to Group by: 50阻塞线程直到达到指定数量后一起释放。实现”瞬间并发”效果,用于压力峰值测试。
BeanShell TimerScript: return Integer.parseInt("${delay}");使用脚本动态计算延迟时间。灵活性高,但性能开销大,建议用JSR223替代。
Throughput Shaping Timer多行配置:Start RPS, End RPS, Duration按预设吞吐量曲线逐步加压。需安装”Concurrency Thread Group”插件,是高级负载测试工具。

3.6 前置处理器与后置处理器的作用与常见类型

前置处理器(Pre Processors)

名称用途说明注意事项
User Parameters在每次迭代前为线程设置变量值常用于为每个线程分配独立用户名、ID等。
BeanShell PreProcessor执行BeanShell脚本,动态设置变量或逻辑可调用Java API,但性能较差,建议用JSR223替代。
JSR223 PreProcessor使用Groovy/JavaScript等脚本语言预处理推荐使用Groovy,性能优于BeanShell。
HTTP URL Re-writing Modifier自动提取URL中的Session ID并重写用于URL重写式会话保持,现已较少使用。

后置处理器(Post Processors)

名称用途说明注意事项
Regular Expression Extractor通过正则提取响应中的动态数据语法较复杂,需注意贪婪与非贪婪匹配。
JSON Extractor提取JSON响应中的字段值支持JSON Path,推荐用于REST API测试。
XPath Extractor提取XML或HTML中的节点内容需了解XPath语法,适用于SOAP或网页解析。
BeanShell PostProcessor使用脚本处理响应并设置变量功能强大,可用于复杂逻辑处理。
Debug PostProcessor将提取结果输出到”View Results Tree”仅用于调试,确认变量是否正确提取。

3.7 逻辑控制器深入:循环、条件、事务控制器等

控制器名称配置说明用途说明注意事项
Loop ControllerLoop Count: 5 或 Infinite循环执行子节点可嵌套使用,实现复杂循环逻辑。
Foreach ControllerInput Variable Prefix: user, Output Variable: item遍历变量数组(如user_1, user_2…)输出变量item可在循环体内引用。
While ControllerCondition: {__jexl3("${counter}" < "10")}条件为真时持续执行需确保条件最终为假,避免死循环。
If ControllerCondition: ${status} == 1, Interpret Condition as Variable Expression: √根据条件决定是否执行子节点勾选”Interpret”后可用Jexl3或JavaScript表达式。
Transaction ControllerName: Login Transaction, Generate Parent Sample: √将多个请求合并为一个事务统计勾选”Generate Parent”后聚合报告中只显示事务总耗时。
Recording Controller无配置,用于存放通过HTTP(S) Test Script Recorder录制的请求代理录制模式下使用不能直接执行,仅用于组织录制的请求。
Include ControllerInclude Test Plan: path/to/external.jmx引入外部测试计划文件实现模块化脚本设计,便于复用。

3.8 监听器类型与结果分析技巧

监听器名称用途说明注意事项
View Results Tree调试用,查看请求/响应详情仅限GUI模式调试,禁用于正式压测。
Summary Report查看每个请求的平均响应时间、错误率等快速定位性能瓶颈接口。
Aggregate Report提供更详细的统计:90% Line, Throughput等是性能分析的核心报告之一。
Aggregate Graph图形化展示聚合报告数据可导出为图片或CSV。
jp@gc - Response Times Over Time显示响应时间随时间变化趋势需安装”Graphs Generator”插件,是分析性能拐点的关键工具。
jp@gc - Hits per Second每秒请求数(TPS)曲线观察系统吞吐量变化,结合响应时间分析系统状态。
jp@gc - Transactions per Second每秒事务数用于衡量系统处理能力。
Simple Data Writer将结果写入文件(.jtl正式测试必须使用,用于后续分析。
Monitor Results监控服务器资源(需服务器端配合)可显示CPU、内存使用率等,用于瓶颈定位。

第四章:动态数据处理与关联

4.1 正则表达式提取器(Regular Expression Extractor)

参数名称语法/示例值用途说明注意事项
Apply toMain sample only / Sub-samples / All samples指定作用范围通常选”Main sample only”。
Field to checkBody / Body as a Document / Response Code 等选择提取源字段Body最常用;Document支持全文搜索。
Reference Nametoken提取后存储的变量名后续用${token}引用。
Regular Expression"access_token":"(.+?)"正则模式,用括号捕获目标内容(.+?)为非贪婪匹配,避免跨标签匹配错误。
Template$1$指定使用第几个捕获组$1$表示第一个()$2$表示第二个。
Match No.0 (随机), 1 (第一个), -1 (全部)匹配结果的选择方式-1会生成token_1, token_2… 和token_matchNr变量。
Default ValueNOT_FOUND提取失败时的默认值避免后续引用空变量导致错误。

4.2 JSON 提取器(JSON Extractor)

参数名称语法/示例值用途说明注意事项
Names of created variablestoken, userId输出变量名,逗号分隔与JSON Path对应,顺序一致。
JSON Path expressions$.data.token, $.data.id使用JSON Path语法定位数据$.root.field表示根节点下字段;$..field 表示递归查找。
Match No. (0 for Random)0, 1, -1匹配数量选择-1提取所有匹配项,生成数组形式变量。
Compute concatenation var name?True / False是否生成拼接变量(如var_ALL用于统计总数或拼接结果。
Default ValuesEMPTY, 0提取失败时的默认值建议设置,防止脚本中断。

4.3 XPath Extractor 提取 XML/HTML 数据

参数名称语法/示例值用途说明注意事项
Apply toMain sample only作用范围
Reference NameorderId存储提取结果的变量名后续用${orderId}引用。
XPath Query//order[@status='success']/@idXPath表达式需掌握XPath语法,如//表示任意层级,@表示属性。
Default ValueNOT_FOUND提取失败默认值
Use Tidy (tolerant parser)True是否使用容错解析器解析HTMLHTML通常不规范,建议开启。
Quiet error reporting (tolerant parser)True静默错误报告减少日志输出。

4.4 使用 BeanShell 或 JSR223 处理复杂提取逻辑

BeanShell PostProcessor 示例

方法/语法代码示例用途说明注意事项
获取响应String response = prev.getResponseDataAsString();获取上一个请求的响应体prev 是预定义变量,代表上一个采样结果。
设置变量vars.put("dynamicId", "ID_" + System.currentTimeMillis());设置JMeter变量vars 是预定义变量,用于操作JMeter变量。
获取变量String name = vars.get("username");读取已有变量
日志输出log.info("Extracted ID: " + vars.get("dynamicId"));输出日志到jmeter.log便于调试脚本。
复杂逻辑处理if (response.contains("success")) { vars.put("status", "OK"); } else { vars.put("status", "FAIL"); }根据响应内容设置状态可实现条件判断、循环等复杂逻辑。

注意:推荐使用 JSR223 PostProcessor 配合 Groovy 语言,性能远优于BeanShell。

4.5 关联技术实战:登录会话保持与 Token 传递

步骤名称操作细节注意事项
发送登录请求使用HTTP Request发送用户名密码,获取响应中的Token或JSESSIONID确保请求参数正确,方法为POST。
提取Token使用JSON Extractor提取$.data.token 或 正则提取"token":"(.+?)"验证提取是否成功,可用Debug PostProcessor查看。
定义HTTP Header Manager添加Header: Authorization: Bearer ${token}大多数API使用Bearer Token认证。
应用到后续请求在其他HTTP Request中自动携带Header,实现认证所有需要登录的接口都应继承该Header Manager。
验证会话有效性发送一个受保护接口请求,检查返回是否为200和预期数据确保Token未过期,权限正确。
全局管理Token可将登录+提取放入setUp Thread Group,使Token全局可用避免每个线程组重复登录,提高效率。

第五章:参数化与数据驱动测试

5.1 用户定义变量(User Defined Variables)

概念名称说明注意事项
定义位置测试计划(Test Plan)下的”User Defined Variables”组件属于全局变量,所有线程组均可访问。
变量语法Name: env, Value: test,引用:${env}支持字符串、数字等基本类型。
初始化时机测试计划启动前一次性初始化运行时无法修改,适用于固定配置(如环境、域名、端口等)。
作用域整个测试计划若多个UVD存在,按顺序执行,后定义的覆盖先定义的同名变量。
典型用途环境标识(dev/test/prod)、基础URL(${base_url})、公共参数常用于集中管理配置,便于跨环境切换。

5.2 CSV Data Set Config 实现多用户数据输入

参数名称语法/示例值用途说明注意事项
Filenamedata/users.csv${data_dir}/users.csv指定CSV文件路径支持相对路径(相对于.jmx文件),推荐使用变量统一管理。
Variable Namesusername,password,role定义列对应的变量名必须与CSV列数一致,逗号分隔,无空格。
Delimiter,;\t字段分隔符若CSV含逗号内容,建议用分号或制表符。
Recycle on EOF?True / False文件读完是否循环True可实现多轮测试数据复用;False需配合”Stop thread on EOF”控制线程。
Stop thread on EOF?False / True读完是否停止线程通常设为False,让线程继续执行;设为True可用于控制测试数据量。
Sharing modeAll threads / Current thread / All threads (shared)线程间数据共享方式All threads:所有线程共享数据流(推荐用于多用户登录);Current thread:各线程独立读取同一文件(适合独立数据集)。

实战建议

  • 使用All threads模式,可实现100个线程共用100条用户数据,每条数据仅被使用一次(需Recycle=False)。
  • 配合”Counter”或__threadNum函数,可实现更复杂的取数逻辑。

5.3 函数助手(Function Helper)常用函数介绍

函数名称语法示例用途说明注意事项
${__Random(1,100,)}生成1-100之间的随机整数用于生成随机ID、数量等每次调用生成新值。
${__UUID()}生成标准UUID字符串,如a8f3e12a-...生成唯一标识符常用于请求ID、订单号等需要唯一性的场景。
${__time(yyyy-MM-dd)}格式化当前时间为2025-10-25获取当前日期时间支持Java SimpleDateFormat语法。
${__threadNum()}返回当前线程编号(从1开始)标识线程ID用于日志记录或生成线程唯一数据。
${__P(property_name,)}读取JMeter属性(可命令行传入)实现外部参数注入jmeter -Jenv=test,脚本中用${__P(env,)}读取。
${__property(file_path,,)}读取或写入JMeter属性跨线程组共享数据可实现setUp与主线程间通信。
${__split(var,.,part,)}将变量按分隔符拆分,提取指定部分处理复合字段${__split("a.b.c",.,2,)}返回b。

使用方式:通过”函数助手对话框”(菜单 > 选项 > 函数助手)生成函数字符串,复制到任一字段中。

5.4 随机变量与唯一值生成(_Random_UUID 等)

生成方式配置/语法示例用途说明注意事项
_Random 函数${__Random(1000,9999,)}生成指定范围内的随机数每次引用都可能不同,适合生成随机手机号、编号等。
_UUID 函数${__UUID()}生成36位UUID全局唯一,适合订单号、请求ID等。
_time + Random${__time(yyyyMMddHHmmss)}_${__Random(100,999,)}组合时间戳与随机数生成唯一键20251025102512_456,避免纯时间戳冲突。
Counter 计数器Start: 1, Increment: 1, Reference Name: counter生成递增序列号所有线程共享计数器,可生成全局唯一ID。
_RandomString${__RandomString(8,abcdef123456,)}生成指定长度和字符集的随机字符串适合生成密码、验证码等。

性能建议:优先使用_UUID_Random,避免在高并发下使用BeanShell生成随机值。

5.5 利用数据库或接口动态获取测试数据

方式一:JDBC Request 获取数据库数据

配置项示例值/说明注意事项
Variable namesuser_id,username查询结果列映射为JMeter变量
Result variable nameuserData将结果集存储为对象,可通过size、get等方法访问
SQL QuerySELECT id, name FROM users WHERE status=1 LIMIT 10;支持任意SELECT语句
使用方式配合”ForEach Controller”遍历结果集实现数据库驱动的数据输入

方式二:HTTP Request 调用接口获取数据

步骤操作说明注意事项
发送数据准备接口如调用/api/test-data返回JSON数组接口应支持分页或过滤,避免数据过多。
使用JSON Extractor提取$.[*].id获取所有IDMatch No. = -1 可提取全部匹配项。
遍历使用数据使用”ForEach Controller”循环处理每个ID实现”获取数据 → 使用数据”的闭环。
结合正则/XPath若接口返回HTML或XML,可用对应提取器解析适用于无API但有页面展示数据的场景。

优势:数据实时、准确,适用于复杂业务场景或数据依赖强的测试。


第六章:断言与测试验证

6.1 响应断言(Response Assertion)配置详解

配置项说明使用示例
Apply toMain sample / Sub-samples / All samples通常选”Main sample only”
Field to checkText Response / Response Code / Response Message / URLText Response最常用;Response Code用于验证状态码(如200)。
Pattern Matching RulesContains / Matches / Equals / SubstringContains最常用;Matches需完整匹配正则。
Patterns to Testsuccess, 200, ${expected_code}, 登录成功可添加多行,任意一行匹配即通过。
Add Pattern点击添加按钮支持正则表达式(如"code":(\d+)
Ignore Status勾选后即使断言失败也不标记请求为失败谨慎使用,可能掩盖问题。

典型场景

  • 验证接口返回"status":"success"
  • 验证HTTP状态码为200
  • 验证错误信息包含”用户名不存在”

6.2 JSON 断言(JSON Assertion)

配置项说明使用示例
Names of JSON paths to assert添加需验证的JSON Path表达式$.code, $.data.id, $.msg
Expected value填写期望值0, ${expected_id}, 操作成功
Match as a regular expression是否将期望值视为正则表达式如期望值为^SUCCESS.*,可匹配SUCCESS_OK等。
Invert assertion (will fail if pattern matches)反向断言(匹配则失败)用于验证”不应出现”的字段。

优势:专为JSON设计,语义清晰,避免正则误匹配。

注意:需确保响应为合法JSON,否则断言失败。

6.3 比较断言(Compare Assertion)用于精确对比

配置项说明注意事项
作用范围可添加多个请求样本进行对比通常用于验证两个请求返回是否一致(如缓存前后)
对比内容响应头、响应体、响应码等可选择对比哪些部分
忽略字段可配置忽略时间戳、ID等动态字段如忽略"timestamp":".*?"
使用场景接口幂等性测试、缓存一致性验证、数据同步校验需手动添加多个采样器到同一比较断言中
性能影响高,仅用于调试或低并发验证禁止在高并发压测中使用。

6.4 大小断言(Size Assertion)检查响应体大小

配置项说明示例值
Size to Assert指定大小值(字节)1024(1KB)
Type of ComparisonIs equal to / Is greater than / Is less than / Is greater than or equal to / Is less than or equal to根据需求选择比较方式

应用场景

  • 验证文件下载完整性:如断言图片响应大小 > 50KB
  • 检查资源是否被压缩
  • 防止空响应

注意事项:大小为响应体字节数,非字符数(中文占2-3字节),需考虑编码影响(UTF-8下中文占3字节)。

6.5 Duration Assertion 控制响应时间阈值

配置项说明示例值
Duration in milliseconds设置最大允许响应时间2000(2秒)
断言逻辑响应时间 ≤ 设定值则通过,否则失败用于性能验证

典型用途

  • SLA监控:如要求95%请求响应时间 < 1.5s
  • 性能回归测试
  • 压力测试阈值控制

结合聚合报告:在Aggregate Report中查看”90% Line”与断言值对比,综合评估系统性能。

注意事项:断言失败会标记请求为”失败”,影响错误率统计,建议在性能验证阶段使用,避免调试阶段误判。


第七章:性能测试类型实践

7.1 并发测试设计与线程组配置

测试目标验证系统在指定并发用户数下的响应能力与稳定性
核心指标并发用户数(Threads)、响应时间(RT)、错误率(Error %)、吞吐量(Throughput)

线程组配置要点

参数配置建议说明
Number of Threads (users)根据业务场景设定,如模拟100用户同时登录表示虚拟用户数,即并发请求数
Ramp-up Period (seconds)0 或极小值(如1秒)若需瞬时并发,设为0;若需逐步启动,设为非零值(如10秒内启动100线程 → Ramp-up=10)
Loop Count固定次数(如10)或”Forever”控制每个线程执行采样器的次数
Scheduler勾选,设置持续时间(Duration)推荐使用”Duration”控制运行时间,避免无限循环

典型场景

  • 登录接口并发测试:100线程,Ramp-up=1,Loop=1 → 实现100用户几乎同时发起请求
  • 页面浏览并发:50线程,Ramp-up=10,持续5分钟 → 模拟渐进式用户访问

注意事项

  • Ramp-up=0 时,JMeter 尽可能快地启动所有线程,但受本地资源限制,未必真正”同时”
  • 高并发下需监控JMeter自身CPU和内存,避免成为瓶颈

7.2 负载测试:阶梯加压与稳定运行

测试类型目标方法
稳定负载测试验证系统在中等压力下的长期稳定性固定线程数 + 持续运行(如50线程,运行30分钟)
阶梯加压测试观察系统在逐步增加负载下的表现使用Concurrency Thread Group + Throughput Shaping Timer

阶梯加压实现方式(推荐)

工具配置示例
Concurrency Thread Group(需安装Custom Thread Groups插件)Target Concurrency: [50, 100, 150, 200],Ramp-up Time: 300(5分钟从50升至200),Hold Target Rate Time: 600(每档位稳定10分钟)
Throughput Shaping Timer配合Concurrency Thread Group,定义负载曲线,可视化调节

关键监控指标

指标正常表现异常信号
响应时间平稳或缓慢上升突增或持续上升
吞吐量(TPS)稳定或小幅波动明显下降
错误率< 0.1%> 1%
服务器资源(CPU、内存、IO)低于80%持续接近100%

输出要求:生成负载测试报告,包含”用户数-响应时间”、“用户数-吞吐量”趋势图。

7.3 压力测试:极限并发与资源瓶颈探测

目标找出系统最大承载能力及瓶颈点(CPU、内存、数据库连接等)

实施策略

方法说明
持续加压至崩溃使用Concurrency Thread Group不断增加并发,直到错误率飙升或响应时间超限
资源监控同步采集服务器CPU、内存、磁盘IO、网络、JVM(GC)、数据库连接池等
观察拐点拐点1:响应时间急剧上升;拐点2:吞吐量不再增长甚至下降;拐点3:错误率突破阈值(如5%)

典型配置

# 示例:压力测试参数
Target Concurrency: 从100开始,每5分钟+50,直至500
Ramp-up Time: 300秒(每档位)
Hold Time: 300秒
Stop when: Error rate > 10% 或 Response Time > 5000ms

瓶颈分析方向

现象可能瓶颈
CPU持续100%应用逻辑复杂、死循环、算法效率低
内存溢出或频繁GC内存泄漏、JVM配置不当、缓存过大
数据库连接池耗尽SQL慢查询、连接未释放、连接池过小
磁盘IO高日志写入频繁、数据库读写密集
网络带宽满返回数据过大、静态资源未压缩

注意:压力测试可能导致系统不可用,严禁在生产环境直接执行。

7.4 分布式测试环境搭建与执行

组件角色配置要求
Master(主控机)控制多个Slave,收集结果,生成报告安装完整JMeter,无需高配置
Slave(执行机)执行压测脚本,生成负载高性能服务器,独立于被测系统
NetworkMaster与Slave间网络延迟应 < 1ms建议在同一局域网

搭建步骤

  1. 环境准备:所有机器安装相同版本JDK和JMeter,关闭防火墙或开放端口(默认1099和RMI端口)

  2. Slave配置:修改 bin/jmeter.properties

    server.rmi.localport=50000
    server_port=1099

    启动Slave:jmeter-server(Linux)或 jmeter-server.bat(Windows)

  3. Master配置:修改 bin/jmeter.properties

    remote_hosts=192.168.1.10:1099,192.168.1.11:1099
  4. 执行测试

    • GUI模式:菜单 → 运行 → Remote Start → 选择Slave
    • 命令行:jmeter -n -t test.jmx -r-r表示运行所有远程主机)

优势:突破单机线程限制,模拟更大并发。

注意:结果文件(.jtl)由Slave生成并回传Master,需确保网络稳定。

7.5 持续集成中集成 JMeter(结合 Jenkins)

目标实现自动化性能测试,融入CI/CD流程

集成方案

工具作用
Jenkins调度任务、触发测试、展示报告
Maven/Gradle管理JMeter依赖与执行(可选)
Ant传统方式,调用JMeter命令行
Performance PluginJenkins插件,解析.jtl并生成趋势图

实现步骤

  1. 准备脚本:将.jmx文件纳入版本控制(如Git)

  2. Jenkins任务配置:构建步骤,执行Shell:

    jmeter -n -t /path/to/test.jmx -l /path/to/results.jtl -e -o /path/to/report/
  3. 结果处理:使用”Publish Performance test result report”插件解析.jtl,或直接发布HTML报告目录

  4. 触发条件:每日构建、代码提交后、发布前门禁

关键优势

  • 自动化执行,减少人为干预
  • 历史趋势对比,及时发现性能退化
  • 与单元测试、接口测试并列,形成完整质量保障

建议:初期可先做”冒烟性能测试”(低并发快速验证),再逐步扩展。


第八章:高级脚本开发

8.1 BeanShell 脚本基础语法与应用场景

特性说明
语言Java语法子集,动态解释执行
组件BeanShell PreProcessor / PostProcessor / Sampler / Assertion
性能较慢,不推荐用于高并发场景

常用语法示例

// 获取变量
String token = vars.get("auth_token");
// 设置变量
vars.put("userId", "1001");
// 日志输出
log.info("Current user: " + vars.get("username"));
// 操作属性(全局)
props.put("global_counter", "100");
// 生成随机数
int rand = (int)(Math.random() * 100);
vars.put("random_num", String.valueOf(rand));

典型应用场景

  • 请求前动态生成签名(MD5、HMAC)
  • 响应后提取复杂逻辑数据
  • 条件判断控制流程(如跳过某些请求)

替代方案:优先使用JSR223 + Groovy(性能更好)。

8.2 JSR223 Sampler 与 Groovy 脚本编程

优势说明
性能Groovy编译为字节码,执行效率接近Java
语法兼容Java,支持闭包、GString等高级特性
API可调用Java类库、JMeter API

常用对象(Groovy中可用)

对象用途
varsvars.get("x"), vars.put("y","1") —— 访问变量
propsprops.get("jmeter.home") —— 访问JMeter属性
loglog.info("msg") —— 写入jmeter.log
SampleResultSampleResult.setResponseData("data") —— 控制采样结果

示例:生成带时间戳的签名

import java.security.MessageDigest

def timestamp = System.currentTimeMillis().toString()
def appId = "test_app"
def secret = "my_secret"
def signStr = "${appId}${timestamp}${secret}"

def md = MessageDigest.getInstance("MD5")
byte[] digest = md.digest(signStr.getBytes("UTF-8"))
def signature = digest.encodeHex().toString()

// 设置为变量
vars.put("timestamp", timestamp)
vars.put("signature", signature)

推荐:所有复杂脚本开发优先使用 JSR223 PreProcessor / PostProcessor + Groovy。

8.3 自定义函数与变量传递机制

机制说明范围
vars.put() / vars.get()线程内变量共享当前线程
props.put() / props.get()全局属性共享所有线程组、所有JVM实例
__setProperty() / __property()函数方式操作属性跨线程组通信
Inter-Thread Communication Plugin专用插件,提供队列机制线程组间安全通信

跨线程组传值示例

线程组A(生成数据)

// JSR223 PostProcessor
props.put("shared_token", "abc123xyz")

线程组B(使用数据)

// 在HTTP请求中使用
${__property(shared_token,,)}

注意:props是静态的,修改会影响所有线程,需注意命名冲突。

8.4 操作文件系统与日志记录

读写文件(Groovy)

// 写入文件
new File("/tmp/log.txt") << "User: ${vars.get('username')} logged at ${new Date()}\n"

// 读取文件(逐行)
new File("data/ids.txt").eachLine { line ->
    log.info("ID: ${line.trim()}")
}

日志记录

log.info("Starting process...")
log.warn("This is a warning")
log.error("An error occurred", new Exception("test"))

日志位置jmeter.log 文件,可用于调试脚本。

安全提示:避免在生产脚本中频繁写文件,影响性能。

8.5 调用外部 API 或数据库进行预处理/后处理

调用外部API(Groovy + HTTPBuilder)

@Grab('org.apache.httpcomponents:httpclient:4.5.13')
import org.apache.http.client.methods.HttpGet
import org.apache.http.impl.client.HttpClients

def client = HttpClients.createDefault()
def get = new HttpGet("https://api.example.com/clear-cache")
def response = client.execute(get)
def statusCode = response.getStatusLine().getStatusCode()

if (statusCode == 200) {
    log.info("Cache cleared successfully")
} else {
    log.error("Failed to clear cache")
}

注意:需将依赖jar包放入JMETER_HOME/lib目录。

数据库操作(JDBC)

  • 推荐使用 JDBC PreProcessor / PostProcessor
  • 配置JDBC Connection Configuration
  • 执行SQL:
-- 预处理:清理数据
DELETE FROM test_users WHERE name LIKE 'test_%';

-- 后处理:验证数据写入
SELECT count(*) FROM orders WHERE status = 'paid';

用途

  • 测试前初始化数据
  • 测试后清理环境
  • 验证业务数据一致性

第九章:结果分析与报告生成

9.1 查看结果树、聚合报告、图形结果解读

监听器名称核心功能使用建议与解读要点
查看结果树 (View Results Tree)查看每个请求的详细响应(Headers、Response、Request),调试脚本、验证断言仅用于调试,高并发下禁用(消耗大量内存)。可筛选”失败”或”成功”请求,支持JSON、HTML、XML格式化显示
聚合报告 (Aggregate Report)汇总所有采样器的性能数据,关键指标:平均响应时间、TPS、错误率、吞吐量核心分析工具。关注 90% Line(90%请求的响应时间 ≤ 该值),#Samples 反映请求总数,用于评估测试量
图形结果 (Graph Results)实时绘制响应时间、吞吐量趋势图,X轴为请求序号,Y轴为响应时间/吞吐量观察响应时间波动是否剧烈、吞吐量是否稳定。不适合高并发,图形渲染慢且占用资源

实战解读示例

  • 若 90% Line 从500ms升至2s,说明系统出现性能退化。
  • 错误率 > 1% 需立即排查(网络、服务、脚本问题)。
  • TPS 曲线下降伴随响应时间上升,可能达到系统瓶颈。

9.2 生成 HTML 性能报告 dashboard

步骤操作说明注意事项
1. 命令行执行测试jmeter -n -t test.jmx -l result.jtl -e -o report_dashboard/-e 启用报告生成,-o 指定输出目录
2. 报告生成配置user.propertiesjmeter.properties 中配置
jmeter.reportgenerator.apdex_satisfied_threshold=500Apdex 满意阈值(ms)
jmeter.reportgenerator.apdex_tolerating_threshold=1500Apdex 容忍阈值(ms)
jmeter.reportgenerator.overall_granularity=60000报告时间粒度(ms)
3. 报告内容自动生成包含以下页面的HTML报告

报告包含页面

  • Over Time:响应时间、TPS、活跃线程随时间变化曲线 — 识别性能拐点
  • Statistics:按采样器分组的详细统计表(类似聚合报告)— 定位慢接口
  • Response Times Distribution:响应时间分布直方图 — 分析延迟集中区间
  • Errors:按错误类型和响应码分类统计 — 快速定位失败原因

优势

  • 图形化、结构化,便于汇报与归档
  • 支持多维度钻取分析
  • 可嵌入CI/CD流程自动生成

9.3 报告关键指标说明(TPS、响应时间、错误率等)

指标名称定义与计算方式业务意义与目标建议
TPS (Transactions Per Second)单位时间内成功处理的事务数(JMeter中常指成功请求数)衡量系统处理能力。目标:稳定且尽可能高。
平均响应时间所有请求响应时间的算术平均值基础性能指标,但易受极端值影响。
90% / 95% / 99% Line90%的请求响应时间 ≤ 该值(如90% Line = 800ms)比平均值更真实,反映大多数用户感受。目标:90% < 1s,99% < 2s。
错误率 (Error %)失败请求数 / 总请求数 × 100%健康度指标。目标:≤ 0.5%(生产环境要求更高)。
吞吐量 (Throughput)总请求数 / 测试总时长(等同于TPS)与TPS一致,单位可能为”KB/sec”表示带宽。
活跃线程数实时并发用户数与TPS结合分析,判断系统并发处理效率。
Apdex (Application Performance Index)(满意请求数 + 0.5×容忍请求数) / 总请求数用户满意度指数。目标:≥ 0.85(良好),≥ 0.94(优秀)。

Apdex 计算示例

设定:满意=500ms,容忍=1500ms
100个请求中:60个 <500ms,30个 500~1500ms,10个 >1500ms
Apdex = (60 + 0.5×30) / 100 = 0.75(需优化)

9.4 结果数据导出与第三方工具分析(Excel、Grafana)

导出为 CSV/Excel

步骤说明
1. 获取JTL文件JMeter运行后生成的result.jtl(本质是CSV)
2. 用Excel打开可筛选、排序、生成图表(如响应时间趋势图)
3. 数据透视表分析按接口、响应码、时间区间进行多维统计

集成 Grafana + InfluxDB

组件角色说明
Backend ListenerJMeter内置组件,将实时结果发送到InfluxDB
InfluxDB时序数据库,存储性能指标
Grafana可视化平台,创建动态仪表盘

配置 Backend Listener

class name: org.apache.jmeter.visualizers.backend.influxdb.InfluxdbBackendListenerClient
influxdbUrl: http://influxdb:8086
application: jmeter-test
measurement: jmeter

优势

  • 实时监控压测过程
  • 自定义丰富图表(如火焰图、热力图)
  • 与Prometheus等生态集成

9.5 常见性能瓶颈定位方法

瓶颈类型定位方法工具/指标
应用层查看JVM内存、GC日志,分析慢方法(Arthas、JProfiler)GC频率高、Full GC频繁,线程阻塞、死锁
数据库检查慢查询日志,监控连接池使用率,SQL执行计划分析数据库CPU高,连接池耗尽(max pool size),锁等待
中间件Redis内存使用、命中率,MQ积压情况,Nginx连接数、5xx错误Redis内存溢出,RabbitMQ消息堆积,Nginx 502/504
网络检查带宽利用率,TCP连接状态(TIME_WAIT过多),DNS解析延迟网络IO打满,netstat 查看连接数
服务器CPU使用率 > 90%,内存不足(Swap使用),磁盘IO等待高top, htop, iostat, vmstat
代码同步阻塞调用,未关闭资源(Connection、Stream),低效算法线程堆栈分析发现wait()sleep()

定位流程

  1. 看 JMeter报告 → 2. 查 服务器资源 → 3. 分析 应用日志 → 4. 审查 数据库/中间件 → 5. 优化 代码逻辑

第十章:最佳实践与常见问题

10.1 JMeter 脚本设计最佳实践

实践原则具体建议
模块化设计使用”模块控制器”或”Include Controller”复用登录、公共头等逻辑
参数化驱动所有动态数据(用户、ID)使用CSV、数据库或函数生成,避免硬编码
断言合理使用关键接口添加断言,但避免过多影响性能;调试阶段可开启,压测时酌情关闭
监听器按需启用仅调试时使用”查看结果树”,压测时仅保留”聚合报告”或”Backend Listener”
命名规范采样器、控制器、变量命名清晰(如 GET /api/users, login_token
版本控制.jmx 文件纳入Git管理,便于协作与回溯
使用插件扩展推荐 Custom Thread Groups、JSON Path Extractor、PerfMon 等

10.2 内存优化与大并发下的调优建议

问题优化方案
JMeter 本身内存不足启动前调整JVM参数:export JVM_ARGS="-Xms2g -Xmx2g -Xmn512m"
监听器消耗过大禁用”查看结果树”、“聚合图形”等;使用 -l result.jtl 重定向结果
高并发卡顿使用 Concurrency Thread Group 精确控制并发,配合 Throughput Shaping Timer 限流
结果文件过大减少采样器数量,仅记录必要字段(修改 jmeter.propertiesjmeter.save.saveservice.*
GC频繁增加堆内存,使用G1垃圾回收器:-XX:+UseG1GC

建议配置(1000+并发)

  • 机器:16核CPU,32GB内存
  • JVM:-Xms8g -Xmx8g -XX:+UseG1GC
  • 禁用所有GUI监听器

10.3 常见错误代码与排查思路

错误类型可能原因排查步骤
Non HTTP response code: java.net.ConnectException网络不通、服务未启动、防火墙拦截ping / telnet 测试连通性,检查服务端口是否开放
500 Internal Server Error服务端异常(空指针、数据库错误)查看服务日志,检查请求参数是否合法
401 Unauthorized / 403 Forbidden认证失败、Token过期、权限不足检查Header中Authorization,验证Token生成逻辑
404 Not FoundURL路径错误、环境不一致核对Base URL和Path,检查环境配置
502 Bad GatewayNginx反向代理后端服务无响应检查后端服务状态,查看Nginx error.log
Response Time Too High系统过载、数据库慢查询、网络延迟检查服务器资源,分析慢接口,使用Duration Assertion定位超时请求

10.4 分布式测试中的网络与同步问题

问题原因与解决方案
Slave 无法连接 Master防火墙未开放1099/50000端口,server.rmi.localport 冲突
时间不同步各节点时间差异导致日志混乱、定时任务异常
网络延迟高Master与Slave跨地域,控制指令延迟
结果聚合慢大量数据通过网络传输,带宽不足
脚本路径不一致Master上路径 /home/user/test.jmx,Slave上不存在

建议:分布式测试前进行连通性测试(jmeter-server 能否注册)。

10.5 版本兼容性与插件管理

问题说明与建议
JMeter 版本选择生产推荐 5.6.3 或 5.7(稳定),避免使用过旧版本(如3.x)
插件兼容性使用 Plugins Manager 安装插件,自动解决依赖(菜单:Options > Plugins Manager),避免手动复制JAR包,易导致版本冲突
升级风险升级前备份脚本,在测试环境验证插件兼容性,查看官方Release Notes
插件推荐Basic Config Elements、Custom Thread Groups、JSON/YAML Support、PerfMon Metrics Collector

管理建议

  • 团队统一JMeter版本与插件清单
  • 使用Docker镜像固化环境,避免”在我机器上能跑”问题