简体   繁体   English

JMeter RecordingController 记录不同格式的请求

[英]JMeter RecordingController Record Request In Different Formats

I have developed a webcrawler that uses Apache-JMeter.我开发了一个使用 Apache-JMeter 的网络爬虫。

I have created a recording controller to record request/response as jmx tree.我创建了一个记录控制器来将请求/响应记录为jmx树。

To record jmx I have two options either I integrate JMeter api in my code or use JMeter GUI, I choose both for testing.为了记录 jmx,我有两个选择,要么在我的代码中集成 JMeter api,要么使用 JMeter GUI,我选择两者进行测试。 So I run the apache-jmeter from code and gui to record the request/response side-by-side.所以我从代码和 gui 运行 apache-jmeter 来并排记录请求/响应。 Below are the jmx results of Code-Base-JMeter and GUI-Base-JMeter for one request下面是一个请求的 Code-Base-JMeter 和 GUI-Base-JMeter 的 jmx 结果

Code-Base-JMeter代码库-JMeter

<HTTPSamplerProxy guiclass="HttpTestSampleGui" testname="19 /rural-property-for-sale/yorkshire/north-yorkshire/holmeonspaldingmoor-26186193/" enabled="true">
          <elementProp name="HTTPsampler.Arguments" elementType="Arguments">
            <collectionProp name="Arguments.arguments"/>
          </elementProp>
          <stringProp name="HTTPSampler.implementation">HttpClient4</stringProp>
          <boolProp name="HTTPSampler.follow_redirects">true</boolProp>
          <boolProp name="HTTPSampler.use_keepalive">false</boolProp>
          <stringProp name="HTTPSampler.domain">www.uklandandfarms.co.uk</stringProp>
          <stringProp name="HTTPSampler.method">GET</stringProp>
          <stringProp name="HTTPSampler.port">0</stringProp>
          <stringProp name="HTTPSampler.protocol">http</stringProp>
          <stringProp name="HTTPSampler.path">/rural-property-for-sale/yorkshire/north-yorkshire/holmeonspaldingmoor-26186193/</stringProp>
          <elementProp name="HTTPSampler.header_manager" elementType="HeaderManager" guiclass="HeaderPanel" testclass="HeaderManager" testname="HTTP Header Manager" enabled="true">
            <collectionProp name="HeaderManager.headers">
              <elementProp name="Cache-Control" elementType="Header">
                <stringProp name="Header.name">Cache-Control</stringProp>
                <stringProp name="Header.value">no-cache</stringProp>
              </elementProp>
              <elementProp name="Accept-Encoding" elementType="Header">
                <stringProp name="Header.name">Accept-Encoding</stringProp>
                <stringProp name="Header.value">gzip</stringProp>
              </elementProp>
              <elementProp name="Pragma" elementType="Header">
                <stringProp name="Header.name">Pragma</stringProp>
                <stringProp name="Header.value">no-cache</stringProp>
              </elementProp>
              <elementProp name="User-Agent" elementType="Header">
                <stringProp name="Header.name">User-Agent</stringProp>
                <stringProp name="Header.value">Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/535.1 (KHTML, like Gecko) Chrome/13.0.782.112 Safari/535.1</stringProp>
              </elementProp>
              <elementProp name="Accept" elementType="Header">
                <stringProp name="Header.name">Accept</stringProp>
                <stringProp name="Header.value">text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2</stringProp>
              </elementProp>
            </collectionProp>
          </elementProp>
          <boolProp name="HTTPSampler.auto_redirects">false</boolProp>
          <boolProp name="HTTPSampler.image_parser">true</boolProp>
        </HTTPSamplerProxy>

