jmeter-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Philippe Mouawad <philippe.moua...@gmail.com>
Subject Re: svn commit: r1641081 - in /jmeter/trunk: ./ bin/ res/maven/ src/components/org/apache/jmeter/visualizers/backend/ src/core/org/apache/jmeter/resources/ src/core/org/apache/jmeter/samplers/ src/core/org/apache/jmeter/save/ xdocs/ xdocs/usermanual/
Date Sun, 30 Nov 2014 20:32:00 GMT
On Sun, Nov 30, 2014 at 10:19 AM, Felix Schumacher <
felix.schumacher@internetallee.de> wrote:

>
>
> Am 29. November 2014 21:12:00 MEZ, schrieb Philippe Mouawad <
> philippe.mouawad@gmail.com>:
> >Hi Felix
> >
> >My answer inline.
> >Regards
> >
> >On Sat, Nov 29, 2014 at 11:51 AM, Felix Schumacher <
> >felix.schumacher@internetallee.de> wrote:
> >
> >> Hello Philippe,
> >>
> >> Am Sonntag, den 23.11.2014, 12:22 +0100 schrieb Philippe Mouawad:
> >> > Thanks a lot for your review which pointed to a synchronisation
> >issue
> >> that
> >> > I fixed, good catch!
> >> >
> >> > I think I took all your notes into account, let me know if I forgot
> >> > something.
> >> in SamplerMetric you have used a sliding window for the statistics.
> >> * Should we make the length of the window configurable?
> >>
> >
> >Yes but it's a new property and we have a lot :-)
> But the size of the window depends on the number of samples per time slot.
> Perhaps it could be dynamically sized?
>

You mean it needs to be increased if there is a big number of requests in
time slot for 1 sample ?
Please clarfify so that I am sure to understand. For now I made it
configurable through a property.

>
> >
> >
> >> * Should min/max and minThreads/maxThreads be limited to the sliding
> >> window, also? At least min and max would be simple to do.
> >>
> >
> >Dev team opinion is welcome, maybe it would be better
> >- min would be percentile(0)
> >- max would be percentile(100)
>
> The stats field has methods to get the minimum and the maximum values. I
> would take those.
>
OK , done

>
> >for minThreads, maxThreads, how would you do it ?
>
> Create another statistical field for the number of threads. Then we could
> provide correct answers for max/min thread numbers plus
> mean/average/percentile.
>
> For this one, I don't see in fact the use case, as number of threads will
not vary a lot so in what way do you think it is incorrect ?
Maybe my question is stupid as I don't see currently the problem but I may
be wrong. Can you clarify ?
Thx


