Получение сообщения об ошибке SQL из транзакции. Commit () - PullRequest
0 голосов
/ 09 июня 2018

У меня есть кусок кода, который перебирает список команд SQL, которые должны обрабатываться как часть одной транзакции.Я хочу иметь способ узнать, была ли эта транзакция успешной в целях регистрации ошибок и обработки.В данный момент по какой-то причине у меня возникла проблема с отображением какого-либо фактического исключения или неудачной фиксации.Я использую код ниже прямо сейчас.Поймать попытку от рекомендации страницы MSDN.Пожалуйста, не стесняйтесь делать любые другие пробелы в этом, что, как вы видите, не на 100% относится к моему вопросу.Это все команды SqlCommands хранимого типа proc с параметрами, добавленными в него до добавления его в список команд SQL.

public static async Task UpdateSQL(string inputQuery, 
    string inputId, List<SqlCommand> commandList, TraceWriter log)
{
    try
    {
        string str = ConfigurationManager.ConnectionStrings
            ["connString"].ConnectionString;

    log.Info($"Running query: {inputQuery}");
    int commandRows = 0;
    using (SqlConnection conn = new SqlConnection(str))
    {
        conn.Open();
        SqlTransaction tr = conn.BeginTransaction();

        try
        {
            SqlCommand cmd = new SqlCommand(inputQuery, conn);
            cmd.Transaction = tr;
            foreach (var command in commandList)
            {
                command.Connection = conn;
                command.Transaction = tr;
                log.Info($"{command.CommandText} query running"); //last log output if unsuccesful (based on end result in database)
                commandRows += await command.ExecuteNonQueryAsync();
            }
            log.Info($"total rows updated: {commandRows}");

            tr.Commit();
            conn.Close();
        }
        catch(Exception ex)
        {
            Console.WriteLine($"Commit Exception Type: {ex.GetType()}");
            Console.WriteLine($"  Message: {ex.Message}");

            try
            {
                tr.Rollback();
                conn.Close();
                log.Info($"{inputId} transaction rolled back");
            }
            catch (Exception ex2)
            {
                // rollback fail Exception
                log.Info($"Rollback Exception Type: {ex2.GetType()}");
                log.Info($"  Message: {ex2.Message}");
                conn.Close();
            }
        }
    }
}

1 Ответ

0 голосов
/ 09 июня 2018

Попробуйте и поймайте SqlException

Затем сделайте это:

StringBuilder sqlErrorMessages = new StringBuilder ("Исключение Sql: \ n");

    foreach (SqlError error in ex.Errors)
    {
        sqlErrorMessages.AppendFormat("Mesage: {0}\n", error.Message)
            .AppendFormat("Severity level: {0}\n", error.Class)
            .AppendFormat("State: {0}\n", error.State)
            .AppendFormat("Number: {0}\n", error.Number)
            .AppendFormat("Procedure: {0}\n", error.Procedure)
            .AppendFormat("Source: {0}\n", error.Source)
            .AppendFormat("LineNumber: {0}\n", error.LineNumber)
            .AppendFormat("Server: {0}\n", error.Server)
            .AppendLine(new string('-',error.Message.Length+7));

    }

Вы будетеполучить исключение в C #, только если серьезность вашей ошибки 16 или выше.Если вы используете PRINT, вы не получите исключение в .NET.

Если вы сможете редактировать код ошибки повышения, это приведет к SqlException в C #:

RAISERROR ('Некоторое сообщение об ошибке ', 16, 1) Затем вы можете перейти к каждой отдельной ошибке в коллекции SqlException.Errors.

Просто замечание: SQL Server продолжит выполнять команды после RAISERROR, если вы не't ВОЗВРАТИТЕ сразу после этого.Если вы не вернетесь, вы можете получить несколько ошибок назад.

...