Sql server sql server 2005死锁在生产环境中超时,而不是在测试环境中超时:为什么?

Sql server sql server 2005死锁在生产环境中超时,而不是在测试环境中超时:为什么?,sql-server,deadlock,Sql Server,Deadlock,在我的开发环境中,我试图重新创建一个我们需要的生产问题 面对MSSQL 2005。本期分为两部分: 问题 1) 出现死锁,MSSQL选择一个连接(“连接X”)作为“牺牲品”。 2) 所有后续使用“连接X”的尝试都失败(我们使用连接池)。MSSQL表示“服务器无法恢复事务” 在这两种情况中#2如果更严重的话:因为“连接X”每一次都会受到重击 重复使用“连接x”的“循环”尝试失败——而且很神秘 用户会看到“随机”错误。我们必须重新启动服务器 我为什么写作 然而,在这一点上,我希望重现问题1。我可以创

在我的开发环境中,我试图重新创建一个我们需要的生产问题 面对MSSQL 2005。本期分为两部分:

问题

1) 出现死锁,MSSQL选择一个连接(“连接X”)作为“牺牲品”。 2) 所有后续使用“连接X”的尝试都失败(我们使用连接池)。MSSQL表示“服务器无法恢复事务”

在这两种情况中#2如果更严重的话:因为“连接X”每一次都会受到重击 重复使用“连接x”的“循环”尝试失败——而且很神秘 用户会看到“随机”错误。我们必须重新启动服务器

我为什么写作

然而,在这一点上,我希望重现问题1。我可以创建一个 容易陷入僵局

但我的问题是:在生产中,MSSQL选择了一个 连接(SPID)作为“死锁牺牲品”,在我的测试环境中,死锁只是挂起…挂起,挂起。永远我不确定,但我让它挂了一夜,到了早上它还挂着

所以这里有一个问题:当死锁发生时,如何让sql server“选择死锁受害者”?

迄今为止的尝试次数

我尝试通过jdbc url设置“lock_timeout”参数(“lock timeout=5000”),但得到的消息与生产中的消息不同(在测试中,“lock request timeout period extended.”而不是生产中的“事务(进程ID 59)在另一个进程的锁资源上被死锁,并被选为死锁牺牲品。”)

关于问题2的一些细节

我研究了这个“无法恢复交易”的问题,发现了一个 几件事:

  • 错误的异常处理可能导致此问题。例如:java代码可以 不关闭语句/PreparedStatement和驱动程序的实现 的“连接”被错误/过时/旧的“事务ID”卡住
  • jdbc驱动程序升级可能会解决这个问题
不过,现在我只想重新创建一个死锁并使sql server “选择死锁受害者”

提前谢谢

附录A.技术环境

发展:

  • sql server 2005 SP3(9.00.4035.00)
  • 驱动程序:sqljdbc.jar版本1.0
  • JBoss3.2.6
  • jdbc-url:jdbc:sqlserver://
制作:

  • sql server 2005 SP2(9.00.3042.00)
  • 驱动程序:sqljdbc.jar版本1.0
  • JBoss3.2.6
  • jdbc-url:jdbc:sqlserver://
附录B.强制死锁的步骤

  • 获得连接A
  • 获取连接B
  • 使用连接运行sql1
  • 使用连接B运行sql2
  • 使用连接B运行sql1
  • 使用连接运行sql2
在哪里 sql1: 更新成员集名称=名称+成员id=71的“x”

sql2:
更新成员集name=name+'x',其中成员id=72

您可以使用

SET DEADLOCK_PRIORITY LOW | MEDIUM | HIGH
有关详细信息,请参阅此链接

您还可以使用以下命令查看打开的事务

DBCC OPENTRAN (db_name)

此命令可帮助您确定导致死锁的原因。有关更多信息,请参阅

正在运行的查询是什么?究竟是什么导致了僵局

您说您有两个连接A和B。A运行sql1,然后运行sql2,而B运行sql2,然后运行sql1。那么,正在进行的工作(查询)是什么?更重要的是,交易在哪里?您使用的是什么隔离级别?什么打开/关闭交易?(是的,这会导致对您的驱动程序使用的异常处理的质疑——如果他们没有检测到并正确处理返回的“it't not work”(它不起作用)消息,那么您绝对需要将他们带回来并向他们开枪——子弹或青霉素,您的电话。)

了解死锁背后的明确细节将允许您重新创建死锁。我首先尝试在应用程序的“下方”重新创建它——也就是说,在SSMS中打开两个窗口,并在必要时手动一步一步地重新创建应用程序的操作。一旦您能够做到这一点,请后退一步并在您的应用程序中复制它——当然,所有这些都在您的开发服务器上

(一个想法——您的开发数据库是生产数据库的副本吗?如果开发数据库比生产数据库小几个数量级,那么您的查询可能是相同的,但SQL在“幕后”所做的将大不相同。)

最后一点,SQL将自动检测和处理死锁(我真的不认为您可以禁用它),如果您的死锁在夜间运行,那么我认为您不会出现死锁,而只是一个传统的锁定/阻塞问题

[现在发布此消息--要查找某些内容,稍后将进行检查。]
[稍后]

有趣的是——SQLServer2005CompactEdition不检测死锁,它只检测超时。你没有在Dev中使用它,是吗


我认为没有办法“关闭”或以其他方式控制死锁超时时间。就在上周,我碰到并弄乱了死锁,一些任意测试表明死锁在5秒内被检测到并解决(对于我们的开发服务器)。看起来你的开发机器上并没有死锁,只是阻塞了。但是要意识到“纸上谈兵的DBA”很难分析这些内容,您确实需要坐下来认真分析发生此问题时系统内的情况。

这里给出了JDBc连接进入错误状态的原因解释:。您应该先升级到,然后再进行其他操作。该链接还包含关于如何修复应用程序处理以避免这种情况的建议,最重要的是关于避免JDBC事务API与本机Transact-SQL事务的混合

至于死锁复制:您没有在测试中重新创建死锁。您刚刚阻止了等待事务提交。死锁是另一回事,SQLServerW
 sql1

   connectionB

      sql2

      sql1

 sql2