how to assert if a method has been called using nunit

余生颓废 提交于 2019-12-03 22:57:39

You should mock TokenManager and TokenValidator, and then create two unit test cases:

  • Case 1: token is validated and GetToken is called exactly once
  • Case 2: token is not validated and GetToken is called exactly twice

Case 1:

[Test]
public void Subscribe_TokenIsValidated_GetTokenIsCalledOnce()
{
    // Arrange:
    var tokenManagerMock = Mock.Of<TokenManager>();

    var tokenValidatorMock = Mock.Of<TokenValidator>(x =>
        x.Validate(It.IsAny<Token>()) == true);

    var subscriber = new Subscriber
    {
        TokenManager = tokenManagerMock,
        TokenValidator = tokenValidatorMock
    };

    // Act:
    subscriber.Subscribe(It.IsAny<string>(), It.IsAny<string>(),
        It.IsAny<string>());

    // Assert:
    Mock.Get(tokenManagerMock).Verify(x =>
        x.GetToken(It.IsAny<string>(), It.IsAny<bool>()), Times.Once);
}

Case 2:

[Test]
public void Subscribe_TokenIsExpiredOrInvalid_GetTokenIsCalledTwice()
{
    // Arrange:
    var tokenManagerMock = Mock.Of<TokenManager>();

    var tokenValidatorMock = Mock.Of<TokenValidator>(x =>
        x.Validate(It.IsAny<Token>()) == false);

    var subscriber = new Subscriber
    {
        TokenManager = tokenManagerMock,
        TokenValidator = tokenValidatorMock
    };

    // Act:
    subscriber.Subscribe(It.IsAny<string>(), It.IsAny<string>(),
        It.IsAny<string>());

    // Assert:
    Mock.Get(tokenManagerMock).Verify(x =>
        x.GetToken(It.IsAny<string>(), It.IsAny<bool>()), Times.Exactly(2));
}

Alternatively, you can create an unit test without mocking TokenValidator and verify if GetToken() has been called at least once. However, creating two cases as in the first example is preferred as we are testing all code paths.

// Arrange:
var tokenManagerMock = Mock.Of<TokenManager>();
var subscriber = new Subscriber {TokenManager = tokenManagerMock};

// Act:
subscriber.Subscribe(It.IsAny<string>(),
    It.IsAny<string>(),
    It.IsAny<string>());

// Assert:
Mock.Get(tokenManagerMock).Verify(x =>
        x.GetToken(It.IsAny<string>(), It.IsAny<bool>()), Times.AtLeastOnce);

Read more about verification in Moq at:

Jack Hughes

You can verify using MOQ using the Verify method. Like this:

var tokenManagerMock = new Mock<ITokenManager>();
var sut = new WhateverItIsCalled(tokenManagerMock.Object);
sut.Subscribe("ssss", "example@example.com", "XXX");
tokenManagerMock.Verify(m => m.GetToken(It.Is<string>(c => c == "ssss", It.Is<bool>(x => x == false)), Times.Once); 

You need to be able to pass the token manager into your system under test somehow. Usually via the ctor or maybe a property.

I would suggest you use something like AutoFixture to remove the ugliness that is "ssss" and make things a bit more DRY.

You may need to make the token manager mock return something appropriate too that will pass the validation. Something like this:

var tokenManagerMock = new Mock<ITokenManager>();
tokenManagerMock.Setup(m => m.GetToken(It.Is<string>(x => x == "ssss", It.IsAny<bool>()).Returns("XXXXXX");
标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!