我正在使用 Autofac
国际奥委会
这是我的容器启动器类,其职责是注册依赖项。
public class ContainerInit
{
public static IContainer BuildContainer()
{
var conFac = new ContainerFactory();
var builder = new ContainerBuilder();
builder.Register(conFac).As<IContainerFactory>().SingleInstance();
builder.Register(c=> new MainClass(conFac)).As<IMainClass>().SingleInstance();
builder.Register(c=> new Database(conFac)).As<IDatabase>().SingleInstance();
var logger = LoggUtil.CreateLogger();
builder.Register(logger).As<ILogger>().SingleInstance();
var container = builder.Build();
ContainerFactory.SetContainer(container);
return container;
}
}
这种方法的问题是,我需要通过
IContainerFactory
我在我的应用程序中使用的每个类的构造函数如下 public class MainClass: IMainClass
{
private readonly ILogger _logger;
private readonly IDatabase _db;
public MainClass(IContainerFactory containerFactory)
{
_logger = containerFactory.GetInstance<ILogger>();
_db = containerFactory.GetInstance<IDatabase>(); //example
}
public AddDetails(Data data)
{
//do some business operations
_db.Add(data);
_logger.Information("added");
}
}
所以很难对这些类进行单元测试。
怎样才能想出一个好的解决方案?
最佳答案
更好的方法是将类中所需的依赖项传递给构造函数:
public class MainClass : IMainClass
{
private readonly ILogger _logger;
private readonly IDatabase _db;
public MainClass(ILogger logger, IDatabase db)
{
_logger = logger;
_db = db;
}
public void AddDetails(Data data)
{
//do some business operations
_db.Add(data);
_logger.Information("added");
}
}
然后您可以使用模拟框架,例如 Moq模拟您的类依赖项并验证是否调用了依赖项:
[TestClass]
public class UnitTest1
{
private Mock<ILogger> _mockLogger = new Mock<ILogger>();
private Mock<IDatabase> _mockDb = new Mock<IDatabase>();
[TestMethod]
public void TestMethod1()
{
// arrange
var mainClass = new MainClass(_mockLogger.Object, _mockDb.Object);
var data = new Data();
// act
mainClass.AddDetails(data);
// assert
_mockDb
.Verify(v => v.Add(data), Times.Once);
}
}
我不会验证您的日志消息,因为这可能会改变并使测试变得脆弱。仅验证对执行该方法的用途至关重要的功能。
关于c# - 单元测试依赖注入(inject),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56521382/