【问题标题】:Injecting derived test class via dependency injection uses base class function通过依赖注入注入派生测试类使用基类函数
【发布时间】:2018-10-16 16:22:34
【问题描述】:

我有一个如下所示的库:

class BaseType {
    public string MyFunction() {
        return "Abc";
    }
}

class MyClass {
    public MyClass(BaseType baseType) {
        Console.WriteLine(myType.MyFunction());
    }
}

现在我正在像这样测试它:

class TestingBaseType : BaseType {
    public new string MyFunction() {
        return "def";
    }
}

class Unittests {
    public void Test() {
        new MyClass(new TestingBaseType());
        //Logs "Abc". But I need "def".
    }
}

我的真实代码没有执行注入的模拟BaseClass。如何在不编辑生产代码的情况下进行这样的测试。由于我编写单元测试的方式,我不想编辑生产代码。

【问题讨论】:

  • 行为正确。不要将newvirtual + override 混淆。
  • 我知道这种行为是正确的,但我不想让BaseType.MyFunction 虚拟,因为我认为单元测试不会影响您的生产代码。人们会想知道为什么方法是虚拟的。
  • 使用一个接口和两个独立的实现。如果你渴望依赖注入,无论如何接口都是必经之路。
  • 我完全同意@OndrejTucny。在对包含应用程序行为的抽象建模时,优先使用组合而不是继承,并使用接口而不是基类。

标签: c# unit-testing dependency-injection


【解决方案1】:

如果不能将基类的方法设为虚拟,则不要使用派生类,而是声明接口。无论如何,接口是实现有效依赖注入的关键概念。

生产代码:

public interface IType
{
    string MyFunction();
}

public class MyType : IType
{
    public string MyFunction() => "Abc";
}

class MyClass 
{
    public MyClass(IType myType) 
    {
        Console.WriteLine(myType.MyFunction());
    }
}

测试代码:

public class MyTestingType : IType
{
    public string MyFunction() => "Def";
}

class Unittests 
{
    public void Test() 
    {
        new MyClass(new MyTestingType());
    }
}

【讨论】:

    猜你喜欢
    • 2012-03-08
    • 2020-01-20
    • 1970-01-01
    • 2014-11-04
    • 1970-01-01
    • 2018-12-27
    • 1970-01-01
    • 1970-01-01
    • 2011-09-02
    相关资源
    最近更新 更多