> Regards
> Felix
>
> >
> >
> >> Regards
> >>  Felix
> >> >
> >> > Regards
> >> > Philippe
> >> >
> >> > On Sunday, November 23, 2014, Felix Schumacher <
> >> > felix.schumacher@internetallee.de> wrote:
> >> >
> >> > > Hi Phillipe,
> >> > > Am 22.11.2014 um 19:29 schrieb Philippe Mouawad:
> >> > >
> >> > >> Hi Felix,
> >> > >> As I said in thread, I commited code and will improve, feel free
> >to
> >> fix
> >> > >> javadocs issues on your side.
> >> > >> I will review your comment.
> >> > >>
> >> > >> I have spent many hours if not days on this code and I am aware
> >it is
> >> not
> >> > >> yet fully completed (although tests are promising) but my aim
> >when
> >> > >> commiting it was to have feedback and help to finish it.
> >> > >>
> >> > > I did not mean to offend you. I can clearly see, that you put a
> >lot of
> >> > > effort
> >> > > in this listener and I will surely try to integrate jmeter into
> >our
> >> > > collectd server.
> >> > >
> >> > > Regards
> >> > >  Felix
> >> > >
> >> > >>
> >> > >> Regards
> >> > >> Philippe
> >> > >>
> >> > >> On Sat, Nov 22, 2014 at 7:21 PM, Felix Schumacher <
> >> > >> felix.schumacher@internetallee.de> wrote:
> >> > >>
> >> > >>  Hello Philippe,
> >> > >>>
> >> > >>> I have hidden a few comments inside the cited code.
> >> > >>> They are mostly around javadoc and naming things.
> >> > >>>
> >> > >>> Am 22.11.2014 um 16:36 schrieb pmouawad@apache.org:
> >> > >>>
> >> > >>>  Author: pmouawad
> >> > >>>> Date: Sat Nov 22 15:36:37 2014
> >> > >>>> New Revision: 1641081
> >> > >>>>
> >> > >>>> URL: http://svn.apache.org/r1641081
> >> > >>>> Log:
> >> > >>>> Bug 55932 - Create a Async BackendListener to allow easy plug
> >of new
> >> > >>>> listener (Graphite, JDBC, Console,...)
> >> > >>>> Bugzilla Id: 55932
> >> > >>>>
> >> > >>>> Added:
> >> > >>>>
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/
> >> > >>>>
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/
> >> > >>>> AbstractBackendListenerClient.java   (with props)
> >> > >>>>
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListener.java
> >> > >>>>   (with props)
> >> > >>>>
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerClient.java   (with props)
> >> > >>>>
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerContext.java
> >> > >>>>   (with props)
> >> > >>>>
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerGui.java   (with props)
> >> > >>>>
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/SamplerMetric.java
> >> > >>>>   (with props)
> >> > >>>> Modified:
> >> > >>>>       jmeter/trunk/bin/saveservice.properties
> >> > >>>>       jmeter/trunk/build.properties
> >> > >>>>       jmeter/trunk/build.xml
> >> > >>>>       jmeter/trunk/eclipse.classpath
> >> > >>>>       jmeter/trunk/res/maven/ApacheJMeter_parent.pom
> >> > >>>>       jmeter/trunk/src/core/org/apache/jmeter/resources/
> >> > >>>> messages.properties
> >> > >>>>       jmeter/trunk/src/core/org/apache/jmeter/resources/
> >> > >>>> messages_fr.properties
> >> > >>>>       jmeter/trunk/src/core/org/apache/jmeter/samplers/
> >> > >>>> SampleResult.java
> >> > >>>>
> >jmeter/trunk/src/core/org/apache/jmeter/save/SaveService.java
> >> > >>>>       jmeter/trunk/xdocs/changes.xml
> >> > >>>>       jmeter/trunk/xdocs/usermanual/component_reference.xml
> >> > >>>>
> >> > >>>> Modified: jmeter/trunk/bin/saveservice.properties
> >> > >>>> URL:
> >http://svn.apache.org/viewvc/jmeter/trunk/bin/saveservice.
> >> > >>>> properties?rev=1641081&r1=1641080&r2=1641081&view=diff
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> --- jmeter/trunk/bin/saveservice.properties (original)
> >> > >>>> +++ jmeter/trunk/bin/saveservice.properties Sat Nov 22
> >15:36:37 2014
> >> > >>>> @@ -53,7 +53,8 @@ _file_version=$Revision$
> >> > >>>>    # 2.5 = 2.10
> >> > >>>>    # 2.6 = 2.11
> >> > >>>>    # 2.7 = 2.12
> >> > >>>> -_version=2.7
> >> > >>>> +# 2.8 = 2.13
> >> > >>>> +_version=2.8
> >> > >>>>    #
> >> > >>>>    #
> >> > >>>>    # Character set encoding used to read and write JMeter XML
> >files
> >> and
> >> > >>>> CSV results
> >> > >>>> @@ -78,6 +79,8 @@ AssertionVisualizer=org.apache.jmeter.vi
> >> > >>>>
> >AuthManager=org.apache.jmeter.protocol.http.control.AuthManager
> >> > >>>>
> >> Authorization=org.apache.jmeter.protocol.http.control.Authorization
> >> > >>>>    AuthPanel=org.apache.jmeter.protocol.http.gui.AuthPanel
> >> > >>>>
> >>
> >+BackendListener=org.apache.jmeter.visualizers.backend.BackendListener
> >> > >>>> +BackendListenerGui=org.apache.jmeter.visualizers.
> >> > >>>> backend.BackendListenerGui
> >> > >>>>    BarChart=org.apache.jmeter.testelement.BarChart
> >> > >>>>    BarChartGui=org.apache.jmeter.report.gui.BarChartGui
> >> > >>>>
> >> BeanShellAssertion=org.apache.jmeter.assertions.BeanShellAssertion
> >> > >>>>
> >> > >>>> Modified: jmeter/trunk/build.properties
> >> > >>>> URL:
> >http://svn.apache.org/viewvc/jmeter/trunk/build.properties?
> >> > >>>> rev=1641081&r1=1641080&r2=1641081&view=diff
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> --- jmeter/trunk/build.properties (original)
> >> > >>>> +++ jmeter/trunk/build.properties Sat Nov 22 15:36:37 2014
> >> > >>>> @@ -118,11 +118,21 @@ commons-logging.loc         = ${maven2.r
> >> > >>>>    #commons-logging.md5         =
> >E2C390FE739B2550A218262B28F290CE
> >> > >>>>    commons-logging.md5         =
> >040b4b4d8eac886f6b4a2a3bd2f31b00
> >> > >>>>    +commons-math3.version         = 3.3
> >> > >>>> +commons-math3.jar             =
> >commons-math3-${commons-math3.
> >> > >>>> version}.jar
> >> > >>>> +commons-math3.loc             = ${maven2.repo}/org/apache/
> >> > >>>> commons/commons-math3/${commons-math3.version}
> >> > >>>> +commons-math3.md5             =
> >87346cf2772dc2becf106c45e0f63863
> >> > >>>> +
> >> > >>>>    commons-net.version         = 3.3
> >> > >>>>    commons-net.jar             =
> >> commons-net-${commons-net.version}.jar
> >> > >>>>    commons-net.loc             = ${maven2.repo}/commons-net/
> >> > >>>> commons-net/${commons-net.version}
> >> > >>>>    commons-net.md5             =
> >c077ca61598e9c21f43f8b6488fbbee9
> >> > >>>>    +commons-pool2.version         = 2.2
> >> > >>>> +commons-pool2.jar             =
> >commons-pool2-${commons-pool2.
> >> > >>>> version}.jar
> >> > >>>> +commons-pool2.loc             = ${maven2.repo}/org/apache/
> >> > >>>> commons/commons-pool2/${commons-pool2.version}
> >> > >>>> +commons-pool2.md5             =
> >51b56c92883812c56fbeb339866ce2df
> >> > >>>> +
> >> > >>>>    # dnsjava for DNSCacheManager
> >> > >>>>    dnsjava.version             = 2.1.6
> >> > >>>>    dnsjava.jar                 =
> >dnsjava-${dnsjava.version}.jar
> >> > >>>>
> >> > >>>> Modified: jmeter/trunk/build.xml
> >> > >>>> URL: http://svn.apache.org/viewvc/jmeter/trunk/build.xml?rev=
> >> > >>>> 1641081&r1=1641080&r2=1641081&view=diff
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> --- jmeter/trunk/build.xml (original)
> >> > >>>> +++ jmeter/trunk/build.xml Sat Nov 22 15:36:37 2014
> >> > >>>> @@ -365,7 +365,9 @@
> >> > >>>>        <include name="${lib.dir}/${commons-jexl2.jar}"/>
> >> > >>>>        <include name="${lib.dir}/${commons-lang3.jar}"/>
> >> > >>>>        <include name="${lib.dir}/${commons-logging.jar}"/>
> >> > >>>> +    <include name="${lib.dir}/${commons-math3}"/>
> >> > >>>>        <include name="${lib.dir}/${commons-net.jar}"/>
> >> > >>>> +    <include name="${lib.dir}/${commons-pool2.jar}"/>
> >> > >>>>        <include name="${lib.dir}/${dnsjava.jar}"/>
> >> > >>>>        <include
> >name="${lib.dir}/${excalibur-datasource.jar}"/>
> >> > >>>>        <include
> >name="${lib.dir}/${excalibur-instrument.jar}"/>
> >> > >>>> @@ -438,8 +440,10 @@
> >> > >>>>        <pathelement
> >location="${lib.dir}/${commons-jexl2.jar}"/>
> >> > >>>>        <pathelement
> >location="${lib.dir}/${commons-lang3.jar}"/>
> >> > >>>>        <pathelement
> >location="${lib.dir}/${commons-logging.jar}"/>
> >> > >>>> +    <pathelement location="${lib.dir}/${commons-math3.jar}"/>
> >> > >>>>        <pathelement location="${lib.dir}/${commons-net.jar}"/>
> >> > >>>> -    <pathelement location="${lib.dir}/${dnsjava.jar}"/>
> >> > >>>> +       <pathelement
> >location="${lib.dir}/${commons-pool2.jar}"/>
> >> > >>>> +       <pathelement location="${lib.dir}/${dnsjava.jar}"/>
> >> > >>>>        <pathelement
> >> location="${lib.dir}/${excalibur-datasource.jar}"/>
> >> > >>>>        <pathelement
> >> location="${lib.dir}/${excalibur-instrument.jar}"/>
> >> > >>>>        <pathelement
> >location="${lib.dir}/${excalibur-logger.jar}"/>
> >> > >>>> @@ -2909,7 +2913,9 @@ run JMeter unless all the JMeter jars ar
> >> > >>>>            <process_jarfile jarname="commons-jexl2"/>
> >> > >>>>            <process_jarfile jarname="commons-lang3"/>
> >> > >>>>            <process_jarfile jarname="commons-logging"/>
> >> > >>>> +        <process_jarfile jarname="commons-math3"/>
> >> > >>>>            <process_jarfile jarname="commons-net"/>
> >> > >>>> +       <process_jarfile jarname="commons-pool2"/>
> >> > >>>>            <process_jarfile jarname="dnsjava"/>
> >> > >>>>            <process_jarfile jarname="excalibur-datasource"/>
> >> > >>>>            <process_jarfile jarname="excalibur-instrument"/>
> >> > >>>>
> >> > >>>> Modified: jmeter/trunk/eclipse.classpath
> >> > >>>> URL: http://svn.apache.org/viewvc/jmeter/trunk/eclipse.
> >> > >>>> classpath?rev=1641081&r1=1641080&r2=1641081&view=diff
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> --- jmeter/trunk/eclipse.classpath (original)
> >> > >>>> +++ jmeter/trunk/eclipse.classpath Sat Nov 22 15:36:37 2014
> >> > >>>> @@ -55,7 +55,9 @@
> >> > >>>>          <classpathentry kind="lib"
> >> path="lib/commons-jexl-2.1.1.jar"/>
> >> > >>>>          <classpathentry kind="lib"
> >path="lib/commons-lang3-3.3.2.
> >> > >>>> jar"/>
> >> > >>>>          <classpathentry kind="lib"
> >path="lib/commons-logging-1.2.
> >> > >>>> jar"/>
> >> > >>>> +    <classpathentry kind="lib"
> >path="lib/commons-math3-3.3.jar"/>
> >> > >>>>          <classpathentry kind="lib"
> >path="lib/commons-net-3.3.jar"/>
> >> > >>>> +    <classpathentry kind="lib"
> >path="lib/commons-pool2-2.2.jar"/>
> >> > >>>>          <classpathentry kind="lib"
> >path="lib/dnsjava-2.1.6.jar"/>
> >> > >>>>          <classpathentry kind="lib" path="lib/excalibur-
> >> > >>>> datasource-2.1.jar"/>
> >> > >>>>          <classpathentry kind="lib" path="lib/excalibur-
> >> > >>>> instrument-1.0.jar"/>
> >> > >>>>
> >> > >>>> Modified: jmeter/trunk/res/maven/ApacheJMeter_parent.pom
> >> > >>>> URL: http://svn.apache.org/viewvc/jmeter/trunk/res/maven/
> >> > >>>>
> >ApacheJMeter_parent.pom?rev=1641081&r1=1641080&r2=1641081&view=diff
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> --- jmeter/trunk/res/maven/ApacheJMeter_parent.pom (original)
> >> > >>>> +++ jmeter/trunk/res/maven/ApacheJMeter_parent.pom Sat Nov 22
> >> 15:36:37
> >> > >>>> 2014
> >> > >>>> @@ -66,7 +66,9 @@ under the License.
> >> > >>>>          <commons-jexl2.version>2.1.1</commons-jexl2.version>
> >> > >>>>          <commons-lang3.version>3.3.2</commons-lang3.version>
> >> > >>>>
> ><commons-logging.version>1.2</commons-logging.version>
> >> > >>>> +      <commons-math3.version>3.3</commons-math3.version>
> >> > >>>>          <commons-net.version>3.3</commons-net.version>
> >> > >>>> +      <commons-pool2.version>2.2</commons-pool2.version>
> >> > >>>>          <dnsjava.version>2.1.6</dnsjava.version>
> >> > >>>>
> ><excalibur-datasource.version>2.1</excalibur-datasource.
> >> > >>>> version>
> >> > >>>>
> ><excalibur-instrument.version>1.0</excalibur-instrument.
> >> > >>>> version>
> >> > >>>> @@ -181,11 +183,21 @@ under the License.
> >> > >>>>            <version>${commons-logging.version}</version>
> >> > >>>>          </dependency>
> >> > >>>>          <dependency>
> >> > >>>> +        <groupId>commons-math3</groupId>
> >> > >>>> +        <artifactId>commons-math3</artifactId>
> >> > >>>> +        <version>${commons-math3.version}</version>
> >> > >>>> +      </dependency>
> >> > >>>> +      <dependency>
> >> > >>>>            <groupId>commons-net</groupId>
> >> > >>>>            <artifactId>commons-net</artifactId>
> >> > >>>>            <version>${commons-net.version}</version>
> >> > >>>>          </dependency>
> >> > >>>>          <dependency>
> >> > >>>> +        <groupId>commons-pool2</groupId>
> >> > >>>> +        <artifactId>commons-pool2</artifactId>
> >> > >>>> +        <version>${commons-pool2.version}</version>
> >> > >>>> +      </dependency>
> >> > >>>> +      <dependency>
> >> > >>>>              <groupId>dnsjava</groupId>
> >> > >>>>              <artifactId>dnsjava</artifactId>
> >> > >>>>              <version>${dnsjava.version}</version>
> >> > >>>>
> >> > >>>> Added:
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/
> >> > >>>> AbstractBackendListenerClient.java
> >> > >>>> URL: http://svn.apache.org/viewvc/jmeter/trunk/src/components/
> >> > >>>>
> >org/apache/jmeter/visualizers/backend/AbstractBackendListenerClient.
> >> > >>>> java?rev=1641081&view=auto
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> ---
> >> jmeter/trunk/src/components/org/apache/jmeter/visualizers/backend/
> >> > >>>> AbstractBackendListenerClient.java (added)
> >> > >>>> +++
> >> jmeter/trunk/src/components/org/apache/jmeter/visualizers/backend/
> >> > >>>> AbstractBackendListenerClient.java Sat Nov 22 15:36:37 2014
> >> > >>>> @@ -0,0 +1,121 @@
> >> > >>>> +/*
> >> > >>>> + * Licensed to the Apache Software Foundation (ASF) under one
> >or
> >> more
> >> > >>>> + * contributor license agreements.  See the NOTICE file
> >distributed
> >> > >>>> with
> >> > >>>> + * this work for additional information regarding copyright
> >> ownership.
> >> > >>>> + * The ASF licenses this file to You under the Apache
> >License,
> >> Version
> >> > >>>> 2.0
> >> > >>>> + * (the "License"); you may not use this file except in
> >compliance
> >> with
> >> > >>>> + * the License.  You may obtain a copy of the License at
> >> > >>>> + *
> >> > >>>> + *   http://www.apache.org/licenses/LICENSE-2.0
> >> > >>>> + *
> >> > >>>> + * Unless required by applicable law or agreed to in writing,
> >> software
> >> > >>>> + * distributed under the License is distributed on an "AS IS"
> >> BASIS,
> >> > >>>> + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
> >express or
> >> > >>>> implied.
> >> > >>>> + * See the License for the specific language governing
> >permissions
> >> and
> >> > >>>> + * limitations under the License.
> >> > >>>> + *
> >> > >>>> + */
> >> > >>>> +
> >> > >>>> +package org.apache.jmeter.visualizers.backend;
> >> > >>>> +
> >> > >>>> +import java.util.Map;
> >> > >>>> +import java.util.concurrent.ConcurrentHashMap;
> >> > >>>> +
> >> > >>>> +import org.apache.jmeter.config.Arguments;
> >> > >>>> +import org.apache.jmeter.samplers.SampleResult;
> >> > >>>> +import org.apache.jorphan.logging.LoggingManager;
> >> > >>>> +import org.apache.log.Logger;
> >> > >>>> +
> >> > >>>> +/**
> >> > >>>> + * An abstract implementation of the BackendListenerClient
> >> interface.
> >> > >>>> This
> >> > >>>> + * implementation provides default implementations of most of
> >the
> >> > >>>> methods in the
> >> > >>>> + * interface, as well as some convenience methods, in order
> >to
> >> simplify
> >> > >>>> + * development of BackendListenerClient implementations.
> >> > >>>> + *
> >> > >>>> + * While it may be necessary to make changes to the
> >> > >>>> BackendListenerClient interface
> >> > >>>> + * from time to time (therefore requiring changes to any
> >> > >>>> implementations
> >> > >>>> of this
> >> > >>>> + * interface), we intend to make this abstract class provide
> >> reasonable
> >> > >>>> + * implementations of any new methods so that subclasses do
> >not
> >> > >>>> necessarily need
> >> > >>>> + * to be updated for new versions. Therefore, when creating a
> >new
> >> > >>>> + * BackendListenerClient implementation, developers are
> >encouraged
> >> to
> >> > >>>> subclass this
> >> > >>>> + * abstract class rather than implementing the
> >> BackendListenerClient
> >> > >>>> interface
> >> > >>>> + * directly. Implementing BackendListenerClient directly will
> >> continue
> >> > >>>> to be
> >> > >>>> + * supported for cases where extending this class is not
> >possible
> >> (for
> >> > >>>> example,
> >> > >>>> + * when the client class is already a subclass of some other
> >> class).
> >> > >>>> + * <p>
> >> > >>>> + * The handleSampleResult() method of BackendListenerClient
> >does
> >> not
> >> > >>>> have a default
> >> > >>>> + * implementation here, so subclasses must define at least
> >this
> >> method.
> >> > >>>> It may
> >> > >>>> + * be useful to override other methods as well.
> >> > >>>> + *
> >> > >>>> + * @see BackendListener#sampleOccurred(org.apache.
> >> > >>>> jmeter.samplers.SampleEvent)
> >> > >>>> + * @since 2.13
> >> > >>>> + */
> >> > >>>> +public abstract class AbstractBackendListenerClient
> >implements
> >> > >>>> BackendListenerClient {
> >> > >>>> +
> >> > >>>> +    private static final Logger log = LoggingManager.
> >> > >>>> getLoggerForClass();
> >> > >>>>
> >> > >>>>  In classes further down the logger is stored in variables
> >named
> >> LOG and
> >> > >>> LOGGER, should we use one name?
> >> > >>> In this class we have a getter for the logger in other classes
> >not.
> >> Why?
> >> > >>>
> >> > >>>  +
> >> > >>>> +    private ConcurrentHashMap<String, SamplerMetric>
> >> metricsPerSampler
> >> > >>>> =
> >> > >>>> new ConcurrentHashMap<String, SamplerMetric>();
> >> > >>>> +
> >> > >>>> +    /* Implements
> >> BackendListenerClient.setupTest(JavaSamplerContext)
> >> > >>>> */
> >> > >>>> +    @Override
> >> > >>>> +    public void setupTest(BackendListenerContext context)
> >throws
> >> > >>>> Exception {
> >> > >>>> +        log.debug(getClass().getName() + ": setupTest");
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /* Implements BackendListenerClient.teardownTest(
> >> > >>>> JavaSamplerContext)
> >> > >>>> */
> >> > >>>> +    @Override
> >> > >>>> +    public void teardownTest(BackendListenerContext context)
> >throws
> >> > >>>> Exception {
> >> > >>>> +        log.debug(getClass().getName() + ": teardownTest");
> >> > >>>> +        metricsPerSampler.clear();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /* Implements
> >BackendListenerClient.getDefaultParameters() */
> >> > >>>> +    @Override
> >> > >>>> +    public Arguments getDefaultParameters() {
> >> > >>>> +        return null;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get a Logger instance which can be used by subclasses
> >to log
> >> > >>>> information.
> >> > >>>> +     *
> >> > >>>> +     * @return a Logger instance which can be used for
> >logging
> >> > >>>> +     */
> >> > >>>> +    protected Logger getLogger() {
> >> > >>>> +        return log;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /* (non-Javadoc)
> >> > >>>> +     * @see org.apache.jmeter.visualizers.
> >> > >>>> backend.BackendListenerClient#
> >> > >>>> createSampleResult(org.apache.jmeter.samplers.SampleResult)
> >> > >>>> +     */
> >> > >>>> +    @Override
> >> > >>>> +    public SampleResult
> >createSampleResult(BackendListenerContext
> >> > >>>> context, SampleResult result) {
> >> > >>>> +        SampleResult sampleResult = (SampleResult)
> >result.clone();
> >> > >>>> +        return sampleResult;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     *
> >> > >>>> +     * @param sampleLabel
> >> > >>>> +     * @return SamplerMetric
> >> > >>>>
> >> > >>>>  No description of the method and the parameters?
> >> > >>>
> >> > >>>  +     */
> >> > >>>> +    protected SamplerMetric getSamplerMetric(String
> >sampleLabel) {
> >> > >>>> +        SamplerMetric samplerMetric = metricsPerSampler.get(
> >> > >>>> sampleLabel);
> >> > >>>> +        if(samplerMetric == null) {
> >> > >>>> +            samplerMetric = new SamplerMetric();
> >> > >>>> +            SamplerMetric oldValue =
> >metricsPerSampler.putIfAbsent(
> >> > >>>> sampleLabel,
> >> > >>>> samplerMetric);
> >> > >>>> +            if(oldValue != null ){
> >> > >>>> +                samplerMetric = oldValue;
> >> > >>>> +            }
> >> > >>>> +        }
> >> > >>>> +        return samplerMetric;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     *
> >> > >>>> +     * @return Map<String, SamplerMetric>
> >> > >>>>
> >> > >>>>  No description of the method and usage of forbidden
> >characters :)
> >> there
> >> > >>> are still more than 800 warnings in the javadoc to prune, so
> >don't
> >> > >>> introduce new ones, please.
> >> > >>>
> >> > >>>  +     */
> >> > >>>> +    protected Map<String, SamplerMetric>
> >getMetricsPerSampler() {
> >> > >>>> +        return metricsPerSampler;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +}
> >> > >>>>
> >> > >>>> Propchange:
> >> jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/AbstractBackendListenerClient.java
> >> > >>>> ------------------------------------------------------------
> >> > >>>> ------------------
> >> > >>>>       svn:mime-type = text/plain
> >> > >>>>
> >> > >>>> Added:
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListener.java
> >> > >>>> URL: http://svn.apache.org/viewvc/jmeter/trunk/src/components/
> >> > >>>> org/apache/jmeter/visualizers/backend/BackendListener.java?
> >> > >>>> rev=1641081&view=auto
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> --- jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListener.java
> >> > >>>> (added)
> >> > >>>> +++ jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListener.java
> >> > >>>> Sat Nov 22 15:36:37 2014
> >> > >>>> @@ -0,0 +1,448 @@
> >> > >>>> +/*
> >> > >>>> + * Licensed to the Apache Software Foundation (ASF) under one
> >or
> >> more
> >> > >>>> + * contributor license agreements.  See the NOTICE file
> >distributed
> >> > >>>> with
> >> > >>>> + * this work for additional information regarding copyright
> >> ownership.
> >> > >>>> + * The ASF licenses this file to You under the Apache
> >License,
> >> Version
> >> > >>>> 2.0
> >> > >>>> + * (the "License"); you may not use this file except in
> >compliance
> >> with
> >> > >>>> + * the License.  You may obtain a copy of the License at
> >> > >>>> + *
> >> > >>>> + *   http://www.apache.org/licenses/LICENSE-2.0
> >> > >>>> + *
> >> > >>>> + * Unless required by applicable law or agreed to in writing,
> >> software
> >> > >>>> + * distributed under the License is distributed on an "AS IS"
> >> BASIS,
> >> > >>>> + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
> >express or
> >> > >>>> implied.
> >> > >>>> + * See the License for the specific language governing
> >permissions
> >> and
> >> > >>>> + * limitations under the License.
> >> > >>>> + *
> >> > >>>> + */
> >> > >>>> +
> >> > >>>> +package org.apache.jmeter.visualizers.backend;
> >> > >>>> +
> >> > >>>> +import java.io.Serializable;
> >> > >>>> +import java.lang.reflect.Method;
> >> > >>>> +import java.util.ArrayList;
> >> > >>>> +import java.util.HashSet;
> >> > >>>> +import java.util.List;
> >> > >>>> +import java.util.Set;
> >> > >>>> +import java.util.concurrent.ArrayBlockingQueue;
> >> > >>>> +import java.util.concurrent.BlockingQueue;
> >> > >>>> +import java.util.concurrent.locks.LockSupport;
> >> > >>>> +
> >> > >>>> +import org.apache.jmeter.config.Arguments;
> >> > >>>> +import org.apache.jmeter.engine.util.NoThreadClone;
> >> > >>>> +import
> >org.apache.jmeter.protocol.java.sampler.JavaSamplerContext;
> >> > >>>> +import org.apache.jmeter.samplers.Remoteable;
> >> > >>>> +import org.apache.jmeter.samplers.SampleEvent;
> >> > >>>> +import org.apache.jmeter.samplers.SampleListener;
> >> > >>>> +import org.apache.jmeter.samplers.SampleResult;
> >> > >>>> +import org.apache.jmeter.testelement.AbstractTestElement;
> >> > >>>> +import org.apache.jmeter.testelement.TestElement;
> >> > >>>> +import org.apache.jmeter.testelement.TestStateListener;
> >> > >>>> +import
> >org.apache.jmeter.testelement.property.TestElementProperty;
> >> > >>>> +import org.apache.jorphan.logging.LoggingManager;
> >> > >>>> +import org.apache.log.Logger;
> >> > >>>> +
> >> > >>>> +/**
> >> > >>>> + * Async Listener that delegates SampleResult handling to
> >> > >>>> implementations of {@link BackendListenerClient}
> >> > >>>> + * @since 2.13
> >> > >>>> + */
> >> > >>>> +public class BackendListener extends AbstractTestElement
> >> > >>>> +    implements Serializable, SampleListener,
> >TestStateListener,
> >> > >>>> NoThreadClone, Remoteable  {
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     *
> >> > >>>> +     */
> >> > >>>> +    private static final long serialVersionUID =
> >> 8184103677832024335L;
> >> > >>>> +
> >> > >>>> +    private static final Logger log = LoggingManager.
> >> > >>>> getLoggerForClass();
> >> > >>>>
> >> > >>>>  See naming comment of log from above
> >> > >>>
> >> > >>>  +
> >> > >>>> +    /**
> >> > >>>> +     * Set used to register instances which implement
> >teardownTest.
> >> > >>>> +     * This is used so that the BackendListenerClient can be
> >> notified
> >> > >>>> when the test ends.
> >> > >>>> +     */
> >> > >>>> +    private static final Set<BackendListener> TEAR_DOWN_SET =
> >new
> >> > >>>> HashSet<BackendListener>();
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Property key representing the classname of the
> >> > >>>> BackendListenerClient to user.
> >> > >>>> +     */
> >> > >>>> +    public static final String CLASSNAME = "classname";
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Queue size
> >> > >>>> +     */
> >> > >>>> +    public static final String QUEUE_SIZE = "QUEUE_SIZE";
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Property key representing the arguments for the
> >> > >>>> BackendListenerClient.
> >> > >>>> +     */
> >> > >>>> +    public static final String ARGUMENTS = "arguments";
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * The BackendListenerClient class used by this sampler.
> >> > >>>> +     * Created by testStarted; copied to cloned instances.
> >> > >>>> +     */
> >> > >>>> +    private Class<?> javaClass;
> >> > >>>>
> >> > >>>>  Could probably named clientClass instead of javaClass, since
> >we
> >> already
> >> > >>> know it is a java class.
> >> > >>>
> >> > >>>  +
> >> > >>>> +    /**
> >> > >>>> +     * If true, the BackendListenerClient class implements
> >> > >>>> teardownTest.
> >> > >>>> +     * Created by testStarted; copied to cloned instances.
> >> > >>>> +     */
> >> > >>>> +    private boolean isToBeRegistered;
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * The BackendListenerClient instance
> >> > >>>> +     */
> >> > >>>> +    private transient BackendListenerClient
> >backendListenerClient =
> >> > >>>> null;
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * The JavaSamplerContext instance used by this sampler
> >to hold
> >> > >>>> information
> >> > >>>>
> >> > >>>>  BackendListenerContext?
> >> > >>>
> >> > >>>  +     * related to the test run, such as the parameters
> >specified
> >> for
> >> > >>>> the
> >> > >>>> sampler
> >> > >>>> +     * client.
> >> > >>>> +     */
> >> > >>>> +    private transient BackendListenerContext context = null;
> >> > >>>> +
> >> > >>>> +    private static final int DEFAULT_QUEUE_SIZE = 5000;
> >> > >>>> +
> >> > >>>> +    private transient BlockingQueue<SampleResult> queue; //
> >> created by
> >> > >>>> server in readResolve method
> >> > >>>> +
> >> > >>>> +    private transient long queueWaits; // how many times we
> >had to
> >> wait
> >> > >>>> to queue a sample
> >> > >>>> +
> >> > >>>> +    private transient long queueWaitTime; // how long we had
> >to
> >> wait
> >> > >>>> (nanoSeconds)
> >> > >>>> +
> >> > >>>> +    // Create unique object as marker for end of queue
> >> > >>>> +    private transient static final SampleResult FINAL_EVENT =
> >new
> >> > >>>> SampleResult();
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Create a BackendListener.
> >> > >>>> +     */
> >> > >>>> +    public BackendListener() {
> >> > >>>> +        setArguments(new Arguments());
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /*
> >> > >>>> +     * Ensure that the required class variables are cloned,
> >> > >>>> +     * as this is not currently done by the
> >super-implementation.
> >> > >>>> +     */
> >> > >>>> +    @Override
> >> > >>>> +    public Object clone() {
> >> > >>>> +        BackendListener clone = (BackendListener)
> >super.clone();
> >> > >>>> +        clone.javaClass = this.javaClass;
> >> > >>>> +        clone.isToBeRegistered = this.isToBeRegistered;
> >> > >>>> +        return clone;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    private void initClass() {
> >> > >>>> +        String name = getClassname().trim();
> >> > >>>> +        try {
> >> > >>>> +            javaClass = Class.forName(name, false,
> >> > >>>> Thread.currentThread().getContextClassLoader());
> >> > >>>> +            Method method =
> >javaClass.getMethod("teardownTest", new
> >> > >>>> Class[]{BackendListenerContext.class});
> >> > >>>> +            isToBeRegistered =
> >!method.getDeclaringClass().equals(
> >> > >>>> AbstractBackendListenerClient.class);
> >> > >>>> +            log.info("Created class: " + name + ". Uses
> >> teardownTest:
> >> > >>>> "
> >> > >>>> + isToBeRegistered);
> >> > >>>> +        } catch (Exception e) {
> >> > >>>> +            log.error(whoAmI() + "\tException initialising: "
> >+
> >> name,
> >> > >>>> e);
> >> > >>>> +        }
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Retrieves reference to BackendListenerClient.
> >> > >>>> +     *
> >> > >>>> +     * Convience method used to check for null reference
> >without
> >> > >>>> actually
> >> > >>>> +     * creating a BackendListenerClient
> >> > >>>> +     *
> >> > >>>> +     * @return reference to BackendListenerClient NOTUSED
> >private
> >> > >>>> BackendListenerClient
> >> > >>>> +     *         retrieveJavaClient() { return javaClient; }
> >> > >>>> +     */
> >> > >>>>
> >> > >>>>  Javadoc for non-existant method?
> >> > >>>
> >> > >>>  +
> >> > >>>> +    /**
> >> > >>>> +     * Generate a String identifier of this instance for
> >debugging
> >> > >>>> purposes.
> >> > >>>> +     *
> >> > >>>> +     * @return a String identifier for this sampler instance
> >> > >>>> +     */
> >> > >>>> +    private String whoAmI() {
> >> > >>>> +        StringBuilder sb = new StringBuilder();
> >> > >>>> +        sb.append(Thread.currentThread().getName());
> >> > >>>> +        sb.append("@");
> >> > >>>> +        sb.append(Integer.toHexString(hashCode()));
> >> > >>>> +        sb.append("-");
> >> > >>>> +        sb.append(getName());
> >> > >>>> +        return sb.toString();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    // TestStateListener implementation
> >> > >>>> +    /* Implements TestStateListener.testStarted() */
> >> > >>>> +    @Override
> >> > >>>> +    public void testStarted() {
> >> > >>>> +        testStarted("");
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /* Implements TestStateListener.testStarted(String) */
> >> > >>>> +    @Override
> >> > >>>> +    public void testStarted(String host) {
> >> > >>>> +        log.debug(whoAmI() + "\ttestStarted(" + host + ")");
> >> > >>>>
> >> > >>>>  Maybe use isDebugEnabled to guard whoAmI() call?
> >> > >>>
> >> > >>>  +        queue = new
> >> ArrayBlockingQueue<SampleResult>(getQueueSize());
> >> > >>>> +        initClass();
> >> > >>>> +        queueWaits=0L;
> >> > >>>> +        queueWaitTime=0L;
> >> > >>>> +        log.info(getName()+":Starting worker with
> >> class:"+javaClass +"
> >> > >>>> and queue capacity:"+getQueueSize());
> >> > >>>> +
> >> > >>>> +        backendListenerClient =
> >createBackendListenerClientImp
> >> > >>>> l(javaClass);
> >> > >>>> +        context = new BackendListenerContext((
> >> > >>>> Arguments)getArguments().
> >> > >>>> clone());
> >> > >>>> +        if(isToBeRegistered) {
> >> > >>>>
> >> > >>>>  space after if and before (?
> >> > >>>
> >> > >>>  +            TEAR_DOWN_SET.add(this);
> >> > >>>> +        }
> >> > >>>> +        try {
> >> > >>>> +            backendListenerClient.setupTest(context);
> >> > >>>> +        } catch (Exception e) {
> >> > >>>> +            throw new java.lang.IllegalStateException("Failed
> >> calling
> >> > >>>> setupTest", e);
> >> > >>>> +        }
> >> > >>>> +
> >> > >>>> +        Worker worker = new Worker(javaClass,
> >> backendListenerClient,
> >> > >>>> (Arguments) getArguments().clone(), queue);
> >> > >>>> +        worker.setDaemon(true);
> >> > >>>> +        worker.start();
> >> > >>>>
> >> > >>>>  Don't we want to stop worker after we're done with one test?
> >> > >>>
> >> > >>>  +        log.info(getName()+":Started  worker with
> >> class:"+javaClass);
> >> > >>>>
> >> > >>>>  Spaces after :?
> >> > >>>
> >> > >>>  +
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /* (non-Javadoc)
> >> > >>>> +     * @see
> >> org.apache.jmeter.samplers.SampleListener#sampleOccurred(
> >> > >>>> org.apache.jmeter.samplers.SampleEvent)
> >> > >>>> +     */
> >> > >>>> +    @Override
> >> > >>>> +    public void sampleOccurred(SampleEvent e) {
> >> > >>>>
> >> > >>>>  Longer name then 'e'? I expect e to be an exception, not an
> >event.
> >> > >>>
> >> > >>>  +        Arguments args = getArguments();
> >> > >>>> +        context = new BackendListenerContext(args);
> >> > >>>> +
> >> > >>>> +        SampleResult sr = backendListenerClient.
> >> > >>>> createSampleResult(context,
> >> > >>>> e.getResult());
> >> > >>>> +        try {
> >> > >>>> +            if (!queue.offer(sr)){ // we failed to add the
> >element
> >> > >>>> first
> >> > >>>> time
> >> > >>>> +                queueWaits++;
> >> > >>>> +                long t1 = System.nanoTime();
> >> > >>>> +                queue.put(sr);
> >> > >>>> +                long t2 = System.nanoTime();
> >> > >>>> +                queueWaitTime += t2-t1;
> >> > >>>>
> >> > >>>>  Will sampleOccurred be called concurrently? If so, than
> >> queueWaitTime
> >> > >>> +=
> >> > >>> will not be correct.
> >> > >>>
> >> > >>>  +            }
> >> > >>>> +        } catch (Exception err) {
> >> > >>>> +            log.error("sampleOccurred, failed to queue the
> >sample",
> >> > >>>> err);
> >> > >>>> +        }
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    private static final class Worker extends Thread {
> >> > >>>> +
> >> > >>>> +        private final BlockingQueue<SampleResult> queue;
> >> > >>>> +        private final BackendListenerContext context;
> >> > >>>> +        private final BackendListenerClient
> >backendListenerClient;
> >> > >>>> +        private Worker(Class<?> javaClass,
> >BackendListenerClient
> >> > >>>> backendListenerClient, Arguments arguments,
> >> BlockingQueue<SampleResult>
> >> > >>>> q){
> >> > >>>>
> >> > >>>>  Same naming argument as above. clientclass instead of
> >javaClass?
> >> > >>>
> >> > >>>  +            queue = q;
> >> > >>>> +            // Allow BackendListenerClient implementations to
> >get
> >> > >>>> access
> >> > >>>> to test element name
> >> > >>>> +            arguments.addArgument(TestElement.NAME,
> >getName());
> >> > >>>> +            context = new BackendListenerContext(arguments);
> >> > >>>> +            this.backendListenerClient =
> >backendListenerClient;
> >> > >>>> +        }
> >> > >>>> +
> >> > >>>> +
> >> > >>>> +        @Override
> >> > >>>> +        public void run() {
> >> > >>>> +            boolean isDebugEnabled = log.isDebugEnabled();
> >> > >>>> +            List<SampleResult> l = new
> >> ArrayList<SampleResult>(queue.
> >> > >>>> size());
> >> > >>>>
> >> > >>>>  samples instead of l?
> >> > >>>
> >> > >>>  +            try {
> >> > >>>> +                boolean eof = false;
> >> > >>>>
> >> > >>>>  endOfLoop?
> >> > >>>
> >> > >>>  +                while (!eof) {
> >> > >>>> +                    if(isDebugEnabled) {
> >> > >>>> +                        log.debug("Thread:"+Thread.
> >> > >>>> currentThread().getName()+"
> >> > >>>> taking SampleResult from queue:"+queue.size());
> >> > >>>> +                    }
> >> > >>>> +                    SampleResult e = queue.take();
> >> > >>>>
> >> > >>>>  Could be named result, or sample instead of e
> >> > >>>
> >> > >>>  +                    if(isDebugEnabled) {
> >> > >>>> +                        log.debug("Thread:"+Thread.
> >> > >>>> currentThread().getName()+"
> >> > >>>> took SampleResult:"+e+", isFinal:" + (e==FINAL_EVENT));
> >> > >>>> +                    }
> >> > >>>> +                    while (!(eof = (e == FINAL_EVENT)) && e
> >!=
> >> null ) {
> >> > >>>> // try to process as many as possible
> >> > >>>> +                        l.add(e);
> >> > >>>> +                        if(isDebugEnabled) {
> >> > >>>> +                            log.debug("Thread:"+Thread.
> >> > >>>> currentThread().getName()+"
> >> > >>>> polling from queue:"+queue.size());
> >> > >>>> +                        }
> >> > >>>> +                        e = queue.poll(); // returns null if
> >> nothing on
> >> > >>>> queue currently
> >> > >>>> +                        if(isDebugEnabled) {
> >> > >>>> +                            log.debug("Thread:"+Thread.
> >> > >>>> currentThread().getName()+"
> >> > >>>> took from queue:"+e+", isFinal:" + (e==FINAL_EVENT));
> >> > >>>> +                        }
> >> > >>>> +                    }
> >> > >>>> +                    if(isDebugEnabled) {
> >> > >>>> +                        log.debug("Thread:"+Thread.
> >> > >>>> currentThread().getName()+
> >> > >>>> +                                " exiting with FINAL
> >EVENT:"+(e ==
> >> > >>>> FINAL_EVENT)
> >> > >>>> +                                +", null:" + (e==null));
> >> > >>>> +                    }
> >> > >>>> +                    int size = l.size();
> >> > >>>>
> >> > >>>>  No need for a temporary variable.
> >> > >>>
> >> > >>>  +                    if (size > 0) {
> >> > >>>> +
> >> backendListenerClient.handleSampleResults(l,
> >> > >>>> context);
> >> > >>>> +                        l.clear();
> >> > >>>> +                    }
> >> > >>>> +                    if(!eof) {
> >> > >>>> +                        LockSupport.parkNanos(100);
> >> > >>>> +                    }
> >> > >>>> +                }
> >> > >>>> +            } catch (InterruptedException e) {
> >> > >>>> +                // NOOP
> >> > >>>> +            }
> >> > >>>> +            // We may have been interrupted
> >> > >>>> +            int size = l.size();
> >> > >>>> +            if (size > 0) {
> >> > >>>> +                backendListenerClient.handleSampleResults(l,
> >> context);
> >> > >>>> +                l.clear();
> >> > >>>> +            }
> >> > >>>>
> >> > >>>>  Same code as a few lines above, could be factored out into a
> >method
> >> > >>> handleSamples(l, context)
> >> > >>>
> >> > >>>  +            log.info("Worker ended");
> >> > >>>> +        }
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Returns reference to
> ><code>BackendListenerClient</code>.
> >> > >>>>
> >> > >>>>  Could use a {@link...}
> >> > >>>
> >> > >>>  +     *
> >> > >>>> +     *
> >> > >>>> +     * @return BackendListenerClient reference.
> >> > >>>> +     */
> >> > >>>> +    static BackendListenerClient
> >createBackendListenerClientImp
> >> > >>>> l(Class<?>
> >> > >>>> javaClass) {
> >> > >>>> +        if (javaClass == null) { // failed to initialise the
> >class
> >> > >>>> +            return new ErrorBackendListenerClient();
> >> > >>>> +        }
> >> > >>>> +        BackendListenerClient client;
> >> > >>>> +        try {
> >> > >>>> +            client = (BackendListenerClient)
> >> javaClass.newInstance();
> >> > >>>> +        } catch (Exception e) {
> >> > >>>> +            log.error("Exception creating: " + javaClass, e);
> >> > >>>> +            client = new ErrorBackendListenerClient();
> >> > >>>> +        }
> >> > >>>> +        return client;
> >> > >>>>
> >> > >>>>  I would return newInstance() in try Block and return new
> >Error.. in
> >> > >>> catch
> >> > >>> Block. javaClass -> clientClass
> >> > >>>
> >> > >>>  +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Method called at the end of the test. This is called
> >only
> >> on one
> >> > >>>> instance
> >> > >>>> +     * of BackendListener. This method will loop through all
> >of the
> >> > >>>> other
> >> > >>>> +     * BackendListenerClients which have been registered
> >> (automatically
> >> > >>>> in the
> >> > >>>> +     * constructor) and notify them that the test has ended,
> >> allowing
> >> > >>>> the
> >> > >>>> +     * BackendListenerClients to cleanup.
> >> > >>>> +     */
> >> > >>>> +    @Override
> >> > >>>> +    public void testEnded() {
> >> > >>>> +        try {
> >> > >>>> +            queue.put(FINAL_EVENT);
> >> > >>>> +        } catch (Exception ex) {
> >> > >>>> +            log.warn("testEnded() with
> >exception:"+ex.getMessage(),
> >> > >>>> ex);
> >> > >>>> +        }
> >> > >>>> +        if (queueWaits > 0) {
> >> > >>>> +            log.warn("QueueWaits: "+queueWaits+";
> >QueueWaitTime:
> >> > >>>> "+queueWaitTime+" (nanoseconds), you may need to increase
> >queue
> >> > >>>> capacity,
> >> > >>>> see property 'backend_queue_capacity'");
> >> > >>>> +        }
> >> > >>>> +        synchronized (TEAR_DOWN_SET) {
> >> > >>>> +            for (BackendListener backendListener :
> >TEAR_DOWN_SET) {
> >> > >>>> +                BackendListenerClient client =
> >backendListener.
> >> > >>>> backendListenerClient;
> >> > >>>> +                if (client != null) {
> >> > >>>> +                    try {
> >> > >>>> +
> >> client.teardownTest(backendListener.context);
> >> > >>>> +                    } catch (Exception e) {
> >> > >>>> +                        throw new java.lang.
> >> > >>>> IllegalStateException("Failed
> >> > >>>> calling teardownTest", e);
> >> > >>>>
> >> > >>>>  If we throw an exception here, we will not try every client.
> >> > >>>
> >> > >>>  +                    }
> >> > >>>> +                }
> >> > >>>> +            }
> >> > >>>> +            TEAR_DOWN_SET.clear();
> >> > >>>> +        }
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /* Implements TestStateListener.testEnded(String) */
> >> > >>>> +    @Override
> >> > >>>> +    public void testEnded(String host) {
> >> > >>>> +        testEnded();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * A {@link BackendListenerClient} implementation used
> >for
> >> error
> >> > >>>> handling. If an
> >> > >>>> +     * error occurs while creating the real
> >BackendListenerClient
> >> > >>>> object, it is
> >> > >>>> +     * replaced with an instance of this class. Each time a
> >sample
> >> > >>>> occurs with
> >> > >>>> +     * this class, the result is marked as a failure so the
> >user
> >> can
> >> > >>>> see
> >> > >>>> that
> >> > >>>> +     * the test failed.
> >> > >>>> +     */
> >> > >>>> +    static class ErrorBackendListenerClient extends
> >> > >>>> AbstractBackendListenerClient {
> >> > >>>> +        /**
> >> > >>>> +         * Return SampleResult with data on error.
> >> > >>>> +         *
> >> > >>>> +         * @see
> >BackendListenerClient#runTest(JavaSamplerContext)
> >> > >>>> +         */
> >> > >>>> +        @Override
> >> > >>>> +        public void handleSampleResults(List<SampleResult>
> >> > >>>> sampleResults, BackendListenerContext context) {
> >> > >>>> +
> >log.warn("ErrorBackendListenerClient#handleSampleResult
> >> > >>>> called, noop");
> >> > >>>> +            Thread.yield();
> >> > >>>> +        }
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /* (non-Javadoc)
> >> > >>>> +     * @see
> >> org.apache.jmeter.samplers.SampleListener#sampleStarted(
> >> > >>>> org.apache.jmeter.samplers.SampleEvent)
> >> > >>>> +     */
> >> > >>>> +    @Override
> >> > >>>> +    public void sampleStarted(SampleEvent e) {
> >> > >>>> +        // NOOP
> >> > >>>> +
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /* (non-Javadoc)
> >> > >>>> +     * @see
> >> org.apache.jmeter.samplers.SampleListener#sampleStopped(
> >> > >>>> org.apache.jmeter.samplers.SampleEvent)
> >> > >>>> +     */
> >> > >>>> +    @Override
> >> > >>>> +    public void sampleStopped(SampleEvent e) {
> >> > >>>> +        // NOOP
> >> > >>>> +
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Set the arguments (parameters) for the
> >> BackendListenerClient to
> >> > >>>> be executed
> >> > >>>> +     * with.
> >> > >>>> +     *
> >> > >>>> +     * @param args
> >> > >>>> +     *            the new arguments. These replace any
> >existing
> >> > >>>> arguments.
> >> > >>>> +     */
> >> > >>>> +    public void setArguments(Arguments args) {
> >> > >>>> +        setProperty(new TestElementProperty(ARGUMENTS,
> >args));
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get the arguments (parameters) for the
> >> BackendListenerClient to
> >> > >>>> be executed
> >> > >>>> +     * with.
> >> > >>>> +     *
> >> > >>>> +     * @return the arguments
> >> > >>>> +     */
> >> > >>>> +    public Arguments getArguments() {
> >> > >>>> +        return (Arguments)
> >getProperty(ARGUMENTS).getObjectValue();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Sets the Classname of the BackendListenerClient object
> >> > >>>> +     *
> >> > >>>> +     * @param classname
> >> > >>>> +     *            the new Classname value
> >> > >>>> +     */
> >> > >>>> +    public void setClassname(String classname) {
> >> > >>>> +        setProperty(CLASSNAME, classname);
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Gets the Classname of the BackendListenerClient object
> >> > >>>> +     *
> >> > >>>> +     * @return the Classname value
> >> > >>>> +     */
> >> > >>>> +    public String getClassname() {
> >> > >>>> +        return getPropertyAsString(CLASSNAME);
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Sets the queue size
> >> > >>>> +     *
> >> > >>>> +     * @param queueSize
> >> > >>>> +     *
> >> > >>>> +     */
> >> > >>>> +    public void setQueueSize(int queueSize) {
> >> > >>>> +        setProperty(QUEUE_SIZE, queueSize,
> >DEFAULT_QUEUE_SIZE);
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Gets the queue size
> >> > >>>> +     *
> >> > >>>> +     * @return int queueSize
> >> > >>>> +     */
> >> > >>>> +    public int getQueueSize() {
> >> > >>>> +        return getPropertyAsInt(QUEUE_SIZE,
> >DEFAULT_QUEUE_SIZE);
> >> > >>>> +    }
> >> > >>>> +}
> >> > >>>>
> >> > >>>> Propchange:
> >> jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListener.java
> >> > >>>> ------------------------------------------------------------
> >> > >>>> ------------------
> >> > >>>>       svn:mime-type = text/plain
> >> > >>>>
> >> > >>>> Added:
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerClient.java
> >> > >>>> URL: http://svn.apache.org/viewvc/jmeter/trunk/src/components/
> >> > >>>> org/apache/jmeter/visualizers/backend/BackendListenerClient.
> >> > >>>> java?rev=1641081&view=auto
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> --- jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerClient.java (added)
> >> > >>>> +++ jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerClient.java Sat Nov 22 15:36:37 2014
> >> > >>>> @@ -0,0 +1,128 @@
> >> > >>>> +/*
> >> > >>>> + * Licensed to the Apache Software Foundation (ASF) under one
> >or
> >> more
> >> > >>>> + * contributor license agreements.  See the NOTICE file
> >distributed
> >> > >>>> with
> >> > >>>> + * this work for additional information regarding copyright
> >> ownership.
> >> > >>>> + * The ASF licenses this file to You under the Apache
> >License,
> >> Version
> >> > >>>> 2.0
> >> > >>>> + * (the "License"); you may not use this file except in
> >compliance
> >> with
> >> > >>>> + * the License.  You may obtain a copy of the License at
> >> > >>>> + *
> >> > >>>> + *   http://www.apache.org/licenses/LICENSE-2.0
> >> > >>>> + *
> >> > >>>> + * Unless required by applicable law or agreed to in writing,
> >> software
> >> > >>>> + * distributed under the License is distributed on an "AS IS"
> >> BASIS,
> >> > >>>> + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
> >express or
> >> > >>>> implied.
> >> > >>>> + * See the License for the specific language governing
> >permissions
> >> and
> >> > >>>> + * limitations under the License.
> >> > >>>> + *
> >> > >>>> + */
> >> > >>>> +
> >> > >>>> +package org.apache.jmeter.visualizers.backend;
> >> > >>>> +
> >> > >>>> +import java.util.List;
> >> > >>>> +
> >> > >>>> +import org.apache.jmeter.config.Arguments;
> >> > >>>> +import org.apache.jmeter.samplers.SampleResult;
> >> > >>>> +
> >> > >>>> +/**
> >> > >>>> + * This interface defines the interactions between the
> >> BackendListener
> >> > >>>> and external
> >> > >>>> + * Java programs which can be executed by JMeter. Any Java
> >class
> >> which
> >> > >>>> wants to
> >> > >>>> + * be executed as a JMeter test must implement this interface
> >> (either
> >> > >>>> directly
> >> > >>>> + * or indirectly through AbstractBackendListenerClient).
> >> > >>>> + * <p>
> >> > >>>> + * JMeter will create one instance of a BackendListenerClient
> >> > >>>> implementation for
> >> > >>>> + * each user/thread in the test. Additional instances may be
> >> created
> >> > >>>> for
> >> > >>>> + * internal use by JMeter (for example, to find out what
> >> parameters are
> >> > >>>> + * supported by the client).
> >> > >>>> + * <p>
> >> > >>>> + * When the test is started, setupTest() will be called on
> >each
> >> > >>>> thread's
> >> > >>>> + * BackendListenerClient instance to initialize the client.
> >Then
> >> > >>>> handleSampleResult() will be
> >> > >>>> + * called for each SampleResult notification. Finally,
> >> teardownTest()
> >> > >>>> will be called
> >> > >>>> + * to allow the client to do any necessary clean-up.
> >> > >>>> + * <p>
> >> > >>>> + * The JMeter BackendListener GUI allows a list of parameters
> >to be
> >> > >>>> defined for the
> >> > >>>> + * test. These are passed to the various test methods through
> >the
> >> > >>>> + * {@link BackendListenerContext}. A list of default
> >parameters
> >> can be
> >> > >>>> defined
> >> > >>>> + * through the getDefaultParameters() method. These
> >parameters and
> >> any
> >> > >>>> default
> >> > >>>> + * values associated with them will be shown in the GUI.
> >Users can
> >> add
> >> > >>>> other
> >> > >>>> + * parameters as well.
> >> > >>>> + * <p>
> >> > >>>> + * When possible, Listeners should extend {@link
> >> > >>>> AbstractBackendListenerClient
> >> > >>>> + * AbstractBackendListenerClient} rather than implementing
> >> > >>>> BackendListenerClient
> >> > >>>> + * directly. This should protect your tests from future
> >changes to
> >> the
> >> > >>>> + * interface. While it may be necessary to make changes to
> >the
> >> > >>>> BackendListenerClient
> >> > >>>> + * interface from time to time (therefore requiring changes
> >to any
> >> > >>>> + * implementations of this interface), we intend to make this
> >> abstract
> >> > >>>> class
> >> > >>>> + * provide reasonable default implementations of any new
> >methods so
> >> > >>>> that
> >> > >>>> + * subclasses do not necessarily need to be updated for new
> >> versions.
> >> > >>>> + * Implementing BackendListenerClient directly will continue
> >to be
> >> > >>>> supported for
> >> > >>>> + * cases where extending this class is not possible (for
> >example,
> >> when
> >> > >>>> the
> >> > >>>> + * client class is already a subclass of some other class).
> >> > >>>> + *
> >> > >>>> + * @since 2.13
> >> > >>>> + */
> >> > >>>> +public interface BackendListenerClient {
> >> > >>>> +    /**
> >> > >>>> +     * Do any initialization required by this client. It is
> >> generally
> >> > >>>> +     * recommended to do any initialization such as getting
> >> parameter
> >> > >>>> values in
> >> > >>>> +     * the setupTest method rather than the runTest method in
> >> order to
> >> > >>>> add as
> >> > >>>> +     * little overhead as possible to the test.
> >> > >>>> +     *
> >> > >>>> +     * @param context
> >> > >>>> +     *            the context to run with. This provides
> >access to
> >> > >>>> +     *            initialization parameters.
> >> > >>>> +     */
> >> > >>>> +    void setupTest(BackendListenerContext context) throws
> >> Exception;
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Perform a single sample for each iteration. This
> >method
> >> returns
> >> > >>>> a
> >> > >>>> +     * <code>SampleResult</code> object.
> ><code>SampleResult</code>
> >> has
> >> > >>>> many
> >> > >>>> +     * fields which can be used. At a minimum, the test
> >should use
> >> > >>>> +     * <code>SampleResult.sampleStart</code> and
> >> > >>>> +     * <code>SampleResult.sampleEnd</code>to set the time
> >that the
> >> > >>>> test
> >> > >>>>
> >> > >>>>  use {@link..} instead of <code>..?
> >> > >>>
> >> > >>>  +     * required to execute. It is also a good idea to set the
> >> > >>>> sampleLabel and
> >> > >>>> +     * the successful flag.
> >> > >>>> +     *
> >> > >>>> +     * @see
> >org.apache.jmeter.samplers.SampleResult#sampleStart()
> >> > >>>> +     * @see
> >org.apache.jmeter.samplers.SampleResult#sampleEnd()
> >> > >>>> +     * @see
> >org.apache.jmeter.samplers.SampleResult#setSuccessful(
> >> > >>>> boolean)
> >> > >>>> +     * @see
> >org.apache.jmeter.samplers.SampleResult#setSampleLabel(
> >> > >>>> String)
> >> > >>>> +     *
> >> > >>>> +     * @param context
> >> > >>>> +     *            the context to run with. This provides
> >access to
> >> > >>>> +     *            initialization parameters.
> >> > >>>> +     *
> >> > >>>> +     */
> >> > >>>> +    void handleSampleResults(List<SampleResult>
> >sampleResults,
> >> > >>>> BackendListenerContext context);
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Do any clean-up required by this test at the end of a
> >test
> >> run.
> >> > >>>> +     *
> >> > >>>> +     * @param context
> >> > >>>> +     *            the context to run with. This provides
> >access to
> >> > >>>> +     *            initialization parameters.
> >> > >>>> +     */
> >> > >>>> +    void teardownTest(BackendListenerContext context) throws
> >> > >>>> Exception;
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Provide a list of parameters which this test supports.
> >Any
> >> > >>>> parameter
> >> > >>>> +     * names and associated values returned by this method
> >will
> >> appear
> >> > >>>> in the
> >> > >>>> +     * GUI by default so the user doesn't have to remember
> >the
> >> exact
> >> > >>>> names. The
> >> > >>>> +     * user can add other parameters which are not listed
> >here. If
> >> this
> >> > >>>> method
> >> > >>>> +     * returns null then no parameters will be listed. If the
> >> value for
> >> > >>>> some
> >> > >>>> +     * parameter is null then that parameter will be listed
> >in the
> >> GUI
> >> > >>>> with an
> >> > >>>> +     * empty value.
> >> > >>>> +     *
> >> > >>>> +     * @return a specification of the parameters used by this
> >test
> >> > >>>> which
> >> > >>>> should
> >> > >>>> +     *         be listed in the GUI, or null if no parameters
> >> should be
> >> > >>>> listed.
> >> > >>>> +     */
> >> > >>>> +    Arguments getDefaultParameters();
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     *
> >> > >>>> +     * @param context
> >> > >>>> +     * @param result
> >> > >>>> +     * @return
> >> > >>>> +     */
> >> > >>>> +    SampleResult createSampleResult(
> >> > >>>> +            BackendListenerContext context, SampleResult
> >result);
> >> > >>>> +}
> >> > >>>>
> >> > >>>> Propchange:
> >> jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerClient.java
> >> > >>>> ------------------------------------------------------------
> >> > >>>> ------------------
> >> > >>>>       svn:mime-type = text/plain
> >> > >>>>
> >> > >>>> Added:
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/
> >> > >>>> BackendListenerContext.java
> >> > >>>> URL: http://svn.apache.org/viewvc/jmeter/trunk/src/components/
> >> > >>>>
> >org/apache/jmeter/visualizers/backend/BackendListenerContext.java?
> >> > >>>> rev=1641081&view=auto
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> ---
> >> jmeter/trunk/src/components/org/apache/jmeter/visualizers/backend/
> >> > >>>> BackendListenerContext.java
> >> > >>>> (added)
> >> > >>>> +++
> >> jmeter/trunk/src/components/org/apache/jmeter/visualizers/backend/
> >> > >>>> BackendListenerContext.java
> >> > >>>> Sat Nov 22 15:36:37 2014
> >> > >>>> @@ -0,0 +1,237 @@
> >> > >>>> +/*
> >> > >>>> +
> >> > >>>> + * Licensed to the Apache Software Foundation (ASF) under one
> >or
> >> more
> >> > >>>> + * contributor license agreements.  See the NOTICE file
> >distributed
> >> > >>>> with
> >> > >>>> + * this work for additional information regarding copyright
> >> ownership.
> >> > >>>> + * The ASF licenses this file to You under the Apache
> >License,
> >> Version
> >> > >>>> 2.0
> >> > >>>> + * (the "License"); you may not use this file except in
> >compliance
> >> with
> >> > >>>> + * the License.  You may obtain a copy of the License at
> >> > >>>> + *
> >> > >>>> + *   http://www.apache.org/licenses/LICENSE-2.0
> >> > >>>> + *
> >> > >>>> + * Unless required by applicable law or agreed to in writing,
> >> software
> >> > >>>> + * distributed under the License is distributed on an "AS IS"
> >> BASIS,
> >> > >>>> + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
> >express or
> >> > >>>> implied.
> >> > >>>> + * See the License for the specific language governing
> >permissions
> >> and
> >> > >>>> + * limitations under the License.
> >> > >>>> + *
> >> > >>>> + */
> >> > >>>> +
> >> > >>>> +package org.apache.jmeter.visualizers.backend;
> >> > >>>> +
> >> > >>>> +import java.util.Iterator;
> >> > >>>> +import java.util.Map;
> >> > >>>> +
> >> > >>>> +import org.apache.jmeter.config.Arguments;
> >> > >>>> +import org.apache.jorphan.logging.LoggingManager;
> >> > >>>> +import org.apache.log.Logger;
> >> > >>>> +
> >> > >>>> +/**
> >> > >>>> + * BackendListenerContext is used to provide context
> >information
> >> to a
> >> > >>>> + * BackendListenerClient implementation. This currently
> >consists
> >> of the
> >> > >>>> + * initialization parameters which were specified in the GUI.
> >> > >>>> + * @since 2.13
> >> > >>>> + */
> >> > >>>> +public class BackendListenerContext {
> >> > >>>> +    /*
> >> > >>>> +     * Implementation notes:
> >> > >>>> +     *
> >> > >>>> +     * All of the methods in this class are currently
> >read-only. If
> >> > >>>> update
> >> > >>>> +     * methods are included in the future, they should be
> >defined
> >> so
> >> > >>>> that a
> >> > >>>> +     * single instance of BackendListenerContext can be
> >associated
> >> with
> >> > >>>> each thread.
> >> > >>>> +     * Therefore, no synchronization should be needed. The
> >same
> >> > >>>> instance
> >> > >>>> should
> >> > >>>> +     * be used for the call to setupTest, all calls to
> >runTest,
> >> and the
> >> > >>>> call to
> >> > >>>> +     * teardownTest.
> >> > >>>> +     */
> >> > >>>> +
> >> > >>>> +    /** Logging */
> >> > >>>> +    private static final Logger log = LoggingManager.
> >> > >>>> getLoggerForClass();
> >> > >>>>
> >> > >>>>  See naming comments for logger above
> >> > >>>
> >> > >>>  +
> >> > >>>> +    /**
> >> > >>>> +     * Map containing the initialization parameters for the
> >> > >>>> BackendListenerClient.
> >> > >>>> +     */
> >> > >>>> +    private final Map<String, String> params;
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     *
> >> > >>>> +     * @param args
> >> > >>>> +     *            the initialization parameters.
> >> > >>>> +     */
> >> > >>>> +    public BackendListenerContext(Arguments args) {
> >> > >>>> +        this.params = args.getArgumentsAsMap();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Determine whether or not a value has been specified
> >for the
> >> > >>>> parameter
> >> > >>>> +     * with this name.
> >> > >>>> +     *
> >> > >>>> +     * @param name
> >> > >>>> +     *            the name of the parameter to test
> >> > >>>> +     * @return true if the parameter value has been
> >specified,
> >> false
> >> > >>>> otherwise.
> >> > >>>> +     */
> >> > >>>> +    public boolean containsParameter(String name) {
> >> > >>>>
> >> > >>>>  hasParameter instead of containsParameter?
> >> > >>>
> >> > >>>  +        return params.containsKey(name);
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get an iterator of the parameter names. Each entry in
> >the
> >> > >>>> Iterator is a
> >> > >>>> +     * String.
> >> > >>>> +     *
> >> > >>>> +     * @return an Iterator of Strings listing the names of
> >the
> >> > >>>> parameters which
> >> > >>>> +     *         have been specified for this test.
> >> > >>>> +     */
> >> > >>>> +    public Iterator<String> getParameterNamesIterator() {
> >> > >>>> +        return params.keySet().iterator();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get the value of a specific parameter as a String, or
> >null
> >> if
> >> > >>>> the
> >> > >>>> value
> >> > >>>> +     * was not specified.
> >> > >>>> +     *
> >> > >>>> +     * @param name
> >> > >>>> +     *            the name of the parameter whose value
> >should be
> >> > >>>> retrieved
> >> > >>>> +     * @return the value of the parameter, or null if the
> >value
> >> was not
> >> > >>>> +     *         specified
> >> > >>>> +     */
> >> > >>>> +    public String getParameter(String name) {
> >> > >>>> +        return getParameter(name, null);
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get the value of a specified parameter as a String, or
> >> return
> >> > >>>> the
> >> > >>>> +     * specified default value if the value was not
> >specified.
> >> > >>>> +     *
> >> > >>>> +     * @param name
> >> > >>>> +     *            the name of the parameter whose value
> >should be
> >> > >>>> retrieved
> >> > >>>> +     * @param defaultValue
> >> > >>>> +     *            the default value to return if the value of
> >this
> >> > >>>> parameter was
> >> > >>>> +     *            not specified
> >> > >>>> +     * @return the value of the parameter, or the default
> >value if
> >> the
> >> > >>>> parameter
> >> > >>>> +     *         was not specified
> >> > >>>> +     */
> >> > >>>> +    public String getParameter(String name, String
> >defaultValue) {
> >> > >>>> +        if (params == null || !params.containsKey(name)) {
> >> > >>>> +            return defaultValue;
> >> > >>>> +        }
> >> > >>>> +        return params.get(name);
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get the value of a specified parameter as an integer.
> >An
> >> > >>>> exception will
> >> > >>>> +     * be thrown if the parameter is not specified or if it
> >is not
> >> an
> >> > >>>> integer.
> >> > >>>> +     * The value may be specified in decimal, hexadecimal, or
> >> octal, as
> >> > >>>> defined
> >> > >>>> +     * by Integer.decode().
> >> > >>>> +     *
> >> > >>>> +     * @param name
> >> > >>>> +     *            the name of the parameter whose value
> >should be
> >> > >>>> retrieved
> >> > >>>> +     * @return the value of the parameter
> >> > >>>> +     *
> >> > >>>> +     * @throws NumberFormatException
> >> > >>>> +     *             if the parameter is not specified or is
> >not an
> >> > >>>> integer
> >> > >>>> +     *
> >> > >>>> +     * @see java.lang.Integer#decode(java.lang.String)
> >> > >>>> +     */
> >> > >>>> +    public int getIntParameter(String name) throws
> >> > >>>> NumberFormatException
> >> > >>>> {
> >> > >>>> +        if (params == null || !params.containsKey(name)) {
> >> > >>>> +            throw new NumberFormatException("No value for
> >parameter
> >> > >>>> named '" + name + "'.");
> >> > >>>>
> >> > >>>>  I would expect an IllegalArgumentException, if no parameter
> >of that
> >> > >>> name
> >> > >>> is found
> >> > >>>
> >> > >>>  +        }
> >> > >>>> +
> >> > >>>> +        return Integer.decode(params.get(name)).intValue();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get the value of a specified parameter as an integer,
> >or
> >> return
> >> > >>>> the
> >> > >>>> +     * specified default value if the value was not specified
> >or
> >> is not
> >> > >>>> an
> >> > >>>> +     * integer. A warning will be logged if the value is not
> >an
> >> > >>>> integer.
> >> > >>>> The
> >> > >>>> +     * value may be specified in decimal, hexadecimal, or
> >octal, as
> >> > >>>> defined by
> >> > >>>> +     * Integer.decode().
> >> > >>>> +     *
> >> > >>>> +     * @param name
> >> > >>>> +     *            the name of the parameter whose value
> >should be
> >> > >>>> retrieved
> >> > >>>> +     * @param defaultValue
> >> > >>>> +     *            the default value to return if the value of
> >this
> >> > >>>> parameter was
> >> > >>>> +     *            not specified
> >> > >>>> +     * @return the value of the parameter, or the default
> >value if
> >> the
> >> > >>>> parameter
> >> > >>>> +     *         was not specified
> >> > >>>> +     *
> >> > >>>> +     * @see java.lang.Integer#decode(java.lang.String)
> >> > >>>> +     */
> >> > >>>> +    public int getIntParameter(String name, int defaultValue)
> >{
> >> > >>>> +        if (params == null || !params.containsKey(name)) {
> >> > >>>> +            return defaultValue;
> >> > >>>> +        }
> >> > >>>> +
> >> > >>>> +        try {
> >> > >>>> +            return
> >Integer.decode(params.get(name)).intValue();
> >> > >>>> +        } catch (NumberFormatException e) {
> >> > >>>> +            log.warn("Value for parameter '" + name + "' not
> >an
> >> > >>>> integer:
> >> > >>>> '" + params.get(name) + "'.  Using default: '"
> >> > >>>> +                    + defaultValue + "'.", e);
> >> > >>>> +            return defaultValue;
> >> > >>>> +        }
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get the value of a specified parameter as a long. An
> >> exception
> >> > >>>> will be
> >> > >>>> +     * thrown if the parameter is not specified or if it is
> >not a
> >> long.
> >> > >>>> The
> >> > >>>> +     * value may be specified in decimal, hexadecimal, or
> >octal, as
> >> > >>>> defined by
> >> > >>>> +     * Long.decode().
> >> > >>>> +     *
> >> > >>>> +     * @param name
> >> > >>>> +     *            the name of the parameter whose value
> >should be
> >> > >>>> retrieved
> >> > >>>> +     * @return the value of the parameter
> >> > >>>> +     *
> >> > >>>> +     * @throws NumberFormatException
> >> > >>>> +     *             if the parameter is not specified or is
> >not a
> >> long
> >> > >>>> +     *
> >> > >>>> +     * @see Long#decode(String)
> >> > >>>> +     */
> >> > >>>> +    public long getLongParameter(String name) throws
> >> > >>>> NumberFormatException {
> >> > >>>> +        if (params == null || !params.containsKey(name)) {
> >> > >>>> +            throw new NumberFormatException("No value for
> >parameter
> >> > >>>> named '" + name + "'.");
> >> > >>>> +        }
> >> > >>>> +
> >> > >>>> +        return Long.decode(params.get(name)).longValue();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Get the value of a specified parameter as along, or
> >return
> >> the
> >> > >>>> specified
> >> > >>>> +     * default value if the value was not specified or is not
> >a
> >> long. A
> >> > >>>> warning
> >> > >>>> +     * will be logged if the value is not a long. The value
> >may be
> >> > >>>> specified in
> >> > >>>> +     * decimal, hexadecimal, or octal, as defined by
> >Long.decode().
> >> > >>>> +     *
> >> > >>>> +     * @param name
> >> > >>>> +     *            the name of the parameter whose value
> >should be
> >> > >>>> retrieved
> >> > >>>> +     * @param defaultValue
> >> > >>>> +     *            the default value to return if the value of
> >this
> >> > >>>> parameter was
> >> > >>>> +     *            not specified
> >> > >>>> +     * @return the value of the parameter, or the default
> >value if
> >> the
> >> > >>>> parameter
> >> > >>>> +     *         was not specified
> >> > >>>> +     *
> >> > >>>> +     * @see Long#decode(String)
> >> > >>>> +     */
> >> > >>>> +    public long getLongParameter(String name, long
> >defaultValue) {
> >> > >>>> +        if (params == null || !params.containsKey(name)) {
> >> > >>>> +            return defaultValue;
> >> > >>>> +        }
> >> > >>>> +        try {
> >> > >>>> +            return Long.decode(params.get(name)).longValue();
> >> > >>>> +        } catch (NumberFormatException e) {
> >> > >>>> +            log.warn("Value for parameter '" + name + "' not
> >a
> >> long: '"
> >> > >>>> + params.get(name) + "'.  Using default: '"
> >> > >>>> +                    + defaultValue + "'.", e);
> >> > >>>> +            return defaultValue;
> >> > >>>> +        }
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     *
> >> > >>>> +     * @param name
> >> > >>>> +     * @param defaultValue
> >> > >>>> +     * @return
> >> > >>>>
> >> > >>>>  No javadoc? Again three warnings more :)
> >> > >>>
> >> > >>>  +     */
> >> > >>>> +    public boolean getBooleanParameter(String name, boolean
> >> > >>>> defaultValue) {
> >> > >>>> +        if (params == null || !params.containsKey(name)) {
> >> > >>>> +            return defaultValue;
> >> > >>>> +        }
> >> > >>>> +        return Boolean.valueOf(params.get(name));
> >> > >>>> +    }
> >> > >>>> +}
> >> > >>>>
> >> > >>>> Propchange:
> >> jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerContext.java
> >> > >>>> ------------------------------------------------------------
> >> > >>>> ------------------
> >> > >>>>       svn:mime-type = text/plain
> >> > >>>>
> >> > >>>> Added:
> >jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerGui.java
> >> > >>>> URL: http://svn.apache.org/viewvc/jmeter/trunk/src/components/
> >> > >>>> org/apache/jmeter/visualizers/backend/BackendListenerGui.
> >> > >>>> java?rev=1641081&view=auto
> >> > >>>> ============================================================
> >> > >>>> ==================
> >> > >>>> --- jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerGui.java (added)
> >> > >>>> +++ jmeter/trunk/src/components/org/apache/jmeter/visualizers/
> >> > >>>> backend/BackendListenerGui.java Sat Nov 22 15:36:37 2014
> >> > >>>> @@ -0,0 +1,282 @@
> >> > >>>> +/*
> >> > >>>> + * Licensed to the Apache Software Foundation (ASF) under one
> >or
> >> more
> >> > >>>> + * contributor license agreements.  See the NOTICE file
> >distributed
> >> > >>>> with
> >> > >>>> + * this work for additional information regarding copyright
> >> ownership.
> >> > >>>> + * The ASF licenses this file to You under the Apache
> >License,
> >> Version
> >> > >>>> 2.0
> >> > >>>> + * (the "License"); you may not use this file except in
> >compliance
> >> with
> >> > >>>> + * the License.  You may obtain a copy of the License at
> >> > >>>> + *
> >> > >>>> + *   http://www.apache.org/licenses/LICENSE-2.0
> >> > >>>> + *
> >> > >>>> + * Unless required by applicable law or agreed to in writing,
> >> software
> >> > >>>> + * distributed under the License is distributed on an "AS IS"
> >> BASIS,
> >> > >>>> + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
> >express or
> >> > >>>> implied.
> >> > >>>> + * See the License for the specific language governing
> >permissions
> >> and
> >> > >>>> + * limitations under the License.
> >> > >>>> + *
> >> > >>>> + */
> >> > >>>> +
> >> > >>>> +package org.apache.jmeter.visualizers.backend;
> >> > >>>> +
> >> > >>>> +import java.awt.BorderLayout;
> >> > >>>> +import java.awt.event.ActionEvent;
> >> > >>>> +import java.awt.event.ActionListener;
> >> > >>>> +import java.util.ArrayList;
> >> > >>>> +import java.util.HashSet;
> >> > >>>> +import java.util.List;
> >> > >>>> +import java.util.Map;
> >> > >>>> +import java.util.Set;
> >> > >>>> +
> >> > >>>> +import javax.swing.ComboBoxModel;
> >> > >>>> +import javax.swing.JComboBox;
> >> > >>>> +import javax.swing.JLabel;
> >> > >>>> +import javax.swing.JPanel;
> >> > >>>> +import javax.swing.JTextField;
> >> > >>>> +
> >> > >>>> +import org.apache.jmeter.config.Argument;
> >> > >>>> +import org.apache.jmeter.config.Arguments;
> >> > >>>> +import org.apache.jmeter.config.gui.ArgumentsPanel;
> >> > >>>> +import org.apache.jmeter.gui.util.HorizontalPanel;
> >> > >>>> +import org.apache.jmeter.testelement.TestElement;
> >> > >>>> +import
> >org.apache.jmeter.testelement.property.PropertyIterator;
> >> > >>>> +import org.apache.jmeter.util.JMeterUtils;
> >> > >>>> +import org.apache.jmeter.visualizers.gui.AbstractListenerGui;
> >> > >>>> +import org.apache.jorphan.logging.LoggingManager;
> >> > >>>> +import org.apache.jorphan.reflect.ClassFinder;
> >> > >>>> +import org.apache.log.Logger;
> >> > >>>> +
> >> > >>>> +/**
> >> > >>>> + * The <code>BackendListenerGui</code> class provides the
> >user
> >> > >>>> interface for the
> >> > >>>> + * {@link BackendListener} object.
> >> > >>>> + * @since 2.13
> >> > >>>> + */
> >> > >>>> +public class BackendListenerGui extends AbstractListenerGui
> >> implements
> >> > >>>> ActionListener {
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     *
> >> > >>>> +     */
> >> > >>>> +    private static final long serialVersionUID =
> >> 4331668988576438604L;
> >> > >>>> +
> >> > >>>> +    /** Logging */
> >> > >>>> +    private static final Logger log = LoggingManager.
> >> > >>>> getLoggerForClass();
> >> > >>>> +
> >> > >>>> +    /** A combo box allowing the user to choose a backend
> >class. */
> >> > >>>> +    private JComboBox classnameCombo;
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * A field allowing the user to specify the size of Queue
> >> > >>>> +     */
> >> > >>>> +    private JTextField queueSize;
> >> > >>>> +
> >> > >>>> +    /** A panel allowing the user to set arguments for this
> >test.
> >> */
> >> > >>>> +    private ArgumentsPanel argsPanel;
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Create a new BackendListenerGui as a standalone
> >component.
> >> > >>>> +     */
> >> > >>>> +    public BackendListenerGui() {
> >> > >>>> +        super();
> >> > >>>> +        init();
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +
> >> > >>>> +    /** {@inheritDoc} */
> >> > >>>> +    @Override
> >> > >>>> +    public String getLabelResource() {
> >> > >>>> +        return "backend_listener"; // $NON-NLS-1$
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Initialize the GUI components and layout.
> >> > >>>> +     */
> >> > >>>> +    private void init() {// called from ctor, so must not be
> >> > >>>> overridable
> >> > >>>> +        setLayout(new BorderLayout(0, 5));
> >> > >>>> +
> >> > >>>> +        setBorder(makeBorder());
> >> > >>>> +        add(makeTitlePanel(), BorderLayout.NORTH);
> >> > >>>> +
> >> > >>>> +        JPanel classnameRequestPanel = new JPanel(new
> >> BorderLayout(0,
> >> > >>>> 5));
> >> > >>>> +        classnameRequestPanel.add(createClassnamePanel(),
> >> > >>>> BorderLayout.NORTH);
> >> > >>>> +        classnameRequestPanel.add(createParameterPanel(),
> >> > >>>> BorderLayout.CENTER);
> >> > >>>> +
> >> > >>>> +        add(classnameRequestPanel, BorderLayout.CENTER);
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Create a panel with GUI components allowing the user
> >to
> >> select a
> >> > >>>> test
> >> > >>>> +     * class.
> >> > >>>> +     *
> >> > >>>> +     * @return a panel containing the relevant components
> >> > >>>> +     */
> >> > >>>> +    private JPanel createClassnamePanel() {
> >> > >>>> +        List<String> possibleClasses = new
> >ArrayList<String>();
> >> > >>>> +
> >> > >>>> +        try {
> >> > >>>> +            // Find all the classes which implement the
> >> > >>>> BackendListenerClient
> >> > >>>> +            // interface.
> >> > >>>> +            possibleClasses =
> >ClassFinder.findClassesThatExtend(
> >> > >>>> JMeterUtils.getSearchPaths(),
> >> > >>>> +                    new Class[] { BackendListenerClient.class
> >});
> >> > >>>> +
> >> > >>>> +            // Remove the BackendListener class from the list
> >> since it
> >> > >>>> only
> >> > >>>>
> >> > >>>>  ErrorBackendListener
> >> > >>>
> >> > >>>  +            // implements the interface for error conditions.
> >> > >>>> +
> >> > >>>> +
> >possibleClasses.remove(BackendListener.class.getName()
> >> +
> >> > >>>> "$ErrorBackendListenerClient");
> >> > >>>> +        } catch (Exception e) {
> >> > >>>> +            log.debug("Exception getting interfaces.", e);
> >> > >>>> +        }
> >> > >>>> +
> >> > >>>> +        JLabel label = new
> >> JLabel(JMeterUtils.getResString("backend_
> >> > >>>> listener_classname"));
> >> > >>>> // $NON-NLS-1$
> >> > >>>> +
> >> > >>>> +        classnameCombo = new
> >JComboBox(possibleClasses.toArray());
> >> > >>>> +        classnameCombo.addActionListener(this);
> >> > >>>> +        classnameCombo.setEditable(false);
> >> > >>>> +        label.setLabelFor(classnameCombo);
> >> > >>>> +
> >> > >>>> +        HorizontalPanel classNamePanel = new
> >HorizontalPanel();
> >> > >>>> +        classNamePanel.add(label);
> >> > >>>> +        classNamePanel.add(classnameCombo);
> >> > >>>> +
> >> > >>>> +        queueSize = new JTextField("", 5);
> >> > >>>> +        queueSize.setName("Queue Size"); //$NON-NLS-1$
> >> > >>>> +        JLabel queueSizeLabel = new JLabel(JMeterUtils.
> >> > >>>> getResString("backend_listener_queue_size")); // $NON-NLS-1$
> >> > >>>> +        queueSizeLabel.setLabelFor(queueSize);
> >> > >>>> +        HorizontalPanel queueSizePanel = new
> >HorizontalPanel();
> >> > >>>> +        queueSizePanel.add(queueSizeLabel,
> >BorderLayout.WEST);
> >> > >>>> +        queueSizePanel.add(queueSize);
> >> > >>>> +
> >> > >>>> +        JPanel panel = new JPanel(new BorderLayout(0, 5));
> >> > >>>> +        panel.add(classNamePanel, BorderLayout.NORTH);
> >> > >>>> +        panel.add(queueSizePanel, BorderLayout.CENTER);
> >> > >>>> +        return panel;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Handle action events for this component. This method
> >> currently
> >> > >>>> handles
> >> > >>>> +     * events for the classname combo box.
> >> > >>>> +     *
> >> > >>>> +     * @param evt
> >> > >>>>
> >> > >>>>  I would spend the few extra characters to make it event
> >instead of
> >> evt
> >> > >>>
> >> > >>>  +     *            the ActionEvent to be handled
> >> > >>>> +     */
> >> > >>>> +    @Override
> >> > >>>> +    public void actionPerformed(ActionEvent evt) {
> >> > >>>> +        if (evt.getSource() == classnameCombo) {
> >> > >>>> +            String className = ((String) classnameCombo.
> >> > >>>> getSelectedItem()).trim();
> >> > >>>> +            try {
> >> > >>>> +                BackendListenerClient client =
> >> (BackendListenerClient)
> >> > >>>> Class.forName(className, true,
> >> > >>>> +                        Thread.currentThread().
> >> > >>>> getContextClassLoader()).
> >> > >>>> newInstance();
> >> > >>>> +
> >> > >>>> +                Arguments currArgs = new Arguments();
> >> > >>>> +                argsPanel.modifyTestElement(currArgs);
> >> > >>>> +                Map<String, String> currArgsMap =
> >> > >>>> currArgs.getArgumentsAsMap();
> >> > >>>> +
> >> > >>>> +                Arguments newArgs = new Arguments();
> >> > >>>> +                Arguments testParams = null;
> >> > >>>> +                try {
> >> > >>>> +                    testParams =
> >client.getDefaultParameters();
> >> > >>>> +                } catch (AbstractMethodError e) {
> >> > >>>> +                    log.warn("BackendListenerClient doesn't
> >> implement
> >> > >>>> "
> >> > >>>> +                            + "getDefaultParameters.  Default
> >> > >>>> parameters
> >> > >>>> won't "
> >> > >>>> +                            + "be shown.  Please update your
> >client
> >> > >>>> class: " + className);
> >> > >>>> +                }
> >> > >>>> +
> >> > >>>> +                if (testParams != null) {
> >> > >>>> +                    PropertyIterator i =
> >testParams.getArguments().
> >> > >>>> iterator();
> >> > >>>>
> >> > >>>>  I would try a for loop instead of explicitly using an
> >iterator
> >> > >>>
> >> > >>>  +                    while (i.hasNext()) {
> >> > >>>> +                        Argument arg = (Argument)
> >> > >>>> i.next().getObjectValue();
> >> > >>>> +                        String name = arg.getName();
> >> > >>>> +                        String value = arg.getValue();
> >> > >>>> +
> >> > >>>> +                        // If a user has set parameters in
> >one
> >> test,
> >> > >>>> and
> >> > >>>> then
> >> > >>>> +                        // selects a different test which
> >supports
> >> the
> >> > >>>> same
> >> > >>>> +                        // parameters, those parameters
> >should
> >> have the
> >> > >>>> same
> >> > >>>> +                        // values that they did in the
> >original
> >> test.
> >> > >>>> +                        if (currArgsMap.containsKey(name)) {
> >> > >>>> +                            String newVal =
> >currArgsMap.get(name);
> >> > >>>> +                            if (newVal != null &&
> >newVal.length()
> >> > 0)
> >> > >>>> {
> >> > >>>> +                                value = newVal;
> >> > >>>> +                            }
> >> > >>>> +                        }
> >> > >>>> +                        newArgs.addArgument(name, value);
> >> > >>>> +                    }
> >> > >>>> +                }
> >> > >>>> +
> >> > >>>> +                argsPanel.configure(newArgs);
> >> > >>>> +            } catch (Exception e) {
> >> > >>>> +                log.error("Error getting argument list for "
> >+
> >> > >>>> className, e);
> >> > >>>> +            }
> >> > >>>> +        }
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Create a panel containing components allowing the user
> >to
> >> > >>>> provide
> >> > >>>> +     * arguments to be passed to the test class instance.
> >> > >>>> +     *
> >> > >>>> +     * @return a panel containing the relevant components
> >> > >>>> +     */
> >> > >>>> +    private JPanel createParameterPanel() {
> >> > >>>> +        argsPanel = new ArgumentsPanel(JMeterUtils.
> >> > >>>> getResString("backend_listener_paramtable")); // $NON-NLS-1$
> >> > >>>> +        return argsPanel;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /** {@inheritDoc} */
> >> > >>>> +    @Override
> >> > >>>> +    public void configure(TestElement config) {
> >> > >>>> +        super.configure(config);
> >> > >>>> +
> >> > >>>> +        argsPanel.configure((Arguments) config.getProperty(
> >> > >>>> BackendListener.ARGUMENTS).getObjectValue());
> >> > >>>> +
> >> > >>>> +        String className = config.getPropertyAsString(
> >> > >>>> BackendListener.CLASSNAME);
> >> > >>>> +        if(checkContainsClassName(classnameCombo.getModel(),
> >> > >>>> className)) {
> >> > >>>> +            classnameCombo.setSelectedItem(className);
> >> > >>>> +        } else {
> >> > >>>> +            log.error("Error setting class:'"+className+"' in
> >> > >>>> BackendListener: "+getName()+
> >> > >>>> +                    ", check for a missing jar in your jmeter
> >> > >>>> 'search_paths' and 'plugin_dependency_paths' properties");
> >> > >>>> +        }
> >> > >>>> +        queueSize.setText(Integer.toString(((BackendListener)
> >> > >>>> config).getQueueSize()));
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /**
> >> > >>>> +     * Check combo contains className
> >> > >>>> +     * @param model ComboBoxModel
> >> > >>>> +     * @param className String class name
> >> > >>>> +     * @return boolean
> >> > >>>>
> >> > >>>>  explain "boolean" or the other params a bit more?
> >> > >>>
> >> > >>>  +     */
> >> > >>>> +    private static final boolean
> >> checkContainsClassName(ComboBoxModel
> >> > >>>> model, String className) {
> >> > >>>> +        int size = model.getSize();
> >> > >>>> +        Set<String> set = new HashSet<String>(size);
> >> > >>>> +        for (int i = 0; i < size; i++) {
> >> > >>>> +            set.add((String)model.getElementAt(i));
> >> > >>>> +        }
> >> > >>>> +        return set.contains(className);
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /** {@inheritDoc} */
> >> > >>>> +    @Override
> >> > >>>> +    public TestElement createTestElement() {
> >> > >>>> +        BackendListener config = new BackendListener();
> >> > >>>> +        modifyTestElement(config);
> >> > >>>> +        return config;
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>> +    /** {@inheritDoc} */
> >> > >>>> +    @Override
> >> > >>>> +    public void modifyTestElement(TestElement config) {
> >> > >>>> +        configureTestElement(config);
> >> > >>>> +        BackendListener backendListener = (BackendListener)
> >config;
> >> > >>>> +        backendListener.setArguments((Arguments)
> >> > >>>> argsPanel.createTestElement());
> >> > >>>> +
> >backendListener.setClassname(String.valueOf(classnameCombo.
> >> > >>>> getSelectedItem()));
> >> > >>>> +
> >backendListener.setQueueSize(Integer.parseInt(queueSize.
> >> > >>>> getText()));
> >> > >>>> +
> >> > >>>> +    }
> >> > >>>> +
> >> > >>>>
> >> > >>>
> >> >
> >>
> >>
> >>
>
>


-- 
Cordialement.
Philippe Mouawad.

Mime
  • Unnamed multipart/alternative (inline, None, 0 bytes)
View raw message