• Post Reply
  • Bookmark Topic Watch Topic
  • New Topic

Can't use Optimistic Locking

 
dinesh thalis
Ranch Hand
Posts: 39
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I want to handle concurrency, in order to do that i use optimistic locking below show my code, but if I try run code below exception happen, how can i solve it.

Java code




Exception



Please give comments
 
dinesh thalis
Ranch Hand
Posts: 39
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Without query.executeUpdate(); every thing work fine if I put query.executeUpdate(); exception happen
 
Christian Dillinger
Ranch Hand
Posts: 197
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Please post your mapping and show us how you use optimistic locking.
That you do not get an exception if you do not execute the line of code which produces the exception is quite obvious...
 
Marembo Ochieng'
Greenhorn
Posts: 19
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
what type of transaction are you using, user managed or container managed transaction? you probably need not include such locking if you are using container managed transaction
 
dinesh thalis
Ranch Hand
Posts: 39
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I'm using Container Manage Transaction(CMT), below show my entity class

Role.java




Update method



After execute above method earlier mention exception happen. My role table contain only one recode and all columns data equal to 1. please help me to overcome this problem.
 
dinesh thalis
Ranch Hand
Posts: 39
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I'm totally confused , if I change persistent provide Toplink to Hibernate work fine why ? please give me comments
 
Marembo Ochieng'
Greenhorn
Posts: 19
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Try not using the annotation @TransactionAttribute(TransactionAttributeType.REQUIRED) it is most likely needed when you do specify user managed transaction.
both transactions cannot be handled in the same entity bean
 
dinesh thalis
Ranch Hand
Posts: 39
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Marembo Ochieng' I think you're wrong

1) @TransactionAttribute(TransactionAttributeType.REQUIRED) use in Container Manage Transaction not User Manage Transaction

2) If I use TransactionAttributeType.REQUIRED - If the method is invoked from a nontransactional client, the container will start a transaction before the method is called and finish it when the method returns. On the other hand, if the caller invokes the method from a transactional context, the method will join the existing transaction. Two Transaction not happen -- according EJB3 in Action book page 219

3) I don't think Container Manage Transaction not handle Database locking automatically if this true please provide such links.

Please give you're precious comments if I wrong or write.

 
James Sutherland
Ranch Hand
Posts: 553
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
You seem to be very confused, the correct way to update objects in JPA is to read the "object" and modify it through its "set" methods, not use a "update" JPQL query.
Update queries in JPQL are for performing mass updates for batch processing, not to be used for updating objects.

Optimistic locking ensures that the object was not changed on the database while it was read into the EntityManager persistence context, but you are changing it directly on the database using your update query.

The lock is also not required, as the lock is always checked when you update the object.

# public void udateRole() {
# Role role;
# try {
# role = em.find(Role.class, "1");
# role.setRoleName("3");
# em.flush(); // not required, but will trigger any exception early.
# } catch (Exception e) {
# System.out.println(e);
# }
# }

If for some odd reason your want to use a raw query, not your object model, then you should remove the em.lock() to avoid lock contention with yourself.
 
dinesh thalis
Ranch Hand
Posts: 39
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
According to your post , you have mention that without locking can be achieved the optimistic locking - please give me some reference link.
In a mission critical system like a banking system how to handle the concurrent access like this;

User A :- Get the particular account record and watching it.
User B :- At the same time get that record and change it committed.
User A :- Now change the account record and committed.

Using version concept(Only Version annotation without em.lock) can we eliminate the concurrent problem?



 
Christian Dillinger
Ranch Hand
Posts: 197
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
If you use optimistic locking you expect that there will be only some conflicts so it is not the regular case.

Using @Version leads to statements like this:

update Foo set bar = ?, bar2 =?, version =? where id=? and version=?;

If data isn't changed by another user this statement MUST update a single row. If data is changed the statement doesn't update a row. So, either the row got deleted or another user updated it AND increased the version-field. In both cases it returns "0 rows changed" and you get an StaleObjectException.
 
  • Post Reply
  • Bookmark Topic Watch Topic
  • New Topic