2011-05-11 34 views
4

我们有一个相当复杂的接口层次结构,我努力让Moq做我想做的事情。Moq - 无法遍历隐藏的IEnumerable

我有一个接口IReservation,它延伸IRulesReservation,并隐藏其枚举器与另一种类型的新实现。

public interface IReservation : IRulesReservation 
{ 
    new IEnumerator<IRoutePart> GetEnumerator(); 
} 

IRulesReservation延伸IEnumerable

public interface IRulesReservation : IEnumerable<IRulesRoutePart> 
{ 
} 

我想要测试的方法需要在IReservation,但在不同的点需要访问IEnumerable<IRulesRoutePart>。我的模拟是建立像这样:

m_mock = new Mock<IReservation>(); 
m_mock.As<IRulesReservation>().Setup(r => r.GetEnumerator()).Returns(routeParts.Select(rp => (IRulesRoutePart)rp).GetEnumerator()); 

在这个例子中,routeParts是来自Mock<IRouteParts>对象都设置有.As<IRulesRoutePart>()IRouteParts列表。

每当我在函数中得到一点代码时,我会使用枚举器进行测试,它将遍历迭代,就像集合是空的一样。

我在做什么错误的设置?或者,Moq无法处理以这种方式隐藏的统计员?


编辑:一些奇怪的行为在模拟运行测试代码时,我刚刚注意到:

Assert.That((reservation.Object as IRulesReservation).Count() == 8); 
Assert.That((reservation.Object as IEnumerable<IRulesRoutePart>).Count() == 8); 

第一行会通过,但第二线将失败。 我试图改变模拟专门设置一个枚举的IEnumerable<IRulesRoutePart>,但没有效果:

m_mock.As<IEnumerable<IRulesRoutePart>>().Setup(r => r.GetEnumerator()).Returns(routeParts.Select(rp => (IRulesRoutePart)rp).GetEnumerator()); 
+0

您是否发现过关于此的其他信息?我遇到了同样的问题,试图找出解决方法。 – poindexter12 2011-10-03 22:30:10

+0

@ poindexter12 - 我从来没有设法解决这个问题,但是我们后来发现Moq会缓存第一次调用模拟GetEnumerator()时得到的枚举器。这意味着后续调用将返回相同的枚举数,这可能是为什么我在后续调用中获得不同的行为。为了解决这个问题,你可以模拟GetEnumerator()来返回一个创建一个新的Enumerator的匿名方法,而不是像上面的示例代码那样直接调用GetEnumerator()的具体实现。祝你好运! – Coxy 2011-10-04 00:25:27

回答

1

请问您设置的回报实际上有数据的对象?这可能是你的问题。

+0

它确实是这样的,在这个例子中,routeParts是一个来自模拟的IRouteParts的列表,它也被设置为()。 – Coxy 2011-05-11 04:37:13

+0

某处必须填充要由您的设置返回的数据。你在哪里用假数据创建一个irouteparts的填充列表? – mluker 2011-05-11 04:45:13

+0

不确定它是如何相关的,但IRouteParts的列表事先已创建,并保存在该示例中名为routeParts的变量中。 – Coxy 2011-05-11 05:01:41