GUI-Base-JMeter GUI-Base-JMeter

      <HTTPSamplerProxy guiclass="HttpTestSampleGui" testclass="HTTPSamplerProxy" testname="32 /" enabled="true">
        <elementProp name="HTTPsampler.Arguments" elementType="Arguments" guiclass="HTTPArgumentsPanel" testclass="Arguments" enabled="true">
          <collectionProp name="Arguments.arguments"/>
        </elementProp>
        <stringProp name="HTTPSampler.domain">www.uklandandfarms.co.uk</stringProp>
        <stringProp name="HTTPSampler.port"></stringProp>
        <stringProp name="HTTPSampler.protocol">http</stringProp>
        <stringProp name="HTTPSampler.contentEncoding">utf-8</stringProp>
        <stringProp name="HTTPSampler.path">/</stringProp>
        <stringProp name="HTTPSampler.method">GET</stringProp>
        <boolProp name="HTTPSampler.follow_redirects">true</boolProp>
        <boolProp name="HTTPSampler.auto_redirects">false</boolProp>
        <boolProp name="HTTPSampler.use_keepalive">true</boolProp>
        <boolProp name="HTTPSampler.DO_MULTIPART_POST">false</boolProp>
        <boolProp name="HTTPSampler.image_parser">true</boolProp>
        <stringProp name="HTTPSampler.embedded_url_re"></stringProp>
        <stringProp name="HTTPSampler.implementation">HttpClient4</stringProp>
        <stringProp name="HTTPSampler.connect_timeout"></stringProp>
        <stringProp name="HTTPSampler.response_timeout"></stringProp>
      </HTTPSamplerProxy>
      <hashTree>
        <HeaderManager guiclass="HeaderPanel" testclass="HeaderManager" testname="HTTP Header Manager" enabled="true">
          <collectionProp name="HeaderManager.headers">
            <elementProp name="Accept-Language" elementType="Header">
              <stringProp name="Header.name">Accept-Language</stringProp>
              <stringProp name="Header.value">en-GB,en;q=0.5</stringProp>
            </elementProp>
            <elementProp name="Upgrade-Insecure-Requests" elementType="Header">
              <stringProp name="Header.name">Upgrade-Insecure-Requests</stringProp>
              <stringProp name="Header.value">1</stringProp>
            </elementProp>
            <elementProp name="Accept-Encoding" elementType="Header">
              <stringProp name="Header.name">Accept-Encoding</stringProp>
              <stringProp name="Header.value">gzip, deflate</stringProp>
            </elementProp>
            <elementProp name="User-Agent" elementType="Header">
              <stringProp name="Header.name">User-Agent</stringProp>
              <stringProp name="Header.value">Mozilla/5.0 (Windows NT 10.0; WOW64; rv:54.0) Gecko/20100101 Firefox/54.0</stringProp>
            </elementProp>
            <elementProp name="Accept" elementType="Header">
              <stringProp name="Header.name">Accept</stringProp>
              <stringProp name="Header.value">text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8</stringProp>
            </elementProp>
          </collectionProp>
        </HeaderManager>
        <hashTree/>
      </hashTree>

Differences between recordings录音之间的差异

1) HTTPSamplerProxy tree ends before the header section in GUI-Base-JMeter recoding, while HTTPSamplerProxy tree ends at last of Code-Base-JMeter 1) HTTPSamplerProxy树在 GUI-Base-JMeter 重新编码中的header部分之前结束,而HTTPSamplerProxy树在 Code-Base-JMeter 的最后结束

2) HeaderManager is tag in GUI-Base-JMeter while in Code-Base-JMeter its property-value of elementProp tag. 2) HeaderManager是 GUI-Base-JMeter 中的标签,而 Code-Base-JMeter 中是elementProp标签的属性值。

3) HeaderManager is sibling of HTTPSamplerProxy in GUI-Base-JMeter while elementProp tag (of HeaderManager property-value) is child of HTTPSamplerProxy . 3) HeaderManager是 GUI-Base-JMeter 中HTTPSamplerProxy兄弟,而elementProp标签( HeaderManager属性值)是HTTPSamplerProxyHTTPSamplerProxy

Basically whole layout is different in both recordings.基本上整个布局在两个录音中都是不同的。 I want Code-Base-JMeter recording same as GUI-Base-JMeter recoding.我希望 Code-Base-JMeter 记录与 GUI-Base-JMeter 记录相同。

I am using Apache-JMeter 3.2 (both for GUI and code)我正在使用 Apache-JMeter 3.2(用于 GUI 和代码)

Below is the code下面是代码

