3

Currently I am autowiring sessionfactory in my service class just for the sake of transaction management .I am creating (hibernate)sessions in the service and based on the response from DAO layer,performing transaction commit/rollback.

My business logic requires me to update more than two database tables in single transaction.

From design perspective,I am rather skeptical to autowire sessionFactory in service layer.

Is there any other alternative to do so?

Thanks

Swapnil
  • 35
  • 1
  • 10
  • can you brief some more in detail? – Vigneshwaran Apr 20 '15 at 08:43
  • It is a REST API based web application where business logic will be handled by a Service.Currently this service class has autowired sessionfactory field.Before any DAO call,a session will be created using openSession() method and a transaction will be started using beginTransaction().based on DAO call results transaction will either be commited or rolled back.My preference was to keep all DB related entities (i.e session,sessionfactory etc) in DAO classes itself.But.If I do that,I don't think I can handle transactions in service class. – Swapnil Apr 20 '15 at 09:18
  • If this is a new design, I would suggest using Spring Data instead of writing your DAOs by hand. – chrylis -cautiouslyoptimistic- Apr 20 '15 at 09:35
  • Please don't as this will lead you to a slippery path and eventually an unmaintainable code base. The solution is simple don't use manual transactions, let spring do that for you, simply make your service method transactional. Spring will open a session for you, and commit it after the method finishes, all dao calls will participate in this transaction and will use the same session. This is all explained in the spring reference guide. – M. Deinum Apr 20 '15 at 09:47

3 Answers3

2

Transaction management at the service layer is not a bad design. If you do not want to autowire ssession factory in your service layer for the sake of separation of concerns, you can

  1. Explicitly delegate the transaction management logic to your own custom transaction management class. OR
  2. Use AOP and use annotations/XML, spring provides good support.
Serge Ballesta
  • 143,923
  • 11
  • 122
  • 252
Amit Parashar
  • 1,447
  • 12
  • 15
1

In general I agree with the others stating that transactions are usually started on the service level (depending on the granularity that you require of course).

However, in the mean time I also started adding @Transactional(propagation = Propagation.MANDATORY) to my DAO layer (and other layers that are not allowed to start transactions but require existing ones) because it is much easier to detect errors where you have forgotten to start a transaction in the caller (e.g. the service). If your DAO is annotated with mandatory propagation you will get an exception stating that there is no active transaction when the method is invoked.

I also have an integration test where I check all beans (bean post processor) for this annotation and fail if there is a @Transactional annotation with propagation other than Mandatory in a bean that does not belong to the services layer. This way I make sure we do not start transactions on the wrong layer.

originally obtained from Where does the @Transactional annotation belong?

Community
  • 1
  • 1
Vigneshwaran
  • 387
  • 1
  • 2
  • 14
-1

Not so. The Spring MVC has a design structure. You have to comply with that. It is not right approach to embed DAO layer in Service Layer. The DAO layer is responsible for handling Transaction related things. Service layer will work like abstraction. What is the need to wrap them in to single one?

Vigneshwaran
  • 387
  • 1
  • 2
  • 14
  • 1
    Are you sure ? The DAO layer is responsible to do the actual IO to database, but the transaction is generally managed at service level to allow one DAO class per table with multiple tables per transaction - but one transaction per service call. – Serge Ballesta Apr 20 '15 at 09:37