我正在尝试使用NHibernate更新销售系统中Quantity
的{{1}}。
Product
然而,NHibernate将以这种形式生成SQL:
using (var session = NHibernateSessionUtil.OpenSession())
{
using (var trans = session.BeginTransaction())
{
var product = session.Load<Product>(1);
product.Quantity += 2;
session.SaveOrUpdate(product);
trans.Commit();
}
}
如果其他客户在处理此代码时更新了产品数量,则数量不正确。 到目前为止我能想到的解决方案是在进行更新之前锁定该行:
UPDATE Product SET quantity = 2 WHERE id = 1;
但是,如果我需要更新一长串产品,这会影响其他客户。
在NHibernate中是否有一个等效的方法来生成SQL,如:
...
var product = session.Load<Product>(1);
// lock row for update
session.Lock(product, LockMode.Upgrade);
product.Quantity += 2;
session.SaveOrUpdate(product);
...
?
任何建议?
的更新 的
我尝试打开具有可序列化隔离级别的会话,如@Fran建议的那样:
UPDATE Product SET quantity = quantity + 2 WHERE id = 1;
问题是在提交此事务之前由另一个客户端修改行时,会发生异常:
...
using (var trans = session.BeginTransaction(IsolationLevel.Serializable))
...
是否意味着我们需要明确锁定需要更新的每一行?即:
{"ERROR: 40001: could not serialize access due to concurrent update"}
如果需要锁定,使用和不使用 IsolationLevel.Serializable 打开交易有什么不同?
答案 0 :(得分:0)
我认为这样做的唯一方法是将对象锁定在可序列化的事务中。
所以当你打开你的交易时,给它一个可序列化的隔离级别。这将锁定对象,直到您提交事务为止。