File APIs for Java Developers
Manipulate DOC, XLS, PPT, PDF and many others from your application.
http://aspose.com/file-tools
The moose likes EJB Certification (SCBCD/OCPJBCD) and the fly likes mock exam + MDB transaction Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login


Win a copy of Spring in Action this week in the Spring forum!
JavaRanch » Java Forums » Certification » EJB Certification (SCBCD/OCPJBCD)
Bookmark "mock exam + MDB transaction" Watch "mock exam + MDB transaction" New topic
Author

mock exam + MDB transaction

Miki Muzsi
Ranch Hand

Joined: Jun 23, 2003
Posts: 120
Problem

Consider the following code occuring in a MyBean code. It updates the
database and sends a message to a queue named Q1. The message driven
bean (not same as MyBean) associated with the queue requires a
transaction and updates the database upon receiving a message.
Assuming that all the variables are properly defined and used, what
will happen if the MDB associated with the queue Q1 rolls back the
transaction but does not throw any exception?


Code

11. public void myBeanMethod()
12. {
...
21. UserTransaction ut = ejbContext.getUserTransaction();
22. ut.begin();
23. queueSender.send(message); //sends a message to a queue Q1.
24. stmt.executeUpdate(query1);
25. ut.rollback();
...
30. }


1 Changes made by the bean code at line 24 will be committed.
2 Line 25 will throw an Exception
3 The message will be sent to the queue.
4 The message will be sent to the queue but the changes made to the
database by the MDB will not be committed.
5 The container will resend the message to the queue.
6 Neither the message is sent nor any database changes get committed.


I would say the correct answer is 4. But it was 6.

My first confusion: why would the transaction rollback in the MDB affect the sending of the message in the MyBean bean? It is suppose to happen everything asynchronously!

Second, could EVER the transaction status of the MDB affect the transaction status of the MyBean (calling bean). Once again I would say no, since the MDB works in a different transaction! Which reminds me again: even though the TX attribute is Required, if a calling bean has a TX it doesn't mean that the bean will run in that TX right? Since MDB have no clients etc. Or is it again up to the container to choose if it uses the same TX or a different TX?

Thanks,
Miki

Miki


Miki<br /> <br />SCJP 1.4, SCBCD 1.3
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
My first confusion: why would the transaction rollback in the MDB affect the sending of the message in the MyBean bean? It is suppose to happen everything asynchronously!

The message will be sent and it is indeed asynchronous.



Second, could EVER the transaction status of the MDB affect the transaction status of the MyBean (calling bean).

No it won't affect as for MDB the a new transaction will be started and the transaction context of the calling bean won;t be propogated.

I don;t remember exacty but I guess this question is from JDiscuss. I believe the answer they have given in the site is wrong.


Sawan


Sawan<br />SCJP,SCWCD,SCBCD<br /> <br />Every exit is an entry somewhere.
Prashant Neginahal
Ranch Hand

Joined: Sep 14, 2002
Posts: 77
Really good question. At first look i thought answers are 2,3,4. I included 4 because MDB which is CMT rollsback the tx, so the message will go back to queue and it will be resent again.

But later i found 6 is the correct answer. Acoording to my analysis, the session deals with two connections here, one is to queue and another is to database. So, only when it commits everything will be executed, otherwise none. This example revels an example in EJB spec at page 335.

Thanks,
Prashant


Thanks, <br />Prashant<br />SCJP, SCBCD
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
11. public void myBeanMethod()
12. {
...
21. UserTransaction ut = ejbContext.getUserTransaction();
22. ut.begin();
23. queueSender.send(message); //sends a message to a queue Q1.
24. stmt.executeUpdate(query1);
25. ut.rollback();
...
30. }




I am not convinced. Suppose the message that is sent remains in the queue for 1 minute. Does that mean that the whole transaction won't commit and will wait for the message to be processed {definitely not}. The sending of message is asynchronous that means it won't wait for the message to be consumed .

The page 335 in the specs shows a client sending a message to a MDB X that in turn updates the data[ this makes one transaction]. This scenario is a little different that the one shown in the above code because the message is sent and will start a new transaction for MDB and the remaining code thats after sending the message will be executed.


sawan
[ June 18, 2005: Message edited by: sawan parihar ]
Miki Muzsi
Ranch Hand

Joined: Jun 23, 2003
Posts: 120
Good reference to 17.2.2 (pg. 335). Thanks.

