0

We have code that runs a couple of threads. Within the run event of the thread, we call 2 web services. We are experiencing performance issues when reaching iteration number 2000. The process runs at about 600ms per web service call and as it continues, it can go to almost 60 seconds...

The actual execution of each web service stays consistent but the port creation becomes slower:

long preStartTime = System.currentTimeMillis();

ServicePortType winPort = (ServicePortType) this.getConnector().getFactory().create();

long preEndTime = System.currentTimeMillis();
LOGGER.debug("@@@Web Service Prep work (1st service) took => " + (preEndTime - preStartTime) + "ms");

This will log at the start at around 80 milliseconds and as the process continues running, it can go up to 50 seconds when at the 2000 iteration:

(iteration 1)    @@@Web Service Prep work (1st service) took => 80ms
(iteration 2000) @@@Web Service Prep work (1st service) took => 524421ms

Here is the connector setup:

    @Override
    public void init(Properties prop) {
    LOGGER.info("@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@");
    LOGGER.info("@@@@@@ Starting HTTPConnector @@@@@@@@@@@@@@");
    LOGGER.info("@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@");
    try {
        factory = new JaxWsProxyFactoryBean();
        factory.setServiceClass(ServicePortType.class);
        LOGGER.debug("@@@URL : " + prop.getProperty("service.url"));
        factory.setAddress(prop.getProperty("service.url"));
        factory.getInInterceptors().add(new LoggingInInterceptor());
        factory.getOutInterceptors().add(new LoggingOutInterceptor());
    } catch (Exception ex) {
        LOGGER.error(ex);
    }

    LOGGER.info("@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@");
    LOGGER.info("@@@@@@ End HTTPConnector @@@@@@@@@@@@@@@@@@@");
    LOGGER.info("@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@");
}

Can anyone guide me here please?

EDIT

I changed this part which was called each and every time to static and it is only created once. Performance is good now, but don't know if that has an impact on anything else.

From this:

ServicePortType winPort = (ServicePortType) this.getConnector().getFactory().create();

To this:

private static UVSInterfaceExtendPortType winPort;
if (winPort == null)
{
   winPort = (UVSInterfaceExtendPortType) this.getConnector().getFactory().create();
}
  • can you post the code in create() of Factory class? – Ravindra babu Aug 29 '15 at 16:32
  • @sunrise: It is part of the JaxWsProxyFactoryBean.java (compiled code). What I am testing now though is only initializing the port once in the constructor. Seems to be working better. Still monitoring it though. – Peet vd Westhuizen Aug 29 '15 at 16:40
  • You should know that officially, JAX-WS proxy classes [are not threadsafe](http://stackoverflow.com/questions/4385204/are-jax-ws-clients-thread-safe). By your use of JaxWsProxyFactoryBean, I'm going to assume you're running CXF , in which case the answer is still [*sometimes*](http://cxf.apache.org/faq.html#FAQ-AreJAXWSclientproxiesthreadsafe%3F). Depending on your setup, the "solution" you've arrived at might cause you problems elswhere. In a production system, more threads doesn't mean better performance in fact, it might actually mean *less* performance. The more threads you have, the... – kolossus Sep 02 '15 at 19:39
  • ...more context switching your processor will have to do (aside from all the other overhead that comes with multithreading). – kolossus Sep 02 '15 at 19:41

1 Answers1

1

The solution for me was to instantiate the portType only once instead of each and every time (As discussed in my edit).

We do about 100k transactions per day and the speed stays below a second for the complete transaction which consists of 2 web service calls and a couple of database calls.