我想收集有关 PostgreSQL 死锁中“赢家”事务和“输家”事务的事后调试信息。
- 我找到了 this wiki 页面,其中包括一些很好的实时 View ,可以提示当前出了什么问题,但如果我理解正确,当失败的交易已经被回滚时,大多数最有用的信息将已经从这些实时 View 中删除。
- 我看到了诸如 deadlock_timeout 之类的选项和 log_lock_waits它记录有关失败交易的信息,但值得注意的是没有获胜交易。似乎没有任何方法可以自定义生成的日志输出以包含比这更详细的信息(值得注意的是,当我事后基于日志进行调试时,这些整数都没有任何意义):
日志:1000.108 毫秒后,进程 11367 仍在等待事务 717 上的 ShareLock 详细信息:持有锁的进程:11366。等待队列:11367。 上下文:在更新关系“foo”的元组 (0,2) 时 语句:更新 foo SET 值 = 3;
我可以使用更好的数据源来收集这些信息吗?
最佳答案
首先,粘贴到问题中的跟踪不是死锁跟踪,而是关于资源锁定的警告,这些锁定的时间足够长(长于 deadlock_timeout
)。这不是错误,也不会中止事务,而死锁对事务来说是致命的。
I want to collect post-mortem debugging information about both the "winner" transaction and the "loser" transaction(s) in a PostgreSQL deadlock.
它们在服务器日志中,连同被终止的查询。
例如,对于此问题中提到的案例,这里有一个带有 log_line_prefix = '%t [%p] '
的死锁跟踪:postgres deadlock without explicit locking
2015-04-09 15:16:42 CEST [21689] ERROR: deadlock detected 2015-04-09 15:16:42 CEST [21689] DETAIL: Process 21689 waits for ShareLock on transaction 1866436; blocked by process 21028. Process 21028 waits for ShareLock on transaction 1866435; blocked by process 21689. Process 21689: insert into b values(1); Process 21028: insert into a values(1); 2015-04-09 15:16:42 CEST [21689] HINT: See server log for query details. 2015-04-09 15:16:42 CEST [21689] STATEMENT: insert into b values(1);
“宽松者”是 PID 21689
作为错误的产生者。 “赢家”是 PID 21028
,因为它只是另一个。
如果从客户端的角度来看,它会得到这样的消息:
ERROR: deadlock detected DETAIL: Process 21689 waits for ShareLock on transaction 1866436; blocked by process 21028. Process 21028 waits for ShareLock on transaction 1866435; blocked by process 21689. HINT: See server log for query details.
没有提及查询,但那是客户刚刚发送的查询。没有提到 looser,但它是一个得到这个错误的,另一个不需要注意任何事情。
关于postgresql - PostgreSQL 中的事后死锁调试,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29532072/