首页 > 解决方案 > 在创建单元测试时,我能做些什么来防止该方法被调用?

问题描述

我想强调一下,我对创建单元测试还很陌生,但我一直在通过谷歌和文档进行广泛搜索,但找不到解决方案或替代方案。所以目前我正在尝试为我的队友和我正在开发的微服务创建单元测试。类构造函数的结构如下

 public Constructor(IOptions<AMQ_Config> amqConfig, IConfiguration configuration)
        {
            this.amqConfig = amqConfig.Value;
            this.amqConfig.UserName = configuration["AMQ:UserName"];
            this.amqConfig.Password = configuration["AMQ:Password"];
            //this.errorTypeConfig = errorTypeConfig.Value;
            this.configuration = configuration;
            AMQSubscriber();
        }

当我在单元测试中创建构造函数的新实例时,它将始终调用并遍历该AMQSubscriber();方法。天真的我只是做了一个重复的构造函数,它排除了该方法并添加了另一个参数:

public UnitTestConstructor(IOptions<AMQ_Config> amqConfig, IConfiguration configuration, IConnection connection)
        {
            this.amqConfig = amqConfig.Value;
            this.amqConfig.UserName = configuration["AMQ:UserName"];
            this.amqConfig.Password = configuration["AMQ:Password"];
            //this.errorTypeConfig = errorTypeConfig.Value;
            this.configuration = configuration;
            this.connection = connection;
        }

但这仅用于单元测试目的。我已经阅读过这样做不是一个好主意,因为它违背了单元测试的目的,但我想不出如何隔离它,因为大多数方法都需要或依赖于参数:IOptions<AMQ_Config> amqConfig, IConfiguration configuration 而且我们的微服务是架构化的用于 Apache NMS AMQ 用于发送、处理和接收消息。

标签: c#unit-testingnms

解决方案


你有几个选择:

1.移动AMQSubscriber()到另一个界面

因此,您的构造函数将如下所示:

public Constructor(IOptions<AMQ_Config> amqConfig, IConfiguration configuration, IAMQSubscriber subscriber)
{
    // Other code ...
    subscriber.AMQSubscriber();
}

在您的单元测试中,您可以使用模拟IAMQSubscriber库进行模拟,也可以提供 void 实现:

class VoidAMQSubscriberForUnitTest : IAMQSubscriber
{
    public void AMQSubscriber()
    { 
        // Do nothing.
    }
}

例如:

// Real
new YourClass(... , new RealAMQSubscriber());
// Unit test
new YourClass(... , new VoidAMQSubscriberForUnitTest()); 

2.制作internal构造函数或静态方法:

在这种情况下,只有同一程序集中的类型和单元测试程序集才能看到这些方法。即停止测试公开的特定方法。

class YourClass
{
    // Only consumed by unit test
    internal YourClass(IOptions<AMQ_Config> amqConfig, IConfiguration configuration, IConnection connection) 
    { }

    // Only consumed by unit test
    internal static YourClass CreateForUnitTest() { }
}

您可能需要将InternalsVisibleToAttribute添加到您的程序集中。


推荐阅读