2 Replies Latest reply on Aug 25, 2011 10:50 PM by Thunder Lei

    Remote JMS server and XA transaction

    Thunder Lei Newbie

      Hi,

       

      I go throug many disctssions related, but not find solution.

      My problem is that, is it possible to use xa transaction on remote JMS server?

       

      The scenario is: we have two JBoss 5 server instances, A and B. Our ear application runs on one server A, while another server is dedicated to running JMS server for all queues.

       

      On server A, our EJBs(including MDBs) want to talk to database and JMS Queue on server B using XA transaction.

       

      Is this picture possible?

       

      I am talking about the Jboss messaging and NOT HornetQ.

       

       

      Thanks in advance for any comments.

      Thunder

        • 1. Re: Remote JMS server and XA transaction
          Thunder Lei Newbie

          After talking to JBoss support team, seems there is no way to achieve this goal.

          • 2. Re: Remote JMS server and XA transaction
            Thunder Lei Newbie

            oooh, I have to say sorry for confusing.

            We can do that.

            To so that, simply you just need to,

             

            In jms-ds.xml

             

            1. define a External jndi Context, which is NOT necessary, just to simply your code, with this external jndi context, you don't need to have local jndi context and remote jndi context if you need to look up ojbects accross servers.

             

            <mbean code="org.jboss.naming.ExternalContext" name="jboss.jndi:service=ExternalContext,jndiName=remote">

                 <attribute name="JndiName">remote</attribute>

                 <attribute name="Properties">

                    java.naming.factory.initial=org.jnp.interfaces.NamingContextFactory

                    java.naming.factory.url.pkgs=org.jnp.interfaces

                            jnp.partitionName=jms_remote

                 <!-- java.naming.provider.url=jnp://serverB:1099 -->

                 </attribute>

              </mbean>

             

             

            2. using external jndi, define a remote JMS Provider pointing the remote server, in abouve case, server B.

             

               <mbean code="org.jboss.jms.jndi.JMSProviderLoader"

                  name="jboss.mq:service=JMSProviderLoader,name=RemoteJMSProvider,server=remotehost">

                <attribute name="ProviderName">RemoteJMSProvider</attribute>

                <attribute name="ProviderAdapterClass">org.jboss.jms.jndi.JNDIProviderAdapter</attribute>

                <attribute name="FactoryRef">remote/ClusteredXAConnectionFactory</attribute>

                <attribute name="QueueFactoryRef">remote/ClusteredXAConnectionFactory</attribute>

                <attribute name="TopicFactoryRef">remote/ClusteredXAConnectionFactory</attribute>

                <depends>jboss.jndi:service=ExternalContext,jndiName=remote</depends>

              </mbean>

             

             

            3. define a connection factory using the JMS Privider, and apply the jms JCA adapter to the connection factory.

             

            <tx-connection-factory>

                <jndi-name>RemoteJmsXA</jndi-name>

                <xa-transaction/>

                <rar-name>jms-ra.rar</rar-name>

                <connection-definition>org.jboss.resource.adapter.jms.JmsConnectionFactory</connection-definition>

                <adapter-display-name>JMS Adapter</adapter-display-name>

                <config-property name="JmsProviderAdapterJNDI" type="java.lang.String">java:/RemoteJMSProvider</config-property>

                <config-property name="SessionDefaultType" type="java.lang.String">javax.jms.Topic</config-property>

            </tx-connection-factory>

             

             

            4. In the EJB code like,

             

            Context ctx = getInitialContext();

                                          ConnectionFactory cf = (ConnectionFactory)ctx.lookup("java:/RemoteJmsXA");

                                          Destination remoteQueue = (Destination)ctx.lookup("remote/javax.jms.RemoteQueue");

                                          connection = cf.createConnection();

                                          sessionProducer = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);

                                          producer = sessionProducer.createProducer(remoteQueue);

                                          ObjectMessage om = sessionProducer.createObjectMessage("StringObjectMessage");

                                          producer.send(om);

                                          System.out.println("============Message Sent========================");

                 // some db update

               Thread.currentThread().sleep(1000 * 15); // verify xa tx

             

             

             

            OK, enjoy your remote JMS xa tx......