You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@openjpa.apache.org by mi...@apache.org on 2008/04/25 00:28:48 UTC
svn commit: r651441 - in /openjpa/trunk:
openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/ openjpa-kernel/
openjpa-kernel/src/main/java/org/apache/openjpa/ee/
openjpa-kernel/src/main/resources/com/
openjpa-kernel/src/main/resources/com/ibm/ op...
Author: mikedd
Date: Thu Apr 24 15:28:42 2008
New Revision: 651441
URL: http://svn.apache.org/viewvc?rev=651441&view=rev
Log:
OPENJPA-149 OPENJPA-159 Moving suspendJTA code to ManagedRuntime
Added:
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/WASRegistryManagedRuntime.java (with props)
openjpa/trunk/openjpa-kernel/src/main/resources/com/
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/license.txt (with props)
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/websphere/
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/websphere/uow/
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/websphere/uow/UOWSynchronizationRegistry.class (with props)
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWAction.class (with props)
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWActionException.class (with props)
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWException.class (with props)
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWManager.class (with props)
openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWManagerFactory.class (with props)
Modified:
openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/AbstractJDBCSeq.java
openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/TableJDBCSeq.java
openjpa/trunk/openjpa-kernel/pom.xml
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AbstractManagedRuntime.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AutomaticManagedRuntime.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/ManagedRuntime.java
openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/RegistryManagedRuntime.java
openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/ee/localizer.properties
openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/ee/TestWASManagedRuntime.java
openjpa/trunk/openjpa-lib/src/main/java/org/apache/openjpa/lib/util/J2DoPrivHelper.java
Modified: openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/AbstractJDBCSeq.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/AbstractJDBCSeq.java?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/AbstractJDBCSeq.java (original)
+++ openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/AbstractJDBCSeq.java Thu Apr 24 15:28:42 2008
@@ -45,7 +45,6 @@
protected int type = TYPE_DEFAULT;
protected Object current = null;
- private static ThreadLocal _outerTransaction = new ThreadLocal();
/**
* Records the sequence type.
@@ -144,24 +143,22 @@
}
/**
- * Return the connection to use based on the type of sequence. This
- * connection will automatically be closed; do not close it.
+ * <P>Return the connection to use based on the type of sequence. This
+ * connection will automatically be closed; do not close it.</P>
+ *
+ * @return If the sequence type is <code>TYPE_TRANSACTIONAL</code> or
+ * <code>TYPE_CONTIGUOUS</code> the connection from the {@link StoreManager}
+ * will be returned.
+ *
+ * <P>Otherwise a new connection will be obtained using DataSource2 from the
+ * current configuration. In this case autocommit is set to false prior to
+ * returning the connection.</P>
*/
protected Connection getConnection(JDBCStore store)
throws SQLException {
if (type == TYPE_TRANSACTIONAL || type == TYPE_CONTIGUOUS)
return store.getConnection();
- else if (suspendInJTA()) {
- try {
- TransactionManager tm = getConfiguration()
- .getManagedRuntimeInstance().getTransactionManager();
- _outerTransaction.set(tm.suspend());
- tm.begin();
- return store.getConnection();
- } catch (Exception e) {
- throw new StoreException(e);
- }
- } else {
+ else {
JDBCConfiguration conf = store.getConfiguration();
DataSource ds = conf.getDataSource2(store.getContext());
Connection conn = ds.getConnection();
@@ -172,32 +169,18 @@
}
/**
- * Close the current connection.
+ * Close the current connection. If the sequence is
+ * <code>TYPE_TRANSACTIONAL</code> or <code>TYPE_CONTIGUOUS</code>
+ * nothing will be done. Otherwise the connection will be closed.
*/
protected void closeConnection(Connection conn) {
if (conn == null)
return;
-
if (type == TYPE_TRANSACTIONAL || type == TYPE_CONTIGUOUS) {
// do nothing; this seq is part of the business transaction
return;
- } else if (suspendInJTA()) {
- try {
- TransactionManager tm = getConfiguration()
- .getManagedRuntimeInstance().getTransactionManager();
- tm.commit();
- try { conn.close(); } catch (SQLException se) {}
-
- Transaction outerTxn = (Transaction)_outerTransaction.get();
- if (outerTxn != null)
- tm.resume(outerTxn);
-
- } catch (Exception e) {
- throw new StoreException(e);
- } finally {
- _outerTransaction.set(null);
- }
- } else {
+ }
+ else {
try {
conn.commit();
} catch (SQLException se) {
Modified: openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/TableJDBCSeq.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/TableJDBCSeq.java?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/TableJDBCSeq.java (original)
+++ openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/kernel/TableJDBCSeq.java Thu Apr 24 15:28:42 2008
@@ -26,6 +26,8 @@
import java.sql.Types;
import java.util.HashMap;
+import javax.transaction.NotSupportedException;
+
import org.apache.openjpa.jdbc.conf.JDBCConfiguration;
import org.apache.openjpa.jdbc.conf.JDBCConfigurationImpl;
import org.apache.openjpa.jdbc.meta.ClassMapping;
@@ -39,7 +41,6 @@
import org.apache.openjpa.jdbc.sql.DBDictionary;
import org.apache.openjpa.jdbc.sql.RowImpl;
import org.apache.openjpa.jdbc.sql.SQLBuffer;
-import org.apache.openjpa.jdbc.sql.SQLExceptions;
import org.apache.openjpa.lib.conf.Configurable;
import org.apache.openjpa.lib.conf.Configuration;
import org.apache.openjpa.lib.conf.Configurations;
@@ -79,7 +80,8 @@
private transient Log _log = null;
private int _alloc = 50;
private int _intValue = 1;
- private final HashMap _stat = new HashMap();
+ private final HashMap<ClassMapping, Status> _stat =
+ new HashMap<ClassMapping, Status>();
private String _table = "OPENJPA_SEQUENCE_TABLE";
private String _seqColumnName = "SEQUENCE_VALUE";
@@ -87,8 +89,7 @@
private Column _seqColumn = null;
private Column _pkColumn = null;
- private int _schemasIdx = 0;
-
+
/**
* The sequence table name. Defaults to <code>OPENJPA_SEQUENCE_TABLE</code>.
* By default, the table will be placed in the first schema listed in your
@@ -270,13 +271,19 @@
protected Object currentInternal(JDBCStore store, ClassMapping mapping)
throws Exception {
if (current == null) {
- Connection conn = getConnection(store);
+ CurrentSequenceRunnable runnable =
+ new CurrentSequenceRunnable(store, mapping);
try {
- long cur = getSequence(mapping, conn);
- if (cur != -1)
- current = Numbers.valueOf(cur);
- } finally {
- closeConnection(conn);
+ if (suspendInJTA()) {
+ // NotSupportedException is wrapped in a StoreException by
+ // the caller.
+ _conf.getManagedRuntimeInstance().doNonTransactionalWork(
+ runnable);
+ } else {
+ runnable.run();
+ }
+ } catch (RuntimeException re) {
+ throw (Exception) (re.getCause() == null ? re : re.getCause());
}
}
return super.currentInternal(store, mapping);
@@ -311,7 +318,6 @@
_stat.put(mapping, status);
}
return status;
-
}
/**
@@ -361,50 +367,43 @@
* Updates the max available sequence value.
*/
private void allocateSequence(JDBCStore store, ClassMapping mapping,
- Status stat, int alloc, boolean updateStatSeq)
- throws SQLException {
- Connection conn = getConnection(store);
- try {
- if (setSequence(mapping, stat, alloc, updateStatSeq, conn))
- return;
- } catch (SQLException se) {
- throw SQLExceptions.getStore(_loc.get("bad-seq-up", _table),
- se, _conf.getDBDictionaryInstance());
- } finally {
- closeConnection(conn);
- }
-
+ Status stat, int alloc, boolean updateStatSeq) throws SQLException {
+ Runnable runnable =
+ new AllocateSequenceRunnable(
+ store, mapping, stat, alloc, updateStatSeq);
try {
- // possible that we might get errors when inserting if
- // another thread/process is inserting same pk at same time
- SQLException err = null;
- // ### why does this not call getConnection() / closeConnection()?
- conn = _conf.getDataSource2(store.getContext()).getConnection();
- try {
- insertSequence(mapping, conn);
- } catch (SQLException se) {
- err = se;
- } finally {
- try { conn.close(); } catch (SQLException se) {}
- }
-
- // now we should be able to update...
- conn = getConnection(store);
- try {
- if (!setSequence(mapping, stat, alloc, updateStatSeq, conn))
- throw (err != null) ? err : new SQLException(_loc.get
- ("no-seq-row", mapping, _table).getMessage());
- } finally {
- closeConnection(conn);
+ if (suspendInJTA()) {
+ // NotSupportedException is wrapped in a StoreException by
+ // the caller.
+ try {
+ _conf.getManagedRuntimeInstance().doNonTransactionalWork(
+ runnable);
+ }
+ catch(NotSupportedException nse) {
+ SQLException sqlEx = new SQLException(nse.getLocalizedMessage());
+ sqlEx.initCause(nse);
+ throw sqlEx;
+ }
+ } else {
+ runnable.run();
}
- } catch (SQLException se2) {
- throw SQLExceptions.getStore(_loc.get("bad-seq-up", _table),
- se2, _conf.getDBDictionaryInstance());
- }
+ } catch (RuntimeException re) {
+ Throwable e = re.getCause();
+ if(e instanceof SQLException )
+ throw (SQLException) e;
+ else
+ throw re;
+ }
}
/**
- * Inserts the initial sequence information into the database, if any.
+ * Inserts the initial sequence column into the database.
+ *
+ * @param mapping
+ * ClassMapping for the class whose sequence column will be
+ * updated
+ * @param conn
+ * Connection used issue SQL statements.
*/
private void insertSequence(ClassMapping mapping, Connection conn)
throws SQLException {
@@ -442,7 +441,16 @@
}
/**
- * Return the current sequence value, or -1 if unattainable.
+ * Get the current sequence value.
+ *
+ * @param mapping
+ * ClassMapping of the entity whose sequence value will be
+ * obtained.
+ * @param conn
+ * Connection used issue SQL statements.
+ *
+ * @return The current sequence value, or <code>SEQUENCE_NOT_FOUND</code>
+ * if the sequence could not be found.
*/
protected long getSequence(ClassMapping mapping, Connection conn)
throws SQLException {
@@ -736,5 +744,117 @@
if (rs == null || !rs.next())
return -1;
return dict.getLong(rs, 1);
+ }
+
+ /**
+ * AllocateSequenceRunnable is a runnable wrapper that will inserts the
+ * initial sequence value into the database.
+ */
+ protected class AllocateSequenceRunnable implements Runnable {
+
+ JDBCStore store = null;
+ ClassMapping mapping = null;
+ Status stat = null;
+ int alloc;
+ boolean updateStatSeq;
+
+ AllocateSequenceRunnable(JDBCStore store, ClassMapping mapping,
+ Status stat, int alloc, boolean updateStatSeq) {
+ this.store = store;
+ this.mapping = mapping;
+ this.stat = stat;
+ this.alloc = alloc;
+ this.updateStatSeq = updateStatSeq;
+ }
+
+ /**
+ * This method actually obtains the current sequence value.
+ *
+ * @throws RuntimeException
+ * any SQLExceptions that occur when obtaining the sequence
+ * value are wrapped in a runtime exception to avoid
+ * breaking the Runnable method signature. The caller can
+ * obtain the "real" exception by calling getCause().
+ */
+ public void run() throws RuntimeException {
+ Connection conn = null;
+ SQLException err = null;
+ try {
+ // Try to use the store's connection.
+
+ conn = getConnection(store);
+ boolean sequenceSet =
+ setSequence(mapping, stat, alloc, updateStatSeq, conn);
+ closeConnection(conn);
+
+ if (!sequenceSet) {
+ // insert a new sequence column.
+ // Prefer connection2 / non-jta-data-source when inserting
+ // a sequence column regardless of Seq.type.
+ conn = _conf.getDataSource2(store.getContext())
+ .getConnection();
+ insertSequence(mapping, conn);
+ conn.close();
+
+ // now we should be able to update using the connection per
+ // on the seq type.
+ conn = getConnection(store);
+ if (!setSequence(mapping, stat, alloc, updateStatSeq, conn))
+ {
+ throw (err != null) ? err : new SQLException(_loc.get(
+ "no-seq-row", mapping, _table).getMessage());
+ }
+ closeConnection(conn);
+ }
+ } catch (SQLException e) {
+ if (conn != null) {
+ closeConnection(conn);
+ }
+ RuntimeException re = new RuntimeException(e.getMessage());
+ re.initCause(e);
+ throw re;
+ }
+ }
+ }
+
+ /**
+ * CurentSequenceRunnable is a runnable wrapper which obtains the current
+ * sequence value from the database.
+ */
+ protected class CurrentSequenceRunnable implements Runnable {
+ private JDBCStore _store;
+ private ClassMapping _mapping;
+
+ CurrentSequenceRunnable(JDBCStore store, ClassMapping mapping) {
+ _store = store;
+ _mapping = mapping;
+ }
+
+ /**
+ * This method actually obtains the current sequence value.
+ *
+ * @throws RuntimeException
+ * any SQLExceptions that occur when obtaining the sequence
+ * value are wrapped in a runtime exception to avoid
+ * breaking the Runnable method signature. The caller can
+ * obtain the "real" exception by calling getCause().
+ */
+ public void run() throws RuntimeException {
+ Connection conn = null;
+ try {
+ conn = getConnection(_store);
+ long cur = getSequence(_mapping, conn);
+ if (cur != -1 ) // USE the constant
+ current = Numbers.valueOf(cur);
+ } catch (SQLException sqle) {
+ RuntimeException re = new RuntimeException(sqle.getMessage());
+ re.initCause(sqle);
+ throw re;
+ } finally {
+ if (conn != null) {
+ closeConnection(conn);
+ }
+ }
+ }
}
}
Modified: openjpa/trunk/openjpa-kernel/pom.xml
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/pom.xml?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/pom.xml (original)
+++ openjpa/trunk/openjpa-kernel/pom.xml Thu Apr 24 15:28:42 2008
@@ -52,8 +52,8 @@
<dependency>
<groupId>commons-pool</groupId>
<artifactId>commons-pool</artifactId>
- <scope>compile</scope>
- </dependency>
+ <scope>compile</scope>
+ </dependency>
</dependencies>
<build>
<plugins>
@@ -142,6 +142,15 @@
</goals>
</execution>
</executions>
+ </plugin>
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <version>2.2</version>
+ <configuration>
+ <excludes>
+ <exclude>**/com/ibm/**</exclude>
+ </excludes>
+ </configuration>
</plugin>
</plugins>
</build>
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AbstractManagedRuntime.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AbstractManagedRuntime.java?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AbstractManagedRuntime.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AbstractManagedRuntime.java Thu Apr 24 15:28:42 2008
@@ -17,7 +17,14 @@
package org.apache.openjpa.ee;
+import javax.transaction.InvalidTransactionException;
+import javax.transaction.NotSupportedException;
import javax.transaction.SystemException;
+import javax.transaction.Transaction;
+import javax.transaction.TransactionManager;
+
+import org.apache.openjpa.lib.util.Localizer;
+import org.apache.openjpa.util.GeneralException;
/*
* AbstractManagedRuntime.java
@@ -26,7 +33,9 @@
*
*/
public abstract class AbstractManagedRuntime implements ManagedRuntime {
-
+
+ private static Localizer _loc =
+ Localizer.forPackage(AbstractManagedRuntime.class);
/**
* Returns a transaction key that can be used to associate transactions
* and Brokers.
@@ -38,4 +47,62 @@
return getTransactionManager().getTransaction();
}
+ /**
+ * <P>
+ * Do a unit of work which will execute outside of the current managed
+ * transaction. The default implementation suspends the transaction prior to
+ * execution, and resumes the transaction afterwards.
+ * </P>
+ *
+ * @param runnable
+ * The runnable wrapper for the work that will be done. The
+ * runnable object should be fully initialized with any state
+ * needed to execute.
+ *
+ * @throws NotSupportedException
+ * if the current transaction can not be obtained, or an error
+ * occurs when suspending or resuming the transaction.
+ */
+ public void doNonTransactionalWork(Runnable runnable) throws
+ NotSupportedException {
+ TransactionManager tm = null;
+ Transaction transaction = null;
+
+ try {
+ tm = getTransactionManager();
+ }
+ catch(Exception e) {
+ NotSupportedException nse =
+ new NotSupportedException(e.getMessage());
+ nse.initCause(e);
+ throw nse;
+ }
+ try {
+ transaction = tm.suspend();
+ } catch (Exception e) {
+ NotSupportedException nse = new NotSupportedException(
+ _loc.get("exc-suspend-tran", e.getClass()).getMessage());
+ nse.initCause(e);
+ throw nse;
+ }
+
+ runnable.run();
+
+ try {
+ tm.resume(transaction);
+ } catch (Exception e) {
+ try {
+ transaction.setRollbackOnly();
+ }
+ catch(SystemException se2) {
+ throw new GeneralException(se2);
+ }
+ NotSupportedException nse =
+ new NotSupportedException(
+ _loc.get("exc-resume-tran", e.getClass()).getMessage());
+ nse.initCause(e);
+ throw nse;
+ }
+
+ }
}
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AutomaticManagedRuntime.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AutomaticManagedRuntime.java?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AutomaticManagedRuntime.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/AutomaticManagedRuntime.java Thu Apr 24 15:28:42 2008
@@ -21,11 +21,13 @@
import java.util.LinkedList;
import java.util.List;
+import javax.transaction.NotSupportedException;
import javax.transaction.SystemException;
import javax.transaction.TransactionManager;
import org.apache.openjpa.lib.conf.Configurable;
import org.apache.openjpa.lib.conf.Configuration;
+import org.apache.openjpa.lib.util.J2DoPrivHelper;
import org.apache.openjpa.lib.util.Localizer;
import org.apache.openjpa.util.InvalidStateException;
@@ -73,6 +75,7 @@
private static final WLSManagedRuntime WLS;
private static final SunOneManagedRuntime SUNONE;
private static final WASManagedRuntime WAS;
+ private static final WASRegistryManagedRuntime WAS_REG;
private static Localizer _loc = Localizer.forPackage
(AutomaticManagedRuntime.class);
@@ -108,24 +111,57 @@
mr = null;
try {
mr = new WASManagedRuntime();
+ } catch (Throwable t) {
}
- catch (Throwable t) {
+ WAS = (WASManagedRuntime) mr;
+
+ mr = null;
+ try {
+ // In a WebSphere environment the thread's current classloader might
+ // not have access to the WebSphere APIs. However the "runtime"
+ // classloader will have access to them.
+
+ // Should not need a doPriv getting this class' classloader
+ ClassLoader cl = AutomaticManagedRuntime.class.getClassLoader();
+
+ Class<WASRegistryManagedRuntime> mrClass =
+ (Class<WASRegistryManagedRuntime>) J2DoPrivHelper
+ .getForNameAction(
+ WASRegistryManagedRuntime.class.getName(),
+ true, cl).run();
+ mr = J2DoPrivHelper.newInstanceAction(mrClass).run();
+ } catch (Throwable t) {
+ // safe to ignore
}
- WAS= (WASManagedRuntime) mr;
+ WAS_REG = (WASRegistryManagedRuntime) mr;
}
private Configuration _conf = null;
private ManagedRuntime _runtime = null;
-
+
public TransactionManager getTransactionManager()
throws Exception {
if (_runtime != null)
return _runtime.getTransactionManager();
- List errors = new LinkedList();
+ List<Throwable> errors = new LinkedList<Throwable>();
TransactionManager tm = null;
- // first try the registry, which is the official way to obtain
+ // Try the registry extensions first so that any applicable vendor
+ // specific extensions are used.
+ if (WAS_REG != null) {
+ try {
+ tm = WAS_REG.getTransactionManager();
+ } catch (Throwable t) {
+ errors.add(t);
+ }
+ if (tm != null) {
+ _runtime = WAS_REG;
+ return tm;
+ }
+ }
+
+ // Then try the registry, which is the official way to obtain
// transaction synchronication in JTA 1.1
if (REGISTRY != null) {
try {
@@ -255,5 +291,24 @@
return _runtime.getTransactionKey();
return null;
+ }
+
+ /**
+ * Delegate nonTransactional work to the appropriate managed runtime. If no
+ * managed runtime is found then delegate {@link AbstractManagedRuntime}.
+ */
+ public void doNonTransactionalWork(Runnable runnable)
+ throws NotSupportedException {
+ // Obtain a transaction manager to initialize the runtime.
+ try {
+ getTransactionManager();
+ } catch (Exception e) {
+ NotSupportedException nse =
+ new NotSupportedException(_loc
+ .get("tm-unavailable", _runtime).getMessage());
+ nse.initCause(e);
+ throw nse;
+ }
+ _runtime.doNonTransactionalWork(runnable);
}
}
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/ManagedRuntime.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/ManagedRuntime.java?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/ManagedRuntime.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/ManagedRuntime.java Thu Apr 24 15:28:42 2008
@@ -18,6 +18,7 @@
*/
package org.apache.openjpa.ee;
+import javax.transaction.NotSupportedException;
import javax.transaction.SystemException;
import javax.transaction.TransactionManager;
@@ -65,5 +66,26 @@
*/
public Object getTransactionKey()
throws Exception, SystemException;
-
+
+ /**
+ * <P>
+ * Do a unit of work which will execute outside of the current managed
+ * transaction.
+ * </P>
+ * <P>
+ * If the runnable object encounters an exception it should be wrapped in a
+ * RuntimeException and thrown back to the caller
+ * </P>
+ *
+ * @param runnable
+ * The runnable wrapper for the work that will be done. The
+ * runnable object should be fully initialized with any state
+ * needed to execute.
+ *
+ * @throws NotSupportedException
+ * if the transaction can not be suspended.
+ */
+ public void doNonTransactionalWork(Runnable runnable)
+ throws NotSupportedException;
+
}
Modified: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/RegistryManagedRuntime.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/RegistryManagedRuntime.java?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/RegistryManagedRuntime.java (original)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/RegistryManagedRuntime.java Thu Apr 24 15:28:42 2008
@@ -32,6 +32,8 @@
import javax.transaction.TransactionSynchronizationRegistry;
import javax.transaction.xa.XAResource;
+import org.apache.openjpa.lib.util.Localizer;
+
/**
* Implementation of the {@link ManagedRuntime} interface that uses
* the {@link TransactionSynchronizationRegistry} interface (new in JTA 1.1)
@@ -42,10 +44,12 @@
*/
public class RegistryManagedRuntime
implements ManagedRuntime {
-
private String _registryName =
"java:comp/TransactionSynchronizationRegistry";
private TransactionManagerRegistryFacade _tm = null;
+
+ private static Localizer _loc =
+ Localizer.forPackage(RegistryManagedRuntime.class);
/**
* Return the cached TransactionManager instance.
@@ -187,6 +191,16 @@
throws RollbackException, IllegalStateException, SystemException {
throw new SystemException();
}
+ }
+
+ /**
+ * <P>
+ * RegistryManagedRuntime cannot suspend transactions.
+ * </P>
+ */
+ public void doNonTransactionalWork(Runnable runnable) throws NotSupportedException {
+ throw new NotSupportedException(
+ _loc.get("tsr-cannot-suspend").getMessage());
}
}
Added: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/WASRegistryManagedRuntime.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/WASRegistryManagedRuntime.java?rev=651441&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/WASRegistryManagedRuntime.java (added)
+++ openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/WASRegistryManagedRuntime.java Thu Apr 24 15:28:42 2008
@@ -0,0 +1,74 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.openjpa.ee;
+
+import com.ibm.wsspi.uow.UOWAction;
+import com.ibm.wsspi.uow.UOWActionException;
+import com.ibm.wsspi.uow.UOWException;
+import com.ibm.wsspi.uow.UOWManager;
+import com.ibm.wsspi.uow.UOWManagerFactory;
+
+/**
+ * WASRegistryManagedRuntime provides WebSphere specific extensions to
+ * {@link RegistryManagedRuntime}. Currently these extensions consist of using
+ * the WebSphere UOWManager interface to submit non transactional work.
+ */
+public class WASRegistryManagedRuntime extends RegistryManagedRuntime {
+ /**
+ * <P>
+ * RegistryManagedRuntime cannot suspend transactions, but WebSphere
+ * provides an interface to submit work outside of the current tran.
+ * </P>
+ */
+ public void doNonTransactionalWork(Runnable runnable)
+ throws RuntimeException, UnsupportedOperationException {
+ try {
+ UOWManagerFactory.getUOWManager().runUnderUOW(
+ UOWManager.UOW_TYPE_LOCAL_TRANSACTION, false,
+ new DelegatingUOWAction(runnable));
+ }
+ catch(UOWActionException e ) {
+ RuntimeException re = new RuntimeException(e.getMessage());
+ re.initCause(e);
+ throw re;
+ }
+ catch(UOWException e ) {
+ RuntimeException re = new RuntimeException(e.getMessage());
+ re.initCause(e);
+ throw re;
+ }
+ }
+
+
+ /**
+ * Delegate for the WebSphere proprietary UOWAction interface. Enables a
+ * {$link Runnable} to be passed in to the WebSphere UOWManager.
+ */
+ class DelegatingUOWAction implements UOWAction {
+ Runnable _del;
+
+ public DelegatingUOWAction(Runnable delegate) {
+ _del = delegate;
+ }
+
+ public void run() throws Exception {
+ _del.run();
+ }
+ }
+}
Propchange: openjpa/trunk/openjpa-kernel/src/main/java/org/apache/openjpa/ee/WASRegistryManagedRuntime.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/license.txt
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/license.txt?rev=651441&view=auto
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/license.txt (added)
+++ openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/license.txt Thu Apr 24 15:28:42 2008
@@ -0,0 +1,18 @@
+You may use or redistribute the files or modules contained in this jar subject to the following terms:
+
+The WebSphere Application Server files or modules contained in this jar
+may be redistrubuted as provided by IBM to you, and only as part of Your
+application distribution.
+
+You may not use IBM's name or trademarks in connection with the marketing
+of Your applications without IBM's prior written consent.
+
+IBM PROVIDES THESE FILES OR MODULES ON AN "AS IS" BASIS AND IBM DISCLAIMS
+ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
+WARRANTY OF NON-INFRINGEMENT AND THE IMPLIED WARRANTIES OF MERCHANTABILITY
+OR FITNESS FOR A PARTICULAR PURPOSE. IBM SHALL NOT BE LIABLE FOR ANY
+DIRECT, INDIRECT, INCIDENTAL, SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT
+OF THE USE OR OPERATION OF THE FILES OR MODULES . IBM HAS NO OBLIGATION
+TO PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS OR MODIFICATIONS TO
+THE FILES OR MODULES .
+
Propchange: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/license.txt
------------------------------------------------------------------------------
svn:eol-style = native
Added: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/websphere/uow/UOWSynchronizationRegistry.class
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/websphere/uow/UOWSynchronizationRegistry.class?rev=651441&view=auto
==============================================================================
Binary file - no diff available.
Propchange: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/websphere/uow/UOWSynchronizationRegistry.class
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWAction.class
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWAction.class?rev=651441&view=auto
==============================================================================
Binary file - no diff available.
Propchange: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWAction.class
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWActionException.class
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWActionException.class?rev=651441&view=auto
==============================================================================
Binary file - no diff available.
Propchange: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWActionException.class
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWException.class
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWException.class?rev=651441&view=auto
==============================================================================
Binary file - no diff available.
Propchange: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWException.class
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWManager.class
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWManager.class?rev=651441&view=auto
==============================================================================
Binary file - no diff available.
Propchange: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWManager.class
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Added: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWManagerFactory.class
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWManagerFactory.class?rev=651441&view=auto
==============================================================================
Binary file - no diff available.
Propchange: openjpa/trunk/openjpa-kernel/src/main/resources/com/ibm/wsspi/uow/UOWManagerFactory.class
------------------------------------------------------------------------------
svn:mime-type = application/octet-stream
Modified: openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/ee/localizer.properties
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/ee/localizer.properties?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/ee/localizer.properties (original)
+++ openjpa/trunk/openjpa-kernel/src/main/resources/org/apache/openjpa/ee/localizer.properties Thu Apr 24 15:28:42 2008
@@ -18,19 +18,27 @@
tm-not-found: Could not perform automatic lookup of EJB container''s \
javax.transaction.TransactionManager implementation. Please ensure that \
you are running the application from within an EJB 1.1 compliant EJB \
- container, and then set the org.apache.openjpa.ManagedRuntime property to the \
- appropriate value to obtain the TransactionManager.
+ container, and then set the org.apache.openjpa.ManagedRuntime property to \
+ the appropriate value to obtain the TransactionManager.
expected-reference: Expected object to be of type Reference, but instead was \
"{0}".
not-supported: This operation is not supported.
was-unsupported-op: Unable to execute {0} on a WebSphere managed transaction. \
WebSphere does not support direct manipulation of managed transactions.
-was-transaction-id-exception: Unable to determine identity of the current WebSphere \
- managed transaction. Please ensure that your are running the application from \
- within WebSphere Application Server (version 5.0.2 or newer).
+was-transaction-id-exception: Unable to determine identity of the current \
+ WebSphere managed transaction. Please ensure that your are running the \
+ application from within WebSphere Application Server (version 5.0.2 or \
+ newer).
was-reflection-exception: An error occured reflecting WebSphere proprietary \
interfaces. Please ensure that you are running the application from within \
WebSphere Application Server (version 5.0.2 or newer).
was-lookup-error: An error occurred looking up the WebSphere extended JTA \
- service. Please ensure that you are running the application from within WebSphere \
- Application Server (version 5.0.2 or newer).
+ service. Please ensure that you are running the application from within \
+ WebSphere Application Server (version 5.0.2 or newer).
+tm-unavailable: Unable to obtain a TransactionManager using {0}.
+tsr-cannot-suspend: The Transaction Synchronization Registry can not suspend \
+ the current transaction.
+exc-suspend-tran: A {0} exception occurred when trying to suspend the current \
+ transaction.
+exc-resume-tran: A {0} exception occurred when trying to resume the current \
+ transaction. The transaction will be marked rollback only.
\ No newline at end of file
Modified: openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/ee/TestWASManagedRuntime.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/ee/TestWASManagedRuntime.java?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/ee/TestWASManagedRuntime.java (original)
+++ openjpa/trunk/openjpa-kernel/src/test/java/org/apache/openjpa/ee/TestWASManagedRuntime.java Thu Apr 24 15:28:42 2008
@@ -36,7 +36,6 @@
* been modified via the maven build.
*
* @throws ClassNotFoundException
- * @author Michael Dick
*/
public void testInterfaceAdded() throws ClassNotFoundException {
Modified: openjpa/trunk/openjpa-lib/src/main/java/org/apache/openjpa/lib/util/J2DoPrivHelper.java
URL: http://svn.apache.org/viewvc/openjpa/trunk/openjpa-lib/src/main/java/org/apache/openjpa/lib/util/J2DoPrivHelper.java?rev=651441&r1=651440&r2=651441&view=diff
==============================================================================
--- openjpa/trunk/openjpa-lib/src/main/java/org/apache/openjpa/lib/util/J2DoPrivHelper.java (original)
+++ openjpa/trunk/openjpa-lib/src/main/java/org/apache/openjpa/lib/util/J2DoPrivHelper.java Thu Apr 24 15:28:42 2008
@@ -201,13 +201,13 @@
* Requires security policy: 'permission java.lang.RuntimePermission
* "getClassLoader";'
*
- * @return Classloader
+ * @return Class
*/
- public static final PrivilegedExceptionAction getForNameAction(
+ public static final PrivilegedExceptionAction<Class<?>> getForNameAction(
final String className, final boolean initializeBoolean,
final ClassLoader classLoader) {
- return new PrivilegedExceptionAction() {
- public Object run() throws ClassNotFoundException {
+ return new PrivilegedExceptionAction<Class<?>>() {
+ public Class<?> run() throws ClassNotFoundException {
return Class.forName(className, initializeBoolean, classLoader);
}
};
@@ -228,10 +228,10 @@
*
* @return Classloader
*/
- public static final PrivilegedAction getClassLoaderAction(
+ public static final PrivilegedAction<ClassLoader> getClassLoaderAction(
final Class clazz) {
- return new PrivilegedAction() {
- public Object run() {
+ return new PrivilegedAction<ClassLoader>() {
+ public ClassLoader run() {
return clazz.getClassLoader();
}
};
@@ -330,21 +330,21 @@
* Requires security policy:
* 'permission java.lang.RuntimePermission "getClassLoader";'
*
- * @return Object
- * @exception IllegalAccessException
+ * @return A new instance of the provided class.
+ * @exception IllegalAccessException
* @exception InstantiationException
*/
- public static final PrivilegedExceptionAction newInstanceAction(
- final Class clazz) throws IllegalAccessException,
+ public static final <T> PrivilegedExceptionAction<T> newInstanceAction(
+ final Class<T> clazz) throws IllegalAccessException,
InstantiationException {
- return new PrivilegedExceptionAction() {
- public Object run() throws IllegalAccessException,
+ return new PrivilegedExceptionAction<T>() {
+ public T run() throws IllegalAccessException,
InstantiationException {
return clazz.newInstance();
}
};
}
-
+
/**
* Return a PrivilegeAction object for loader.getParent().
*