据我所知,当一个线程试图更新另一个线程锁定的记录行时,会发生LockAcquisitionException
。 (如果我错了,请纠正我)
所以我尝试模拟如下:
我使用dbVisualizer
锁定了一行记录,然后我使用应用程序在同一记录上运行更新查询。最后,我只是使用原因码68来点击global transaction time out
而不是LockAcquisitionException
。
因此,我认为我的理解是错误的。 LockAcquisitionException
不会以这种方式发生。可以建议或提供一些简单的例子来创建LockAcquisitionException
?
答案 0 :(得分:0)
由于锁定超时,您将获得LockAcquisitionException(SQLCODE = -911 SQLERRMC = 68)。
比较dbViz与hibernate的操作可能没有用,因为它们可能在jdbc级别使用不同的类/方法和设置,这可能会影响异常细节。重要的是,在Db2级别,无论是否为锁定超时报告异常名称,两者都经历了SQLCODE = -911且SQLERRMC = 68。
根据许多因素,您可以在UPDATE或DELETE或INSERT或SELECT(以及其他包括DDL和命令)等语句上获得锁定超时。
所有锁定超时都有一个共同点:一个事务等待太长时间并且回滚,因为另一个事务没有足够快地提交。
锁定超时诊断和锁定超时避免是不同的主题。
根据选择的设计,可以在数据库级别,连接级别或语句级别设置等待锁定的时间长度,包括混合这些设计。您还可以通过调整数据库参数(如CUR_COMMIT,LOCK_TIMEOUT)以及调整语句级别或连接级别的隔离级别来调整Db2的锁定行为。
在考虑避免之前确保准确诊断是明智的。
当您运行Db2-LUW v10.5.0.9时,请仔细研究此页面及所有相关链接:
有很多情况可能导致锁定超时,因此最好确切地知道哪种情况与您的案例相关。
避免锁冲突是配置和事务设计的问题,因此这是一个更大的主题。配置可以是Db2级别,也可以是应用程序层或两者。
有时,错误会导致锁定超时,例如,当app-server线程的数据库连接挂起但尚未提交且应用程序未正确清理时。
您应该诊断锁定超时中的参与者。在Db2-LUW上有不同的锁定冲突诊断方法,所以选择适合你的方法。
仍可在V10.5.0.9上运行的一个简单诊断工具是使用Db2-registry变量DB2_CAPTURE_LOCKTIMEOUT = ON,尽管该方法已弃用。您可以动态设置此变量(并取消设置),而无需任何服务中断。因此,如果您有一个可重新生成的方案,导致SQLCODE = -911 SQLERRMC = 68(锁定超时),您可以打开此变量,重复测试,然后关闭变量。如果该变量已打开,并且发生锁定超时,Db2将写入一个新文本文件,其中包含有关锁定情况中参与者的信息,其中显示的详细信息可帮助您了解正在发生的情况,并且可让您考虑解决问题的方法。有足够的事实。您不希望永久保留此变量,因为如果您遇到大量锁定超时,它会影响性能并填满Db2诊断文件系统。所以你必须要小心。在此页面的知识中心中了解此变量: https://www.ibm.com/support/knowledgecenter/SSEPGG_10.5.0/com.ibm.db2.luw.admin.regvars.doc/doc/r0005657.html 您可以通过仔细研究这些文件的内容来诊断锁定超时,当然,了解详细信息也是必要的。这是一项常规的DBA活动。
另一种方法是使用db2pdcfg -catch和自定义db2cos脚本来决定在Db2抛出-911之后要做什么。这需要编写脚本技能,它可以让您确定在-911之后要收集哪些诊断以及存储这些诊断的位置。
另一种涉及更多工作但可能支付更多红利的方法是使用event monitor for locking
。文档位于:
https://www.ibm.com/support/knowledgecenter/en/SSEPGG_10.5.0/com.ibm.db2.luw.sql.ref.doc/doc/r0054074.html
一定要学习"相关概念"和"相关任务"页面也。