这篇文章将为大家详细讲解有关SQLServer中怎么实现死锁,文章内容质量较高,因此小编分享给大家做个参考,希望大家阅读完这篇文章后对相关知识有一定的了解。
SQLServer怎么死锁
压力测试的业务场景:
1.模拟用户提交申请
a)涉及到的表
i.申请主表,一次申请生成一条数据。
ii.申请的医生明细,一次申请包含多个医生,一个申请包含100个医生
iii.单个医生明细,每个医生一条明细数据
综上所述一条申请的创建,需要插入201条数据。
b)申请逻辑
i.首先调用保存
ii.然后执行提交逻辑
各种逻辑验证,这是历史原因造成的(一个维护了几年的项目代码逻辑的混乱是难以想象的),总是在提交数据时做双重较验,比如数据是否有重复行的逻辑,这里会反复读取申请医生表以及医生明细这两个申请明细子表。这也是产生死锁的主要原因,此场景已经满足了同时读取以及修改同一表的情况。除此还会往其它表中插入数据,比如一些状态跟踪信息,发邮件等。
SQLServer怎么死锁
至于为什么被分割成两个逻辑来处理这原本是同一动作的需求,已经法考正最初的设计者了,这些逻辑包含各种EntityFramwork的查询写法,很难做有效的优化。
2.压力设置
a)并发8个用户
b)每1分钟增加5个用户
降低事务隔离级别为readuncommitted,结果是并不能消除死锁,但死锁的次数有所降低,主要时共享锁引发的死锁次数降低了。
分段分析法,也可以说是排除法。只执行一部分逻辑,比如我们上面的一个申请分为两步,先保存后提交,只保存的结果是死锁依旧。
寻找死锁跟踪的方法,试图寻找死锁的本质原因。我简单的按我自己的理解翻译了一些MVP写的文章,大家可以参考。
[翻译]:SQL死锁-锁的类型
解释了SQL中的各种锁以及它们之间的兼容性,只有了解了这些才能知道锁发生的场景,比如知道了共享锁之间是兼容的就能马上反应出纯读的操作是不会发生阻塞的
[翻译]:SQL死锁-锁与事务级别
事务隔离级别的不同会影响锁的行为,其中重要说明了降低事务隔离级别并不能消除死锁
[翻译]:SQL死锁-阻塞
只有出现了阻塞才会升级成死锁,所有了解阻塞是第一件事
[翻译]:SQL死锁-阻塞探测
这篇通过两种方式说明如何去跟踪分析死锁的本质原因,通过SQL自带的性能监控工且可以很方便的导出出现死锁的相关信息
[翻译]:SQL死锁-为什么会出现死锁
这篇非常详细的说明了死锁产生的原理
死锁文章的重要结论:
大部分死锁是因为未经过优化的查询导致的,但因为我们项目在处理这个申请的逻辑中有太多逻辑,不太可能在短时间内进行有效的优化,所以我暂时采用了一个也许不是很好的方案,即想办法降低排它锁的相互竞争,说的简单点说是在程序中通过一定的手段避免并发去调用更新或者插入数据的逻辑。
偏门解决方案:
通过一个取票排队的队列去解决数据插入以及更新的并发,原理就是一个线程想要插入数据时,先取票然后排队,当号轮到它时才能执行数据库操作,其它线程正在执行时,我们通过自族锁来实现排队。这个方法最大程序上解决死锁的问题,但不推荐这么做,之所以采用这种非常规手段,也是受制于现有程序的逻辑。
关于SQLServer中怎么实现死锁就分享到这里了,希望以上内容可以对大家有一定的帮助,可以学到更多知识。如果觉得文章不错,可以把它分享出去让更多的人看到。
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。