小编iva*_*olo的帖子

SQL Server 2005阻止问题(ASYNC_NETWORK_IO)

我负责在IIS和SQL Server 2005上运行的第三方应用程序(无法访问源)(500个并发用户,1TB数据,8个IIS服务器).我们最近开始看到对数据库的严重阻塞(在生产中运行此应用程序几个月后没有问题).这种情况在白天以大约每30分钟的随机间隔发生,每次影响20到100次.所有会话最终都会使应用程序超时并且会话中止.

问题消失,然后逐渐重新出现.负责阻止的SPID始终具有以下功能:

  • 等待类型= ASYNC_NETWORK_IO
  • 正在运行的SQL是"(@claimid varchar(15))SELECT claimid,enrollid,status,orgclaimid,resubclaimid,primaryclaimid FROM claim WHERE primaryclaimid = @claimid AND primaryclaimid <> claimid)".这是相对无害的SQL,应该只返回一个或两个记录,而不是大数据集.
  • 没有其他SQL语句涉及阻塞,只有这个SQL语句.
  • 这是参数化SQL,其执行计划缓存在sys.dm_exec_cached_plans中.
  • 此SPID在声明表上具有对象级S锁,因此也会阻止声明表的所有UPDATE/INSERT.
  • 主机ID各不相同.不同的Web服务器负责阻塞会话.例如,有时我们追溯到Web服务器1,有时是Web服务器2.

当我们追溯到阻塞中涉及的Web服务器时,我们会看到以下内容:

  • Web服务器上的事件日志中始终存在某种与应用程序相关的错误,该错误链接到SQL会话中的主机ID和主机进程ID.
  • 错误消息各不相同,通常是某种SystemOutofMemory.(这些错误消息似乎与我们过去看到的错误消息类似,没有产生如此严重的后果.我们认为之前发生过,但没有导致阻塞.为什么现在?)
  • Web服务器或SQL Server上的网络适配器没有已知问题.

(无论如何,违规查询返回的记录集很小.)

事情排除在外:

  • 索引经常进行碎片整理.
  • 统计定期更新.
  • 关于claim.primaryclaimid的统计数据的样本量增加.
  • 强制重新编译缓存的执行计划.
  • 使用primaryclaimid,claimid创建复合索引.
  • 没有网络问题.
  • Web服务器上没有已知问题.
  • Web服务器上的应用程序软件没有变化.

我们假设事件链是这样的:

  1. Web服务器进程提交上面的SQL.
  2. SQL Server执行SQL,在此期间它获取声明表上的锁.
  3. Web服务器进程出错并死亡.
  4. SQL服务器会话挂起,等待Web服务器进程读取数据集.
  5. 需要在声明表的某些部分(处理声明的任何人)上获取X锁的SQL Server会话被声明表上的锁阻止,并保持阻塞,直到它们全部达到应用程序超时.

任何在等待供应商帮助时进行故障排除的建议都将受到欢迎.

有没有办法强制SQL Server仅锁定此特定SQL语句的行/页级别?有没有办法在ASYNC_NETWORK_IO等待上设置阈值?

performance sql-server-2005

5
推荐指数
1
解决办法
1万
查看次数

标签 统计

performance ×1

sql-server-2005 ×1