Oracle Update Statements – Resolving Lock Race Conditions

hibernatejavalockingoracle

Say I have a table MY_TABLE without optimistic lock column. I have the following update statement that will be executed with org.hibernate.SQLQuery:

UPDATE MY_TABLE SET NAME = ? WHERE SOME_NUMBER = ? AND NAME = ?

In some place in my Java code, I'll create a new async thread to execute this update. Say that at a given time after some seconds this thread is executed:

Thread 1:

UPDATE MY_TABLE SET NAME = 'TEST2' WHERE SOME_NUMBER = 3 AND NAME = 'TEST'

This operation can take some minutes. Few milliseconds later the following thread is executed:

Thread 2:

UPDATE MY_TABLE SET NAME = 'TEST3' WHERE SOME_NUMBER = 3 AND NAME = 'TEST'

I need to make sure that, since the rows affected are the same, the UPDATE from the first thread is executed before the one from the second thread.

Does the default lock strategies from Oracle already guarantee that? Or do I need anything else?

Thanks!

Best Answer

No

You can be sure that one of the threads will obtain the lock and hold it until the transaction ends. And while it holds the lock, no other transaction can get the lock. But there is no guarantee that the thread you started first will get the lock first, because there is no coordination of the threads from the start to the update statement.

This is no special problem of Oracle but that is typical when working with threads. If you want to guarantee some order of processing you are responsible to coordinate this. For example your first thread requests a lock L (in your program, on your client or in the database, what ever is necessary)) and after it got the lock the second thread is started and requests the lock L. But L is released not before the first thread has finished.