为什么这个例外既不是沉默的也不是信息

本文关键字:沉默 信息 为什么 | 更新日期: 2023-09-27 18:17:06

这个遗留代码可以从应用程序中的无数地方调用:

    public void DBCommand(string dynSQL, bool Silent)
    {
        checkConnection();
        SqlCeCommand cmd = objCon.CreateCommand();
        SqlCeTransaction trans = this.GetConnection().BeginTransaction();
        cmd.Transaction = trans;
        try
        {
            cmd.CommandText = dynSQL;
            cmd.ExecuteNonQuery();
            trans.Commit();
        }
        catch (Exception ex)
        {
            MessageBox.Show(
                string.Format("DBCommand Except in DBConnection.DBCommand: {0}. InnerException: {1}", ex.Message, ex.InnerException));//TODO: Remove
            try 
            {
                trans.Rollback();
            }
            catch (SqlCeException) 
            {
                // Handle possible exception here
            }
//              MessageBox.Show(
//                  string.Format("DBCommand Except in DBConnection.DBCommand: {0}. InnerException: {1}", ex.Message, ex.InnerException));//TODO: Remove
                WriteDBCommandException(dynSQL, ex, Silent);
            }
        }

当加载一个特定文件并将其内容插入到数据库中时,我将收到五次此消息。然而异常的Message和InnerException总是空字符串。

我甚至(可能有点迷信或不合逻辑)将MessageBox.Show()从一个位置移动到另一个位置,看看这是否会有什么不同(它没有)。

显示异常,但没有给出任何关于问题所在的有用信息;我已经看过(手动的,或者更准确地说,我猜是字面上的光学扫描)有问题的数据,这一切似乎都没问题。

那么,为什么这个异常消息哭泣和哀号,但没有沟通的问题是什么,就像一个疝气但哑巴婴儿(嘴巴张得很大,眼泪流下来,但没有声音)?

更新

好吧,我改编了ErikEJ的代码片段(不能使用helpink或StringIsNullOrEmpty,因为我使用的是很久很久以前的工具,在Alley Oop, Bertha Butt和Artie Shaw的时代):

            // from method that throws the exception
            catch (SqlCeException sqlfail)
            {
                MessageBox.Show(GetSQLCEErrorInfo(sqlfail));
            }
            catch (Exception ex)
. . .
        public static string GetSQLCEErrorInfo(SqlCeException args)
        {
            SqlCeErrorCollection errorCollection = args.Errors;
            StringBuilder bld = new StringBuilder();
            Exception inner = args.InnerException;
            if (null != inner)
            {
                bld.Append("'nInner Exception: " + inner.ToString());
            }
            // Enumerate the errors to a message box.
            foreach (SqlCeError err in errorCollection)
            {
                bld.Append("'n Error Code: " + err.HResult.ToString("X", 
System.Globalization.CultureInfo.InvariantCulture));
                bld.Append("'n Message   : " + err.Message);
                bld.Append("'n Minor Err.: " + err.NativeError);
                bld.Append("'n Source    : " + err.Source);
                // Enumerate each numeric parameter for the error.
                foreach (int numPar in err.NumericErrorParameters)
                {
                    if (0 != numPar) bld.Append("'n Num. Par. : " + numPar);
                }
                // Enumerate each string parameter for the error.
                foreach (string errPar in err.ErrorParameters)
                {
                    if ((null != errPar) && (errPar.Trim() != string.Empty))  //IsNullOrEmpty(errPar))
                    {
                        bld.Append("'n Err. Par. : " + errPar);
                    }
                }
            }
            return bld.ToString();
        }

…我看到了以下内容:

Error Code: 80040E14
Message : There was an error parsing the query. [Token line number, Token line offset,, Token in error,,]
Minor Err.: 25501
Source : Microsoft SQL Server 2000 Windows CE Edition
Num. Par. : 1
Num. Par. : 47
Err. Par. " [

…然后:

Exception: SLQ Server CE does not support parallel transactions.
Location. DBConnection.GetInstance(siteNo)

(这两个我都得到两次);但为什么只有两次呢?它插入几百条记录……有人会认为,如果它失败一次,它就会失败每一次。

为什么这个例外既不是沉默的也不是信息

你做错了,你需要在捕获一般异常之前捕获由ExecuteNonQuery引起的更专门的SqlCeException。对于sqlceexception,需要特殊处理,可以这样获取所有相关信息:

public static string ShowErrors(System.Data.SqlServerCe.SqlCeException e)
{
System.Data.SqlServerCe.SqlCeErrorCollection errorCollection = e.Errors;
StringBuilder bld = new StringBuilder();
Exception inner = e.InnerException;
if (!string.IsNullOrEmpty(e.HelpLink))
{
    bld.Append("'nCommand text: ");
    bld.Append(e.HelpLink);
}
if (null != inner)
{
    bld.Append("'nInner Exception: " + inner.ToString());
}
// Enumerate the errors to a message box.
foreach (System.Data.SqlServerCe.SqlCeError err in errorCollection)
{
    bld.Append("'n Error Code: " + err.HResult.ToString("X", System.Globalization.CultureInfo.InvariantCulture));
    bld.Append("'n Message   : " + err.Message);
    bld.Append("'n Minor Err.: " + err.NativeError);
    bld.Append("'n Source    : " + err.Source);
    // Enumerate each numeric parameter for the error.
    foreach (int numPar in err.NumericErrorParameters)
    {
        if (0 != numPar) bld.Append("'n Num. Par. : " + numPar);
    }
    // Enumerate each string parameter for the error.
    foreach (string errPar in err.ErrorParameters)
    {
        if (!string.IsNullOrEmpty(errPar)) bld.Append("'n Err. Par. : " + errPar);
    }
  }
  return bld.ToString();
}