SQL Server似乎以异步方式运行

时间:2014-10-02 09:20:04

标签: sql-server tsql stored-procedures rbar

我知道默认情况下SQL语句不会异步执行,但我的情况似乎表现得那样。

表格

  • [#data]
  • [tbl_Bucket]
  • [tbl_IDPool]

程序

  • [sp_InsertIntoBucket]
  • [sp_GenerateID]
  • [sp_UpdateIDPool]

过程

  • 应用程序调用{​​{1}}
  • [sp_InsertIntoBucket]来电[sp_InsertIntoBucket]
  • [sp_GenerateID]查询[sp_GenerateID]并生成值
  • [tbl_IDPool]来电[sp_GenerateID]
  • [sp_UpdateIDPool]写入[sp_UpdateIDPool]
  • [tbl_IDPool]将其生成的值返回到[sp_GenerateID]
  • [sp_InsertIntoBucket]将该值用作[sp_InsertIntoBucket]
  • 中新记录的主键
  • [tbl_Bucket]将生成的值返回给调用者

方案

[sp_InsertIntoBucket]包含发往[#data]的信息(1500 - 12000条记录)。由于[tbl_Bucket]一次只能处理一条记录,因此该流程为RBAR&#ed; - 对于[sp_InsertIntoBucket] [#data]中的每条记录都会被调用。

问题

[sp_InsertIntoBucket]生成重复值。在[sp_GenerateID]中的实际INSERT发生之前,我已经有13到130个重复生成的值,并且会抛出错误。

生成的值取决于[sp_InsertIntoBucket]中的数据,因此为每个[tbl_IDPool]调用调用[sp_UpdateIDPool]以确保 next 也很重要[sp_GenerateID]调用会生成唯一值。

我怀疑这与[sp_GenerateID][sp_GenerateID]写完[sp_UpdateIDPool]之前第二次被调用有关。但这没有意义,因为RBAR应等待[tbl_IDPool]等待[sp_InsertIntoBucket]等待[sp_GenerateID],等待[sp_UpdateIDPool],然后再转到下一个[#data]条目,正确?

我尝试了什么

  • WAITFOR DELAY "00:00:00.003" - 这很有效,但我正在寻找更好,更有效,更优雅的解决方案。
  • WHILECURSOR - 唯一的区别是CURSOR略慢。
  • WITH (NOLOCK) [sp_GenerateID] [tbl_IDPool]查询中有{{1}}希望写入(第一次调用)会锁定读取(第二次调用)。

1 个答案:

答案 0 :(得分:0)

[sp_GenerateID]开头尝试指定

SET TRANSACTION ISOLATION LEVEL SERIALIZABLE

然后将剩余内容包含在事务块中。

BEGIN TRANSACTION
...
COMMIT TRANSACTION