You are viewing a plain text version of this content. The canonical link for it is here.
Posted to ojb-user@db.apache.org by Mark Neighbors <mn...@visualanalytics.com> on 2004/07/30 22:29:16 UTC

Looks like TransactionImpl.abort is not called when a SQLException is thrown from ConnectionManagerImpl.localCommit

It looks like TransactionImpl.abort is not called when a SQLException is thrown
from ConnectionManagerImpl.localCommit

The call sequence is

   * org.apache.ojb.broker.accesslayer.ConnectionManagerImpl.localCommit
   * org.apache.ojb.broker.core.PersistenceBrokerImpl.commitTransaction
   * org.apache.ojb.odmg.TransactionImpl.commit

The jdbc commit is performed in ConnectionManagerImpl.localCommit.

If a SQLException is thrown from the jdbc driver then

(1) localCommit has an exception handler for SQLException.  The SQLException is
    wrapped in a org.apache.ojb.broker.TransactionAbortedException and then the
    TransactionAbortedException is thrown back to PersistenceBrokerImpl.
    commitTransaction.
    
(2) PersistenceBrokerImpl.commitTransaction implicitly rethrows the org.apache.
    ojb.broker.TransactionAbortedException back to TransactionImpl.commit.
    
(3) But there isn't an exception handler for org.apache.ojb.broker.
    TransactionAbortedException and so TransactionImpl.commit implicitly
    rethrows the exception back to the application.
    
TransactionImpl.commit has an exception handler for org.odmg.
ODMGRuntimeException.  TransactionImpl.abort is called from this exception
handler.

org.apache.ojb.odmg.TransactionAbortedExceptionOJB extends org.odmg.
ODMGRuntimeException, but org.apache.ojb.broker.TransactionAbortedException
does not.  This seems to be the problem.

I temporarily added the following exception handler to TransactionImpl.commit
and TransactionImpl.abort was called.

   catch (org.apache.ojb.broker.TransactionAbortedException ex)
   {
      m_txStatus = Status.STATUS_MARKED_ROLLBACK;
      if (log.isDebugEnabled()) log.debug("Commit fails, do abort this tx", ex);
      abort();
      handleOJBTransactionAbortedException(ex) ;
   }

where

   private void handleOJBTransactionAbortedException(
       org.apache.ojb.broker.TransactionAbortedException e)
      throws org.odmg.TransactionAbortedException
   {
      if (e.getCause() != null)
      {
         throw new org.apache.ojb.odmg.TransactionAbortedExceptionOJB(
                      e.getCause()) ;
      }
      else
      {
         throw new org.apache.ojb.odmg.TransactionAbortedExceptionOJB(e) ;
      }
   }
    
I also made similar patches in other TransactionImpl methods.  The patched
TransactionImpl class is included.  The patched class is at rc6 since we are
currently at rc6, but the source for 1.0 seems the same here.

Thanks in advance,
Mark