Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Expected invocation on the mock once, but was 0 times With Moq

I am getting an error

Invocation on the mock once, but was 0 times

and below is the my code structure

public class GenerateAddress : IGenerateAddress 
{
    public GenerateAddress(IAddress createAdd, IValidate validate) {
       //constructor 
    }

    public Address GetAddressFromA(string name){..}
}

public class SaveAddress : ISaveAddress 
{
    public SaveAddress(IGenerateAddress generateaddress) {
        //constructor 
    }

    public bool Save(string name)
    {
        var address = generateaddress.GetAddressFromA(name);
        ......
        //Rest of the code to save 
    }
}

Test Method to Test Class SaveAddress

public void TestVerifyGetAddressIsCalled()
{
    var mockIAddress = new Mock<IAddress>();
    var mockValidate = new Mock<IValidate>();

    var genAddress = new Mock<IGenerateAddress>();

    var objGenAdress = new GenerateAddress(mockIAddress.Object, mockValidate.Object) // 

    var objSaveAddress = new SaveAddress(objGenAdress);

    objSaveAddress.Save("dddd");

    //Verify if IGenerateAddress 'GenerateAddress' is called

    genAddress.Verify(a=>a.GenerateAddress("ddddd"),Times.Once); // Throws Excepted Invocation 
}

I need to verify if GenerateAddress is called or not. I also did Setup and assigned values to Address object but even those values are not been set .. Not sure what is going wrong.

like image 813
Hafeez Khan Avatar asked Apr 21 '16 14:04

Hafeez Khan


2 Answers

You are using an IGenerateAddress you created manually (objGenAdress) with SaveAddress instead of the mocked genAddress.

Also given that the SUT is the SaveAddress which only needed the IGenerateAddress, there is no need for the other mocks.

public void TestVerifyGetAddressIsCalled() { 
    //Arrange
    var genAddress = new Mock<IGenerateAddress>();

    var objSaveAddress = new SaveAddress(genAddress.Object);

    var name = "dddd";

    //Act
    objSaveAddress.Save(name);

    //Assert
    //Verify if 'IGenerateAddress.GenerateAddress' is called    
    genAddress.Verify(a => a.GenerateAddress(name), Times.Once);
}
like image 160
Nkosi Avatar answered Oct 28 '22 20:10

Nkosi


It looks like you're calling Save with 'dddd' (4 d's), but verifying it was called with 'ddddd' (5 d's).

It's safer to put the real data in a variable and reference it in both cases:

var name = "dddd";
objSaveAddress.Save(name);

genAddress.Verify(a=>a.GenerateAddress(name),Times.Once);
like image 34
Adam V Avatar answered Oct 28 '22 18:10

Adam V