NSubstitute在循环中多次调用时返回意外值

时间:2012-07-26 01:51:01

标签: c# loops nsubstitute

我遇到的情况是使用NSubstitute使用输出参数模拟方法时的情况。 我不确定如何最好地在文本中解释它,所以我将使用一些人为的例子和测试用例......

在这个人为的例子中,我将使用一个IDictionary<string, string>的NSubstitute模拟。

private static IDictionary<string, string> GetSubstituteDictionary()
{
    IDictionary<string, string> dict = Substitute.For<IDictionary<string, string>>();

    string s;
    dict.TryGetValue("key", out s).Returns(ci => { ci[1] = "value"; return true; });

    return dict;
}

现在,当我以简单的方式使用这个模拟对象时,它会按预期返回:

[Test]
public void ExampleOne()
{
    var dict = GetSubstituteDictionary();

    string value;
    bool result = dict.TryGetValue("key", out value);

    Assert.That(result, Is.True); // this assert passes.
    Assert.That(value, Is.EqualTo("value")); // this assert passes.
}

但是,当我在for循环中调用相同的代码时,我会遇到一些意想不到的行为:

[Test]
public void ExampleTwo()
{
    var dict = GetSubstituteDictionary();

    for (int i = 0; i < 2; i++)
    {
        string value;
        bool result = dict.TryGetValue("key", out value);

        Assert.That(result, Is.True); // this assert FAILS - unexpected!
        Assert.That(value, Is.EqualTo("value")); // this assert still passes.
    }
}

特别是,Assert.That(result, Is.True);断言在循环的第一次迭代中传递,但在第二次(以及任何后续)迭代时失败。

但是,如果我将string value;行修改为string value = null;,则断言将通过所有迭代。

造成这种异常的原因是什么?这是由于我缺少的C#for循环的一些语义,还是NSubstitute库的问题?

1 个答案:

答案 0 :(得分:4)

原因是value变量在循环中发生变化(通过输出参数设置),因此它不再匹配您存根的调用。

您可以尝试使用.ReturnsForAnyArgs(),但您需要检查存根中的密钥,而不是通过参数匹配器。