我们正在编写一个简单的应用程序:
我们尝试了一些让连接处于SUSPENDED状态(由sp_who2验证)的事情,或者花费更长的时间来完成SQL查询本身(可能是某种死锁?)。
我们是:
public static void StartQuery() {
// build the query for array[i]
// ...
SqlConnection conn = new SqlConnection(AsyncConnectionString);
conn.Open();
cmd.BeginExecuteReader(CallbackHandler, cmd);
i++;
}
public static void CallbackHandler(IAsyncResult ar) {
// unpack the cmd
cmd.EndExecuteReader();
// read some stuff to a DataTable...
// SqlBulkCopy to another database (synchronously)
cmd.Connection.Close();
cmd.Connection.Dispose();
StartQuery();
}
是否有人在强大的模式上有建议或链接来解决此类问题?
谢谢!
答案 0 :(得分:4)
我假设您确实在连接字符串上设置了AsyncronousProcessing
。在CLR中汇集的数千个BeginExecute查询是一个灾难的处方:
max worker threads
限制,并开始经历长时间连接Open
次并经常超时。更好的方法是使用一个队列,工作池从中加载并执行它们。典型的生产者 - 消费者。工作人员(消费者)的数量将由SQL Server资源(CPU核心,内存,负载的IO模式)调整,但安全数量是服务器核心数量的2倍。每个工作人员都使用专用连接进行工作。工作人员的角色和队列的作用不是为了加快工作,而是相反,它们充当限制机制,以防止您淹没服务器。
更好的方法是将队列保留在数据库中,作为从崩溃中恢复的方法。请参阅Using Tables as Queues了解正确的方法,因为基于表的排队非常容易出错。
最后,您可以让SQL Server通过Activation处理所有内容,排队,限制和处理本身。请参阅Asynchronous Procedure Execution和后续文章Passing Parameters to a Background Procedure。
哪一个是正确的解决方案取决于你对你的问题了解的很多因素,但我没有,所以我不推荐你应该走哪条路。