Moq 正在进行方法调用和 returning 真实数据,而不是 Setup 中的 return 数据

Moq is making method call and returning real data, and not the return data in Setup

我正在尝试 return 静态声明的 NWatchNativeNode[] 数组,但 Moq 似乎实际上是在调用用于获取真实系统数据的真实方法。是不是下面的设置不正确?

我想确定什么时候

GetNodesInCriticalCondition()被调用,criticalNodes1被return编辑。

单元测试代码

var criticalNodes1 = new NWatchNativeNode[]
{
    factory.CreateNativeNode(NWatchNodeType.NetworkSwitch,
        "MySwitch",
        "MyAlias",
        12345
        ),
    factory.CreateNativeNode(NWatchNodeType.NetworkSwitch,
        "MySwitch2",
        "MyAlias2",
        54321
        ),
};

var mock = new Mock<NWatchCasModelStatusScheduleEntry>(_application);
mock.Setup(x => x.GetNodesInCriticalCondition()).Returns(criticalNodes1);

var nodes = mock.Object.GetNodesInCriticalCondition();
Assert.AreEqual(2, nodes.Length);  // This should return true

根据您的要求,这里有一个如何使用 Moq 进行测试的快速示例。

让我们先做一些 classes 和接口来测试。

public interface IFoo
{
    IEnumerable<int> GetFoos();
}

public class Foo : IFoo
{
    public IEnumerable<int> GetFoos()
    {
        return Enumerable.Range(1, 10);
    }
}

public class Bar
{
    private readonly IFoo foo;

    public Bar(IFoo foo)
    {
        this.foo = foo;
    }

    public IEnumerable<int> SquareFoos()
    {
        foreach(var item in foo.GetFoos())
        {
            yield return item * item;
        }
    }
}

现在,Bar 依赖于 IFoo 接口。现在我们想在 Bar class 上测试 SquareFoos 的功能。这是我们正在测试的主题。我们要模拟的是传递给Bar的构造函数的IFoo接口。这为我们提供了以下单元测试设置。

// Arrange
var mock = new Mock<IFoo>();
mock.Setup(m => m.GetFoos()).Returns(Enumerable.Range(1, 2));

var sut = new Bar(mock.Object);

// Act
var results = sut.SquareFoos().ToList();

// Assert
Assert.AreEqual(2, results.Count);

在这种情况下,我们模拟了 GetFoos returns 以允许我们测试我们的 Bar class.

Mock returns 真实系统数据的最可能原因是您的方法 GetNodesInCriticalCondition() 未声明 [​​=12=]。

为了Moq能够设置方法调用,这些方法必须是virtual,否则无法覆盖它们,因此无法拦截它们,这导致原始方法被调用。

编辑:
如果您的方法是 internal,您必须将其访问权限授予 单元测试项目Moq.
您可以通过添加
[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2")]
[assembly: InternalsVisibleTo("TestProjectNameSpace")]
到您正在为其创建模拟的项目的 AssemblyInfo.cs 文件。