1

我正在尝试用 NSubstitute替换调用Any(),但测试失败并显示为IDBSet<T>ArgumentNullException

测试名称:TestMethod1 测试全名:Clientmanagement.Tests.UnitTest1.TestMethod1 测试源:c:\develop\Clientmanagement\Clientmanagement.Tests\UnitTest1.cs:第 12 行测试结果:失败测试持续时间:0:00:00.3701927

结果消息:测试方法 Clientmanagement.Tests.UnitTest1.TestMethod1 抛出异常:System.ArgumentNullException:值不能为空。参数名称:参数结果 StackTrace:在 System.Linq.Expressions.Expression.RequiresCanRead(Expression expression, String paramName) at System.Linq.Expressions.Expression.ValidateOneArgument(MethodBase method, ExpressionType nodeKind, Expression arg, ParameterInfo pi)
at System。 Linq.Expressions.Expression.ValidateArgumentTypes(MethodBase 方法,ExpressionType nodeKind,ReadOnlyCollection 1 参数)在 System.Linq.Expressions.Expression.Call(Expression 实例,MethodInfo 方法,Expression[] 参数)在 System.Linq.Queryable.Any[TSource ](可查询1& arguments)
at System.Linq.Expressions.Expression.Call(Expression instance, MethodInfo method, IEnumerable
1 source, Expression1 谓词)在 c:\develop\Clientmanagement\Clientmanagement.Tests\UnitTest1.cs:line 19 中的 Clientmanagement.Tests.UnitTest1.TestMethod1()

这是我的测试方法的样子

public void EnsureThatIdentifierIsUnique() {
  IClientContext context = Substitute.For<IClientContext>();

  IDbSet<Client> clients = Substitute.For<IDbSet<Client>>();

  context.Clients.Returns(clients);

  clients.Any(p=>p.Identifier == "Test").Returns(true);  // this line throws the exception

  ClientService service = new ClientService(context);

  service.CreateClient("Test");
}

现在我的问题是是否可以IQueryable用 NSubstitute 替代方法?我的测试方法设置错了吗?

4

1 回答 1

1

现在我的问题是是否可以用 NSubstitute 替换 IQueryable 的方法?

Any不是上的方法IQueryable。它是一种扩展方法 - 一种静态方法,就像它是一个实例方法一样被调用。因此,除非 NSubstitute 可以以某种方式模拟静态方法(如Typemock Isolator那样),否则您将遇到问题。

一个真正智能的面向 LINQ 的模拟系统基本上可以在生产代码提供类似的表达式树时提供虚假信息并对其做出Queryable响应 - 但它会非常脆弱。如果可能的话,最好使用内存数据库。

通常,如果另一个序列是等效的,则不应依赖生产代码进行精确的调用序列。例如,将您的生产代码编写

clients.Where(p=>p.Identifier == "Test").Any()

它不那么可读,但它基本上等同于Any使用谓词调用。您的测试应该能够实现生产代码所达到的效果,而不是实现它所需的确切步骤。

于 2013-09-12T06:40:20.830 回答