简体   繁体   中英

Oracle Toplink: Atomically incrementing/decrementing amount

I have concurrent application which needs to update the incremented/decremented (change in balance) to the balance column in account table.

I'm using Oracle Toplink. One way to do the concurrent updates is to use Optimistic locking by using version column.

1) Optimistic Locking

update account set balance=?, version=? where id=? and version=?

2) Atomic update

update account set balance=balance + ? where id=?

I would like to use 2) option as it is easier and doesn't require me to read the value first before updating (as in 1) ).

SQLCall sc = new SQLCall("update account set balance=balance + #delta where id=#id");
DataModifyQuery data = new DataModifyQuery(sc);
data.addArgument("delta", BigDecimal.class);
data.addArgument("id", Long.class);
Vector param = new Vector(2); 
param.add(new BigDecimal(.01));
param.add(new Long(12345));
getSession().executeQuery(data, param);

I'm facing problem in executing the update query. The issue is that it doesn't reflect the amount at the end.

is 2) option is really updating Atomically?

Did I follow right coding approach. Anything wrong with this example?

Please guide

Your atomic update is not atomic.

If multiple transactions do that concurrently, both will increment their own view of the current balance, and the last one will win. Indeed, transactions are isolated from each other (that's the I in ACID ), and don't see the changes made by other transactions.

You still need locking (optimistic or pessimistic) to do that correctly.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM