单元测试-如何测试仅插入日志消息的“ void”方法(Serilog)

时间:2018-10-20 17:38:38

标签: c# unit-testing logging void serilog

我需要测试一种Order类型的方法,它只是使用LOG框架(Serilog)在我的LOG变量上插入一条消息。

请参阅实现示例:

void

在这种情况下,我们需要为public class MyClass { public MyClass(ILogger<IProcess> logger) { this.logger = logger; } private readonly ILogger logger; //...Anothers methods... public void LogInit(Guid processId, string folder, string[] args) { var myObject = new { ProcessId = processId, Folder = folder, Arguments = args }; this.logger.LogWarning("{@myObject}", myObject); } }

创建一个测试

真的需要测试此方法吗?或者说,存在它有意义吗?

我正在阅读有关以下内容的信息:

  

“如果您的方法没有副作用,并且不返回任何东西,那么它就什么也没有做。”

在这种情况下,仅“单独”创建该方法以维护代码的组织并将类的职责分开更多。

那有意义吗?

编辑: @PeterBons

我们无权访问在接口(LogInit (...))中注册的消息,例如:logger ...

3 个答案:

答案 0 :(得分:3)

您必须模拟记录器,并检查是否调用了LogWarning方法。您可以为此使用Moq。另外,如果要测试LogInit,则需要通过定义[InternalVisibleTo('someTestProjName')]来公开或内部进行此操作

测试方法将如下所示(xUnit):

OnGetAsync(string title)

答案 1 :(得分:2)

如果您使用的是Serilog,则可以使用Test Correlator Sink查看方法调用产生的日志事件。

[TestMethod]
public void A_test()
{
    var myClass = new MyClass(new LoggerConfiguration().WriteTo.TestCorrelator().CreateLogger());

    using (TestCorrelator.CreateContext())
    {
        myClass.LogInit();

        TestCorrelator.GetLogEventsFromCurrentContext()
            .Should().ContainSingle()
            .Which.MessageTemplate.Text
            .Should().Be("{@myObject}");
    }
}

答案 2 :(得分:-1)

您的方法未返回任何内容,因此确定是否会更难测试。 现在,您的方法唯一要做的就是为Serilog库准备记录的对象。如果您对于创建该对象具有更复杂的逻辑,则可以将其提取到其自己的方法中,并使其返回该日志对象,那么可以很容易地对其进行测试。创建的方法的好处在于,它创建了一个额外的层,因此,如果您决定更改日志记录库,则只能在一个地方进行。