【问题标题】:C# ASP.Net: Exception (some times only) during long database operationC# ASP.Net:长时间数据库操作期间出现异常(仅有时)
【发布时间】:2011-06-18 11:47:36
【问题描述】:

我们有一个使用 WCF 连接到其业务层的 ASP.Net Web 应用程序。有时,当它执行一个巨大的操作时,我会遇到异常。有趣的是,当我第一次运行它时它就成功了。之后它抛出异常。

异常:套接字连接被中止。

操作是将邮政编码从 csv 文件上传到数据库表中。首先,我们从 csv 文件中读取并制作一个冗长的邮政编码字符串。这将传递给存储过程并执行数据库操作。

注意 1:) 当我放置断点并进行测试时,很明显字符串的创建(在从 csv 获取数据并附加之后)非常快(不到一分钟)。

注 2:) 我删除了事务(从 C# 代码中)并进行了测试,即使这样异常仍然存在。

注 3:) csv 中有十万(十万)条记录。每行有四列(邮政编码、城市、县、州)。 csv 文件的大小为 3MB。

我对事务日志的大小有疑问。然后我使用以下命令缩小了日志文件。 DBCC SHRINKFILE('MyDB_log', 1) 去

然后我使用 SELECT [Size],Max_Size,Data_Space_Id,[File_Id],Type_Desc,[Name] FROM FRAMIS_R2075.sys.database_files WHERE data_space_id = 0 检查了日志大小

大小为 128;最大尺寸为 268435456; Type_Desc = “日志”

即使缩小了异常仍然会出现。

框架:.Net 3.0

数据库:SQL Server 2005

好吧,当我又等了 20 分钟时,业务层似乎也有异常。它说,“调用读取器时调用读取的尝试无效”。通过看到这一点,我删除了 DbDataReader 并使用 SqlCommand 来更新数据库表。再次,业务层出现异常,大约 20 分钟后出现“超时异常”。知道为什么会这样吗?

  private void ProcessDatabaseOperationsForZipCode(StringBuilder dataStringToProcess, int UserID)
    {
        int CountOfUnchangedZipCode = 0;
        string strRetiredZipCode = "";
        string strNewZipCode = "";
        dataStringToProcess.Remove(dataStringToProcess.Length - 1, 1);


        if (dataStringToProcess.Length > 0)
        {

            //TimeSpan.FromMinutes(0) - to make transaction scope as infinite.
            using (TransactionScope transaction = TransactionScopeFactory.GetTransactionScope(TimeSpan.FromMinutes(0)))
            {


                SqlConnection mySqlConnection = new SqlConnection("data source=myServer;initial catalog=myDB; Integrated Security=SSPI;");
                SqlCommand mySqlCommand = new SqlCommand("aspInsertUSAZipCode", mySqlConnection);
                mySqlCommand.CommandType = CommandType.StoredProcedure;
                mySqlCommand.Parameters.Add("@DataRows",dataStringToProcess.ToString());
                mySqlCommand.Parameters.Add("@currDate", DateTime.Now);
                mySqlCommand.Parameters.Add("@userID", UserID);
                mySqlCommand.Parameters.Add("@CountOfUnchangedZipCode", 1000);
                mySqlCommand.CommandTimeout = 0;
                mySqlConnection.Open();
                int numberOfRows = mySqlCommand.ExecuteNonQuery();

         //Database db = DatabaseFactory.CreateDatabase();
                //DbCommand cmd = db.GetStoredProcCommand("aspInsertUSAZipCode");
                //cmd.CommandTimeout = 0;
                //db.AddInParameter(cmd, "@DataRows", DbType.String, dataStringToProcess.ToString());
                //db.AddInParameter(cmd, "currDate", DbType.DateTime, DateTime.Now);
                //db.AddInParameter(cmd, "userID", DbType.Int32, UserID);
                //db.AddOutParameter(cmd, "CountOfUnchangedZipCode", DbType.String, 1000);


                //using (DbDataReader rdrUpgradeTypes = (DbDataReader)db.ExecuteReader(cmd))
                //{
                //    //while (rdrUpgradeTypes.Read())
                //    //{
                //    //    if (!String.IsNullOrEmpty(Utility.GetString(rdrUpgradeTypes, "NewZipCode")))
                //    //    {
                //    //        strNewZipCode = strNewZipCode + "," + Utility.GetString(rdrUpgradeTypes, "NewZipCode");
                //    //    }
                //    //}
                //}


                transaction.Complete();

            }
        }


    }

【问题讨论】:

  • 增加超时时间看看...

标签: c# asp.net sql-server-2005 exception transactions


【解决方案1】:

问题可能是与 SQL Server 的连接超时 - 连接和命令的默认超时均为 30 秒。

您可以延长超时时间(在连接字符串和代码中)或将更新分成块。

【讨论】:

  • @Lijo - 在这些情况下有什么例外?您是否在命令 超时上都设置了这个无限超时?
  • 服务器端有什么异常???我建议你阅读 MSDN 上关于 Command 的文档。
  • 好吧,当我又等了 20 分钟时,似乎业务层也出现了异常。它说,“调用读取器时调用读取的尝试无效”。通过看到这一点,我删除了 DbDataReader 并使用 SqlCommand 来更新数据库表。再次,业务层出现异常,大约 20 分钟后出现“超时异常”。知道为什么会这样吗? [代码在原帖中给出]
  • @Lijo - 您没有在任何地方设置Connection 的连接超时。这是在连接字符串上完成的:“Connection Timeout=30;”,例如
  • 我在连接字符串中添加了 Connection Timeout = 0。当我删除事务时,我从 SQlClient 得到了 insuffieint memory 异常。然后我将数据库操作分成不同的批次。然后我删除了交易。它工作正常(当我删除事务时)。但是当我带回事务时,它抛出了 MSDTC 异常。你能回答stackoverflow.com/questions/6401918/…
【解决方案2】:

感谢 Oded 耐心地回答我的问题。当我将庞大的数据库操作分成小批量(配置 MSDTC 后)时,我的问题得到了解决。

在大型数据库操作期间,可能会出现内存不足错误。但如果它在事务中,则此错误可能不可见。

1) 删除事务,看看是否有“内存不足”异常。

2) 将大型数据库操作分解为小批量以消除“内存不足”异常

3) 在应用层和数据库中配置 MSDTC

4) 确保 WCF 不会突然超时。根据数据库操作应该有足够的时间。

5) 观察数据库服务器重启时的行为(这是最后一个选项)

一些有用的信息在

There is insufficient system memory in resource pool 'default' to run this query

MSDTC Exception during Transaction: C#

C# ASP.Net: Exception (some times only) during long database operation

SQL Server 2005 Error 701 - out of memory

其他一些检查:

1) 运行数据库引擎的windows账号是否有“Lock pages in memory permission”?

2) Chek SQL Sever 服务包版本。

3) 检查虚拟内存分页文件的大小

4) 检查最大服务器内存

5) 确定 MemToLeave 设置

6) 《SQL Server 内存配置与 MemToLeave》

【讨论】:

    猜你喜欢
    • 2015-04-13
    • 2019-10-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-01-10
    相关资源
    最近更新 更多