[mule-user] Multiple HTTP connectors issue for AxisConnector

5 views
Skip to first unread message

Mark Sullivan

unread,
Nov 14, 2007, 4:29:35 PM11/14/07
to us...@mule.codehaus.org
This appears to be something similar to
http://mule.mulesource.org/jira/browse/MULE-1665, but when I use the
attached configuration on Linux (2.6 series kernel), Mule 1.4.3 ear
embedded in JBoss 4.2.1.GA, Java5, I get the following error:

2007-11-09 11:41:56,347 DEBUG [org.mule.impl.MuleMessage] new copy of
message for Thread[connector.axis.0.dispatcher.5,7,jboss]
2007-11-09 11:41:56,348 DEBUG
[org.mule.providers.soap.axis.extensions.MuleSoapHeadersHandler] After
Client Request, Message is:
<?xml version="1.0" encoding="UTF-8"?><soapenv:Envelope
xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:xsd="http://www.w3.org/2001
/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><soapenv:Header><mule:header
soapenv:actor="http://www.muleumo.org/providers/soap
/1.0" soapenv:mustUnderstand="0"
xmlns:mule="http://www.muleumo.org/providers/soap/1.0"><mule:MULE_CORRELATION_ID>ID:TSOCA-47976-1194631951031-3:39
:1:1:1</mule:MULE_CORRELATION_ID><mule:MULE_CORRELATION_GROUP_SIZE>-1</mule:MULE_CORRELATION_GROUP_SIZE><mule:MULE_CORRELATION_SEQUENCE>-1</mule:MU
LE_CORRELATION_SEQUENCE></mule:header></soapenv:Header><soapenv:Body><notify
xmlns="http://com.rsc/tmossim"><arg0 xsi:type="xsd:string" xmlns="">&l
t;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot;?&gt;
&lt;notificationList
xmlns=&quot;http://demo.kay.com/notification&quot;&gt;&lt;notification&gt;&lt;acknowledged&gt;false&lt;/acknowledged&gt;&lt;ti
me&gt;2007/11/09
18:41:56.111&lt;/time&gt;&lt;site&gt;TSOC-A&lt;/site&gt;&lt;source&gt;SV
Ops&lt;/source&gt;&lt;description&gt;Succession change of
control &lt;/description&gt;&lt;criticality&gt;WARN&lt;/criticality&gt;&lt;/notification&gt;&lt;/notificationList&gt;</arg0
></notify></soapenv:Body></soapenv:Envelope>
2007-11-09 11:41:56,348 DEBUG
[org.mule.providers.service.TransportServiceDescriptor] Endpoint
resolver not set, Loading default resolver: org.mule
.impl.endpoint.UrlEndpointBuilder
2007-11-09 11:41:56,348 DEBUG
[org.mule.providers.service.TransportServiceDescriptor] Endpoint
resolver not set, Loading default resolver: org.mule
.impl.endpoint.UrlEndpointBuilder
2007-11-09 11:41:56,349 DEBUG [org.mule.config.i18n.MessageFactory]
Loading resource bundle: META-INF.services.org.mule.i18n.core-messages
for loca
le en_US
2007-11-09 11:41:56,349 DEBUG [org.mule.config.i18n.MessageFactory]
Loading resource bundle: META-INF.services.org.mule.i18n.core-messages
for loca
le en_US
2007-11-09 11:41:56,349 DEBUG [org.mule.config.i18n.MessageFactory]
Loading resource bundle: META-INF.services.org.mule.i18n.core-messages
for loca
le en_US
2007-11-09 11:41:56,349 ERROR [org.mule.impl.DefaultExceptionStrategy]
********************************************************************************
Message : There are at least 2 connectors matching
protocol "http", so the connector to use must be specified on the
endpoint using t
he 'connector' property/attribute (java.lang.IllegalStateException)
Type : org.mule.providers.service.TransportFactoryException
Code : MULE_ERROR--2
JavaDoc :
http://mule.mulesource.org/docs/apidocs/org/mule/providers/service/TransportFactoryException.html
********************************************************************************
Exception stack is:
1. There are at least 2 connectors matching protocol "http", so the
connector to use must be specified on the endpoint using the
'connector' proper
ty/attribute (java.lang.IllegalStateException)
org.mule.providers.service.TransportFactory:443
(http://java.sun.com/j2se/1.5.0/docs/api/java/lang/IllegalStateException.html)
2. There are at least 2 connectors matching protocol "http", so the
connector to use must be specified on the endpoint using the
'connector' proper
ty/attribute (java.lang.IllegalStateException)
(org.mule.providers.service.TransportFactoryException)
org.mule.providers.service.TransportFactory:111
(http://mule.mulesource.org/docs/apidocs/org/mule/providers/service/TransportFactoryException.htm
l)
********************************************************************************
Root Exception stack trace:
java.lang.IllegalStateException: There are at least 2 connectors
matching protocol "http", so the connector to use must be specified on
the endpoin
t using the 'connector' property/attribute
at org.mule.providers.service.TransportFactory.getConnectorByProtocol(TransportFactory.java:443)
at org.mule.providers.service.TransportFactory.createEndpoint(TransportFactory.java:101)
at org.mule.impl.ImmutableMuleEndpoint.createEndpointFromUri(ImmutableMuleEndpoint.java:598)
at org.mule.impl.ImmutableMuleEndpoint.getOrCreateEndpointForUri(ImmutableMuleEndpoint.java:663)
at org.mule.impl.ImmutableMuleEndpoint.getOrCreateEndpointForUri(ImmutableMuleEndpoint.java:663)
at org.mule.impl.ImmutableMuleEndpoint.<init>(ImmutableMuleEndpoint.java:234)
at org.mule.impl.endpoint.MuleEndpoint.<init>(MuleEndpoint.java:73)
at org.mule.providers.soap.axis.extensions.UniversalSender.lookupEndpoint(UniversalSender.java:283)
at org.mule.providers.soap.axis.extensions.UniversalSender.invoke(UniversalSender.java:112)
at org.apache.axis.strategies.InvocationStrategy.visit(InvocationStrategy.java:32)
at org.apache.axis.SimpleChain.doVisiting(SimpleChain.java:118)
at org.apache.axis.SimpleChain.invoke(SimpleChain.java:83)
at org.apache.axis.client.AxisClient.invoke(AxisClient.java:165)
at org.apache.axis.client.Call.invokeEngine(Call.java:2784)
at org.apache.axis.client.Call.invoke(Call.java:2767)
at org.apache.axis.client.Call.invoke(Call.java:2443)
at org.apache.axis.client.Call.invoke(Call.java:2366)
at org.apache.axis.client.Call.invoke(Call.java:1812)
at org.mule.providers.soap.axis.AxisMessageDispatcher.doDispatch(AxisMessageDispatcher.java:135)
at org.mule.providers.AbstractMessageDispatcher$Worker.run(AbstractMessageDispatcher.java:561)
at org.mule.impl.work.WorkerContext.run(WorkerContext.java:310)
at edu.emory.mathcs.backport.java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:987)
at edu.emory.mathcs.backport.java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:528)
at java.lang.Thread.run(Thread.java:595)

********************************************************************************

Basically the system filters JMS messages from JMS topics and forwards
them out to multiple web services on the same remote host. Once the
error stops it persists until mule is restarted. After inspecting the
code it looks like a concurrency issue in
TransportFactory.getConnectorByProtocol(String protocol), where two
threads entering are creating a new HttpConnector and adding it to the
pool, leaving the third thread coming in to see them both and fail. A
possible solution to this would be to make mule synchronous, but that
seems like a bit much. By dumping the connector pool I do see that
there are two HttpConnectors listed, along with my AxisConnectors.

Any help would be appreciated.

Regards,

Mark

tsat-config.xml

Andrew Perepelytsya

unread,
Nov 14, 2007, 4:43:27 PM11/14/07
to us...@mule.codehaus.org
I'm not sure your analysis is correct. Here's the current source code of the method:

    public static UMOConnector getConnectorByProtocol(String protocol)
    {
        UMOConnector connector;
        UMOConnector resultConnector = null;
        Map connectors = MuleManager.getInstance().getConnectors();
        for (Iterator iterator = connectors.values().iterator(); iterator.hasNext();)
        {
            connector = (UMOConnector) iterator.next ();
            if (connector.supportsProtocol(protocol))
            {
                if (resultConnector == null)
                {
                    resultConnector = connector;
                }
                else
                {
                    throw new IllegalStateException(
                        CoreMessages.moreThanOneConnectorWithProtocol(protocol).getMessage());
                }
            }
        }
        return resultConnector;
    }

The getConnectors() returns an unmodifiable map, and then, there's no modification of it anyway.

Andrew

Mark Sullivan

unread,
Nov 14, 2007, 5:09:26 PM11/14/07
to us...@mule.codehaus.org
Hi Andrew,

Thanks for the reply. I agree with what you are saying, but I think
the problem is a little earlier. So in the method that calls this
method in the same class:

TransportFactory.createEndpoint(UMOEndpointURI uri, String type):

public static UMOEndpoint createEndpoint(UMOEndpointURI uri, String
type) throws EndpointException
{
logger.info("creating new endpoint for " + uri.getAddress() +
" of type " + type);
String scheme = uri.getFullScheme();
UMOConnector connector;
try
{
logger.info("getCreateConnector = " +
uri.getCreateConnector() + " for uri " + uri.getConnectorName() + ",
address " + uri.getAddress());
if (uri.getCreateConnector() == ALWAYS_CREATE_CONNECTOR)
{
logger.info("in always create");
connector = createConnector(uri);
MuleManager.getInstance().registerConnector(connector);
}
else if (uri.getCreateConnector() == NEVER_CREATE_CONNECTOR)
{
logger.info("in never create");
connector = getConnectorByProtocol(scheme);
}
else if (uri.getConnectorName() != null)
{
logger.info("in uri.getConnectorName() != null, the
name is " + uri.getConnectorName());
connector =
MuleManager.getInstance().lookupConnector(uri.getConnectorName());
if (connector == null)
{
throw new TransportFactoryException(

CoreMessages.objectNotRegisteredWithManager("Connector: " +
uri.getConnectorName()));
}
}
else
{
logger.info("in else, getting connector for protocol "
+ scheme);
logger.info("the connector is " + connector);
if (connector == null)
{
connector = createConnector(uri);
MuleManager.getInstance().registerConnector(connector);
}
}
}
catch (Exception e)
{
throw new TransportFactoryException(e);
}

Now assuming we have uri.getCreateConnector() =
GET_OR_CREATE_CONNECTOR = 0, I think it is possible that two threads
could enter this method at the same time. They would both call:

connector = getConnectorByProtocol(scheme);

and get null for the connector object, and then both proceed to create
new connectors which will find their way (i think) into the global
pool. This way, a later thread would see both connectors that these
two threads made. Again, this assumes some unlucky timing between the
first two threads, but I think it is possible. Granted I have not
looked through the entire code base.

Regards,
Mark

---------------------------------------------------------------------
To unsubscribe from this list please visit:

http://xircles.codehaus.org/manage_email

Reply all
Reply to author
Forward
0 new messages