使用 Moq 和 xUnit 对服务进行单元测试
Unit Testing a Service with Moq & xUnit
抱歉,这可能是一个非常业余的问题,但我很难理解如何正确使用 Moq。作为一个整体,我对单元测试还很陌生,但我想我开始来掌握它。
所以这是我的问题...我有下面的代码片段,它在 Visual Studio 中使用 TestServer
,我将其用于单元测试...我正在尝试模拟IGamesByPublisher
以便我的测试不依赖于存储库中的数据(或者模拟 GamesByPublisher
会更好吗?...或者我是否需要两者都做?)
public static TestServerWithRepositoryService => new TestServer(services =>
{
services.AddScoped<IGamesByPublisher, GamesByPublisher();
}).AddAuthorization("fake.account", null);
[Fact] // 200 - Response, Happy Path
public async Task GamesByPublisher_GamesByPublisherLookup_ValidRequestData_Produces200()
{
// Arrange
var server = ServerWithRepositoryService;
// Act
var response = await server.GetAsync(Uri);
// Assert
Assert.NotNull(response);
Assert.Equal(HttpStatusCode.OK, response.StatusCode);
}
这里是IGamesByPublisher
public interface IGamesByPublisher interface.
{
Task<IEnumerable<Publisher>> Execute(GamesByPublisherQueryOptions options);
}
}
我试过了
public static TestServerWithRepositoryService => new TestServer(services =>
{
services.AddScoped<Mock<IGamesByPublisher>, Mock<GamesByPublisher>>();
}).AddAuthorization("fake.account", null);
然后我尝试了
// Not exactly what I attempted, but that code is long gone...
var mock = new Mock<IGamesByPublisher >();
var foo = new GamesByPublisherQueryOptions();
mock.Setup(x => x.Execute(foo)).Returns(true);
我并没有真正找到关于使用 Moq 的优秀文档,只是 GitHub 上的快速入门指南,我不确定如何应用它(可能是我自己的经验水平有问题...... .).
我显然缺少一些使用 Moq 的基础知识...
你很接近。
public static TestServerWithRepositoryService => new TestServer(services => {
var mock = new Mock<IGamesByPublisher>();
var publishers = new List<Publisher>() {
//...populate as needed
};
mock
.Setup(_ => _.Execute(It.IsAny<GamesByPublisherQueryOptions>()))
.ReturnsAsync(() => publishers);
services.RemoveAll<IGamesByPublisher>();
services.AddScoped<IGamesByPublisher>(sp => mock.Object);
}).AddAuthorization("fake.account", null);
上面创建了模拟,将其预期行为设置为 return 发布者列表,任何时候 Execute
被调用 GamesByPublisherQueryOptions
。
然后删除所需接口的所有注册以避免冲突,然后在请求解析接口时将服务注册到 return 模拟。
抱歉,这可能是一个非常业余的问题,但我很难理解如何正确使用 Moq。作为一个整体,我对单元测试还很陌生,但我想我开始来掌握它。
所以这是我的问题...我有下面的代码片段,它在 Visual Studio 中使用 TestServer
,我将其用于单元测试...我正在尝试模拟IGamesByPublisher
以便我的测试不依赖于存储库中的数据(或者模拟 GamesByPublisher
会更好吗?...或者我是否需要两者都做?)
public static TestServerWithRepositoryService => new TestServer(services =>
{
services.AddScoped<IGamesByPublisher, GamesByPublisher();
}).AddAuthorization("fake.account", null);
[Fact] // 200 - Response, Happy Path
public async Task GamesByPublisher_GamesByPublisherLookup_ValidRequestData_Produces200()
{
// Arrange
var server = ServerWithRepositoryService;
// Act
var response = await server.GetAsync(Uri);
// Assert
Assert.NotNull(response);
Assert.Equal(HttpStatusCode.OK, response.StatusCode);
}
这里是IGamesByPublisher
public interface IGamesByPublisher interface.
{
Task<IEnumerable<Publisher>> Execute(GamesByPublisherQueryOptions options);
}
}
我试过了
public static TestServerWithRepositoryService => new TestServer(services =>
{
services.AddScoped<Mock<IGamesByPublisher>, Mock<GamesByPublisher>>();
}).AddAuthorization("fake.account", null);
然后我尝试了
// Not exactly what I attempted, but that code is long gone...
var mock = new Mock<IGamesByPublisher >();
var foo = new GamesByPublisherQueryOptions();
mock.Setup(x => x.Execute(foo)).Returns(true);
我并没有真正找到关于使用 Moq 的优秀文档,只是 GitHub 上的快速入门指南,我不确定如何应用它(可能是我自己的经验水平有问题...... .).
我显然缺少一些使用 Moq 的基础知识...
你很接近。
public static TestServerWithRepositoryService => new TestServer(services => {
var mock = new Mock<IGamesByPublisher>();
var publishers = new List<Publisher>() {
//...populate as needed
};
mock
.Setup(_ => _.Execute(It.IsAny<GamesByPublisherQueryOptions>()))
.ReturnsAsync(() => publishers);
services.RemoveAll<IGamesByPublisher>();
services.AddScoped<IGamesByPublisher>(sp => mock.Object);
}).AddAuthorization("fake.account", null);
上面创建了模拟,将其预期行为设置为 return 发布者列表,任何时候 Execute
被调用 GamesByPublisherQueryOptions
。
然后删除所需接口的所有注册以避免冲突,然后在请求解析接口时将服务注册到 return 模拟。