Indeed I also see that there is a difference in the two scenarios (the one I describe and the one from 17.2.2). The difference is that in 17.2.2 is not described that the MDB starts/executes a (new) transaction. And that is the whole point. If MDB would do smth in a transaction, would that transaction be the same started by X? Could it be configured in such a way that the tx of the MDB and B and C are all commit or all rolled back?

Because than indeed what sawan, says is very true:
Suppose the message that is sent remains in the queue for 1 minute. Does that mean that the whole transaction won't commit and will wait for the message to be processed


It would have been much more clear if the TX attribute of an MDB would be RequiresNew and NOT Required
Which reminds me to another thing: in HF, Kathy (or Bert) says (on page 500 right box): "Message driven beans can only use two attributes: Required and NotSupported. ... RequiresNew? Thst's useless because
there will never be a pre-existing transaction. So if this is correct than ... "

Anyboy any more ideas?
Roger Chung-Wee
Ranch Hand

Joined: Sep 29, 2002
Posts: 1683

I believe that you are correct. As JMS cannot determine which (or if any) transaction to use for an asynchronously delivered message, JMS asynchronous message delivery is not supported within JTA user transactions.

The solution is for a message-driven bean to start a JTA transaction, perorm JMS and other operations and commit. Of course, all resources such as the JMS server and the database must be XA-enabled.


SCJP 1.4, SCWCD 1.3, SCBCD 1.3
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
It would have been much more clear if the TX attribute of an MDB would be RequiresNew and NOT Required .

I came across this question many times but never saw a convincing answer thats why thought it will be good to discuss with you guys.

In this thread I replied about what I think that why the transaction attribute should be Required and not RequiresNew.
http://www.coderanch.com/t/160859/java-EJB-SCBCD/certification/pg

sawan
Miki Muzsi
Ranch Hand

Joined: Jun 23, 2003
Posts: 120
Sawan, in that thread you mention that
There is nothing written in specs that why RequiresNew can't be


Actuallly in the spec pg. 316 (bottom of the page), is exactly what HF says on pg 500: RequiresNew doesn't make sense ... because there can be no preexisting transaction context.

Which means, that the tx status of an MDB can never ever "affect" other tx.

Miki
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
Miki ,

RequiresNew doesn't make sense ... because there can be no preexisting transaction context.

I find it hard to understand this line. If there is no pre existing transaction context still specifying it as RequiresNew will work as it will start a new transaction that is what we want. The reason that appeals me more is that Required is there for the container provided to handle the message receipe and the onMessage() call in one transaction and may be for some other reasons.


sawan
amit taneja
Ranch Hand

Joined: Mar 14, 2003
Posts: 810
why i m not seeing properly allinged messages ?

is there is problem in my browser or what ?

there are many times i face this problem and huge horizontal bar ?

why ?


Thanks and Regards, Amit Taneja
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
Its not the problem with your browser. Some problem with the formatting of the text. Anyways we can still read the posts right..relax.




sawan
Tapan Verma
Greenhorn

Joined: Jun 18, 2005
Posts: 4
Is this possible?
Queue Transactions are one-phase commit whereas DB Transactions are 2-phase commit. Hence, is a combination of 1-phase and 2-phase commits under one transaction possible?

Thanks.
Prashant Neginahal
Ranch Hand

Joined: Sep 14, 2002
Posts: 77
I guess i am not clear in what i am saying. Before getting into this question let me confirm my basic understanding. In JMS, two things happen.

a) Client(like MyBean) sends message to distination(Queue/Topic).
b) MDB will consume the messages through server.

The option a) is NOT asynchronous and option b) which consumption and execution the message is asyncronous.

Let me come to this question now. Once the message is delivered to Queue, its over. It will execute asynchronously and whether it commits or rolledback it is restricted to ONLY its context that happens in OnMessage() method.

My understanding is, since the line 23 and line 24 happens in transaction (ut), only when it commits following things happen.
1) Sending of message to queue Q1, and
2) updating the database that is query1

So, since at line 25, this transaction is getting rolled back i guess nuthing will happen, that is neither 1) or 2). So, here MDB transaction does not come into picture at all.

Please do let me know if i am wrong.

Thanks,
Prashant
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
My understanding is, since the line 23 and line 24 happens in transaction (ut), only when it commits following things happen.
1) Sending of message to queue Q1, and
2) updating the database that is query1


This is not right. In fact the message is sent. When the control will reach line 23 the message will be sent and is placed in the queue. After that the rollback happens at line 25 which won't do anything to the message that is already in the queue.

