简体   繁体   中英

Can JMS MessageListener start XA transactions?

Let's say I write the following code (pure standalone Java with Atomikos, no Spring, no JavaEE, no beans):

XASession session = conn.createXASession();
MessageConsumer consumer = session.createConsumer(session.createQueue("QNAME"));
consumer.setMessageListener(new MessageListener() {
    @Override
    public void onMessage(Message message) {
        //some logic involving other XA resources
    }
});

It's obvious I haven't told my XASession about my TransactionManager or vice versa, so the message received doesn't belong to any transaction. Can I somehow change that? I thought about doing this:

XASession session = conn.createXASession();
MessageConsumer consumer = session.createConsumer(session.createQueue("QNAME"));
Transaction tx;
tm.begin(); //tm is TransactionManager
tx = tm.getTransaction();
tx.enlistResource(session.getXAResource());
consumer.setMessageListener(new MessageListener() {
    @Override
    public void onMessage(Message message) {
        //some logic involving other XA resources
        tm.commit();
        tm.begin();
        tx = tm.getTransaction();
        tx.enlistResource(session.getXAResource());
    }
});

But I am worried that

  • cross-thread XA transactions are not a thing
  • if the message doesn't come for a long time the broker will time out the transaction

I believe you'd need to implement some kind of wrapper (similar to what's done in Java EE and Spring) in order to coordinate with the transaction manager behind the scenes for every message received before your onMessage is invoked and then after onMessage is done. Interleaving the ending and beginning of different transactions in a single invocation of onMessage seems unlikely to turn out well if even function at all.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM