JMeter是否支持线程间共享内存,避免大请求体重复占用内存?
JMeter大请求体多线程测试OOM解决方案
${__FileToString()}函数的执行逻辑是每个线程独立触发文件读取、独立生成字符串对象存入线程私有内存,300并发下会生成300份10MB的重复请求体数据,单这部分内存占用就接近3GB,触发OOM是必然结果。以下方案可实现全线程共享单份数据副本,从根源降低内存占用:
- 全局属性共享方案(改动最小,推荐)
- 在测试计划最前方添加
setUp Thread Group(初始化线程组),配置线程数为1、循环次数为1,保证整个测试启动阶段仅执行1次 - 在该初始化线程组下添加JSR223 Sampler,选择Groovy作为脚本语言,写入如下代码:
// 测试启动时仅读取1次文件,存入JVM级全局属性 String requestBody = new File("data.json").text props.put("shared_req_body", requestBody)- 将原HTTP请求体里的
${__FileToString(data.json)}替换为${__P(shared_req_body,)}即可
关键说明:
props是JMeter的JVM级全局属性容器,所有线程读取的是同一个字符串对象的引用,不会为每个线程生成独立副本,这部分请求体的内存占用会从3GB左右降到固定10MB。不要用vars存储该内容,vars是线程私有变量容器,存入后依然会为每个线程复制独立副本,起不到节省内存的作用。 - 在测试计划最前方添加
- 文件流直传方案(零额外内存占用,适合无需修改请求体的场景)
如果你的请求体不需要做动态参数替换,可以完全跳过"把文件加载到内存"的步骤:- 清空HTTP请求的请求体输入框
- 切换到HTTP请求的「Send Files With The Request」标签,新增条目选择本地的data.json文件
- 配置项填写:
Parameter Name留空,MIME Type填application/json,取消勾选Use multipart/form-data for POST选项
该模式下JMeter不会把整个文件加载到堆内存,而是直接通过文件流将内容写入请求网络通道,哪怕请求体体积更大也不会占用过多堆内存。
- 避坑提醒
不要在HTTP请求体中直接嵌套调用${__FileToString()},就算后续需要对请求体做动态参数修改,也请先把基础内容加载到全局属性后,再基于全局属性做局部调整,避免重复读取文件生成大量重复内存对象。
内容的提问来源于stack exchange,提问作者sai
相关产品推荐
相关产品推荐

