Почему событие C# SqlConnection.StateChange НЕ запускается в реальном времени, когда база данных сервера SQL недоступна? - PullRequest
0 голосов
/ 07 мая 2020

У меня есть код, в котором соединение действительно устанавливается, но я продолжаю зацикливаться, чтобы узнать, недоступно ли соединение (т.е. если база данных SQL сервера больше не доступна).

I открыть соединение и подписаться на событие StateChange соединения.

Если в течение 60 секунд (время транзакции), я вручную отключаю базу данных SQL сервера или останавливаю службу SQL сервера , даже тогда событие изменения состояния соединения не вызывается.

Итак, как узнать в реальном времени, недоступна ли SQL серверная база данных или SQL серверная служба, или соединение было потеряно ?

ПРИМЕЧАНИЕ. Я запускаю этот сценарий на SQL Server SSMS в течение 60 секунд, чтобы перевести базу данных в автономный режим.

USE master
GO

ALTER DATABASE [databaseName]
SET OFFLINE WITH ROLLBACK IMMEDIATE
GO

Это код в C#:

private void button10_Click(object sender, EventArgs e)
{
    var options = new TransactionOptions()
        {
            IsolationLevel = System.Transactions.IsolationLevel.RepeatableRead,
            Timeout = TimeSpan.FromSeconds(60)
        };

    using (TransactionScope scope = new TransactionScope(TransactionScopeOption.Required, options))
    {
        using (SqlConnection con = new SqlConnection("Connection String"))
        {
            con.Open();
            con.StateChange += new StateChangeEventHandler(OnConnectionStateChanged);

            while (true)
            {
                Application.DoEvents();
            }
        }
    }
}

private void OnConnectionStateChanged(object sender, StateChangeEventArgs args)
{
    MessageBox.Show("Connection state was changed.");
}

Если я зацикливаюсь и жду, даже если база данных SQL сервера отключена, я не получаю уведомления by SqlConnection.StateChange.

ПРИМЕЧАНИЕ. Непрерывное while l oop предназначено только для имитации любых процессов в транзакции, чтобы проверить, запускается ли состояние соединения или нет.

1 Ответ

1 голос
/ 07 мая 2020
Событие

StateChange никогда не будет запущено, потому что оно предназначено для состояния соединения, а не для экземпляра базы данных, поэтому оно не будет работать как проверка работоспособности, чтобы увидеть, работает ли ваша база данных.

Из документов:

Событие StateChange возникает, когда состояние соединения изменяется с закрытого на открытое или с открытого на закрытое.

Мне неизвестна архитектура этого приложения, но, возможно, вам может помочь Database Probe .

В качестве альтернативы вы можете запустить что-то вроде этого:

private static bool IsServerConnected(string connectionString)
{
    using (SqlConnection connection = new SqlConnection(connectionString))
    {
        try
        {
            connection.Open();
            return true; 
        }
        catch (SqlException)
        {
            return false;
        }
    }
}

Где вы могли бы создать собственное исключение вместо возврата false, если это то, что вам нужно.

Надеюсь, это поможет!

...