模拟方法不传递正确的值
Mocked method do not pass correct value
我想了解模拟在 Xunit 中如何使用 AutoFixture 工作。我已经创建了服务和存储库 类 及其接口。模拟方法应该传递与默认值不同的值。
模拟方法总是传递默认值而不是我在“.Returns()”中写入的值。我已经尝试过 AutoConfiguredMoqCustomization,但它提供了完全随机的值,我无法取回。
Repository.cs
public class Repository : IRepository
{
public int GetInt()
{
return 999;
}
}
Service.cs
public class Service : IService
{
private readonly Repository _repository;
public Service()
{
_repository = new Repository();
}
public string GetStringFromInt()
{
return _repository.GetInt().ToString();
}
}
测试
[Fact]
public void Test()
{
var fixture = new Fixture().Customize(new AutoMoqCustomization());
var repositoryMock = fixture.Create<Mock<IRepository>>();
var service = fixture.Create<Service>();
repositoryMock.Setup(x => x.GetInt()).Returns(1);
var act = service.GetStringFromInt();
Assert.Equal("1", act);
}
如您所见,Repository 中的默认值是 999,我期望从 repositoryMock 得到 1,但结果是“999”而不是“1”。
哦,我明白我的问题了。当我使用自动最小起订量测试服务声明参数时,必须在所有模拟存储库之后
测试
[Theory, AutoMoqData]
public void Test([Frozen] Mock<IRepository> repositoryMock, Service service)
{
...
}
属性
public class AutoMoqDataAttribute : AutoDataAttribute
{
public AutoMoqDataAttribute() : base(GetDefaultFixture)
{
}
private static IFixture GetDefaultFixture()
{
return new Fixture().Customize(new AutoMoqCustomization());
}
}
你做错了 DI,你没有将存储库注入你的服务。
像这样尝试。
public class Repository : IRepository
{
public int GetInt()
{
return 999;
}
}
public class Service : IService
{
IRepository Repository;
public Service(IRepository repository)
{
this.Repository = repository;
}
public string GetStringFromInt()
{
return Repository.GetInt().ToString();
}
}
现在当你模拟 IRepository 时,你可以将它添加到服务中。
您正在构造函数中使用新的 Repository(),因此您正在使用该实现
你应该先冻结你的模拟。当您在 AutoFixture 上调用 Create 时,它每次都会为您创建一个新实例。在修改后的代码中尝试以下操作(您在构造函数中使用该类型的接口)。
public class ServiceTests
{
private readonly IFixture fixture = new Fixture().Customize(new AutoMoqCustomization());
public ServiceTests()
{
fixture.Register<IService>(() => fixture.Create<Service>());
}
[Fact]
public void Test()
{
// Arrange
var repositoryMock = fixture.Freeze<Mock<IRepository>>();
repositoryMock.Setup(x => x.GetInt()).Returns(1);
var service = fixture.Create<IService>();
// Act
var act = service.GetStringFromInt();
// Verify
Assert.Equal("1", act);
}
}
为了检查您是否正确设置了autofixture,您可以在以后的单元测试中尝试以下操作。
var repo1 = fixture.Create<IRepository>();
var repo2 = fixture.Create<IRepository>();
Assert.Equal(repo1.GetHashCode(), repo2.GetHashCode());
如果以上都失败了,说明你还没有冻结一个类型。这些代码行让我在过去省去了很多头疼的事情...
我想了解模拟在 Xunit 中如何使用 AutoFixture 工作。我已经创建了服务和存储库 类 及其接口。模拟方法应该传递与默认值不同的值。
模拟方法总是传递默认值而不是我在“.Returns()”中写入的值。我已经尝试过 AutoConfiguredMoqCustomization,但它提供了完全随机的值,我无法取回。
Repository.cs
public class Repository : IRepository
{
public int GetInt()
{
return 999;
}
}
Service.cs
public class Service : IService
{
private readonly Repository _repository;
public Service()
{
_repository = new Repository();
}
public string GetStringFromInt()
{
return _repository.GetInt().ToString();
}
}
测试
[Fact]
public void Test()
{
var fixture = new Fixture().Customize(new AutoMoqCustomization());
var repositoryMock = fixture.Create<Mock<IRepository>>();
var service = fixture.Create<Service>();
repositoryMock.Setup(x => x.GetInt()).Returns(1);
var act = service.GetStringFromInt();
Assert.Equal("1", act);
}
如您所见,Repository 中的默认值是 999,我期望从 repositoryMock 得到 1,但结果是“999”而不是“1”。
哦,我明白我的问题了。当我使用自动最小起订量测试服务声明参数时,必须在所有模拟存储库之后
测试
[Theory, AutoMoqData]
public void Test([Frozen] Mock<IRepository> repositoryMock, Service service)
{
...
}
属性
public class AutoMoqDataAttribute : AutoDataAttribute
{
public AutoMoqDataAttribute() : base(GetDefaultFixture)
{
}
private static IFixture GetDefaultFixture()
{
return new Fixture().Customize(new AutoMoqCustomization());
}
}
你做错了 DI,你没有将存储库注入你的服务。 像这样尝试。
public class Repository : IRepository
{
public int GetInt()
{
return 999;
}
}
public class Service : IService
{
IRepository Repository;
public Service(IRepository repository)
{
this.Repository = repository;
}
public string GetStringFromInt()
{
return Repository.GetInt().ToString();
}
}
现在当你模拟 IRepository 时,你可以将它添加到服务中。
您正在构造函数中使用新的 Repository(),因此您正在使用该实现
你应该先冻结你的模拟。当您在 AutoFixture 上调用 Create 时,它每次都会为您创建一个新实例。在修改后的代码中尝试以下操作(您在构造函数中使用该类型的接口)。
public class ServiceTests
{
private readonly IFixture fixture = new Fixture().Customize(new AutoMoqCustomization());
public ServiceTests()
{
fixture.Register<IService>(() => fixture.Create<Service>());
}
[Fact]
public void Test()
{
// Arrange
var repositoryMock = fixture.Freeze<Mock<IRepository>>();
repositoryMock.Setup(x => x.GetInt()).Returns(1);
var service = fixture.Create<IService>();
// Act
var act = service.GetStringFromInt();
// Verify
Assert.Equal("1", act);
}
}
为了检查您是否正确设置了autofixture,您可以在以后的单元测试中尝试以下操作。
var repo1 = fixture.Create<IRepository>();
var repo2 = fixture.Create<IRepository>();
Assert.Equal(repo1.GetHashCode(), repo2.GetHashCode());
如果以上都失败了,说明你还没有冻结一个类型。这些代码行让我在过去省去了很多头疼的事情...