Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sqlite/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
带有C#-Sqlite的NHibernate在>;中没有数据库连接。NET 2.0_Nhibernate_Sqlite - Fatal编程技术网

带有C#-Sqlite的NHibernate在>;中没有数据库连接。NET 2.0

带有C#-Sqlite的NHibernate在>;中没有数据库连接。NET 2.0,nhibernate,sqlite,Nhibernate,Sqlite,我试图用C#Sqlite运行我的单元测试,而不是去一个真正的数据库,或者用这篇博文作为指导来模拟我们的数据库层 不幸的是,NHibernate要求连接为DbConnection,而C#-Sqlite驱动程序不提供该连接。我查看了源代码并注意到以下代码: #if NET_2_0 public class SqliteConnection : DbConnection, ICloneable #else public class SqliteConnection : IDbConnectio

我试图用C#Sqlite运行我的单元测试,而不是去一个真正的数据库,或者用这篇博文作为指导来模拟我们的数据库层

不幸的是,NHibernate要求连接为DbConnection,而C#-Sqlite驱动程序不提供该连接。我查看了源代码并注意到以下代码:

#if NET_2_0
public class SqliteConnection : DbConnection, ICloneable
#else
    public class SqliteConnection : IDbConnection, ICloneable
#endif
相应地,作者决定停止使用“旧”基类,并使用IDbConnection、IDbTransaction。。。而不是接口

更改代码是没有选择的,因为这将等同于编写一个必须测试和维护的新客户机


有没有人知道一个简单的解决方案可以让c#sqlite的当前版本与NHibernate一起工作?

我正在使用sqlite进行测试。我有不同的方法

我让NH创建连接,但将其存储在静态变量中,以将其传递给后续会话

当我开始编写测试框架时,我有如下初始化代码:

static IDbConnection staticSqliteConnection;

if (staticSqlliteConnection == null)
{
  sessionFactory.CreateSession().Connection;
}
public class SingleConnectionProvider : DriverConnectionProvider
{
    private static IDbConnection staticConnection = null;

    public static void ResetConnection()
    {
        if (staticConnection == null) return;
        staticConnection.Dispose();
        staticConnection = null;
    }

    public override IDbConnection GetConnection()
    {
        if (staticConnection == null) 
        {
            staticConnection = base.GetConnection();
        }
        if (staticConnection.State != ConnectionState.Open)
        {
            staticConnection.Open();
        }
        return staticConnection;
    }

    protected override void Dispose(bool isDisposing)
    {
        ResetConnection();
    }
}
然后,我遇到了一些问题,在我的生产代码中有太多测试特定的代码(我宁愿没有)。如果将连接传递到会话,则Hi-Lo id生成器也不工作

然后我编写了一个ConnectionProvider类,如下所示:

static IDbConnection staticSqliteConnection;

if (staticSqlliteConnection == null)
{
  sessionFactory.CreateSession().Connection;
}
public class SingleConnectionProvider : DriverConnectionProvider
{
    private static IDbConnection staticConnection = null;

    public static void ResetConnection()
    {
        if (staticConnection == null) return;
        staticConnection.Dispose();
        staticConnection = null;
    }

    public override IDbConnection GetConnection()
    {
        if (staticConnection == null) 
        {
            staticConnection = base.GetConnection();
        }
        if (staticConnection.State != ConnectionState.Open)
        {
            staticConnection.Open();
        }
        return staticConnection;
    }

    protected override void Dispose(bool isDisposing)
    {
        ResetConnection();
    }
}
在单元测试清理方法中,调用
SingleConnectionProvider.ResetConnection()
,这将为下一个测试销毁数据库


整个过程当然不是完全线程安全的。您可以创建任意数量的会话,但应避免同时创建会话。

如果查看代码示例

#if NET_2_0
public class SqliteConnection : DbConnection, ICloneable
#else
    public class SqliteConnection : IDbConnection, ICloneable
#endif

您可以看到,通过定义编译器选项NET_2_0并重新编译,它将公开较旧的接口

我使用System.Data.SQLite和自定义连接提供程序解决了问题:

public class SqLiteInMemoryConnectionProvider : DriverConnectionProvider
{
    public static IDbConnection Connection;

    public static event EventHandler ConnectionReset;

    public static void ResetConnection()
    {
        if(Connection == null) return;

        Connection.Close();
        Connection.Open();

        if(ConnectionReset != null) ConnectionReset(null, new EventArgs());
    }

    public override IDbConnection GetConnection()
    {
        if (Connection == null)
        {
            Connection = base.GetConnection();
        }
        if (Connection.State != ConnectionState.Open)
        {
            Connection.Open();
        }
        return Connection;
    }

    public override void CloseConnection(IDbConnection conn) { }
}
与Stefan Steineggers解决方案的不同之处在于,我正在关闭并重新打开会话以重置,因为如果我只是处理了它,NHibernate无法获得新连接。 此外,我还添加了一个事件,用于在我的factory类中重建会话工厂(将模式导出到数据库)


我不确定到底是什么问题。我可以告诉您如何使用sqlite进行测试…异常是:15:03:28877错误[7]SchemaValidator[(null)]-无法获取数据库元数据System.InvalidCastException:Das Objekt des Typs“Community.CsharpSqlite.SQLiteClient.SqliteConnection“kann nicht in Typ”System.Data.Common.DbConnection“umgewandelt werden”。bei NHibernate.Tool.hbm2ddl.ManagedProviderConnectionHelper.Prepare()bei NHibernate.Tool.hbm2ddl.SchemaValidator.Validate()我是移植C#SQLite的人。我没有意识到还有人需要Net2.0支持,因为所有的forumn评论都鼓励放弃它。此外,在大多数情况下,客户由Mono项目组提供。如果您确实需要Net 2.0定义编译器选项Net_2_0,如果该选项不起作用,请在此处开始讨论或请求。您是否尝试了连接提供程序?成功了吗?至少一开始我没有崩溃。明天我将尝试使用会话工厂并报告;)谢谢您的解决方案,我将尝试自己实现一个连接提供程序来解决这个问题。目前,我刚刚做了一个测试,创建了一个新的会话工厂来测试Sqlite是如何工作的。“fluntly.Configure()..BuildSessionFactory()”抛出上述错误消息。从长远来看,我想用基于sqlite数据库的真实工厂来替换所有模拟的会话工厂。啊-我认为NET_2_0是一个类似于“Debug”的“内置”选项,并试图构建针对.NET 2.0的项目,但没有成功。我星期一试试这个。感谢您为移植SQLite所做的工作!使用NET_2_0进行编译是不可能的:(DbConnectionFactory现在被标记为“内部”-代码不编译。即使我将目标框架更改为2.0。我会在手头有时间时尝试Stefan Steineggers的答案。