To Initialize初始化

    public void init(Integer port) throws Exception {

        JMeterUtils.setJMeterHome(Constants.JMETER_HOME);
        JMeterUtils.loadJMeterProperties(JMeterUtils.getJMeterBinDir() + "/jmeter.properties");
        JMeterUtils.initLocale();

        LoopController loopController = new LoopController();
        loopController.setEnabled(true);
        loopController.setLoops(1);

        RecordingController rc = new RecordingController();
        rc.setName("Recording Controller");

        TestPlan testPlan = new TestPlan();

        ThreadGroup threadGroup1 = new ThreadGroup();
        threadGroup1.setSamplerController(loopController);
        threadGroup1.addTestElement(rc); // Target

        ListedHashTree testPlanTree = new ListedHashTree();
        testPlanTree.add(testPlan);
        testPlanTree.add(threadGroup1, testPlan);

        this.treeModel = new JMeterTreeModel(new Object());

        JMeterTreeNode root = (JMeterTreeNode) treeModel.getRoot();
        treeModel.addSubTree(testPlanTree, root);

        proxy = new ProxyControl();
        proxy.setNonGuiTreeModel(treeModel);
        proxy.setTarget(treeModel.getNodeOf(threadGroup1));
        proxy.setGroupingMode(2); // GROUPING_IN_SIMPLE_CONTROLLERS = 2
//      proxy.setGroupingMode(3); // GROUPING_STORE_FIRST_ONLY = 3
        proxy.setSamplerTypeName("2"); // SAMPLER_TYPE_HTTP_SAMPLER_HC4 = "2"
        proxy.setRegexMatch(Boolean.TRUE);
        proxy.setPort(port); // Global Settings -> Port
        proxy.setCaptureHttpHeaders(Boolean.TRUE);
        proxy.setSamplerFollowRedirects(Boolean.TRUE);
//      proxy.setSamplerRedirectAutomatically(Boolean.TRUE);
        proxy.setSamplerDownloadImages(Boolean.TRUE);

        treeModel.addComponent(proxy, (JMeterTreeNode) root.getChildAt(1));
    }

Start JMeter启动 JMeter

this.proxy.startProxy();

Stop/Record JMeter停止/记录 JMeter

/**
 * The method stop() is use to stop JMeter recording controller proxy.
 * 
 * @return The tree that is recorded till now
 */
public String stop() {

    OutputStream out = null;

    try {
        this.proxy.stopProxy();

        if (this.treeModel == null) {
            return null;
        }

        out = new ByteArrayOutputStream();

        HashTree tree = treeModel.getTestPlan();

        JMeter.convertSubTree(tree);

        SaveService.saveTree(tree, out);
    } catch (Exception e) {
        return null;
    }

    return out.toString();
}

Warning : This is not a legitimate solution/answer, its just a workaround as nobody give me any solution yet.警告:这不是一个合法的解决方案/答案,它只是一种解决方法,因为还没有人给我任何解决方案。

I make an xslt expression to transform Code-Base-JMeter-Jmx to Gui-Base-JMeter-Jmx我制作了一个 xslt 表达式来将 Code-Base-JMeter-Jmx 转换为 Gui-Base-JMeter-Jmx

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
    <xsl:output omit-xml-declaration="yes" indent="yes" />
    <xsl:strip-space elements="*" />
    <xsl:template match="/">
        <xsl:apply-templates />
        <hashTree>
            <HeaderManager guiclass="HeaderPanel" testclass="HeaderManager" testname="HTTP Header Manager" enabled="true">
                <xsl:copy-of select="HTTPSamplerProxy/elementProp[@elementType = 'HeaderManager']/collectionProp[@name='HeaderManager.headers']" />
            </HeaderManager>
            <hashTree />
        </hashTree>
    </xsl:template>
    <xsl:template match="HTTPSamplerProxy/elementProp[@elementType = 'HeaderManager']" />
    <xsl:template match="@*|node()">
        <xsl:copy>
            <xsl:apply-templates select="@*|node()" />
        </xsl:copy>
    </xsl:template>
</xsl:stylesheet>

Now what if in next version(s) of JMeter they change the jmx/xml output, then again I have to change my xslt to cater the change, which is not a good way at all.现在,如果在下一个版本的 JMeter 中他们更改了 jmx/xml 输出,那么我又必须更改我的 xslt 以适应更改,这根本不是一个好方法。

So I am still hungry to have a legitimate solution.所以我仍然渴望有一个合法的解决方案。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM