欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

性能测试相关分享

程序员文章站 2024-03-23 22:02:10
...

性能测试相关
1.为什么要做性能测试
.基于网络的分布式应用
.用户数量增加-系统负载
.能够承受的并发用户数量
.带宽-CPU-内存的占用
.硬盘速度是否跟得上
.系统稳定性-响应时间
2.性能测试概念
-负载测试:Load Testing 用户数量性能
-压力测试:Stress Testing 高压力:系统奔溃,卡死
-容量测试:Volumn Testing 最大支撑数量,响应时间
-吞吐量/吞吐率: IO 对应: 性能测试相关分享
3.性能测试关注点
性能测试相关分享
4 性能测试原理

性能测试相关分享
示例:

  
Jmeter性能测试
Jmeter性能测试
一 Jmeter简单使用
1、创建一个线程组


添加之后如下所示:


参数解释:
Number of Threads (users):虚拟用户数,一个虚拟用户占用一个进程或线程,设置多少虚拟用户数在这里也就是设置多少个线程数。  
Ramp-Up Period (in seconds):准备时长,设置的虚拟用户数需要多长时间全部启动。如果线程数为10,准备时长为2,那么需要2秒钟启动10个线程,也就是每秒钟启动5个线程。 
Loop Count:循环次数,如果勾选Forever,那么所有线程会一直发送请求,一到选择停止运行脚本。
Delay Thread creation until needed:直到需要时延迟线程的创建。
Scheduler:调度器(配置调度器时,需要勾选循环次数为永远) 
Duration (seconds):持续时间
Startup delay:启动延迟时间

2、创建一个HTTP请求


添加之后如下:
这里我们用百度做测试,用GET请求去请求百度搜索"testSomething"关键字(params需要点击add添加,关键字需要点击URL Encode)


3、添加察看结果树


4、点击运行查看结果
这里我们可以看到请求是200成功


二 Jmeter性能测试

1、Java脚本代码编写
1、从Jmeter的安装目录lib/ext中拷贝两个文件ApacheJMeter_core.jar和ApacheJMeter_java.jar到项目中,然后引入这两个JAR包。

或者在maven项目的pom.xml文件中添加:
  <dependencies>
    <!--jmeter-->
    <dependency>
      <groupId>org.apache.jmeter</groupId>
      <artifactId>ApacheJMeter_core</artifactId>
      <version>5.0</version>
    </dependency>

    <dependency>
      <groupId>org.apache.jmeter</groupId>
      <artifactId>ApacheJMeter_java</artifactId>
      <version>5.0</version>
    </dependency>
    <!--jmeter-->
  
    ...
    </dependencies>
  
然后用maven install,会自动下载插件

2、创建一个类TestSomething,需要继承于AbstractJavaSamplerClient,同时需要重写几个方法:

package com.fshows.test.performance;

import com.alibaba.fastjson.JSONObject;
import okhttp3.*;
import org.apache.jmeter.config.Arguments;
import org.apache.jmeter.protocol.java.sampler.AbstractJavaSamplerClient;
import org.apache.jmeter.protocol.java.sampler.JavaSamplerContext;
import org.apache.jmeter.samplers.SampleResult;

import java.io.IOException;
import java.util.Objects;
import java.util.concurrent.TimeUnit;

public class TestSomething extends AbstractJavaSamplerClient {

    private String encoding = "utf-8";
    private String url = "https://www.baidu.com/";

    /*
     * 初始化方法,初始化性能测试时的每个线程
     * 实际运行时仅执行一次,在测试方法运行前执行,类似于init方法
     */
    @Override
    public void setupTest(JavaSamplerContext context) {
        super.setupTest(context);
        // 这里做测试前提条件的准备
    }

    /*
     * 性能测试时的线程运行体
     * 测试执行的循环体,根据线程数和循环次数的不同可执行多次
     */
    @Override
    public SampleResult runTest(JavaSamplerContext javaSamplerContext) {
        SampleResult result = new SampleResult();
        result.setDataType(SampleResult.TEXT);

        // 根据被测接口创建请求,组装参数


        // 放置请求参数requestDate,可以在Jmeter结果树的request看到
        result.setSamplerData(requestDate.toString());

        // 定义一个事务,表示这是事务的起始点
        result.sampleStart();

        // 请求接口,拿到返回值response


        //定义一个事务,表示这是事务的结束点
        results.sampleEnd();

        // 解析response
        String responseBody = Objects.requireNonNull(response.body()).string();
        JSONObject jsonObject = JSONObject.parseObject(responseBody);

        if (jsonObject.getBoolean("success")) {
            result.setSuccessful(true);
            result.setResponseMessage(responseBody);
            result.setResponseData(responseBody, encoding);
        } else {
            result.setSuccessful(false);
            result.setResponseData("response content error:" + responseBody, encoding);
        }


        // 某些post请求传递json数据的实现,这里我们用OkHttpClient去发送请求
        OkHttpClient okHttpClient = new OkHttpClient.Builder()
                .connectTimeout(10, TimeUnit.SECONDS)//设置连接超时时间
                .readTimeout(20, TimeUnit.SECONDS)//设置读取超时时间
                .build();

        // 拼接json参数
        JSONObject jsonObj = new JSONObject();
        jsonObj.put("jsonKey", "jsonValue");
        MediaType JSON = MediaType.parse("application/json; charset=utf-8");
        RequestBody requestJsonBody = RequestBody.create(JSON, jsonObj.toString());

        Request request = new Request.Builder()
                .url(url) // 目标url
                .post(requestJsonBody) // json数据
                .addHeader("headersKey", "headersValue") // 某些请求头传递的数据
                .addHeader("content-type", "application/json")
                .build();
        Call call = okHttpClient.newCall(request);

        result.setSamplerData(request.toString());
        try {
            // 请求获取response
            Response response = call.execute();
            // 解析response

        } catch (IOException e) {
            result.setResponseData("request to server error:" + e, encoding);
            result.setSuccessful(false);
            return result;
        } catch (Exception e) {
            result.setResponseData("other error:" + e, encoding);
            result.setSuccessful(false);
            return result;
        }
        
        // 最后需return result
        return result;
    }


