Cleanup after unexpected exception from external delegation call
Issue: SPR-17559
This commit is contained in:
parent
6d7827e36b
commit
c024bdcc6f
|
@ -115,21 +115,28 @@ public abstract class DataSourceUtils {
|
|||
Connection con = fetchConnection(dataSource);
|
||||
|
||||
if (TransactionSynchronizationManager.isSynchronizationActive()) {
|
||||
// Use same Connection for further JDBC actions within the transaction.
|
||||
// Thread-bound object will get removed by synchronization at transaction completion.
|
||||
ConnectionHolder holderToUse = conHolder;
|
||||
if (holderToUse == null) {
|
||||
holderToUse = new ConnectionHolder(con);
|
||||
try {
|
||||
// Use same Connection for further JDBC actions within the transaction.
|
||||
// Thread-bound object will get removed by synchronization at transaction completion.
|
||||
ConnectionHolder holderToUse = conHolder;
|
||||
if (holderToUse == null) {
|
||||
holderToUse = new ConnectionHolder(con);
|
||||
}
|
||||
else {
|
||||
holderToUse.setConnection(con);
|
||||
}
|
||||
holderToUse.requested();
|
||||
TransactionSynchronizationManager.registerSynchronization(
|
||||
new ConnectionSynchronization(holderToUse, dataSource));
|
||||
holderToUse.setSynchronizedWithTransaction(true);
|
||||
if (holderToUse != conHolder) {
|
||||
TransactionSynchronizationManager.bindResource(dataSource, holderToUse);
|
||||
}
|
||||
}
|
||||
else {
|
||||
holderToUse.setConnection(con);
|
||||
}
|
||||
holderToUse.requested();
|
||||
TransactionSynchronizationManager.registerSynchronization(
|
||||
new ConnectionSynchronization(holderToUse, dataSource));
|
||||
holderToUse.setSynchronizedWithTransaction(true);
|
||||
if (holderToUse != conHolder) {
|
||||
TransactionSynchronizationManager.bindResource(dataSource, holderToUse);
|
||||
catch (RuntimeException ex) {
|
||||
// Unexpected exception from external delegation call -> close Connection and rethrow.
|
||||
releaseConnection(con, dataSource);
|
||||
throw ex;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -266,21 +266,28 @@ public abstract class EntityManagerFactoryUtils {
|
|||
em = (!CollectionUtils.isEmpty(properties) ? emf.createEntityManager(properties) : emf.createEntityManager());
|
||||
}
|
||||
|
||||
// Use same EntityManager for further JPA operations within the transaction.
|
||||
// Thread-bound object will get removed by synchronization at transaction completion.
|
||||
emHolder = new EntityManagerHolder(em);
|
||||
if (synchronizedWithTransaction) {
|
||||
Object transactionData = prepareTransaction(em, emf);
|
||||
TransactionSynchronizationManager.registerSynchronization(
|
||||
new TransactionalEntityManagerSynchronization(emHolder, emf, transactionData, true));
|
||||
emHolder.setSynchronizedWithTransaction(true);
|
||||
try {
|
||||
// Use same EntityManager for further JPA operations within the transaction.
|
||||
// Thread-bound object will get removed by synchronization at transaction completion.
|
||||
emHolder = new EntityManagerHolder(em);
|
||||
if (synchronizedWithTransaction) {
|
||||
Object transactionData = prepareTransaction(em, emf);
|
||||
TransactionSynchronizationManager.registerSynchronization(
|
||||
new TransactionalEntityManagerSynchronization(emHolder, emf, transactionData, true));
|
||||
emHolder.setSynchronizedWithTransaction(true);
|
||||
}
|
||||
else {
|
||||
// Unsynchronized - just scope it for the transaction, as demanded by the JPA 2.1 spec...
|
||||
TransactionSynchronizationManager.registerSynchronization(
|
||||
new TransactionScopedEntityManagerSynchronization(emHolder, emf));
|
||||
}
|
||||
TransactionSynchronizationManager.bindResource(emf, emHolder);
|
||||
}
|
||||
else {
|
||||
// Unsynchronized - just scope it for the transaction, as demanded by the JPA 2.1 spec...
|
||||
TransactionSynchronizationManager.registerSynchronization(
|
||||
new TransactionScopedEntityManagerSynchronization(emHolder, emf));
|
||||
catch (RuntimeException ex) {
|
||||
// Unexpected exception from external delegation call -> close EntityManager and rethrow.
|
||||
closeEntityManager(em);
|
||||
throw ex;
|
||||
}
|
||||
TransactionSynchronizationManager.bindResource(emf, emHolder);
|
||||
|
||||
return em;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue