• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Ron McLeod
  • Tim Cooke
  • Liutauras Vilda
  • Jeanne Boyarsky
Sheriffs:
  • Paul Clapham
  • Rob Spoor
  • Junilu Lacar
Saloon Keepers:
  • Stephan van Hulst
  • Tim Holloway
  • Piet Souris
  • Carey Brown
Bartenders:

An issue in using Spring transaction

 
Ranch Hand
Posts: 178
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Here's a portion of our code:




In the code of UsersWebService:




Since the data insert in TBL_ACCOUNT is not yet committed, insertUserInfo method of UserswebService will always throw an exception, which shouldn't be since technically, there is already inserted data in TBL_ACCOUNT, its just not committed yet.

Is there a way to deal with this scenario ? (besides manual transaction handling)

by the way we are using Spring transaction version 4.2.4.RELEASE






 
Saloon Keeper
Posts: 26538
187
Android Eclipse IDE Tomcat Server Redhat Java Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I don't know if I'm interpreting that properly, but when working with transactions, sometimes the transaction scope is important. For example, if method A is transactional and method B is transactional, you have the option to either have method B inherit the context of method A's transaction OR you can have method B run as an independent transaction. In the second case, the actions of method A are as yet uncommitted, therefore cannot be relied on in the logic of method B.

There are Spring transaction parameters that determine which scope applies.
 
Andres Delrotti
Ranch Hand
Posts: 178
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

OR you can have method B run as an independent transaction



That's what I initially planned to do. The thing is, if method B fails, I would need to manually revert method A's DB changes. We want to avoid doing a manual revert. Is there an easier way to do this?

If method B is within the same transaction as A, it would not be able to see in the database, method A's changes since it is still uncommitted.
 
Tim Holloway
Saloon Keeper
Posts: 26538
187
Android Eclipse IDE Tomcat Server Redhat Java Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I think it's a matter of how you use JPA.

If you persist or merge data in method A, the changes should appear in the context of method B as long as you are using JPA properly. That is, you retrieve data in method B using the same persistence manager, you retrieve it after it was persisted (don't use out of date objects), and you don't forcibly fetch directly from the database. That is the essence of a complex transaction - that everything succeeds or fails as a unit and if any part of the transaction fails, you'd roll the whole thing back.

You can forcibly flush the operations out to the physical database, if necessary. Or break out an independent sub-transaction that effectively does just that, but about the only case where I do that is in cases where I need a generated key and cannot take advantage of more civilized options.
 
Andres Delrotti
Ranch Hand
Posts: 178
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Tim Holloway wrote:
If you persist or merge data in method A, the changes should appear in the context of method B as long as you are using JPA properly. That is, you retrieve data in method B using the same persistence manager, you retrieve it after it was persisted (don't use out of date objects), and you don't forcibly fetch directly from the database.
quote]

I get what you mean but problem is, method B is a web service. Method A is a dao method in the current application.

The option of transferring or copying Method A's logic in Method B is not viable because of that design principle of Cohesion - a web service in our system should have a single, well-focused purpose. Method B is also reused by other systems.

 
Tim Holloway
Saloon Keeper
Posts: 26538
187
Android Eclipse IDE Tomcat Server Redhat Java Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Yeah, I think I mis-interpreted the context of your web service.

If the web service is running in some other web application or even in the same application using a different EntityManager, then naturally the uncommitted actions in the calling method will not be available in the web service method. Unless you're using XA, a transaction only covers the particular app and EntityManager that started it.

In a case like that, you definitely WOULD have to commit the changes that you want the web service to see before you invoke it.

As I said earlier, that could be done by making a sub-transaction to do that. You might find it simplest in Spring to handle that in a separate method so that you can use transaction annotations of the logic in question. Otherwise you could do it in manual logic.

You might be able to use JPA flush() to force out the changes.

If you want these changes to be conditional on success of the entire transaction, you'd have to manually roll them back once committed. In other words, manually undo them.

If you want those changes to be invisible to all other processes and users, then you'd need to put the whole thing under XA transaction management. Which is not trivial.
 
With a little knowledge, a cast iron skillet is non-stick and lasts a lifetime.
reply
    Bookmark Topic Watch Topic
  • New Topic