当您在多线程环境中接收到同一字段的并发插入和更新时,有没有解决问题的方法?
示例
线程1
BEGIN
insert into users (name,age) values('spiderman',27)
COMMIT线程2
BEGIN
update into users set age = 26 where name='spiderman';
COMMIT大多数情况下,更新(事务)并不知道插入操作的发生,因此它会抛出错误。
我在这里看到的是竞态条件的经典示例,避免竞态条件的一种方法是使用有效锁。
如何在数据库中不存在的记录上应用锁(记录)。
在上面的for insert语句示例中,以便Update知道记录还不在数据库中。
发布于 2016-04-21 01:50:17
基于锁的解决方案将非常困难,而且可能不值得这么麻烦。你必须找到一种方法来创建一组包含所有可能的“name”字段的数据,然后围绕这些数据创建一个建议锁系统。它也很可能容易出错。
然而,如果问题真的是确保UPDATE在INSERT之后才能运行,那么有更简单的解决方案。
具体来说,脑海中浮现的是这样的东西:
BEGIN;
SELECT count(*) FROM users WHERE name = 'spiderman';
-- on the application side, check to see what the result is
-- if it's 0, ROLLBACK
-- if it's >0:
UPDATE users SET age = 26 WHERE name = 'spiderman';
COMMIT;如果您最终回滚,您将返回并稍后重试,无论这意味着简单的事情,如sleep 10秒并重试,还是更复杂的事情,如将工作项放回队列中,并继续进行不同的工作。
如果您关心在SELECT和UPDATE之间发生的更新,可以使用SELECT FOR UPDATE,它将锁定选定的行,直到您的事务完成。
https://stackoverflow.com/questions/36747951
复制相似问题