Previous: HTTP Transport Up: Transports Next: Local Transport

JMS Transport

This guide gives you a quick rundown of how to configure XFire to use JMS as a transport. JMS is one of the easiest means to create a reliable SOAP connection. Additionally it is much faster then things such as WS-Reliability.

This example assumes that you already know how to:

  • Configure services via XFire's services.xml format
  • Build and deploy simple XFire applications
  • Use your JMS provider
  • A working knowledge of Spring

We're just going to show a simple synchronous Echo example running over JMS. The first thing you need to do is create your services.xml file:

<beans xmlns="http://xfire.codehaus.org/config/1.0">

  <!--
    Register the JMS transport. Note: this needs to happen *before* we
    create our service.
    -->
  <xfire>
    <transports>
      <bean id="jmsTransport"
            class="org.codehaus.xfire.transport.jms.JMSTransport"
            xmlns="http://xbean.org/schemas/spring/1.0">
        <constructor-arg ref="xfire"/>
        <constructor-arg ref="connectionFactory"/>
      </bean>
    </transports>
  </xfire>

  <service xmlns:e="urn:Echo">
    <name>Echo</name>
    <serviceClass>org.codehaus.xfire.test.Echo</serviceClass>
    <implementationClass>org.codehaus.xfire.test.EchoImpl</implementationClass>
    <bindings>
      <soap11Binding name="e:EchoJMSBinding" transport="urn:xfire:transport:jms">
        <endpoints>
          <endpoint name="e:EchoJMSEndpoint" url="jms://Echo" />
        </endpoints>
      </soap11Binding>
    </bindings>
  </service>

  <bean id="connectionFactory"
        class="org.apache.activemq.ActiveMQConnectionFactory"
        singleton="true"
        xmlns="http://xbean.org/schemas/spring/1.0/">
    <constructor-arg value="vm://localhost?broker.persistent=false" type="java.lang.String"/>
  </bean>

</beans>

There is a lot in here, so lets recap this a little bit.

The xfire section contains a transports element. In transports we are creating our JMSTransport via the Spring bean syntax. XFire will then automatically register this transport for us into the TransportManager.

The service element contains our service definition. This is pretty standard, except you'll notice we're creating a new binding for JMS. soap11Binding transport="urn:xfire:transport:jms" tells XFire that we want to add a SOAP 1.1 binding for JMS. In the endpoints section we tell XFire exactly what that endpoint will be. The JMS urls take the form of jms://QueueName.

In the sections below we configure our JMS QueueConnectionFactory using ActiveMQ.

Once all of this is properly configured we will of course want to write a client:

import java.lang.reflect.Proxy;

import org.codehaus.xfire.client.XFireProxy;
import org.codehaus.xfire.client.XFireProxyFactory;
import org.codehaus.xfire.service.Service;
import org.codehaus.xfire.service.binding.ObjectServiceFactory;
import org.codehaus.xfire.spring.AbstractXFireSpringTest;
import org.codehaus.xfire.test.Echo;
import org.codehaus.xfire.transport.jms.JMSTransport;
import org.springframework.context.ApplicationContext;
import org.apache.xbean.spring.context.ClassPathXmlApplicationContext;

public class JMSExampleTest
    extends AbstractXFireSpringTest
{
    protected ApplicationContext createContext()
    {
        return new ClassPathXmlApplicationContext(new String[] {
                "/org/codehaus/xfire/transport/jms/example/jms.xml",
                "/org/codehaus/xfire/spring/xfire.xml" });
    }

    public void testClient()
            throws Exception
    {
        // Create a ServiceFactory to create the ServiceModel.
        // We need to add the JMSTransport to the list of bindings to create.
        ObjectServiceFactory sf = new ObjectServiceFactory(getTransportManager());
        sf.addSoap11Transport(JMSTransport.BINDING_ID);

        // Create the service model
        Service serviceModel = sf.create(Echo.class);

        // Create a proxy for the service
        XFireProxyFactory factory = new XFireProxyFactory(getXFire());
        Echo echo = (Echo) factory.create(serviceModel, "jms://Echo");

        // Since JMS doesn't really have a concept of anonymous endpoints, we need
        // need to let xfire know what JMS endpoint we should use
        ((XFireProxy) Proxy.getInvocationHandler(echo)).getClient().setEndpointUri("jms://Peer1");

        // run the client!
        String resString = echo.echo("hello");
        assertEquals("hello", resString);
    }
}


Previous: HTTP Transport Up: Transports Next: Local Transport