    // 入口函数
    public static void main(String[] args) {
        JavaSamplerContext arg0 = new JavaSamplerContext(new Arguments());
        TestSomething test = new TestSomething();
        test.setupTest(arg0);
        test.runTest(arg0);
    }
}


2、Jmeter运行
1、首先需要将代码打包,将得到的jar包放在apache-jmeter-5.0\lib\ext目录下,然后重启Jmeter
启动如果出现内存溢出的异常 java.lang.OutOfMemoryError: Java heap space
在apache-jmeter-5.0\bin目录下根据系统找到对应的启动项进行修改



if not defined HEAP (
    rem See the unix startup file for the rationale of the following parameters,
    rem including some tuning recommendations
    set HEAP=-Xms1g -Xmx8g -XX:MaxMetaspaceSize=512m
)

2、这次添加完线程组之后需要添加一个 Java Request


添加之后就可以看到打的jar包内写的代码用例


3、对Java Request添加查看响应结果
View Results Tree : 结果树查看
Aggregate Report:聚合报告


我们在线程组里模拟100个users - Number of Threads (users),然后运行一个Java Request,查看聚合报告

参数解释:
Label:每个JMeter的element(例如 Java Request)都有一个Name属性,这里显示的就是Name属性的值
#Samples:请求数,表示这次测试中一共发出了多少个请求
Average:平均响应时间,默认情况下是单个Request的平均响应时间
Median:中位数,也就是 50% 用户的响应时间  
90% Line:90% 用户的响应时间  
Min:最小响应时间  
Max:最大响应时间  
Error%:错误率,错误请求数/请求总数  
Throughput:吞吐量,默认情况下表示每秒完成的请求数(Request per Second)
KB/Sec:每秒从服务器端接收到的数据量

3、Jmeter并发
1、Jmeter启动了之后线程就会直接发送测试请求,但是如果要模拟在一瞬间高并发量测试的时候,需要调高线程数量,这很耗测试机器的性能,往往无法支持较大的并发数,无法控制每次测试的瞬间并发量,这时候需要使用synchronized timer阻塞线程,直到指定的线程数量到达后,再一起释放,可以瞬间产生很大的压力

添加synchronized timer




参数解释:
Number of Simulated Users to Group by:每集合够多少个模拟用户(线程)后发送一次测试请求;如果设置为0,等同于设置为线程租中的线程数;确保设置的值不大于它所在线程组包含的用户数(线程数),否则会一直集结线程而不发出测试请求,直到超时(如果设置了的话)
Example:Number of Simulated Users to Group by: 100   表示并发量是100,也就是说,Jmeter会等到100个线程都运行到此处时,这100个线程才开始执行后面的操作,先到达的线程将会在此等候

Timeout in milliseconds:超时时间,即多少毫秒后同时释放已集结的的线程,发送测试请求;如果设置为0,Timer将等待线程数达到了"Number of Simultaneous Users to Group"中设置的值才释放
Example:Timeout in milliseconds: 100  表示超时时间为100ms,当100ms后还没达到"Number of Simultaneous Users to Group"中设置的值,Timer将不再等待,直接释放已到达的线程

当我们要进行并发测试时,比如要进行500的并发量测试,需要进行的设置如下:




这样Jmeter就会集结500个线程(users),集结完成后会在0s内发送完请求,达到并发效果

2、synchronized timer放置位置说明
如果希望定时器仅应用于其中一个sampler,则把该定时器作为子节点加入,如下图


如果希望synchronizing timer应用于多个sampler,如下图,当执行一个sampler之前时,和sampler处于相同作用域的定时器都会被执行


注意:
在Jmeter中,timer是在sampler之前执行的。不管这个定时器的位置放在sampler之后,还是之前。当然,如果有多个timer的时候,在相同作用域下,会按上下顺序执行timer,这个就需要慎重放置timer的顺序;不过,为了更好的可读性,还是建议将timer放在对应的sampler前面或子节点中

4、Jmeter分布式
待补充

三 相关下载

1、Jmeter
Jmeter下载:http://jmeter.apache.org/download_jmeter.cgi
apache-jmeter-5.0.zip(54.3 MB)

2、插件
此外,Jmeter还提供了插件来满足不同情况下的需求
插件下载:https://jmeter-plugins.org/install/Install/

如果不想看,可阔以,把下面这个东东放到lib/ext目录,然后重启JMeter,在options下选择自己需要的安装
https://jmeter-plugins.org/get/  < 就这个


可能,大概,也许会用到的插件:
 aaa@qq.com - Active Threads Over Time -- 活跃线程数量随时间的推移变化
 aaa@qq.com Transaction per Second -- 每秒事务处理量
 aaa@qq.com Response Times Over Time -- 响应时间随着时间的推移变化