Reputation: 469
In my Spring MVC application, I have a method in a controller that needs to save a bunch of objects (built from an uploaded file) to a database. Let us leave aside for the moment the whole question about whether transactions should be done in the controller or service layer -- the point is that it should technically be feasible to do it in the controller, but I am finding problems. If you look at the code below, what I am expecting is that if any of the three calls to saveContact fails with an Exception (any exception, since I put rollbackFor = Exception.class ), then all three should be rolled back. Still, what I see is that if for example the third one fails, the data from the first two is still present in the database. The exception thrown is a PersistenceException, so I believe this should trigger the rollback, but it doesn't (it bubbles up to the client's browser, which is what I expected since I'm not catching it).
code removed for security reasons
Thanks
Upvotes: 2
Views: 3077
Reputation: 125242
@Transactional
on that method doesn't have any added value as it is an internal method call (and your class is already transactional). Spring uses proxies and only calls into the object pass thorough the proxy.
Also your code is flawed you shouldn't catch and swallow exceptions as that interferes with the tx support (it relies on transactions to determine to rollback or not, currently there is never an exception hence always tries to commit).
Finally you are using MySQL make sure that you are using table types that actually supports transactions (MyISAM tables don't have tx support).
I would however strongly suggest to move the transactional part (or the business logic which you are now doing in your controller) to a service. The controller (or web layer in general) should only be a thin layer converting the incoming request into something useable for the service layer and the result into something useable for the web to display.
Upvotes: 1
Reputation: 21194
With proxy-target-class="true" you're telling spring to use cglib to handle the proxying but you've specified scoped-proxy="interfaces".
See https://stackoverflow.com/a/15568457/117839
Upvotes: 2