如何在Dapper中支持其他IDbConnection方法(使用DapperWrapper)

本文关键字:方法 使用 DapperWrapper IDbConnection 其他 Dapper 支持 | 更新日期: 2023-09-27 18:26:43

我正试图为使用Dapper方法的存储库创建一些单元测试,但我很难弄清楚如何让我的代码接受模拟的DbConnection。我发现DapperWrapper承认了这个问题,并完成了我所需要的大部分内容,但它提供的IDbExecutor接口不包括我在代码中打开和关闭连接所需的一些基本IDbConnection方法。

例如,下面是我的基本存储库类中的一个属性,该属性定义了所有存储库中使用的数据库连接,从工厂检索该连接,并在连接关闭或不存在时打开该连接。此代码不起作用,因为IDbExecutor没有公开Open或Close方法,接口上也不能有State属性。

private IDbExecutor _db;
protected IDbExecutor Db
{
    get
    {
        if (_db == null)
        {
            _db = DbConnectionFactory.GetConnection();
            _db.Open();
        }
        else if (_db != null && _db.State != ConnectionState.Open)
        {
            _db.Open();
        }
        return _db;
    }
    set
    {
        _db = value;
    }
}

有没有一种方法可以扩展或继承IDbExecutor,使我可以引用SQL连接的这些方法和属性(以及在我的mock连接对象中)?还是有更好的方法来解决整个问题?

编辑

下面是我尝试运行的一个测试的示例。我创建了一个实现IDbExecutor的TestExecutor类。在这种情况下,它被设置为返回我们想要的测试值——我们稍后可能会根据我们的测试需求使用工厂来创建它。

[Test]
public void TestGetAllDealsSuccess()
{        
    var executor = new TestExecutor();
    var dealRepo = new DealRepository(executor);
    var deals = dealRepo.GetAllDeals();
    //verify that expected deal data was returned
}

DealRepository基于一个AbstractRepository类,该类包含上面显示的DB属性。

protected AbstractBaseRepository(IDbExecutor conn)
{
    _db = conn;
}

然后在DealRepository中,我们对DB对象运行查询:

var results = Db.Query<Deal>("GetDeals", sprocParameters).ToList();

当调用Db属性时,它会运行我上面原始摘录中的get代码,这会确保对象存在并打开,如果不存在,则创建一个并打开它。这就是我们遇到问题的地方,因为open和State成员在IDbExecutor上不存在。

如何在Dapper中支持其他IDbConnection方法(使用DapperWrapper)

查看DataAbstractions.Dapper.

"围绕Dapper和Dapper.Contrib的轻量级抽象,它还维护行为IDbConnection。"