Recently I came across an application which manage transaction's at Dao layer that means there is no proper transaction management and if an exception occurs during runtime will leave inappropriate data in database.
Consider this simple Architectural layers
Consider this simple Architectural layers
Brief description of each block starting from the bottom.
DB1 .. DBn → Databases, an application sometimes refers to multiple databases and simple application has one.
Dao Layer → Encapsulates logic to add, update, delete and read data from Databases using JPA, Hibernate or JDBC.
Entity/Dto → Simple Pojo classes which encapsulate database entities
WebServices Client → Another Integration Layers like Dao which communicates with other systems via SOAP, JMS etc.
Service Layer → This layer contains business logic which encapsulate the data (Dao & Webservices client) they operate on and provide hardened interfaces as the only way to access their functionality. This approach reduces side effects and allows services to evolve at their own pace without impacting the other components of the overall system.
UI/Controller → If you use any MVC framework then this layer contains Controller or Action classes which directly serve browser requests and delegates all operations to Service Layers Classes i.e. they don't have any business logic in them.
Web Services → This layer contains Web Services or External facing API's if you plan to expose some functionality for other systems to integrate via SOAP, REST, RMI etc. Also this should just delegate all functionality to Service Layers classes, Main reason we have this extra layer to expose some functionality is to have its own space to evolve with different revisions without impacting the overall system, this separation is very important if you system needs to involve over time and external changes.
Coming back to the original topic as which layer to manage transactions, also you can clearly see in the Architecture diagram above that Service Layer lies at the heart of the system exposing business logic to UI and other API's and hence that's where Transactions should be manage.
Checkout this sample transaction management code
/**
*
* @author intesar
*/
@Service
public class UserServiceImpl implements UserService {
/**
* Dummy Use Case # 33
* Admin can select multiple users on UI page and update the active status and then saves
* updates multiple users in a single transactions
* @param users
*/
@Override
@Transactional(propagation = Propagation.REQUIRED)
public void updateUsers(List<User> users){
for ( User user: users ) {
userDao.merge(user);
}
}
@Autowired
protected UserDao userDao;
protected static final Log log = LogFactory.getLog(UserServiceImpl.class);
}
As you can see in the above code snippet updateUsers(..) method part of Service Layer class, updates multiple users in a single operation and if any user update fails then entire operation rollsback. However this not possible if we are managing transactions at Dao layer.
I am using Spring framework to manage my transactions though you can use JEE or any other framework.
DB1 .. DBn → Databases, an application sometimes refers to multiple databases and simple application has one.
Dao Layer → Encapsulates logic to add, update, delete and read data from Databases using JPA, Hibernate or JDBC.
Entity/Dto → Simple Pojo classes which encapsulate database entities
WebServices Client → Another Integration Layers like Dao which communicates with other systems via SOAP, JMS etc.
Service Layer → This layer contains business logic which encapsulate the data (Dao & Webservices client) they operate on and provide hardened interfaces as the only way to access their functionality. This approach reduces side effects and allows services to evolve at their own pace without impacting the other components of the overall system.
UI/Controller → If you use any MVC framework then this layer contains Controller or Action classes which directly serve browser requests and delegates all operations to Service Layers Classes i.e. they don't have any business logic in them.
Web Services → This layer contains Web Services or External facing API's if you plan to expose some functionality for other systems to integrate via SOAP, REST, RMI etc. Also this should just delegate all functionality to Service Layers classes, Main reason we have this extra layer to expose some functionality is to have its own space to evolve with different revisions without impacting the overall system, this separation is very important if you system needs to involve over time and external changes.
Coming back to the original topic as which layer to manage transactions, also you can clearly see in the Architecture diagram above that Service Layer lies at the heart of the system exposing business logic to UI and other API's and hence that's where Transactions should be manage.
Checkout this sample transaction management code
/**
*
* @author intesar
*/
@Service
public class UserServiceImpl implements UserService {
/**
* Dummy Use Case # 33
* Admin can select multiple users on UI page and update the active status and then saves
* updates multiple users in a single transactions
* @param users
*/
@Override
@Transactional(propagation = Propagation.REQUIRED)
public void updateUsers(List<User> users){
for ( User user: users ) {
userDao.merge(user);
}
}
@Autowired
protected UserDao userDao;
protected static final Log log = LogFactory.getLog(UserServiceImpl.class);
}
As you can see in the above code snippet updateUsers(..) method part of Service Layer class, updates multiple users in a single operation and if any user update fails then entire operation rollsback. However this not possible if we are managing transactions at Dao layer.
I am using Spring framework to manage my transactions though you can use JEE or any other framework.
Comments
Javin
Why String is immutable in Java
If your service method calls several DAO methods, when you put your transaction management in the DAO layer each previous DAO method will be comitted, even if a subsequent DAO method throws an exception. Possibly erronous data will remain in the database this way.
If your transaction management is around your Service method, when one of the DAO methods throws an Exception your entire Service call will be rollbacked and no modified data will remain in the database.
The adventage of having a BO layer is that other technologies than WS (eg JMS) can access to the BO logic, and you can make transactional multiple DAO calls.
In brief, having a BO layer have to adventages:
1) solves your problem of transactinality
2) makes your app more extensible (for other communication technologies)
Best regards