Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/postgresql/9.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Postgresql Postgres:事务上的共享锁死锁_Postgresql_Deadlock - Fatal编程技术网

Postgresql Postgres:事务上的共享锁死锁

Postgresql Postgres:事务上的共享锁死锁,postgresql,deadlock,Postgresql,Deadlock,最近,我们开始在日志中发现很多死锁错误。(Postgres服务器9.6.5) 我们的表由两列组成,一列是自动递增主键,另一列是json对象。 json对象的两个属性定义为唯一。 现在在日志中,我们不断得到错误,即不同行上的两个简单insert查询相互阻塞 ============ process 65325 detected deadlock while waiting for ShareLock on transaction 2934224126 after 1000.050 ms DETA

最近,我们开始在日志中发现很多死锁错误。(Postgres服务器9.6.5)

我们的表由两列组成,一列是自动递增主键,另一列是json对象。 json对象的两个属性定义为唯一。 现在在日志中,我们不断得到错误,即不同行上的两个简单insert查询相互阻塞

============

process 65325 detected deadlock while waiting for ShareLock on transaction 2934224126 after 1000.050 ms

DETAIL:  Process holding the lock: 35530. Wait queue: .

CONTEXT:  while inserting index tuple (128,10) in relation "A"

STATEMENT:  INSERT INTO A AS t (info) VALUES('{"x":"y",....)

ERROR:  deadlock detected

DETAIL:  Process 65325 waits for ShareLock on transaction 2934224126; blocked by process 35530.

Process 35530 waits for ShareLock on transaction 2934224125; blocked by process 65325.

Process 65325: INSERT INTO A AS t (info) VALUES({"x":"y",....)

Process 35530: INSERT INTO A AS t (info) VALUES({"x":"z",....)
====================

process 65325 detected deadlock while waiting for ShareLock on transaction 2934224126 after 1000.050 ms

DETAIL:  Process holding the lock: 35530. Wait queue: .

CONTEXT:  while inserting index tuple (128,10) in relation "A"

STATEMENT:  INSERT INTO A AS t (info) VALUES('{"x":"y",....)

ERROR:  deadlock detected

DETAIL:  Process 65325 waits for ShareLock on transaction 2934224126; blocked by process 35530.

Process 35530 waits for ShareLock on transaction 2934224125; blocked by process 65325.

Process 65325: INSERT INTO A AS t (info) VALUES({"x":"y",....)

Process 35530: INSERT INTO A AS t (info) VALUES({"x":"z",....)
所以基本上两个不同的行处于死锁状态。
对于这种死锁可能发生的情况有什么建议吗?

行永远不会处于死锁状态。处于死锁状态的不是两个不同的行,而是两个不同的事务。您的日志显示每个事务最近的插入尝试。据推测,每个事务中都有以前的插入。但是这些不会出现在日志中,除非它们出现在其他原因中(比如log_statement=all)

因此,如果T1成功地(并且不可见地,查看日志文件)插入了“x”:“y”,T2成功地并且不可见地插入了“x”:“z”,现在T1尝试插入“x”:“z”,T2尝试“x”:“y”,将会出现死锁。假设唯一索引位于info上->>'x'

如果您不使用JSON,这将是相同的问题


缓解措施是,不要在每个事务中插入超过一行。或者,如果您这样做了,请始终按指定的顺序插入它们(例如,由于拉丁字母顺序,在“z”之前插入“y”),尽管在这种情况下,您只需将死锁错误替换为唯一的密钥冲突。或者,准备好抓住死锁并重试。

在过时的9.6.5版和当前的9.6.16版之间,有几个与“伪死锁”相关的错误修复。谢谢,虽然日志记录似乎很混乱,因为明确提到的查询与唯一约束不冲突。我将尝试实施您的缓解建议。@varun日志中提到的语句是冲突的一部分,但它们不是冲突的全部。PostgreSQL没有保存当前事务中先前执行的语句的内存,因此无法报告这些语句。(也许应该教我们用历史陈述保留一个有限大小的缓冲区)是的,如果我们也有历史陈述,僵局理解将变得显而易见。再次感谢!由于此提示帮助修复了一个死锁问题,因此我得到了多个服务器将数据写入同一个表的情况,即使每组行在服务器上都是唯一的。只需对行进行排序即可解决此问题。谢谢@jjanes