gpt4 book ai didi

unit-testing - 单元测试 DbContext

转载 作者:行者123 更新时间:2023-12-03 06:03:00 25 4
gpt4 key购买 nike

我研究了一些有关可用于对 DbContext 进行单元测试的技术的信息。我想向上下文添加一些内存中数据,以便我的测试可以针对它运行。我正在使用数据库优先方法。

我发现最有用的两篇文章是 thisthis 。该方法依赖于创建 MyContext 和 FakeContext 都将实现的 IContext 接口(interface),从而允许模拟上下文。

但是,我试图避免使用存储库来抽象 EF,如 pointed by some人们,因为 EF 4.1 已经通过 DbSet 和 DbContext 实现了存储库和工作单元模式,我真的很想保留 EF 团队实现的所有功能,而不必自己使用通用存储库来维护它们,就像我在其他中所做的那样项目(这有点痛苦)。

使用 IContext 将会引导我走上同样的道路(或者不会?)。

我考虑过创建一个继承自主 MyContext 的 FakeContext,从而利用其下面的 DbContext 来运行我的测试而无需访问数据库。我找不到类似的实现,所以我希望有人可以帮助我。

我是否做错了什么,或者这是否会导致我遇到一些我没有预料到的问题?

最佳答案

问自己一个问题:你要测试什么?

您提到了 FakeContext 和 Mocking the context - 为什么要同时使用两者?这些只是执行相同操作的不同方法 - 提供仅测试上下文的实现。

还有一个更大的问题 - 伪造或模拟上下文或集合只有一个结果:您不再测试真实的代码。

简单的例子:

public interface IContext : IDisposable
{
IDbSet<MyEntity> MyEntities { get; }
}

public class MyEntity
{
public int Id { get; set; }
public string Path { get; set; }
}

public class MyService
{
private bool MyVerySpecialNetMethod(e)
{
return File.Exists(e.Path);
}

public IEnumerable<MyEntity> GetMyEntities()
{
using (IContext context = CreateContext())
{
return context.MyEntities
.Where(e => MyVerySpecialNetMethod(e))
.Select(e)
.ToList();
}
}
}

现在想象一下您的 SUT 中有这个(被测系统 - 在单元测试中它是一个单元 = 通常是一个方法)。在测试代​​码中,您提供 FakeContextFakeSet 并且它将起作用 - 您将进行绿色测试。现在,在生产代码中,您将提供另一个派生的 DbContextDbSet,并且您将在运行时收到异常。

为什么?因为通过使用 FakeContext,您还更改了 LINQ 提供程序,而不是 LINQ to Entities,您正在运行 LINQ to Objects,因此调用无法转换为 SQL 的本地 .NET 方法以及许多其他 LINQ 功能都可以工作。在 LINQ to Entities 中不可用!您还可以在数据修改中发现其他问题 - 引用完整性、级联删除等。这就是为什么我认为处理上下文/LINQ to Entities 的代码应该包含集成测试并针对真实数据库执行。

关于unit-testing - 单元测试 DbContext,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6766478/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com