To conclude in the above case the message will be placed in the queue.


Hope that helps.

sawan
[ June 19, 2005: Message edited by: sawan parihar ]
Miki Muzsi
Ranch Hand

Joined: Jun 23, 2003
Posts: 120
Parshat, you made your point very clear, and it would indeed explain the result of the test.

But as Sawan suggests, are you sure once you have sent the message "queueSender.send(message);" the message is still not definately sent? Does sending of a message relate to a transaction? I am not saying you are not right just that I always thought TXs are always related to database updates. On the contrary I think you have a good point because also on pg. 334/335 the spec is talking about "The EJB server ensures that the operations on A, B and C are either all commited or all rolled back". Where A is a Queue and B,C are databases. So I never really understood what does "operations on A" mean? Which it seems now that it means exactly what you are suggesting "sending the message".

Which still puzzels me. So sending a message is like updating a database, without commit. And you still have a chance to rollback, meaning what? the message gets deleted?

Then what if I send a message while I am not in a TX? It gets immediately delivered?

Parshat, could you find smth in the spec about this? Or how did you come up with the idea?

Miki
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
Hello friends,
It would be much more clear if you guys can do the similar tests on the container that you have. I have tested the same scenario in weblogic and websphere and the message is indeed sent. May be you guys might have other servers which you can use to test this scenario and after that post the results back.

Also would like to add that there should be some way that the sending of message can take part in a transaction. I was just thinking that if in practical cases suppose we have to create a customer in the ejb and tell the finance department about the new customer by sending an message then this all should be one transaction. On the other hand the things work differently.


Conclusion : The code above sends a message to the queue if you are using weblogic or websphere and I believe the behaviour should be same for other servers


Thanks.

sawan

[ June 19, 2005: Message edited by: sawan parihar ]
[ June 19, 2005: Message edited by: sawan parihar ]
Roger Chung-Wee
Ranch Hand

Joined: Sep 29, 2002
Posts: 1683
Also would like to add that there should be some way that the sending of message can take part in a transaction. I was just thinking that if in practical cases suppose we have to create a customer in the ejb and tell the finance department about the new customer by sending an message then this all should be one transaction.

Refer to my last post on how this can be done.
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
The solution is for a message-driven bean to start a JTA transaction, perorm JMS and other operations and commit. Of course, all resources such as the JMS server and the database must be XA-enabled.

Yes you are right. But it is like changing your design to do this thing. Don't find it a good way of doing things. Suppose in the scenario that I have written in my previous post I have to send the message. It's going to be pain.

Anyways thanks.
Miki Muzsi
Ranch Hand

Joined: Jun 23, 2003
Posts: 120
So by using an MDB with bean transaction demarcation, the way the "original test" is suggesting, you can put everything, including sending of the message, in one transaction?

This would mean that the answer to this is 6: "Neither the message is sent nor any database changes get committed. ". Is that correct?

Thanks all for your responses, too bad the other experts seem to be on holiday . Or maybe working on the next book :-)

Miki
sawan parihar
Ranch Hand

Joined: Aug 24, 2004
Posts: 250
This would mean that the answer to this is 6: "Neither the message is sent nor any database changes get committed. ". Is that correct?


hahah we are back at the same place. No answer 6 is not correct. The message will be sent.


sawan
Prashant Neginahal
Ranch Hand

Joined: Sep 14, 2002
Posts: 77
Guys,

I have tried following code using RI.

------------------------------------------------------
UserTransaction ut = context.getUserTransaction();
ut.begin();
Context ctx = new InitialContext();
QueueConnectionFactory qFact = (QueueConnectionFactory) ctx.lookup("java:comp/env/prashu/QueueConnectionFactory");
Queue q = (Queue) ctx.lookup("jms/Queue");

QueueConnection qConn = qFact.createQueueConnection();
QueueSession qSession = qConn.createQueueSession(true, Session.AUTO_ACKNOWLEDGE);
QueueSender qSender = qSession.createSender(q);
Message msg = qSession.createMessage();
qSender.send(msg);
System.out.println("Message is sent");
qConn.close();
ut.rollback();
System.out.println("Tx rolled back.....");
---------------------------------------------------------------

Result is
Message is NOT sent. The behavior is same when
--there is a transaction and it is rolled back, and
--no transaction at all.

Yes, message is sent when i committed the transaction.

Thanks,
Prashant
 
I agree. Here's the link: http://aspose.com/file-tools
 
subject: mock exam + MDB transaction