Moq4: Verifiable throw NullReferenceException for async Task methods

Created on 4 Mar 2014  路  2Comments  路  Source: moq/moq4

Have interface

 public interface IDataStoreService
    {
        Task<T> GetDataAsync<T>(string key);
        Task SaveDataAsync<T>(string key, T item, bool storeAlways = false);
    }

In test create mock object

 var mockDataService = new Mock<IDataStoreService>();
            mockDataService.Setup(
                service => service.SaveDataAsync(It.IsAny<string>(), It.IsAny<object>(), It.IsAny<bool>())).Verifiable();

Act it with this code

 var settingsService = new MyStorageService(mockDataService.Object);
  var rez = await settingsService.Set("setting", "ok");

Moq throws NullReferenceException on SaveDataAsync call in MyStorageService.

If I change interface method to

   Task<bool> SaveDataAsync<T>(string key, T item, bool storeAlways = false);

and change setup to

   mockDataService.Setup(
                service => service.SaveDataAsync(It.IsAny<string>(), It.IsAny<object>(), It.IsAny<bool>())).ReturnsAsync(true);

all works fine.

Most helpful comment

You're not returning a task, therefore, a null is being returned.

If your method signature returns a task, you need to return one ;)

var mockDataService = new Mock<IDataStoreService>();
mockDataService.Setup(
            service => service.SaveDataAsync(It.IsAny<string>(), It.IsAny<object>(), It.IsAny<bool>()))
       .Returns(Task.FromResult(true)).Verifiable();

Note that a Task is a Task, so you can return that just fine. No need to change the method signature.

All 2 comments

Also just ran into this problem...Seems you can't properly mock methods that simply return a task?!

You're not returning a task, therefore, a null is being returned.

If your method signature returns a task, you need to return one ;)

var mockDataService = new Mock<IDataStoreService>();
mockDataService.Setup(
            service => service.SaveDataAsync(It.IsAny<string>(), It.IsAny<object>(), It.IsAny<bool>()))
       .Returns(Task.FromResult(true)).Verifiable();

Note that a Task is a Task, so you can return that just fine. No need to change the method signature.

Was this page helpful?
0 / 5 - 0 ratings