Is there any way to make sure a periodic (every 10 seconds) and persistent timer is cancelled when an exception occurs? The implementation of the @Timeout
method is something like this (simplified from legacy code):
@Timeout
@TransactionAttribute(REQUIRES_NEW)
public void onTimeout(Timer timer) {
try {
doSomeBusinessLogic();
} catch (Exception e) {
// throwing this exception makes sure rollback is triggered
throw new EJBException(e);
}
}
Upon any exception in doSomeBusinessLogic()
, its transaction needs to be rolled back. This is working fine. However, I would also make sure that the timer is cancelled.
The straightforward solution is to put timer.cancel()
in the catch block. This is not working, however, because the cancelling will also be rolled back (JEE6 Turorial):
An enterprise bean usually creates a timer within a transaction. If this transaction is rolled back, the timer creation also is rolled back. Similarly, if a bean cancels a timer within a transaction that gets rolled back, the timer cancellation is rolled back. In this case, the timer’s duration is reset as if the cancellation had never occurred.
How can I make sure that the timer is cancelled (preventing any further timeouts) if an exception/rollback occurs? Setting a maximum nuber of retries would also be sufficient, but I don't think this is supported by JBoss.
Application server is JBoss AS 7.2.
I also tried solution proposed by Sergey and it seems to work - timer is cancelled. Tested on JBoss EAP 6.2. Here is the code I used for testing: