Tuesday 29 September 2009

Transaction decisions

When creating a Spring/Hibernate application in a collaborative development environment, functionality can grow exponentially and your business layer can contain methods which result in the execution of 20 or more queries for one operation, which if not combined in an atomic operation will lead to possible data integrity issues and incremental functional failure of your application.

So now you have all your service objects working nicely, now suddenly, you need to integrate support for transactions into your service layer. If you where clever you would have done this BEFORE you started to develop your service layer but often support for transactions is not top of the list of priorities and gets left behind. Not a good thing but its not the end of the world.

You have a few options once in this situation

a) Do nothing
This is the easiest option. If your application is not mission critical, the application is low volume and you have the time and resources to maintain data much more subject to data integrity errors,  then this may be your best option. Its certainly the cheapest, but it is not a technical solution its an operational one.

b) Programmatic transaction support.
In a nutshell, we need to write code, lots more code to declare, commit or rollback transactions.

Within the Spring enviroment you have two ways to do this, the TransactionTemplate or the PlatformTransactionManager which can be passed into the service layer via dependency injection.

In many service layer operations the high level logic in most servoce layer methods is execute the operations , commit if no exception. If this describes your application then the declarative approach is almost certianly the better option.

The advantage of the programmatic approach fine-grained access to transaction logic, which in my opinion, in most business applications is not neccessary and the extra code you need to write for each service layer method is invasive and time consuming.

Should you have conditions other than Exceptions in which you would roll back the transaction maybe this way would be better, but then again, you could just create a checked exception for the condition and go with the next stratgey which I will discuss, which is declarative transaction management.

c) Declarative Transaction Management
Wouldnt it be great if you could declare a method in your service layer to be transactional, and the application code would then acknowledge that, execute your method and once it was happy that the execution was without error, commit all the changes to the persistant data store?

That pretty much sums up declarative transaction management and in an application with consistent transaction logic, probably the most consistent,elegant and least invasive way to go.

In Spring , aspects are used to achieve this, and pretty much the only design decision that needs to be taken is whether to use XML driven or annotation driven transaction declarations. I prefer annotations as its simpler and ties the transaction settings(Check here for your options) to the target method explicitly.

The XML driven notation requires the use of pointcut expressions in which the method signatures will fall into transactional scope if the method is in the scope of the pointcut expression. The XML configuration route would be good if you wanted to make your entire service layer or an entire service object transactional. I prefer to use transactions only if there is a risk of data integrity errors, so mostly on writes and deletes and not reads.

If you are interested in configuration details, here is the URL  to the Spring reference documentation, which covers the technical aspects of implementing transaction management.

If your application is large and complex, and does not support transactions, and you have decided on the strategy you wish to adapt, I think having automated unit tests for your existing functionality is a must, as some things will just not work once wrapped in a transaction or the service layer logic may not be condusive to supporting transactions, so the tests would be the best way to figure out what is breaking after the introduction for support for transactions.

No comments: