Jmeter 支持自定义jar包压测MQ实现

添加自己需要的依赖:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>org.example</groupId>
    <artifactId>MqDemo01</artifactId>
    <version>1.0-SNAPSHOT</version>

    <!-- 防止打出jar包后,中文参数乱码 -->
    <properties>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <lombok.version>1.16.22</lombok.version>
        <jackson.version>2.8.10</jackson.version>
    </properties>

<!--    打jar包设置-->
    <build>
        <finalName>Rocketmq-test1</finalName>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <configuration>
                    <source>8</source>
                    <target>8</target>
                </configuration>
            </plugin>
            <plugin>
                <artifactId>maven-assembly-plugin</artifactId>
                <configuration>
                    <archive>
                        <manifest>
                            <mainClass>com.shizhuang.duapp.TestDemo.test.sendMQ</mainClass>
                        </manifest>
                    </archive>
                    <descriptorRefs>
                        <descriptorRef>jar-with-dependencies</descriptorRef>
                    </descriptorRefs>
                </configuration>
                <!--下面是为了使用 mvn package命令,如果不加则使用mvn assembly-->
                <executions>
                    <execution>
                        <id>make-assemble</id>
                        <phase>package</phase>
                        <goals>
                            <goal>single</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>

        </plugins>

    </build>
    <dependencies>
        <!-- rocketmq -->
        <dependency>
            <groupId>com.poizon</groupId>
            <artifactId>fusion-alicloud-rocketmq</artifactId>
            <version>2.0.6</version>
            <exclusions>
                <exclusion>
                    <artifactId>shutdown-gracefully</artifactId>
                    <groupId>com.dewu.shutdown</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>fusion-checks</artifactId>
                    <groupId>com.poizon</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>fusion-coloring-env</artifactId>
                    <groupId>com.poizon</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>fusion-monitor-instrument-core</artifactId>
                    <groupId>com.poizon</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>ha-manage-client</artifactId>
                    <groupId>com.shizhuang.duapp</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>slf4j-api</artifactId>
                    <groupId>org.slf4j</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>fusion-bgdeploy-client</artifactId>
                    <groupId>com.poizon</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>fusion-utils</artifactId>
                    <groupId>com.poizon</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>fusion-warning</artifactId>
                    <groupId>com.poizon</groupId>
                </exclusion>
            </exclusions>
        </dependency>
        <dependency>
            <groupId>org.apache.rocketmq</groupId>
            <artifactId>rocketmq-client</artifactId>
            <version>4.8.1-DMQ-SNAPSHOT</version>
        </dependency>
        <dependency>
            <groupId>org.apache.rocketmq</groupId>
            <artifactId>rocketmq-client</artifactId>
            <version>4.8.0.3-DW-SNAPSHOT</version>
        </dependency>


        <dependency>
            <groupId>org.apache.jmeter</groupId>
            <artifactId>ApacheJMeter_java</artifactId>
            <version>4.0</version>
            <scope>provided</scope>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <version>1.18.28</version>
            <scope>provided</scope>
        </dependency>

    </dependencies>


</project>

实现自定义Jmeter的Sample

要实现能在Jmeter上运行的Java请求,我们需要创建一个测试类实现JavaSamplerClient接口或者继承AbstractJavaSamplerClient,重写一下几个方法:
- public Arguments getDefaultParameters():设置可用参数及的默认值,暴露在Jmeter界面中的参数;
- public void setupTest():脚本初始化操作,每个线程启动时执行且仅执行一次;
- public SampleResult runTest():Jmeter线程循环执行方法;
- public void teardownTest():Jmeter结束方法,每个线程结束时执行且仅执行一次;
根据以上四个方法的特点,我们将对应的mq代码操作放到不同的方法中,详细代码如下:

package ***;

import com.aliyun.openservices.shade.com.alibaba.rocketmq.client.exception.MQClientException;
import com.aliyun.openservices.shade.com.alibaba.rocketmq.client.producer.DefaultMQProducer;
import com.aliyun.openservices.shade.com.alibaba.rocketmq.client.producer.SendResult;
import com.aliyun.openservices.shade.com.alibaba.rocketmq.common.message.Message;
import org.apache.jmeter.config.Arguments;
import org.apache.jmeter.protocol.java.sampler.JavaSamplerClient;
import org.apache.jmeter.protocol.java.sampler.JavaSamplerContext;
import org.apache.jmeter.samplers.SampleResult;
import lombok.extern.slf4j.Slf4j;

@Slf4j
public class sendMQ implements JavaSamplerClient {
    DefaultMQProducer producer =null;

    @Override
    public Arguments getDefaultParameters() {
        Arguments params = new Arguments();
        params.addArgument("topic","");
        params.addArgument("tag","");
        params.addArgument("msg","");
        params.addArgument("nameSrvAddr","");
        params.addArgument("producerGroup","");
        return params;
    }

    @Override
    public void setupTest(JavaSamplerContext javaSamplerContext) {

        String nameSrvAddr = javaSamplerContext.getParameter("nameSrvAddr").replace("\"","");
        String producerGroup = javaSamplerContext.getParameter("producerGroup").replace("\"","");
        if(producer==null){
            producer = new DefaultMQProducer(producerGroup);
            producer.setNamesrvAddr(nameSrvAddr);
            producer.setVipChannelEnabled(false);
            try {
                producer.start();
            }catch (MQClientException e){
                log.error(e.getErrorMessage());
                e.printStackTrace();
            }
        }
    }

    @Override
    public SampleResult runTest(JavaSamplerContext javaSamplerContext) {
        String topic = javaSamplerContext.getParameter("topic");
        String tag = javaSamplerContext.getParameter("tag");
        String msg = javaSamplerContext.getParameter("msg");
        String key = "test#" + System.currentTimeMillis();
        String status = "";
        //创建jmeter请求结果对象
        SampleResult sampleResult = new SampleResult();
        //设置请求名称
        sampleResult.setSampleLabel("producer");
        sampleResult.sampleStart();
        Message sendMsg = new Message(topic,tag,key,msg.getBytes());
        SendResult sendResult = null;
        try{
            sendResult = producer.send(sendMsg);
        }catch (Exception e){
            log.error(e.getMessage());
            e.printStackTrace();
        }
        //将消息的发送状态设置到jmeter的请求响应中
        status = sendResult.getSendStatus().toString();
        sampleResult.setResponseData(status+","+msg,"utf-8");
        if(sendResult.getSendStatus().toString().equals("SEND_OK")){
            //发送成功
            sampleResult.setSuccessful(true);
        }else {
            sampleResult.setSuccessful(false);
        }

        sampleResult.sampleEnd();
        return sampleResult;
    }

    @Override
    public void teardownTest(JavaSamplerContext javaSamplerContext) {
//        producer.shutdown();
    }


}

打包-本地支持

上述代码完成后,我们需要将代码及其依赖的包导出为jar包(非必需的jar包可以排除掉,否则打出的jar包会很大),并放到jmeter的lib/ext目录下