简体   繁体   English

为什么我的单元测试在 switch 语句中失败?

[英]Why is my unit test failing for a switch statement?

Hi I am trying to unit test the following and check that this switch/case statement works:嗨,我正在尝试对以下内容进行单元测试并检查此 switch/case 语句是否有效:

DiagnosticsComponentFactory class DiagnosticsComponentFactory

private readonly IServiceProvider _serviceCollection;

public IComponent Create (string name)
{
    switch (name)
    {
        case BoardItemComponent.TypeName:
            return _serviceCollection.GetService<BoardItemComponent>();
        default:
            throw new NotSupportedException();
    }
}

My BoardItemComponent class:我的BoardItemComponent类:

public class BoardItemComponent
{
    public const string TypeName = "name";

    public BoardItemComponent(IConfigurationRepository configurationRepository) : base(configurationRepository)
    {

    }
}

BoardItemComponent is derived from IComponent , and it's added like follows in my Startup.cs file: BoardItemComponent是从IComponent派生的,它在我的Startup.cs文件中添加如下:

services.AddScoped<IComponent, BoardItemComponent>();

my unit test:我的单元测试:

[Test]
public void GetComponent_GivenComponentFactory_ExpectBoardComponent()
{
    var serviceCollection = new ServiceCollection();
    ComponentFactoryRegistration.Register(serviceCollection);
    var factory = new DiagnosticsComponentFactory(serviceCollection.BuildServiceProvider());
    var component = factory.Create("name");
    Assert.IsNotNull(component);
}

When I debug my unit test, component is null , despite it following all the correct steps.当我调试我的单元测试时, componentnull ,尽管它遵循了所有正确的步骤。 It goes into the switch case statement correctly and recognizes that is the correct case, however it still returns null .它正确地进入 switch case 语句并识别出这是正确的情况,但它仍然返回null

From what I have shared (and apologies, as I know that the names in these code snippets are vague without context), is there any obvious reason that my unit test fails?从我分享的内容(和道歉,因为我知道这些代码片段中的名称在没有上下文的情况下是模糊的),我的单元测试失败是否有任何明显的原因? I'm new when it comes to unit testing in C#.在 C# 中进行单元测试时,我是新手。

Based on your comments you indicated that the component is registered as根据您的评论,您表示该组件已注册为

services.AddScoped<IComponent, BoardItemComponent>();

The provider is aware of the IComponent interface, but is asking for BoardItemComponent implementation提供者知道IComponent接口,但要求BoardItemComponent实现

_serviceCollection.GetService<BoardItemComponent>();

The above will return null if the provider is unaware how to resolve BoardItemComponent when explicitly requested.如果提供者在明确请求时不知道如何解析BoardItemComponent ,则上述内容将返回null

Register the implementation注册实现

services.AddScoped<BoardItemComponent>();

and you can also associate it with the abstraction using the factory delegate您还可以使用工厂委托将其与抽象相关联

services.AddScoped<IComponent>(sp => sp.GetRequiredService<BoardItemComponent>());

Isolated testing should now be able to be done accordingly现在应该能够相应地进行隔离测试

[Test]
public void GetComponent_GivenComponentFactory_ExpectBoardComponent() {
    //Arrange
    var serviceCollection = new ServiceCollection();
    serviceCollection.AddScoped<BoardItemComponent>();
    serviceCollection.AddScoped<IConfigurationRepository>(sp => Mock.Of<IConfigurationRepository>());

    var factory = new DiagnosticsComponentFactory(serviceCollection.BuildServiceProvider());

    //Act
    var component = factory.Create(BoardItemComponent.TypeName);

    //Assert
    Assert.IsNotNull(component);
}

Now it was indicated that there may be more implementation in the future.现在表示未来可能会有更多的实施。

Lets say for example比如说

services.AddScoped<BoardItemComponent>();
services.AddScoped<AnotherItemComponent>();

The factory can then be refactored然后可以重构工厂

public class DiagnosticsComponentFactory {    
    private readonly IServiceProvider services;

    public DiagnosticsComponentFactory (IServiceProvider services) {
        this.services = services;
    }

    public IComponent Create (string name) {
        switch (name) {
            case BoardItemComponent.TypeName:
                return services.GetRequiredService<BoardItemComponent>();
            case AnotherItemComponent.TypeName:
                return services.GetRequiredService<AnotherItemComponent>();
            default:
                throw new NotSupportedException();
        }
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM