这对我来说毫无意义,但也许有敏锐的眼睛的人可以发现问题所在。

我有一个使用FileSystemWatcher的Windows服务。它处理一些文件并将数据上载到MSSQL数据库。它在我的机器上完全可以正常工作-与Visual Studio分离(即不调试)并作为服务运行。如果将此编译后的代码复制到我们的服务器,并使其指向相同的数据库,甚至指向相同的文件(!),则每次都会出现此错误:

System.InvalidOperationException: Invalid operation. The connection is closed.
   at System.Data.SqlClient.SqlConnection.GetOpenTdsConnection()
   at System.Data.SqlClient.SqlBulkCopy.CopyBatchesAsyncContinuedOnError(Boolean cleanupParser)
   at System.Data.SqlClient.SqlBulkCopy.<>c__DisplayClass30.<CopyBatchesAsyncContinuedOnSuccess>b__2c()
   at System.Data.SqlClient.AsyncHelper.<>c__DisplayClass9.<ContinueTask>b__8(Task tsk)


我尝试将本地代码指向服务器的文件,并且工作正常。 .Net 4.5.1在两台计算机上。服务都在同一个域用户下运行。令人困惑。也许我对SqlBulkCopy.WriteToServerAsync()不了解?它会自动共享连接或其他内容吗?它在通话之间或其他时间之间关闭吗?以下是相关代码:

private static void ProcessFile(FileInfo fileInfo)
{
    using (var bulkCopy = new SqlBulkCopy("Data Source=myserver;Initial Catalog=mydb;Persist Security Info=True;User ID=myusr;Password=mypwd;")
    using (var objRdr = ObjectReader.Create(ReadLogFile(fileInfo)
                                    .Where(x => !string.IsNullOrEmpty(x.Level)),
                                         "Id", "AppId", "AppDomain", "AppMachine",
                                         "LocalDate", "UtcDate", "Thread", "Level", "Logger", "Usrname",
                                         "ClassName", "MethodName", "LineNo", "Message", "Exception",
                                         "StackTrace", "Properties"))
    {
        bulkCopy.DestinationTableName = "EventLog";
        bulkCopy.BulkCopyTimeout = 600;
        bulkCopy.EnableStreaming = true;
        bulkCopy.BatchSize = AppConfig.WriteBatchSize;
        bulkCopy.WriteToServerAsync(objRdr).ContinueWith(t =>
            {
                if (t.Status == TaskStatus.Faulted)
                {
                    CopyToFailedDirectory(fileInfo);
                    _log.Error(
                        string.Format(
                            "Error copying logs to database for file {0}. File has been copied to failed directory for inspection.",
                            fileInfo.FullName), t.Exception.InnerException ?? t.Exception);
                    Debug.WriteLine("new handle error {0}",
                                    (t.Exception.InnerException ?? t.Exception).Message);
                }
                if (t.Status == TaskStatus.RanToCompletion)
                {
                    _log.InfoFormat("File {0} logs have been copied to database.", fileInfo.FullName);
                    Debug.WriteLine("Yay, finished {0}!", fileInfo.Name);
                }
                // if this is the last one, delete the original file
                if (t.Status == TaskStatus.Faulted || t.Status == TaskStatus.RanToCompletion)
                {
                    Debug.WriteLine("deleting file {0}", fileInfo.Name);
                    PurgeFile(fileInfo);
                }
            });
    }
}


如果您要求,请注意以下几点:


ObjectReader是FastMember IDataReader实现。快速疯狂。它会将文件读入具有列出的属性的自定义对象。
它将为每个文件引发错误。
同样,它既可以作为服务也可以作为控制台应用程序在我的机器上运行。我什至让它在服务器上工作一次。它引发了错误,并且再也无法正常工作。


有任何想法吗?

最佳答案

看起来像是异步问题。

如果我错了,请告诉我,但是我注意到的是,您在using语句中包含了SqlBulkCopyObjectReader,这很棒,但是,您正在异步进行所有处理。一旦调用它,它开始工作,您的using语句将处理您的对象,这也会终止您的连接。

奇怪的是,这听起来有时候确实可行,但在那时它可能只是成为比赛条件。

关于c# - SqlBulkCopy.WriteToServer()不断获取“连接已关闭”,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/24272645/

10-10 11:49