C# Moq是一种自动返回的液体

C# Moq是一种自动返回的液体,c#,testing,mocking,moq,iqueryable,C#,Testing,Mocking,Moq,Iqueryable,我正在使用模拟的IQueryable(使用Moq)设置一个测试,我希望在调用时返回它自己。其中(): [SetUp] public void Setup() { mockPocos = new Mock<IQueryable<Poco>>(); mockPocos.Setup(foo => foo.Where(It.IsAny<Expression<Func<Poco, bool>>>())) .R

我正在使用模拟的
IQueryable
(使用Moq)设置一个测试,我希望在调用
时返回它自己。其中()

[SetUp]
public void Setup() {
    mockPocos = new Mock<IQueryable<Poco>>();
    mockPocos.Setup(foo => foo.Where(It.IsAny<Expression<Func<Poco, bool>>>()))
        .Returns(mockPocos.Object);
}
我怎样才能让它工作


编辑:作为对评论的回应,这就是为什么我想这样使用最小起订量

在我正在测试的方法中,我有如下代码:

public int[] MethodToTest(IQueryable<Poco> pocos, MockableDependency dependency)
{
    var mostRecentUpdate = (from poco in pocos
                                select poco.Date_Last_Updated).Max();
    var recentPocos = pocos.Where(x => x.Date_Last_Updated.CompareTo(mostRecentUpdate) >= 0);

    ///...snip...

    result[0] = SomePrivateCalculation(recentPocos.Count);
    result[1] = dependency.DoADifferentCalculation(recentPocos);
}
public int[]MethodToTest(IQueryable poco、MockableDependency)
{
var mostRecentUpdate=(来自pocos中的poco
选择poco.Date_Last_Updated).Max();
var recentPocos=pocos.Where(x=>x.Date\u Last\u Updated.CompareTo(mostRecentUpdate)>=0);
///…剪断。。。
结果[0]=SomePrivateCountation(recentPocos.Count);
结果[1]=依赖性.DOADifferenceCalculation(recentPocos);
}

我已经在模拟
MockableDependency
,所以我实际上不需要担心
Poco
中的
Poco
是什么。但是,我希望能够控制
recentPocos.Count
的值是多少,并且我希望能够知道,在访问
.Count
之前,无论有多少查询运行在
pocos
上,它都将返回相同的值。

MattiasG暗示着解决方案。您应该提供一个可查询的POCO,该POCO将始终生成一个查询,该查询的已知结果将给出您期望的.Count

所以这里的代码中没有显示的东西,是正确完成的;传递POCO的方法也应该被模拟,以提供您可以正确断言的数据

很难找到测试之间的良好平衡。这真的是一种艺术形式。但是,如果您正在使用moq,您应该关注高阶“工作单元”,而不是单个方法内部的情况

换言之。假设您设法使Count始终返回5。然后进行测试,检查依赖项方法中的计数是否为5。它是。你完成了什么?好的,您可以断言Count将返回一个int(我们有点知道它已经在工作了),但是您还没有真正测试您的应用程序代码

但要回答你的实际问题: -您必须创建一个新的接口IMyOwnCustomMockableQuery,其中包含一些到iQuerable的转换器或包装类,然后为IMyOwnCustomMockableQuery创建一个新的linq实现,该实现将您不想模拟的所有调用转发到iQuerable上的exensions


当然,这将非常复杂,需要自己进行测试。=)对于不测试应用程序的测试,似乎有很多工作要做。我不推荐这种方法。

看起来您不想模仿IQueryable,而是LINQ查询。这是什么意思?(我不知道LINQ在封面后面是如何工作的。)我不确定你怎么能用Moq来模拟LINQ查询。我只是提醒你,你想要模拟函数
Where
,这是LINQ提供的一种扩展方法,而不是
IQueryable
的一部分。我认为你的模拟方式太过分了。您应该将模拟策略定位于高阶服务,并能够替换整个子系统。您所做的似乎是试图部分模拟Linq上的各个接口方法,这甚至不是一个实现。我看不出这样做有什么好处。迈克尔·维克多·斯塔伯格:我更新了我的问题以回应你的评论。
public int[] MethodToTest(IQueryable<Poco> pocos, MockableDependency dependency)
{
    var mostRecentUpdate = (from poco in pocos
                                select poco.Date_Last_Updated).Max();
    var recentPocos = pocos.Where(x => x.Date_Last_Updated.CompareTo(mostRecentUpdate) >= 0);

    ///...snip...

    result[0] = SomePrivateCalculation(recentPocos.Count);
    result[1] = dependency.DoADifferentCalculation(recentPocos);
}