You are viewing a plain text version of this content. The canonical link for it is here.
Posted to derby-commits@db.apache.org by km...@apache.org on 2009/04/14 18:02:41 UTC

svn commit: r764856 - in /db/derby/code/branches/10.3/java: client/org/apache/derby/client/net/NetXAResource.java engine/org/apache/derby/jdbc/EmbedXAResource.java testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/XATransactionTest.java

Author: kmarsden
Date: Tue Apr 14 16:02:41 2009
New Revision: 764856

URL: http://svn.apache.org/viewvc?rev=764856&view=rev
Log:
DERBY-4141  XAExceptions thrown by Derby can have errorCode 0 


Modified:
    db/derby/code/branches/10.3/java/client/org/apache/derby/client/net/NetXAResource.java
    db/derby/code/branches/10.3/java/engine/org/apache/derby/jdbc/EmbedXAResource.java
    db/derby/code/branches/10.3/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/XATransactionTest.java

Modified: db/derby/code/branches/10.3/java/client/org/apache/derby/client/net/NetXAResource.java
URL: http://svn.apache.org/viewvc/db/derby/code/branches/10.3/java/client/org/apache/derby/client/net/NetXAResource.java?rev=764856&r1=764855&r2=764856&view=diff
==============================================================================
--- db/derby/code/branches/10.3/java/client/org/apache/derby/client/net/NetXAResource.java (original)
+++ db/derby/code/branches/10.3/java/client/org/apache/derby/client/net/NetXAResource.java Tue Apr 14 16:02:41 2009
@@ -167,7 +167,7 @@
             }
             netAgent.endReadChain();
         } catch (SqlException sqle) {
-            rc = XAException.XAER_RMERR;
+            rc = getSqlExceptionXAErrorCode(sqle);
             exceptionsOnXA = org.apache.derby.client.am.Utils.accumulateSQLException
                     (sqle, exceptionsOnXA);
         } finally {
@@ -179,6 +179,25 @@
     }
 
     /**
+     * Get XAException.errorCode from SqlException
+     * For disconnect exception, return XAER_RMFAIL
+     * For other exceptions return XAER_RMERR
+     * 
+     * For server side SQLExceptions during 
+     * XA operations the errorCode has already been determined
+     * and wrapped in an XAException for return to the client.
+     * see EmbedXAResource.wrapInXAException
+     * 
+     * @param sqle  SqlException to evaluate.
+     * @return XAException.XAER_RMFAIL for disconnect exception,
+     *         XAException.XAER_RMERR for other exceptions.
+     */
+    private int getSqlExceptionXAErrorCode(SqlException sqle) {      
+       int seErrorCode = sqle.getErrorCode();
+       return (seErrorCode == 40000 ? XAException.XAER_RMFAIL : XAException.XAER_RMERR);
+    }
+
+    /**
      * Ends the work performed on behalf of a transaction branch. The resource manager dissociates the XA resource from
      * the transaction branch specified and let the transaction be completed.
      * <p/>
@@ -228,7 +247,7 @@
             }
             netAgent.endReadChain();
         } catch (SqlException sqle) {
-            rc = XAException.XAER_RMERR;
+            rc = getSqlExceptionXAErrorCode(sqle);
             exceptionsOnXA = org.apache.derby.client.am.Utils.accumulateSQLException
                     (sqle, exceptionsOnXA);
         } finally {
@@ -290,7 +309,7 @@
         } catch (SqlException sqle) {
             exceptionsOnXA = org.apache.derby.client.am.Utils.accumulateSQLException
                     (sqle, exceptionsOnXA);
-            throwXAException(XAException.XAER_RMERR);
+            throwXAException(getSqlExceptionXAErrorCode(sqle));
         } finally {
             conn_.pendingEndXACallinfoOffset_ = -1; // indicate no pending callinfo
         }
@@ -371,7 +390,7 @@
 
             netAgent.endReadChain();
         } catch (SqlException sqle) {
-            rc = XAException.XAER_RMERR;
+            rc = getSqlExceptionXAErrorCode(sqle);
             exceptionsOnXA = org.apache.derby.client.am.Utils.accumulateSQLException
                     (sqle, exceptionsOnXA);
         } finally {
@@ -442,7 +461,7 @@
                 }
             }
         } catch (SqlException sqle) {
-            rc = XAException.XAER_RMERR;
+            rc = getSqlExceptionXAErrorCode(sqle);
             exceptionsOnXA = org.apache.derby.client.am.Utils.accumulateSQLException
                     (sqle, exceptionsOnXA);
         } finally {
@@ -495,7 +514,7 @@
                 callInfo.xaRetVal_ = XAResource.XA_OK; // re-initialize XARETVAL
             }
         } catch (SqlException sqle) {
-            rc = XAException.XAER_RMERR;
+            rc = getSqlExceptionXAErrorCode(sqle);
             exceptionsOnXA = org.apache.derby.client.am.Utils.accumulateSQLException
                     (sqle, exceptionsOnXA);
         } finally {
@@ -569,7 +588,7 @@
         	if(conn_.autoCommit_)
         		conn_.flowAutoCommit();
         } catch (SqlException sqle) {
-        	rc = XAException.XAER_RMERR;
+        	rc = getSqlExceptionXAErrorCode(sqle);
             exceptionsOnXA = org.apache.derby.client.am.Utils.accumulateSQLException
                     (sqle, exceptionsOnXA);
         } 
@@ -618,7 +637,7 @@
             }
 
         } catch (SqlException sqle) {
-            rc = XAException.XAER_RMERR;
+            rc = getSqlExceptionXAErrorCode(sqle);
             exceptionsOnXA = org.apache.derby.client.am.Utils.accumulateSQLException
                     (sqle, exceptionsOnXA);
         } finally {

Modified: db/derby/code/branches/10.3/java/engine/org/apache/derby/jdbc/EmbedXAResource.java
URL: http://svn.apache.org/viewvc/db/derby/code/branches/10.3/java/engine/org/apache/derby/jdbc/EmbedXAResource.java?rev=764856&r1=764855&r2=764856&view=diff
==============================================================================
--- db/derby/code/branches/10.3/java/engine/org/apache/derby/jdbc/EmbedXAResource.java (original)
+++ db/derby/code/branches/10.3/java/engine/org/apache/derby/jdbc/EmbedXAResource.java Tue Apr 14 16:02:41 2009
@@ -28,6 +28,7 @@
 import javax.transaction.xa.Xid;
 import javax.transaction.xa.XAException;
 
+import org.apache.derby.iapi.error.ExceptionSeverity;
 import org.apache.derby.iapi.error.StandardException;
 import org.apache.derby.iapi.jdbc.BrokeredConnection;
 import org.apache.derby.iapi.jdbc.ResourceAdapter;
@@ -792,30 +793,32 @@
         // Map interesting exceptions to XAException
         String sqlstate = se.getSQLState();
         String message = se.getMessage();
+        int seErrorCode = se.getErrorCode();      
+        int xaErrorCode;
         
         XAException xae;
         
-        if (sqlstate == null) {
-            // no idea what was wrong, throw non-descript error.
-            if (message != null)
-                xae = new XAException(message);
-            else
-                xae = new XAException(XAException.XAER_RMERR);
-        } else if (sqlstate.equals(StandardException.getSQLStateFromIdentifier(
+        // Determine the XAException.errorCode.  This is known for 
+        // some specific exceptions. For other exceptions, we will
+        // return XAER_RMFAIL for SESSION_SEVERITY or greater and
+        // XAER_RMERR for less severe errors. DERBY-4141.
+        if (sqlstate.equals(StandardException.getSQLStateFromIdentifier(
                             SQLState.STORE_XA_XAER_DUPID)))
-            xae = new XAException(XAException.XAER_DUPID);
+            xaErrorCode = XAException.XAER_DUPID;
         else if (sqlstate.equals(StandardException.getSQLStateFromIdentifier(
                                 SQLState.STORE_XA_PROTOCOL_VIOLATION)))
-            xae = new XAException(XAException.XA_RBPROTO);
+            xaErrorCode = XAException.XA_RBPROTO;
         else if (sqlstate.equals(SQLState.DEADLOCK))
-            xae = new XAException(XAException.XA_RBDEADLOCK);
+            xaErrorCode = XAException.XA_RBDEADLOCK;
         else if (sqlstate.equals(SQLState.LOCK_TIMEOUT))
-            xae = new XAException(XAException.XA_RBTIMEOUT);
-        else if (message != null)
-            xae = new XAException(message);
+            xaErrorCode = XAException.XA_RBTIMEOUT;
+        else if (seErrorCode >=  ExceptionSeverity.SESSION_SEVERITY)
+            xaErrorCode = XAException.XAER_RMFAIL;            
         else
-            xae = new XAException(XAException.XAER_RMERR);
+            xaErrorCode = XAException.XAER_RMERR;
         
+        xae = new XAException(message);
+        xae.errorCode = xaErrorCode;
         if (JVMInfo.JDK_ID >= JVMInfo.J2SE_14)
             xae.initCause(se);
         return xae;

Modified: db/derby/code/branches/10.3/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/XATransactionTest.java
URL: http://svn.apache.org/viewvc/db/derby/code/branches/10.3/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/XATransactionTest.java?rev=764856&r1=764855&r2=764856&view=diff
==============================================================================
--- db/derby/code/branches/10.3/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/XATransactionTest.java (original)
+++ db/derby/code/branches/10.3/java/testing/org/apache/derbyTesting/functionTests/tests/jdbcapi/XATransactionTest.java Tue Apr 14 16:02:41 2009
@@ -274,6 +274,27 @@
         Assert.assertTrue(rs.getInt(1) == timeoutStatementsCommitted);
     }
 
+    /**
+     * DERBY-4141 XAExceptions caused by SQLExceptions should have a
+     * non-zero errorCode. SESSION_SEVERITY or greater map to
+     * XAException.XAER_RMFAIL. Lesser exceptions map to XAException.XAER_RMERR 
+     * @throws Exception
+     */
+    public void testXAExceptionErrorCodeOnSQLExceptionDerby4141() throws Exception {
+        XADataSource xaDataSource = J2EEDataSource.getXADataSource();
+        XAConnection xaConn = xaDataSource.getXAConnection();
+        XAResource xaRes = xaConn.getXAResource();        
+        Xid xid = createXid(123, 1);
+        // close the XAConnection so we get an SQLException on
+        // start();
+        xaConn.close();
+        try {
+            xaRes.start(xid, XAResource.TMNOFLAGS);
+            fail("Should have gotten an XAException. xaConn is closed.");
+        } catch (XAException xae) {
+            assertEquals(XAException.XAER_RMFAIL, xae.errorCode);
+        }
+    }
 
     /* ------------------- end helper methods  -------------------------- */