如何使用Moq返回一个Task<string>?

4

我正在使用 XUnitMoq 对逻辑层的代码进行测试。我的逻辑层还与数据层通信,因此我想模拟接口以保持我的测试简单。

当调用异步任务方法时,我想知道如何返回 Task<string>。我的 GetOrder 方法调用 GetOrderById 方法,但数据层方法返回 null。

编辑: 根据所有反馈,我修改了我的单元测试。现在它可以正常工作了。
我的测试:

public async void GetOrder()
{
    //Arrange 
    string expected = "test";
    
    var mock = new Mock<IRepository>();
    mock.Setup(arg => arg.GetOrderNameById(It.IsAny<int>())
        .Returns(Task.FromResult(expected));
    var survey = new SurveyResult(mock.Object);

    //Act 
    string result = await survey.GetOrderNameById(It.IsAny<int>()));

    //Assert
    Assert.Equal(expected, result);
}

2
请注意,如果您在 string result = await survey.GetResult(score); 后面紧跟着 Assert.Equal(expected, result);,则无需为单元测试返回布尔值。 - Sir Rufo
你的测试没有展示出 async void 的使用。 - Pavel Anikhouski
2个回答

4

使用 Task.FromResult(expected)

mock.Setup(arg => arg.GetScoreByTotalWeighting(value)).Returns(Task.FromResult(expected))

我建议在返回结果时,如果你不关心某个参数,应避免使用value作为参数。你可以使用It.IsAny<int>()这样的形式:

mock.Setup(arg => arg.GetScoreByTotalWeighting(It.IsAny<int>())).Returns(Task.FromResult(expected))

在设置`mock.Setup(arg => arg.GetScoreByTotalWeighting(value))`为`value == 0`后,调用`survey.GetResult(score)`时传入了`score = 50`的参数,可能会导致问题。可以在两个地方都使用`It.IsAny()`来避免这个问题,或者传递相同的值。
解决方法:
使用以下代码设置:
`mock.Setup(arg => arg.GetScoreByTotalWeighting(It.IsAny()))`
并且在调用`survey.GetResult(score)`时,确保传递与`GetScoreByTotalWeighting()`方法内部使用的相同值。
public async Task GetResult()
{
    //Arrange 
    string expected = "test";

    var mock = new Mock<IRetreiveQuestionRepository>();
    mock.Setup(arg => arg.GetScoreByTotalWeighting(It.IsAny<int>()))
        .ReturnsAsync(expected);
    var survey = new SurveyResult(mock.Object);

    //Act 
    string result = await survey.GetResult(It.IsAny<int>());

    //Assert
    Assert.Equal(expected, result);
}

我之前不知道It.IsAny<int>()这个东西,这非常有用,正好是我需要的。 - user12426245

0
你应该能够使用你目前正在使用的 .ReturnsAsync 方法。不知道实现方式,很难说为什么你的主题返回 null。但我建议你仔细检查存根以查看是否指定了传递给真实实现的值,或者是否缺少其他方法的存根。 希望这可以帮到你 :)

2
我添加了真实的实现以澄清我的问题。 - user12426245

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接