如何避免被死锁阻塞?

时间:2018-10-19 20:28:04

标签: postgresql

我是否可以写一条UPDATE语句,如果出现死锁,该语句就不会理会执行?

我有一个很小的但经常更新的表。

该语句经常在其上运行。...

UPDATE table_a SET lastChangedTime = 'blah' WHERE pk = 1234;

pk是主键。

此语句不时地被阻塞。这本身并不是什么大问题;问题是,每次有锁时,Postgres似乎都需要花费一两分钟的时间才能自行整理,而我可能会丢失很多数据。

table_a非常不稳定,并且lastChangedTime一直都在变化,因此,我宁愿它只是偶尔地等待两分钟以使UPDATE被执行,而不是没有打扰。好的,我的数据可能不像我想要的那样最新,但至少我不会在2分钟内锁定整个表。


更新以下评论:

应用程序与数据库的交互非常简单,它仅发出简单的一行UPDATEINSERT语句,并立即提交每个语句。导致我头大伤脑筋的问题之一是某事物如何工作一百万次而不会出现问题,然后又在看起来与所有其他记录都相同的另一条记录上失败了。


最终建议/问题..... UPDATE语句正在从C#应用程序中调用。如果我将“命令超时”更改为一个非常短的值-假设1毫秒会产生预期的效果?还是最终会因大量中断的事务而阻塞数据库?

1 个答案:

答案 0 :(得分:0)

为避免等待锁,请先运行

SELECT 1 FROM table_a WHERE pk = 1234 FOR UPDATE NOWAIT;

如果行上有锁,则该语句将立即失败,您可以继续进行其他操作。

请注意,SELECT ... FOR UPDATE语句必须与您的UPDATE语句位于同一数据库事务中。

作为一般建议,您应该使用较短的事务,这将减少锁定等待的时间和死锁的风险。