ConcurrentModificationException in ClientImpl caused by toString-method on 
requestContext
-----------------------------------------------------------------------------------------

                 Key: CXF-2835
                 URL: https://issues.apache.org/jira/browse/CXF-2835
             Project: CXF
          Issue Type: Bug
    Affects Versions: 2.2.6
            Reporter: Henning Jensen


We have about 10 threads running at the same time against the same web service. 
Some of the requests fail with the following stacktrace:

{code}
javax.xml.ws.soap.SOAPFaultException: Fault string, and possibly fault code, 
not set
        at 
org.apache.cxf.jaxws.JaxWsClientProxy.invoke(JaxWsClientProxy.java:146)
        at $Proxy218.getFlightData(Unknown Source)
        at com.example.FlightDataAction.run(FlightDataAction.java:94)
        at 
java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886)
        at 
java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908)
        at java.lang.Thread.run(Thread.java:619)
Caused by: java.util.ConcurrentModificationException
        at java.util.HashMap$HashIterator.nextEntry(HashMap.java:793)
        at java.util.HashMap$EntryIterator.next(HashMap.java:834)
        at java.util.HashMap$EntryIterator.next(HashMap.java:832)
        at java.util.AbstractMap.toString(AbstractMap.java:485)
        at java.lang.String.valueOf(String.java:2826)
        at java.lang.StringBuilder.append(StringBuilder.java:115)
        at java.util.AbstractMap.toString(AbstractMap.java:490)
        at java.util.Collections$SynchronizedMap.toString(Collections.java:2026)
        at java.lang.String.valueOf(String.java:2826)
        at java.lang.StringBuilder.append(StringBuilder.java:115)
        at org.apache.cxf.endpoint.ClientImpl.processResult(ClientImpl.java:535)
        at org.apache.cxf.endpoint.ClientImpl.invoke(ClientImpl.java:486)
        at org.apache.cxf.endpoint.ClientImpl.invoke(ClientImpl.java:310)
        at org.apache.cxf.endpoint.ClientImpl.invoke(ClientImpl.java:262)
        at org.apache.cxf.frontend.ClientProxy.invokeSync(ClientProxy.java:73)
        at 
org.apache.cxf.jaxws.JaxWsClientProxy.invoke(JaxWsClientProxy.java:124)
        ... 5 more
{code}

>From ClientImpl:

{code}

    protected Map<Thread, Map<String, Object>> responseContext 
        = Collections.synchronizedMap(new WeakHashMap<Thread, Map<String, 
Object>>());
....

    protected Object[] processResult(Message message,
                                   Exchange exchange,
                                   BindingOperationInfo oi,
                                   Map<String, Object> resContext) throws 
Exception {
....

        // Grab the response objects if there are any
        List resList = null;
        Message inMsg = exchange.getInMessage();
        if (inMsg != null) {
            if (null != resContext) {
                resContext.putAll(inMsg);
                if (LOG.isLoggable(Level.FINE)) {
                    LOG.fine("set responseContext to be" + responseContext);
                }
            }
            resList = inMsg.getContent(List.class);
        }
...
{code}

The use of toString on responseContext is causing a 
ConcurrentModificationException when there are many threads working at the same 
time on the same service. The LOG.fine -line is not optimal since the string is 
actually resolved no matter if the log line is going to be written to the log 
file or not. Using String.format() would fix the issue when log level is not 
FINE, but would not fix the actual problem caused by many threads at the same 
time. I'm not sure what the developer wish to log in this cause, but limiting 
the object traversal and not using toString should do the trick. 




-- 
This message is automatically generated by JIRA.
-
You can reply to this email to add a comment to the issue online.

Reply via email to