This documentation is for WSO2 Enterprise Service Bus version 5.0.0. For the latest ESB, view the latest WSO2 Enterprise Integrator documentation.

All docs This doc

Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

...

  1. Configure the JMS local transaction by defining the following parameter in the <ESB HOME>/repository/conf/axis2/axis2.xml file. By default the session is not transacted. In order to make it transacted, set the parameter to true.

    Code Block
    languagehtml/xml
    <parameter name="transport.jms.SessionTransacted">true</parameter>

    Once done, the JMS listener configuration for WSO2 MB in the axis2.xml file should be as follows:

    Code Block
    languagehtml/xml
    <transportReceiver name="jms" class="org.apache.axis2.transport.jms.JMSListener">
           <parameter name="myTopicConnectionFactory" locked="false">
                <parameter name="java.naming.factory.initial" locked="false">org.wso2.andes.jndi.PropertiesFileInitialContextFactory</parameter>
                <parameter name="java.naming.provider.url" locked="false">repository/conf/jndi.properties</parameter>
                <parameter name="transport.jms.ConnectionFactoryJNDIName" locked="false">TopicConnectionFactory</parameter>
            	<parameter name="transport.jms.ConnectionFactoryType" locked="false">topic</parameter>
            	<parameter name="transport.jms.SessionTransacted">true</parameter>
           </parameter>
     
           <parameter name="myQueueConnectionFactory" locked="false">
               	<parameter name="java.naming.factory.initial" locked="false">org.wso2.andes.jndi.PropertiesFileInitialContextFactory</parameter>
               	<parameter name="java.naming.provider.url" locked="false">repository/conf/jndi.properties</parameter>
               	<parameter name="transport.jms.ConnectionFactoryJNDIName" locked="false">QueueConnectionFactory</parameter>
            	<parameter name="transport.jms.ConnectionFactoryType" locked="false">queue</parameter>
            	<parameter name="transport.jms.SessionTransacted">true</parameter>	
    	   </parameter>
     
           <parameter name="default" locked="false">
               	<parameter name="java.naming.factory.initial" locked="false">org.wso2.andes.jndi.PropertiesFileInitialContextFactory</parameter>
               	<parameter name="java.naming.provider.url" locked="false">repository/conf/jndi.properties</parameter>
               	<parameter name="transport.jms.ConnectionFactoryJNDIName" locked="false">QueueConnectionFactory</parameter>
            	<parameter name="transport.jms.ConnectionFactoryType" locked="false">queue</parameter>
            	<parameter name="transport.jms.SessionTransacted">true</parameter>
    		</parameter>
       </transportReceiver>
  2. Copy and paste the following configuration into the Synapse configuration in <ESB_HOME>/repository/deployment/server/synapse-configs/<node>/synapse.xml.

    Code Block
    languagehtml/xml
    <definitions xmlns="http://ws.apache.org/ns/synapse">
       <proxy name="StockQuoteProxy" transports="jms" startOnLoad="true">
          <target>
             <inSequence>
                <property name="OUT_ONLY" value="true"/>
                <callout serviceURL="http://localhost:9000/services/SimpleStockQuoteService">
                   <source type="envelope"/>
                   <target key="placeOrder"/>
                </callout>
                <log level="custom">
                   <property name="Transaction Action" value="Committed"/>
                </log>
             </inSequence>
             <faultSequence>
                <property name="SET_ROLLBACK_ONLY" value="true" scope="axis2"/>
                <log level="custom">
                   <property name="Transaction Action" value="Rollbacked"/>
                </log>
             </faultSequence>
          </target>
          <parameter name="transport.jms.ContentType">
             <rules>
                <jmsProperty>contentType</jmsProperty>
                <default>application/xml</default>
             </rules>
          </parameter>
       </proxy>
       <sequence name="fault">
          <log level="full">
             <property name="MESSAGE" value="Executing default &#34;fault&#34; sequence"/>
             <property name="ERROR_CODE" expression="get-property('ERROR_CODE')"/>
             <property name="ERROR_MESSAGE" expression="get-property('ERROR_MESSAGE')"/>
          </log>
          <drop/>
       </sequence>
       <sequence name="main">
          <log/>
          <drop/>
       </sequence>
    </definitions>

    According to the above configuration, a message will be read from the JMS queue and will be sent to the SimpleStockQuoteService running on the Axis2 back-end server. If a failure occurs, the transaction will roll back. 

    In the above configuration, the following property is set to true in the fault handler, in order to roll back the transaction when a failure occurs. 

    Code Block
    languagehtml/xml
    <property name="SET_ROLLBACK_ONLY" value="true" scope="axis2"/>
    Tip

    If you are using a JMS Inbound endpoint for the transaction, set the scope of the SET_ROLLBACK_ONLY property to default as follows:

    <property name="SET_ROLLBACK_ONLY" scope="default" type="STRING" value="true"/>
  3. Deploy the back-end service SimpleStockQuoteService . For instructions on deploying sample back-end services, see Deploying sample back-end services.
  4. Start the Axis2 server. For instructions on starting the Axis2 server, see Starting the Axis2 server.

    You now have a running ESB instance, WSO2 Message Broker instance and a sample back-end service to simulate the sample scenario. Now let's execute the JMS client.

    Info

    Due to the asynchronous behavior of the Send Mediator, you cannot you use it with a http/https endpoint, but you can use it in asynchronous use cases, for example with another JMS as endpoint.

...

Testing the sample scenario

Successful scenario

In order to simulate the successful scenario, the message should mediate successfully.

When You can test the sample scenario as follows.

Successful scenario

If the message mediates successfully, you will view the output on the Axis2 server start-up console will be as follows:

Image Removed

The . Also, the ESB debug log will display an INFO message as follows, indicating that the transaction is committed. 

Image Removed

Failure Scenario In order to simulate the failure scenario, you need to stop the scenario

Stop the sample Axis2 Server and and execute the JMS client once again. 
In again to simulate the failure scenario. In this scenario, the ESB debug log will display an INFO message as follows, indicating that the transaction is rolled back.

Image Removed

JMS distributed transactions 
Anchor
Distributed
Distributed

...

Sample Scenario

ESB listens to the message queue and sends that message to multiple queues. If something goes wrong in sending the message to one of those queues, the original message should be rolled back to the listening queue and none of the other queues should receive the message. Thus, the entire transaction should be rolled back.

 

Prerequisites

  • Windows, Linux or Solaris operating systems with WSO2 ESB installed. For instructions on downloading and installing  WSO2 ESB, see Installation Guide.
  • WSO2 ESB's JMS transport configured with ActiveMQ. For instructions, see Configure with ActiveMQ.

Configuring the sample scenario

  1. Create the JMSListenerProxy proxy service in ESB with the following configuration:

    Code Block
    languagexml
    <proxy xmlns="http://ws.apache.org/ns/synapse"
           name="JMSListenerProxy"
           transports="https http jms"
           startOnLoad="true">
       <description/>
       <target>
          <inSequence>
             <property name="OUT_ONLY" value="true"/>
             <log level="custom">
                <property name="MESSAGE_ID_A" expression="get-property('MessageID')"/>
             </log>
             <log level="custom">
                <property name="BEFORE" expression="$body"/>
             </log>
             <property name="MESSAGE_ID_B"
                       expression="get-property('MessageID')"
                       scope="operation"
                       type="STRING"/>
             <property name="failureResultProperty"
                       scope="default"
                       description="FailureResultProperty">
                <result xmlns="">failure</result>
             </property>
             <enrich>
                <source clone="true" xpath="$ctx:failureResultProperty"/>
                <target type="body"/>
             </enrich>
             <log level="custom">
                <property name="AFTER" expression="$body"/>
             </log>
             <property name="BEFORE1" value="ABCD" scope="axis2" type="STRING"/>
            <callout serviceURL="jms:/ActiveMQPublisher1?transport.jms.ConnectionFactoryJNDIName=XAConnectionFactory&amp;java.naming.factory.initial=org.apache.activemq.jndi.ActiveMQInitialContextFactory&amp;java.naming.provider.url=tcp://localhost:61616&amp;transport.jms.DestinationType=queue;transport.jms.TransactionCommand=begin">
                <source type="envelope"/>
                <target xmlns:s12="http://www.w3.org/2003/05/soap-envelope"
                        xmlns:s11="http://schemas.xmlsoap.org/soap/envelope/"
                        xpath="s11:Body/child::*[fn:position()=1] | s12:Body/child::*[fn:position()=1]"/>
             </callout>
             <callout serviceURL="jms:/ActiveMQPublisher2?transport.jms.ConnectionFactoryJNDIName=XAConnectionFactory&amp;java.naming.factory.initial=org.apache.activemq.jndi.ActiveMQInitialContextFactory&amp;java.naming.provider.url=tcp://localhost:61616&amp;transport.jms.DestinationType=queue">
                <source type="envelope"/>
                <target xmlns:s12="http://www.w3.org/2003/05/soap-envelope"
                        xmlns:s11="http://schemas.xmlsoap.org/soap/envelope/"
                        xpath="s11:Body/child::*[fn:position()=1] | s12:Body/child::*[fn:position()=1]"/>
             </callout>
             <callout serviceURL="jms:/ActiveMQPublisher3?transport.jms.ConnectionFactoryJNDIName=XAConnectionFactory&amp;java.naming.factory.initial=org.apache.activemq.jndi.ActiveMQInitialContextFactory&amp;java.naming.provider.url=tcp://localhost:61616&amp;transport.jms.DestinationType=queue;transport.jms.TransactionCommand=end">
                <source type="envelope"/>
                <target xmlns:s12="http://www.w3.org/2003/05/soap-envelope"
                        xmlns:s11="http://schemas.xmlsoap.org/soap/envelope/"
                        xpath="s11:Body/child::*[fn:position()=1] | s12:Body/child::*[fn:position()=1]"/>
             </callout>
             <drop/>
          </inSequence>
          <faultSequence>
             <log level="custom">
                <property name="Transaction Action" value="Rollbacked"/>
             </log>
             <callout serviceURL="jms:/ActiveMQPublisherFault?transport.jms.ConnectionFactoryJNDIName=XAConnectionFactory&amp;java.naming.factory.initial=org.apache.activemq.jndi.ActiveMQInitialContextFactory&amp;java.naming.provider.url=tcp://localhost:61616&amp;transport.jms.DestinationType=queue;transport.jms.TransactionCommand=rollback">
                <source type="envelope"/>
                <target xmlns:s12="http://www.w3.org/2003/05/soap-envelope"
                        xmlns:s11="http://schemas.xmlsoap.org/soap/envelope/"
                        xpath="s11:Body/child::*[fn:position()=1] | s12:Body/child::*[fn:position()=1]"/>
             </callout>
          </faultSequence>
       </target>
       <parameter name="transport.jms.ContentType">
          <rules>
             <jmsProperty>contentType</jmsProperty>
             <default>application/xml</default>
          </rules>
       </parameter>
       <parameter name="transport.jms.Destination">MyJMSQueue</parameter>
    </proxy>

    In the above configuration,  ESB listens to a JMS queue named MyJMSQueue and consumes messages as well as sends messages to multiple JMS queues in a transactional manner.

  2. To place a message into MyJMSQueue, execute the following command from <ESB_HOME>/samples/axis2Client directory:

    Code Block
    languagexml
    ant stockquote -Dmode=placeorder -Dtrpurl="jms:/MyJMSQueue?transport.jms.ConnectionFactoryJNDIName=QueueConnectionFactory&java.naming.factory.initial=org.apache.activemq.jndi.ActiveMQInitialContextFactory&java.naming.provider.url=tcp://localhost:61616&transport.jms.ContentTypeProperty=Content-Type&transport.jms.DestinationType=queue"

    You can see how ESB consumes messages from the queue named MyJMSQueue and sends the messages to multiple queues.

    To check the rollback functionality provide an unreachable host name to any destination queue and save the configurations. You should be able to observe ESB fault sequence getting invoked and failed message delivered to the destination configured in fault sequence.