我正在使用 ninject 在我的生产环境中注入依赖项。在编写单元测试时,我看到了两种选择。我可以创建具体的类并使用 ninject 注入它们,或者我可以使用像 mock 这样的模拟框架。
我的思考过程是同时使用两者,并决定是否可以以可重用的方式构造 TestInterface。这样我们就不会浪费时间编写相同的 Mocked 方法来一遍又一遍地返回一个空列表。
这种事情有最佳实践吗?
我正在使用 ninject 在我的生产环境中注入依赖项。在编写单元测试时,我看到了两种选择。我可以创建具体的类并使用 ninject 注入它们,或者我可以使用像 mock 这样的模拟框架。
我的思考过程是同时使用两者,并决定是否可以以可重用的方式构造 TestInterface。这样我们就不会浪费时间编写相同的 Mocked 方法来一遍又一遍地返回一个空列表。
这种事情有最佳实践吗?
对于类的单元测试,将 DI 容器包含在“被测系统”(SUT)中没有多大意义。
如果您在组件或应用程序级别进行验收测试/单元测试,那么在 SUT 中包含 Ninject 是非常有意义的。
对于类级单元测试,通常采用基于动态代理的模拟框架,如MOQ或FakeItEasy。
给定一个实现:
public interface IDependency {
void Foo(string bar);
}
public class SomeClass
{
private readonly IDependency dependency;
public SomeClass(IDependency dependency)
{
this.dependency = dependency;
}
public void SomeMethod(string arg)
{
this.dependency.Foo(arg);
}
}
测试看起来像(xUnit 风格):
public class SomeClassTest
{
private readonly Mock<IDependency> dependency;
private SomeClass testee;
public SomeClassTest()
{
this.dependency = new Mock<IDependency>();
this.testee = new SomeClass(this.dependency.Object);
}
[Fact]
public void SomeMethod_MustPassArgumentToFoo()
{
const string expectedArgument = "AnyArgument;
this.testee.SomeMethod(expectedArgument);
this.dependency.Verify(x => x.Foo(expectedArgument));
}
}
JustMock 内置了 NInject 以及基于它的模拟容器。
当您第一次获取实例时,会自动注入依赖项的模拟:
var container = new MockingContainer<ClassUnderTest>();
var testee = container.Instance;
另外,您可以使用 NInject 的语法来细粒度地控制注入行为,以及 JustMock 的语法来配置模拟行为。