26

我有以下代码来测试数据库连接,它会定期运行以测试数据库可用性:

private bool CheckDbConn()
{
   SqlConnection conn = null;
   bool result = true;

   try
   {
       conn = DBConnection.getNewCon();
       ConnectionState conState = conn.State;

       if (conState == ConnectionState.Closed || conState == ConnectionState.Broken)
       {
          logger.Warn(LogTopicEnum.Agent, "Connection failed in DB connection test on CheckDBConnection");
          return false;
       }             
   }
   catch (Exception ex)
   {
      logger.Warn(LogTopicEnum.Agent, "Error in DB connection test on CheckDBConnection", ex);
      return false; // any error is considered as db connection error for now
   }
   finally
   {
      try
      {
         if (conn != null)
         {
            conn.Close();
         }
      }
      catch (Exception ex)
      {
         logger.Warn(LogTopicEnum.Agent, "Error closing connection on CheckDBConnection", ex);
         result = false;
      }
   }
   return result;
}

和:

static public SqlConnection getNewCon()
{
    SqlConnection newCon = new SqlConnection();
    newCon.ConnectionString = DBConnection.ConnectionString; // m_con.ConnectionString;
    newCon.Open();
    return newCon;
}

我的问题是:这会按预期工作吗?

具体来说,我担心ConnectionState. 状态是否可能是:正在连接(因为Open()是同步的)?

在这种情况下我该怎么办?

4

7 回答 7

54

你可以这样试试。

    public bool IsServerConnected()
    {
        using (var l_oConnection = new SqlConnection(DBConnection.ConnectionString))
        {
            try
            {
                l_oConnection.Open();
                return true;
            }
            catch (SqlException)
            {
                return false;
            }
        }
    }
于 2013-04-23T13:56:37.333 回答
13

SqlConnectionSqlException当它无法连接到服务器时会抛出一个。

public static class SqlExtensions
{
    public static bool IsAvailable(this SqlConnection connection)
    {
        try
        {
            connection.Open();
            connection.Close();
        }
        catch(SqlException)
        {
            return false;
        }

        return true;
    }
}

用法:

using(SqlConnection connection = GetConnection())
{
    if(connection.IsAvailable())
    {
        // Success
    }
}
于 2013-04-23T13:58:15.840 回答
11

您的代码看起来不错,但您确实需要使用 IDisposable 模式,以及一些命名约定:

private bool CheckDbConnection(string connectionString)
{
    try
    {
        using(var connection = new SqlConnection(connectionString))
        {
            connection.Open();
            return true;
        }
    }
    catch (Exception ex)
    {
        logger.Warn(LogTopicEnum.Agent, "Error in DB connection test on CheckDBConnection", ex);
        return false; // any error is considered as db connection error for now
    }
}

并且connection.Close()不应该扔。只需使用该using块,您就可以了。

无需测试Close状态,因为您刚刚打开它。
更多关于Broken状态:

Broken 与数据源的连接已断开。这只能在打开连接后发生。处于这种状态的连接可能会关闭然后重新打开。(此值保留用于产品的未来版本。)

所以真的,不需要测试。

Connecting如果您在多线程上下文中并且您的连接实例是共享的,则该状态可能会被捕获。但这不是你的情况。

于 2013-04-23T14:03:34.100 回答
3

如果调用,此代码不会阻止 UI。

public static class DatabaseExtensions
{
    public static async Task<bool> IsConnectionViable(this string connectionStr)
    {
        await using var sqlConn = new SqlConnection(connectionStr);
        return await sqlConn.IsConnectionViable();
    }

    public static async Task<bool> IsConnectionViable(this SqlConnection connection)
    {
        var isConnected = false;

        try
        {
            await connection.OpenAsync();
            isConnected = (connection.State == ConnectionState.Open);
        }
        catch (Exception)
        {
            // ignored
        }

        return isConnected;
    }
}
于 2021-01-30T05:53:01.243 回答
0

此代码适用于 Mysql。

public class Program
{
string connection = "SERVER=localhost; user id=root; password=; database=dbname";
private void Form1_Load(object sender, System.EventArgs e)
{
checkifconnected();
}

private void checkifconnected()
{
MySqlConnection connect = new MySqlConnection(connection);
try{
connect.Open();
MessageBox.Show("Database connected");
}
catch
{
MessageBox.Show("you are not connected to database");
}
}

public static void Main()
{

}
}
于 2019-01-21T21:30:24.660 回答
0

我正在使用@Ramesh Durai的解决方案,但发现至少在我的设置中(应用程序启动后定期调用/测试应用程序;使用.Net 3.5和Sql Server 2012数据库)使IsConnected()数据库脱机后的第一次调用正在返回true. 但是,它在ExecuteScalar()下面的行中抛出了预期的异常:

public bool IsConnected() {
    using (var conn = new SqlConnection(DBConnection.ConnectionString)) {
        using (var cmd = New SqlCommand("SELECT 1", conn)) {
            try {
                conn.Open();
                cmd.ExecuteScalar();
                return true;
            } catch (SqlException) {
                return false;
            }
        }
    }
}
于 2018-03-05T01:51:48.983 回答
0

实际上,在 Visual Studio 中,连接类具有 sonnectionstate 属性。

当连接状态改变时,会触发连接状态改变事件。

您可能想查看这篇文章。

https://msdn.microsoft.com/en-us/library/aa326268(v=vs.71).aspx

于 2016-07-18T20:22:34.390 回答