为什么moq在其设置中不使用此参数?

时间:2011-11-08 16:09:12

标签: c# tdd mocking moq

我有这个测试

[Fact]
public void Get_if_item_is_not_in_cache_return_null_returns_true()
{
    var repo = new Repository<IProduct>(
        this.factoryMock.Object, 
        this.cacheMock.Object, 
        this.readerMock.Object, 
        this.storageMock.Object);

    var key = 1;
    const string Name = "Product1";
    var date = new DateTime(0, DateTimeKind.Utc);
    var product1 = this.Product; /* returns new Product(
                                  *     "Product1", 
                                  *     new DateTime(0, DateTimeKind.Utc), 
                                  *     new Dictionary<string, decimal> 
                                  *         { { "@1lom", 0m }, { "@2lom", 0m } })     */

    this.cacheMock.Setup(
        m => m.Add(key, product1)).Returns(product1);
    this.cacheMock.Setup(
        m => m.Get<IList<IDictionary<string, object>>>(0)).Returns(null as IList<IDictionary<string, object>>);
    this.cacheMock.Setup(
        m => m.Get<IProduct>(key)).Returns(null as IProduct);
    this.factoryMock.Setup(
        m => m.Create(
            Name, 
            date, 
            this.cacheMock.Object.Get<IList<IDictionary<string, object>>>(0))).Returns(product1);

    var product2 = repo.Get(key, Name, date);

    Assert.Null(product2);
    this.cacheMock.VerifyAll();
    this.factoryMock.VerifyAll();
}

我得到了这个例外

  
    

Moq.MockVerificationException:以下设置未匹配:

         

ICache m =&gt; m.Add(1,)

  

调用包含第二个参数,但为什么moq在安装过程中无法识别?当我省略.Add的设置时,它可以工作吗?


更新 这是执行的代码

public virtual T Get(int key, string productName, DateTime date)
{
    return this.Cache.Get<T>(key) ?? this.PersistenStorage.Query(productName, date) ?? this.CreateNewCacheItem(productName, date);
}

protected virtual T CreateNewCacheItem(string productName, DateTime date)
{
    var product = this.Factory.Create(productName, date, this.Cache.Get<IList<IDictionary<string, object>>>(this.RawDataKey));
    return this.Cache.Add(product.GetHashCode(), product);
}

1 个答案:

答案 0 :(得分:5)

当你在Moq中使用安装程序时,你会说&#34;当你看到这些参数时,请回复此信息&#34;。对于像Product这样的引用类型,它只有在看到确切的实例时才会起作用。因此,当Get运行时,它会在内部创建一个新的Product实例,并且不符合您对product1的期望。

正如Chris所提到的,如果您在安装程序中使用It.IsAny<Product>(),它将匹配新实例并按预期工作。