为什么在 Moq 中使用非内联 It.IsAny<T> 无法正常工作?
Why does using an non-inlined It.IsAny<T> in Moq not work correctly?
将 It.IsAny<T>()
分配给变量以在模拟对象的 Setup
中使用无法按预期工作:下面显示的测试失败。
但是,如果我内联 anyString
变量,测试就会通过。这是怎么回事?
public class MyService
{
private readonly IDependency _dependency;
public MyService(IDependency dependency)
{
_dependency = dependency;
}
public string UseTheDependency(string input)
{
return _dependency.GetValue(input);
}
}
public interface IDependency
{
string GetValue(string input);
}
public class Tests
{
[Test]
public void TestTheTestClass()
{
var mockDependency = new Mock<IDependency>();
var anyString = It.IsAny<string>();
mockDependency.Setup(x => x.GetValue(anyString)).Returns("expected value");
var service = new MyService(mockDependency.Object);
var result = service.UseTheDependency("something random");
Assert.That(result, Is.EqualTo("expected value"));
}
}
这是因为 Setup
方法采用 Linq 表达式 (Expression<Func<IDependency, string>>
) 作为参数,而不是委托 (Func<IDependency, string>
)。它允许 Moq 检查抽象语法树以了解正在配置的调用。如果您使用在表达式外声明的变量,Moq 不知道您使用了 It.IsAny
,它只会看到 null
(从技术上讲,它会看到对 anyString
字段的访问封装捕获的局部变量的对象,并且该字段仅包含 null
).
将 It.IsAny<T>()
分配给变量以在模拟对象的 Setup
中使用无法按预期工作:下面显示的测试失败。
但是,如果我内联 anyString
变量,测试就会通过。这是怎么回事?
public class MyService
{
private readonly IDependency _dependency;
public MyService(IDependency dependency)
{
_dependency = dependency;
}
public string UseTheDependency(string input)
{
return _dependency.GetValue(input);
}
}
public interface IDependency
{
string GetValue(string input);
}
public class Tests
{
[Test]
public void TestTheTestClass()
{
var mockDependency = new Mock<IDependency>();
var anyString = It.IsAny<string>();
mockDependency.Setup(x => x.GetValue(anyString)).Returns("expected value");
var service = new MyService(mockDependency.Object);
var result = service.UseTheDependency("something random");
Assert.That(result, Is.EqualTo("expected value"));
}
}
这是因为 Setup
方法采用 Linq 表达式 (Expression<Func<IDependency, string>>
) 作为参数,而不是委托 (Func<IDependency, string>
)。它允许 Moq 检查抽象语法树以了解正在配置的调用。如果您使用在表达式外声明的变量,Moq 不知道您使用了 It.IsAny
,它只会看到 null
(从技术上讲,它会看到对 anyString
字段的访问封装捕获的局部变量的对象,并且该字段仅包含 null
).