This is the fifth of a series of articles about Persistence with Spring. This article will focus on the configuration of transactions with Spring 3.1 and JPA. For a step by step introduction about setting up the Spring context using Java based configuration and the basic Maven pom for the project, see this article. 

The Persistence with Spring series:

Spring and Transactions

Spring provides a consistent and comprehensive transaction abstraction over many supported environments. There are two distinct ways of configuring and using transactions – annotations and AOP – each with their own advantages. The reference should provide enough material on both the decision to use the Spring transaction programming model, as well as a in depth discussion of its architecture.

The @Transactional configuration

By default, @Transactional will set the propagation to REQUIRED, the readOnly flag to false, and the rollback only for unchecked exceptions. Also note that the isolation level is set to the database default; when using JPA, the isolation level is that of the underlying persistence provider. In the case of Hibernate, the isolation level of all transactions should be REPEATABLE_READ.

For the purpose of this discussion, the relevant application layers will be DAO, Service and Controller. These layers can of course vary from application to application, without changing the underlying principles discussed here.

The @Transactional semantics of the Service and DAO layers should both be configured with REQUIRED propagation and the readOnly flag set to true for the relevant methods. The Controller layer should contain no transaction logic.

Note that this is also the way the DAO implementation is configured in Spring Data. For a detailed analysis of the persistence layer with Spring data, see the previous article of this series.

Assuming a clean separation of layers, where the Controller layer will only invoke the Service layer, which in turn will only call the DAO, then the DAO layer will never be called in a non-transactional context. As such the DAO will never be the transaction owner, and a more strict transaction configuration should be used for it. In this situation, the transactional semantics should be MANDATORY propagation and no readOnly flag. The MANDATORY propagation will simply ensure that a transaction has already been started when the DAO layer is entered, double checking the stated assumption that the DAO is never the transaction owner. The readOnly flag is also not needed because it will be set by the transaction owner as well.

Read the rest of the article