Contact Us 1-800-596-4880

Manage Transactions in JMS Connector

Transactional actions in JMS enable you to execute a series of operations to perform only when the transaction occurs. Use this feature when you want to:

  • Publish a message as part of a transaction
    When you use the Publish operation, the application sends the message to the destination after the transaction occurs. If for some reason the transaction fails and a rollback occurs, the message is not sent.

  • Consume a message as part of a transaction
    When you use either the On New Message source or the Consume operation, the message is acknowledged only after the transaction occurs. If the transaction rolls back, the message returns to the destination for redelivery.

Anypoint Connector for JMS (JMS Connector) provides support for executing the operations by configuring the Transactional action field.

Configure Transactions for Sources

If you want the On New Message source to use a transactional action when sending the messages, configure the Transactional action field to ALWAYS_BEGIN. With this configuration, each new message is processed in a transaction that propagates to all the components in the flow and occurs after the flow execution completes successfully. The transaction rolls back if the flow execution returns an error.

By default, other components in the flow do not join the transaction created by the On New Message source. To execute other operations using the source transaction, configure in those components the Transactional action field either with ALWAYS_JOIN or JOIN_IF_POSSIBLE.

In the following example, you configure the transactional action for new messages:

  1. In Studio, select the On New Message source from your flow.

  2. Set the Destination field to ${originQueue}.

  3. In the Advanced tab, set the Transactional action field to ALWAYS_BEGIN.

In the Advanced tab
Figure 1. JMS Connector Transactional action configuration

In the XML editor, the <jms:listener> and transactionalAction configurations look like this:

<jms:listener config-ref="JMS_Config" destination="${originQueue}" transactionalAction="ALWAYS_BEGIN"/>

Configure Transactions for Operations

To execute an operation like Publish or Consume as part of a transaction, configure the Transactional action field to ALWAYS_JOIN or JOIN_IF_POSSIBLE.

In the following example, you configure the Publish and Consume operations that join a transaction initiated by the On New Message source:

  1. In the Mule Palette view, select JMS > On New Message.

  2. Drag On New Message onto the Studio canvas.

  3. In the On New Message configuration screen, set the Destination field to ${originQueue}.

  4. In the Advanced tab, set the Transactional action field to ALWAYS_BEGIN.

  5. Drag a Publish operation to the right of the On New Message source.

  6. Set the the Destination field to #[attributes.properties.userProperties.redirectDestination].

  7. In the Advanced tab, set the Transactional action field to JOIN_IF_POSSIBLE.

  8. Drag a Consume operation to the right of the Publish operation.

  9. Set the the Destination field to #[attributes.properties.userProperties.callbackDestination].

  10. In the Advanced tab, set the Transactional action field to JOIN_IF_POSSIBLE.

In the Advanced tab
Figure 2. JMS Connector Transactional action configuration for Consume operation

In the XML editor, the transactionalAction configuration looks like this:

<flow name="joiningToListenerTransaction">
    <jms:listener config-ref="JMS_Config" destination="${originQueue}" transactionalAction="ALWAYS_BEGIN"/>
    <jms:publish config-ref="JMS_Config" destination="#[attributes.properties.userProperties.redirectDestination]" transactionalAction="JOIN_IF_POSSIBLE"/>
    <jms:consume config-ref="JMS_Config" destination="#[attributes.properties.userProperties.callbackDestination]" transactionalAction="JOIN_IF_POSSIBLE"/>
</flow>

In the following example, you configure a scoped transaction, using a Try scope component, the JMS Publish and Publish consume operations, and the Validation module Is true operation:

  1. In the Mule Palette view, select HTTP > Listener.

  2. Drag Listener onto the Studio canvas.

  3. In the Listener configuration screen, set the Path field to /orders.

  4. Drag a Try scope component to the right of the Listener source.

  5. Set the Transactional action field to ALWAYS_BEGIN.

  6. Drag a JMS Publish operation into the Try scope component.

  7. Set the the Destination field to ${billingService} and the Transactional action field to ALWAYS_JOIN.

  8. Drag a JMS Publish operation to the right of the first Publish operation.

  9. Set the the Destination field to ${shipmentService} and the Transactional action field to ALWAYS_JOIN.

  10. Drag a Publish consume operation to the right of the second Publish operation.

  11. Set the the Destination field to ${invoicesVerificationService}.

  12. Drag a Validation module Is true operation to the right of the Publish consume operation.

  13. Select Expression for the Expression menu and set the value to #[payload].

In the XML editor, the transactionalAction configuration look like this:

<flow name="nonTxPublishMustNotJoinCurrentTx">
    <http:listener config-ref="HTTP_Config" path="/orders"/>
    <try transactionalAction="ALWAYS_BEGIN">
        <jms:publish config-ref="config" destination="${billingService}" transactionalAction="ALWAYS_JOIN"/>
        <jms:publish config-ref="config" destination="${shipmentService}" transactionalAction="ALWAYS_JOIN"/>
        <jms:publish-consume config-ref="JMS_Config" destination="${invoicesVerificationService}"/>
        <validation:is-true expression="#[payload]"/>
    </try>
</flow>
View on GitHub