Transaction managers are the central abstraction in Spring's transaction infrastructure. They abstract over different transaction APIs (JTA, JDBC, Hibernate, JPA) providing a consistent programming model.
Central interface for imperative transaction management. All transaction manager implementations must implement this interface.
/**
* Central interface for imperative transaction management.
* This is the main abstraction for transaction management in Spring.
*/
public interface PlatformTransactionManager extends TransactionManager {
/**
* Get a transaction according to the specified definition, or create a new one
* if necessary. Returns a TransactionStatus object that can be used to control
* transaction execution and query transaction status.
*
* @param definition TransactionDefinition instance (can be null for defaults)
* @return transaction status object representing the new or current transaction
* @throws TransactionException in case of lookup, creation, or system errors
*/
TransactionStatus getTransaction(TransactionDefinition definition)
throws TransactionException;
/**
* Commit the given transaction. If the transaction has been marked rollback-only
* programmatically, perform a rollback.
*
* @param status object returned by getTransaction
* @throws TransactionException in case of commit or system errors
*/
void commit(TransactionStatus status) throws TransactionException;
/**
* Rollback the given transaction.
*
* @param status object returned by getTransaction
* @throws TransactionException in case of system errors
*/
void rollback(TransactionStatus status) throws TransactionException;
}Usage Example:
import org.springframework.transaction.PlatformTransactionManager;
import org.springframework.transaction.TransactionDefinition;
import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.support.DefaultTransactionDefinition;
@Service
public class ManualTransactionService {
private final PlatformTransactionManager transactionManager;
public ManualTransactionService(PlatformTransactionManager transactionManager) {
this.transactionManager = transactionManager;
}
public void executeWithManualControl() {
// Create transaction definition
TransactionDefinition def = new DefaultTransactionDefinition();
// Start transaction
TransactionStatus status = transactionManager.getTransaction(def);
try {
// Execute business logic
performDatabaseOperations();
// Commit transaction
transactionManager.commit(status);
} catch (Exception e) {
// Rollback on error
transactionManager.rollback(status);
throw e;
}
}
private void performDatabaseOperations() {
// Database operations here
}
}PlatformTransactionManager implementation for JTA (Java Transaction API). Used for distributed transactions and integration with Java EE application servers.
/**
* PlatformTransactionManager implementation for JTA.
* Supports distributed transactions across multiple resources.
*/
public class JtaTransactionManager extends AbstractPlatformTransactionManager
implements TransactionFactory, InitializingBean, Serializable {
/** Default JNDI location for UserTransaction */
public static final String DEFAULT_USER_TRANSACTION_NAME = "java:comp/UserTransaction";
/** Default JNDI location for TransactionSynchronizationRegistry */
public static final String DEFAULT_TRANSACTION_SYNCHRONIZATION_REGISTRY_NAME =
"java:comp/TransactionSynchronizationRegistry";
/**
* Create a new JtaTransactionManager instance.
*/
public JtaTransactionManager();
/**
* Create a new JtaTransactionManager instance with the given UserTransaction.
*/
public JtaTransactionManager(UserTransaction userTransaction);
/**
* Create a new JtaTransactionManager instance with the given
* UserTransaction and TransactionManager.
*/
public JtaTransactionManager(
UserTransaction userTransaction,
TransactionManager transactionManager
);
/**
* Set the JTA UserTransaction to use.
*/
public void setUserTransaction(UserTransaction userTransaction);
/**
* Set the JNDI name of the JTA UserTransaction.
*/
public void setUserTransactionName(String userTransactionName);
/**
* Set the JTA TransactionManager to use.
*/
public void setTransactionManager(TransactionManager transactionManager);
/**
* Set the JNDI name of the JTA TransactionManager.
*/
public void setTransactionManagerName(String transactionManagerName);
/**
* Set the JTA TransactionSynchronizationRegistry to use.
*/
public void setTransactionSynchronizationRegistry(
TransactionSynchronizationRegistry transactionSynchronizationRegistry
);
/**
* Set the JNDI name of the JTA TransactionSynchronizationRegistry.
*/
public void setTransactionSynchronizationRegistryName(String name);
/**
* Set whether to allow custom isolation levels on JTA transactions.
* Default is false.
*/
public void setAllowCustomIsolationLevels(boolean allowCustomIsolationLevels);
}Usage Examples:
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.transaction.jta.JtaTransactionManager;
@Configuration
public class JtaConfig {
// Basic JTA configuration with default JNDI lookups
@Bean
public JtaTransactionManager transactionManager() {
JtaTransactionManager txManager = new JtaTransactionManager();
// Will look up UserTransaction at default location
return txManager;
}
// With explicit UserTransaction and TransactionManager
@Bean
public JtaTransactionManager customJtaTransactionManager(
UserTransaction userTransaction,
TransactionManager transactionManager) {
JtaTransactionManager txManager = new JtaTransactionManager();
txManager.setUserTransaction(userTransaction);
txManager.setTransactionManager(transactionManager);
txManager.setAllowCustomIsolationLevels(true);
return txManager;
}
// With custom JNDI names
@Bean
public JtaTransactionManager jndiBasedJtaTransactionManager() {
JtaTransactionManager txManager = new JtaTransactionManager();
txManager.setUserTransactionName("java:comp/env/UserTransaction");
txManager.setTransactionManagerName("java:comp/env/TransactionManager");
return txManager;
}
}Abstract base class for PlatformTransactionManager implementations. Provides the template method pattern for transaction management.
/**
* Abstract base class for PlatformTransactionManager implementations.
* Provides the transaction management template and common configuration.
*/
public abstract class AbstractPlatformTransactionManager
implements PlatformTransactionManager, ConfigurableTransactionManager, Serializable {
/** Synchronization always active */
public static final int SYNCHRONIZATION_ALWAYS = 0;
/** Synchronization only on actual transactions */
public static final int SYNCHRONIZATION_ON_ACTUAL_TRANSACTION = 1;
/** No synchronization */
public static final int SYNCHRONIZATION_NEVER = 2;
/**
* Set when transaction synchronizations should be activated.
* Default is SYNCHRONIZATION_ALWAYS.
*/
public void setTransactionSynchronization(int transactionSynchronization);
/**
* Set the default timeout in seconds.
* Default is -1 (no timeout).
*/
public void setDefaultTimeout(int defaultTimeout);
/**
* Set whether nested transactions are allowed.
* Default is false.
*/
public void setNestedTransactionAllowed(boolean nestedTransactionAllowed);
/**
* Set whether existing transactions should be validated before participating.
* Default is false.
*/
public void setValidateExistingTransaction(boolean validateExistingTransaction);
/**
* Set whether to globally mark an existing transaction as rollback-only
* after a participating transaction failed.
* Default is true.
*/
public void setGlobalRollbackOnParticipationFailure(
boolean globalRollbackOnParticipationFailure
);
/**
* Set whether to fail early on commit if the transaction has been
* marked rollback-only globally.
* Default is false.
*/
public void setFailEarlyOnGlobalRollbackOnly(boolean failEarlyOnGlobalRollbackOnly);
/**
* Set whether to rollback on commit failure.
* Default is false.
*/
public void setRollbackOnCommitFailure(boolean rollbackOnCommitFailure);
/**
* Set transaction execution listeners.
*/
public void setTransactionExecutionListeners(
Collection<TransactionExecutionListener> listeners
);
// Template methods to be implemented by subclasses
/**
* Return the current transaction object.
*/
protected abstract Object doGetTransaction() throws TransactionException;
/**
* Check if the given transaction object indicates an existing transaction.
*/
protected abstract boolean isExistingTransaction(Object transaction)
throws TransactionException;
/**
* Begin a new transaction with the given definition.
*/
protected abstract void doBegin(
Object transaction,
TransactionDefinition definition
) throws TransactionException;
/**
* Perform an actual commit of the given transaction.
*/
protected abstract void doCommit(DefaultTransactionStatus status)
throws TransactionException;
/**
* Perform an actual rollback of the given transaction.
*/
protected abstract void doRollback(DefaultTransactionStatus status)
throws TransactionException;
/**
* Suspend the resources of the current transaction (optional).
*/
protected Object doSuspend(Object transaction) throws TransactionException;
/**
* Resume the resources of the current transaction (optional).
*/
protected void doResume(Object transaction, Object suspendedResources)
throws TransactionException;
/**
* Set the given transaction rollback-only (optional).
*/
protected void doSetRollbackOnly(DefaultTransactionStatus status)
throws TransactionException;
/**
* Clean up after completion (optional).
*/
protected void doCleanupAfterCompletion(Object transaction);
}Usage Example (Custom Transaction Manager):
import org.springframework.transaction.support.AbstractPlatformTransactionManager;
import org.springframework.transaction.support.DefaultTransactionStatus;
public class CustomTransactionManager extends AbstractPlatformTransactionManager {
private final ResourceManager resourceManager;
public CustomTransactionManager(ResourceManager resourceManager) {
this.resourceManager = resourceManager;
setNestedTransactionAllowed(true);
setDefaultTimeout(30);
}
@Override
protected Object doGetTransaction() {
CustomTransactionObject txObject = new CustomTransactionObject();
txObject.setResourceHolder(resourceManager.getResourceHolder());
return txObject;
}
@Override
protected boolean isExistingTransaction(Object transaction) {
CustomTransactionObject txObject = (CustomTransactionObject) transaction;
return txObject.hasTransaction();
}
@Override
protected void doBegin(Object transaction, TransactionDefinition definition) {
CustomTransactionObject txObject = (CustomTransactionObject) transaction;
resourceManager.beginTransaction(
definition.getIsolationLevel(),
definition.getTimeout()
);
txObject.setNewTransaction(true);
}
@Override
protected void doCommit(DefaultTransactionStatus status) {
CustomTransactionObject txObject = (CustomTransactionObject) status.getTransaction();
resourceManager.commit();
}
@Override
protected void doRollback(DefaultTransactionStatus status) {
CustomTransactionObject txObject = (CustomTransactionObject) status.getTransaction();
resourceManager.rollback();
}
@Override
protected void doCleanupAfterCompletion(Object transaction) {
CustomTransactionObject txObject = (CustomTransactionObject) transaction;
resourceManager.releaseConnection();
}
}Configuration interface for transaction managers supporting execution listeners.
/**
* Configuration interface for transaction manager implementations.
* Allows for registering transaction execution listeners.
*/
public interface ConfigurableTransactionManager extends TransactionManager {
/**
* Set transaction execution listeners for this transaction manager.
*/
void setTransactionExecutionListeners(
Collection<TransactionExecutionListener> listeners
);
/**
* Get the transaction execution listeners for this transaction manager.
*/
Collection<TransactionExecutionListener> getTransactionExecutionListeners();
/**
* Add a transaction execution listener.
*/
default void addListener(TransactionExecutionListener listener);
}Usage Example:
@Configuration
public class TransactionListenerConfig {
@Bean
public PlatformTransactionManager transactionManager() {
JtaTransactionManager txManager = new JtaTransactionManager();
// Add transaction execution listener
txManager.addListener(new TransactionExecutionListener() {
@Override
public void beforeBegin(TransactionExecution transaction) {
logger.info("Transaction starting: {}", transaction.getTransactionName());
}
@Override
public void afterCommit(TransactionExecution transaction, Throwable commitFailure) {
if (commitFailure == null) {
logger.info("Transaction committed successfully");
} else {
logger.error("Transaction commit failed", commitFailure);
}
}
});
return txManager;
}
}Callback interface for monitoring transaction lifecycle events.
/**
* Callback interface for stateless listening to transaction creation/completion.
* Allows monitoring of transaction lifecycle events.
*/
public interface TransactionExecutionListener {
/**
* Called before a new transaction begins.
*/
default void beforeBegin(TransactionExecution transaction);
/**
* Called after a new transaction has begun, or after begin failure.
*/
default void afterBegin(TransactionExecution transaction, Throwable beginFailure);
/**
* Called before transaction commit.
*/
default void beforeCommit(TransactionExecution transaction);
/**
* Called after transaction commit (success or failure).
*/
default void afterCommit(TransactionExecution transaction, Throwable commitFailure);
/**
* Called before transaction rollback.
*/
default void beforeRollback(TransactionExecution transaction);
/**
* Called after transaction rollback (success or failure).
*/
default void afterRollback(TransactionExecution transaction, Throwable rollbackFailure);
}Usage Example:
public class MetricsTransactionListener implements TransactionExecutionListener {
private final MeterRegistry meterRegistry;
public MetricsTransactionListener(MeterRegistry meterRegistry) {
this.meterRegistry = meterRegistry;
}
@Override
public void afterCommit(TransactionExecution transaction, Throwable commitFailure) {
if (commitFailure == null) {
meterRegistry.counter("transactions.committed").increment();
} else {
meterRegistry.counter("transactions.commit.failed").increment();
}
}
@Override
public void afterRollback(TransactionExecution transaction, Throwable rollbackFailure) {
meterRegistry.counter("transactions.rolled.back").increment();
}
}Extended interface for transaction managers with resource awareness.
/**
* Extension of PlatformTransactionManager for resource-specific transaction management.
*/
public interface ResourceTransactionManager extends PlatformTransactionManager {
/**
* Return the resource factory that this transaction manager operates on.
* For example, a JDBC DataSource or a JMS ConnectionFactory.
*/
Object getResourceFactory();
}Usage Example:
@Service
public class DataSourceAwareService {
private final ResourceTransactionManager transactionManager;
public DataSourceAwareService(ResourceTransactionManager transactionManager) {
this.transactionManager = transactionManager;
}
public void performOperation() {
// Get the underlying DataSource
DataSource dataSource = (DataSource) transactionManager.getResourceFactory();
// Use transaction manager
TransactionTemplate template = new TransactionTemplate(transactionManager);
template.executeWithoutResult(status -> {
// Execute operations
});
}
}@Configuration
@EnableTransactionManagement
public class MultipleTransactionManagersConfig {
@Bean(name = "orderTransactionManager")
@Primary
public PlatformTransactionManager orderTransactionManager() {
return new DataSourceTransactionManager(orderDataSource());
}
@Bean(name = "customerTransactionManager")
public PlatformTransactionManager customerTransactionManager() {
return new DataSourceTransactionManager(customerDataSource());
}
@Bean
public DataSource orderDataSource() {
// Configure order database
return new HikariDataSource();
}
@Bean
public DataSource customerDataSource() {
// Configure customer database
return new HikariDataSource();
}
}
@Service
public class MultiDbService {
// Use specific transaction manager
@Transactional("orderTransactionManager")
public void saveOrder(Order order) {
orderRepository.save(order);
}
@Transactional("customerTransactionManager")
public void saveCustomer(Customer customer) {
customerRepository.save(customer);
}
}@Configuration
public class DistributedTransactionConfig {
@Bean
public JtaTransactionManager jtaTransactionManager() {
JtaTransactionManager txManager = new JtaTransactionManager();
// Configure for distributed transactions
txManager.setUserTransactionName("java:comp/UserTransaction");
txManager.setTransactionManagerName("java:comp/TransactionManager");
// Allow custom isolation levels if supported
txManager.setAllowCustomIsolationLevels(true);
return txManager;
}
@Bean
public DataSource xaDataSource1() {
// XA-capable data source
return configureXaDataSource("db1");
}
@Bean
public DataSource xaDataSource2() {
// XA-capable data source
return configureXaDataSource("db2");
}
}
@Service
public class DistributedTransactionService {
@Transactional
public void performDistributedTransaction() {
// Operations span multiple XA resources
dataSource1Repository.save(entity1);
dataSource2Repository.save(entity2);
jmsTemplate.send(message);
// All commit or rollback together
}
}@Configuration
public class CustomTxManagerConfig {
@Bean
public PlatformTransactionManager transactionManager() {
JtaTransactionManager txManager = new JtaTransactionManager();
// Configure synchronization behavior
txManager.setTransactionSynchronization(
AbstractPlatformTransactionManager.SYNCHRONIZATION_ON_ACTUAL_TRANSACTION
);
// Set default timeout
txManager.setDefaultTimeout(60);
// Configure nested transaction support
txManager.setNestedTransactionAllowed(false);
// Validate existing transactions before participating
txManager.setValidateExistingTransaction(true);
// Global rollback on participation failure
txManager.setGlobalRollbackOnParticipationFailure(true);
// Fail early on global rollback
txManager.setFailEarlyOnGlobalRollbackOnly(true);
// Rollback on commit failure
txManager.setRollbackOnCommitFailure(true);
return txManager;
}
}PlatformTransactionManager is the central abstraction for all transaction managersJtaTransactionManager is required for distributed transactions (XA)@Primary annotation when having multiple transaction managers to indicate the defaultAbstractPlatformTransactionManager