Db连接对象的生命周期

时间:2014-10-20 11:46:30

标签: c# sql ado.net inversion-of-control structuremap

详细信息 - 我在C#中有一个SQL数据库帮助程序,其中包含一个建立连接的方法

    public void EstablishConnection()
    {

        oConnection = oFactory.CreateConnection();

        if (oConnection.State == ConnectionState.Closed)
        {
            oConnection.ConnectionString = StringConnection;
            oConnection.Open();
            oConnectionState = ConnectionState.Open;
        }
    }

对于像(ExecuteNonQuery等)这样的db方法的调用,这是典型方法的样子

  public DataSet DataAdapter(CommandType cmdType, string cmdText, Parameters[] cmdParms)
    {

        DbDataAdapter dda = null;
        try
        {
            EstablishFactoryConnection();
            dda = oFactory.CreateDataAdapter();
            PrepareCommand(false, cmdType, cmdText, cmdParms);

            dda.SelectCommand = oCommand;
            DataSet ds = new DataSet();
            dda.Fill(ds);
            return ds;
        }
        catch (Exception ex)
        {
            throw ex;
        }
        finally
        {
            if (null != oCommand)
                oCommand.Dispose();
            CloseFactoryConnection();
        }
    }

和CloseFactoryConnection();方法如下所示

 public void CloseFactoryConnection()
    {
        //check for an open connection            
        try
        {
            if (oConnection.State == ConnectionState.Open)
            {
                oConnection.Close();
                oConnectionState = ConnectionState.Closed;
            }
        }
        catch (DbException oDbErr)
        {
            //catch any SQL server data provider generated error messag
            throw new Exception(oDbErr.Message);
        }
        catch (System.NullReferenceException oNullErr)
        {
            throw new Exception(oNullErr.Message);
        }
        finally
        {
            if (null != oConnection)
                oConnection.Dispose();
        }
    }

问题 - 我在我的所有存储库中都使用了这个类(DBHelper),其中IOC容器构造函数注入了它。这些实例的生活方式是HttpContextLifecycle(我使用的是Structuremap,它表示这种生活方式意味着将为每个HttpContext创建一个实例。在HttpContext.Items集合中缓存实例。)

这是我正在使用的数据库连接类的正确生活方式吗?

创建连接/打开它/关闭它的类应该实例化为单例吗?或按要求?

这些数据库连接建立类的普遍接受的生活方式是什么?我使用的是ado.net而且没有ORM。

谢谢

1 个答案:

答案 0 :(得分:2)

由于ADO.NET已使用连接池,因此无需缓存/重用DbConnection个实例。鉴于此,您的课程似乎没有添加任何有用的东西,而不是简单地写出代码 - 您唯一要抽象的是连接字符串,并且由此充分处理使其可配置(ConnectionStrings["DatabaseName"])。

除了缺乏附加值,你的班级还有其他问题。捕获NullReferenceException是一个很大的禁忌 - NullReferenceException表示代码中存在严重错误,应该通过调查崩溃来解决,而不是将其作为另一个例外包装(当你包装时,不要使用Exception,因为它是非特定的,客户端无法捕获它而不会捕获所有内容,这是另一件坏事。当然,更好的是,应该通过适当检查null(见What is a NullReferenceException, and how do I fix it?

来防止这种情况发生。

要了解为什么您的课程可能没用,请考虑CloseFactoryConnection可以简化为以下内容而不会造成任何功能损失:

public void CloseFactoryConnection() {
    using (oConnection) { }
}

因此,要对您的问题给出一个广泛的答案:如果您不使用ORM,您可能根本不想要一个用于建立数据库连接的课程,除了您已经使用的课程之外拿到。如果您想使用依赖注入来获取数据,请不要在此级别使用它,但是在对象级别 - 您希望能够完全不使用数据库,而不仅仅是从{ {1}}已创建。