首页 > 解决方案 > NSubstitute 无法确定项目“运行所有测试”时要使用的参数规范

问题描述

我有一个测试方法:

public class MyTests
{
  [Fact]
  public void Test_Method()
  {
     // Arrange 
     var returns = Result.Ok(new List<string>() { "Test" }.AsEnumerable());  

     this.mockService.ServiceMethod(Arg.Any<Guid>()).Returns(returns); //returns Result<IEnumerable<string>>


     //Act
     var actResult = this.anotherService.Backup();

     //Assert
     Assert.True(actResult.Success);
  }
  ...

要测试此方法:

public class AnotherService
{

  internal Result Backup()
  {
    var ret = this.mockService.ServiceMethod().Value;

    ...

    return Result.Ok();
  }

当我只为Test_Method()一切正常运行该方法时。当我尝试为整个MyTests班级运行时,我在此引用方法上收到以下错误:

NSubstitute.Exceptions.AmbiguousArgumentsException: '无法确定要使用的参数规范。请对同一类型的所有参数使用规范。

我相信这个问题与这种情况无关: How NOT to use argument matchers

NSubstitute.Analyzers:

NSubstitute.Analyzers

有什么可做的吗?

标签: mockingnsubstitute

解决方案


评论和问题更新后更新:

如果在对我的原始答案进行更改后仍然存在问题,则可能是夹具中的另一个测试导致了问题。我建议将NSubstitute.Analyzers添加到项目中,这样可以在编译时使用 Roslyn 发现 NSubstitute 使用的潜在问题。(我建议将这个添加到所有使用 NSubstitute 的项目中;它真的可以帮助避免很多潜在的问题!)

如果 NSubstitute.Analyzers 没有找到错误,那么不幸的是,我们只剩下一些手动步骤,如本答案中所述。


原答案:

参数匹配器需要与指定调用或断言接收到调用结合使用。

您发布的测试有两个可能导致此问题的地方:

  • 正如@Fabio 在评论中提到的那样,在mockService.ServiceMethod()没有相应的.Returns.
  • 参数匹配器用于实际调用anotherService.Backup()

尝试像这样修改测试:

  [Fact]
  public void Test_Method()
  {
     // Arrange       
     this.mockService.ServiceMethod(Arg.Any<Guid>()).Returns(...);
     //                               ^- Arg matcher   ^- so need Returns()

     //Act
     var actResult = this.anotherService.Backup(Guid.NewGuid());
     //         Do not use arg matchers for real calls -^

     //Assert
     Assert.True(actResult.Success);
  }

您的夹具中可能还有另一个导致此问题的原因,但是参数匹配器的这两种用法肯定不会有帮助!

您提到的参数匹配器文档中描述了这些问题;如果文档在这些方面不清楚,请提出改进​​本节的任何建议。从其他角度获取有关文档的输入非常有用,因此您在这方面所做的任何贡献都将不胜感激!


推荐阅读