-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 7 posts ] 
Author Message
 Post subject: Pessimistic locking?
PostPosted: Fri Feb 02, 2007 1:38 pm 
Beginner
Beginner

Joined: Wed May 05, 2004 12:45 pm
Posts: 21
Need help with Hibernate? Read this first:
http://www.hibernate.org/ForumMailingli ... AskForHelp

3.2.1.ga:

Mapping documents:

Code between sessionFactory.openSession() and session.close():

Full stack trace of any exception that occurs:

Oracle 10g

The generated SQL (show_sql=true):

Debug level Hibernate log excerpt:


Problems with Session and transaction handling?

Read this: http://hibernate.org/42.html


Hello,

I am just playing around with pessimistic locking and I need a bit of clarification. I tried using two notations to use pessimistic locking.

1. call session.get(Class, id, LockMode)
2. call session.lock( Object, LockMode)

The first option behaves as I would expect it to with "select for update". If there are two threads T1 and T2, the second thread T2 will block on the line. After T1 commits T2 will continue. T2 will read the new values committed by T1.

However the second notations with session.lock (Object, LockMode.UPGRADE) is confusing me a bit. In the second case T2 will block as well and continue after T1 commits. When T2 unblocks and performs a read it will not see changes committed by T1.

What is the purpose of this second notation? Even though it blocks it doesn't pick up committed changes by T1. I am using Oracle with default read-committed isolation.

Thank you.


Top
 Profile  
 
 Post subject:
PostPosted: Fri Feb 02, 2007 9:53 pm 
Hibernate Team
Hibernate Team

Joined: Tue Aug 26, 2003 7:19 pm
Posts: 2364
Location: Brisbane, Australia
Read commited depends on when the read/tx occured/started.


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 05, 2007 12:36 pm 
Beginner
Beginner

Joined: Wed May 05, 2004 12:45 pm
Posts: 21
Thanks David,

My apologies I did not understand your reply/question. In both cases I start a transaction right before executing a query on the session object and I commit right after updating the value.

Code:

     tx = sess.beginTransaction();
     Query query = session.createQuery( SELECT_SOMETHING );
     Iterator iterator = query.iterate();
   if ( iterator.hasNext() ) {
      CapabilityEntity  capabilityEntity = (CapabilityEntity)iterator.next();
                session.lock(capabilityEntity, LockMode.UPGRADE)
               ....
       }
     tx.commit();



Top
 Profile  
 
 Post subject:
PostPosted: Tue Feb 06, 2007 1:05 am 
Senior
Senior

Joined: Sat Aug 19, 2006 6:31 pm
Posts: 139
fkzeljo wrote:

Code:

     tx = sess.beginTransaction();
     Query query = session.createQuery( SELECT_SOMETHING );
     Iterator iterator = query.iterate();
   if ( iterator.hasNext() ) {
      CapabilityEntity  capabilityEntity = (CapabilityEntity)iterator.next();
                session.lock(capabilityEntity, LockMode.UPGRADE)
               ....
       }
     tx.commit();



Hi,

Is the above snippet the code that is run by both threads? The read happens before the lock. Assume T1 runs and does iterator.next(). Before it gets the lock, T2 gets to run and does the read. At this point there's no lock yet and hence T2 gets the current value. Then T1 gets to run and gets the lock. At this point T2 is blocked until T1 commits.


Top
 Profile  
 
 Post subject:
PostPosted: Tue Feb 06, 2007 1:03 pm 
Beginner
Beginner

Joined: Wed May 05, 2004 12:45 pm
Posts: 21
Thanks for your reply,


Yes the code is run for both thread and I agree with your statement. My questions is how is then that syntax:

session.lock(capabilityEntity, LockMode.UPGRADE)

used for pessimistic locking since T2 will do a read before T1 locks. How do you ensure that T2 can not do a read before T1 locks, something like "select ... for update".

Is the proper way of using a pessimistic locking first to issue a query that retrieves ids and then do a

session.get ( Class, id, LockMode)

which will ensure that T2 can not do a read before T1 locks?

Thanks for your help,


Top
 Profile  
 
 Post subject:
PostPosted: Wed Feb 07, 2007 2:19 am 
Senior
Senior

Joined: Sat Aug 19, 2006 6:31 pm
Posts: 139
I see your point now.

I don't think session.lock() is intended to be used that way.

session.lock() will perform a version check and if it detects that another transaction has modified the object, it will throw an exception.

You can give it a try (I did).
You need to have the "version" element in your mapping file and Pojo.
Code:
<version name="version"></version>


Now you might say that this is the same as setting optimistic-lock="version".

There's actually a slight difference. With optimistic locking, the detection is done at commit. With session.lock it is at the time the call is made.

Budyanto


Top
 Profile  
 
 Post subject:
PostPosted: Wed Feb 07, 2007 12:17 pm 
Beginner
Beginner

Joined: Wed May 05, 2004 12:45 pm
Posts: 21
Thanks himawan for your replies,

Thanks for your input, I know I can always use optimistic locking with LockMode.READ to verify whether object has been modified by another transaction. I just wanted to figure out how pessimistic locking works, I see also that you can specify LockMode.UPGRADE_NOWAIT which will work properly for pessimistic locking.

Anyways thanks for your help.


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 7 posts ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.