【问题标题】:Unit testing Entity Framework 6 with context inheriting from IdentityDbContext使用从 IdentityDbContext 继承的上下文对实体框架 6 进行单元测试
【发布时间】:2014-06-04 18:49:10
【问题描述】:

我正在寻找使用 instructions provided here 的 Entity Framework 6 对某些方法进行单元测试。

不过,我的设置略有不同 - 我也在使用 ASP.Net Identity(使用 EF 的默认实现)。因此,我的上下文继承自 IdentityDbContext。

当我运行测试时,我得到一个包含以下详细信息的异常:

Castle.Proxies.IdentityUserLogin: : EntityType 'IdentityUserLogin' has no key defined. Define the key for this EntityType.    
Castle.Proxies.IdentityUserRole: : EntityType 'IdentityUserRole' has no key defined. Define the key for this EntityType.    
IdentityUserLogins: EntityType: EntitySet 'IdentityUserLogins' is based on type 'IdentityUserLogin' that has no keys defined.    
IdentityUserRoles: EntityType: EntitySet 'IdentityUserRoles' is based on type 'IdentityUserRole' that has no keys defined.

我读过,在正常使用中,这些都是在默认的 OnModelCreating 方法中设置的。

但是任何人都可以就在上面链接的方法中说明的模拟上下文中处理这个问题提供建议吗?

谢谢

安迪

【问题讨论】:

  • 您使用的是最小起订量还是类似的东西?
  • 是的,使用最小起订量。我基本上遵循上述问题中链接到的 MSDN 页面中的说明。
  • 我知道这是一年后的事了,但你有没有让这个工作?奇怪的是 POST 对我有效,但 PUT 失败。
  • 我没有。切换到使用 Effort 库来测试 EF 而不是尝试继续使用此方法,部分原因在下面的答案中指出。

标签: c# asp.net entity-framework unit-testing asp.net-identity


【解决方案1】:

正如那篇文章所指出的,当您模拟 EF 类型时,您会完全改变它们的行为:查询作为 LINQ-to-Objects 执行,而不是 LINQ-to-SQL。这意味着您可以轻松编写单元测试,以通过在现实世界中使用失败的代码。一个很好的例子是:

context.Foos.Where(candidate => SomePredicate(candidate));

这意味着您需要完全理解有效的 LINQ-to-SQL 表达式才能编写单元测试,但您编写这些单元测试是因为您想验证您的理解。那么,这真的给你带来了什么?你从这些单元测试中获得了多少价值?我是从一个曾经花了很长时间模拟我的 EF 层却发现一旦涉及到数据库后代码就出错的人的角度来看的。

在我看来,更好的测试策略是创建Gateway 类,作为DbContext 和该上下文的消费者之间的中介。

class FooGateway : IFooGateway
{
    IEnumerable<Foo> GetFoosThatObeySomePredicate() { /* ... */ }
}

Gateways 公开了可以有效模拟的接口。在您的数据消费类中使用这些接口,以便您可以编写高质量的单元测试,然后接受您需要编写集成测试来测试Gateway 类本身:这些测试需要一个真实的数据库,因此您需要基础设施来创建数据库作为测试的一部分。

【讨论】:

  • 感谢 cmets。是的,你指出了这个过程的一个重要警告。在我看来,尽管这样做仍有一些价值。您是对的,一旦引入数据库,通过的测试可能会失败,但失败的测试不会意外通过 - 所以从回归测试的角度来看有一些好处。所以点了,但仍然有兴趣尝试让它发挥作用。
  • 但关键是你最好把时间花在组建一个体面的集成测试基础设施上。
猜你喜欢
  • 2012-10-19
  • 1970-01-01
  • 1970-01-01
  • 2017-07-03
  • 1970-01-01
  • 2012-08-25
  • 1970-01-01
  • 2018-03-27
  • 1970-01-01
相关资源
最近更新 更多