Reputation: 915
I'm trying to mock the following GetOrSet method in InMemoryCache class.
public class InMemoryCache : ICacheService
{
public T GetOrSet<T>(string cacheKey, Func<T> getItemCallback) where T : class
{
T item = MemoryCache.Default.Get(cacheKey) as T;
if (item == null)
{
item = getItemCallback();
DateTime expireDateTime = new DateTime(DateTime.Today.Year, DateTime.Today.Month, DateTime.Today.Day, 4, 0, 0).AddDays(1);
MemoryCache.Default.Add(cacheKey, item, expireDateTime);
}
return item;
}
}
In my test, I have
var mockCacheService = new Mock<ICacheService>();
mockCacheService.Setup(x => x.GetOrSet..
Can someone help me fill up the dots?
I'm setting up like this
mockCacheService.Setup(x => x.GetOrSet(It.IsAny<string>(), It.IsAny<Func<object>>()))
.Returns(new Dictionary<string, string> { { "US", "USA"} });
but, when I make a call like this it returns null
var countries = _cacheService.GetOrSet("CountriesDictionary", () => webApiService.GetCountries())
Upvotes: 0
Views: 1967
Reputation: 27009
It depends what you want to test. Here are a few examples:
var mockCacheService = new Mock<ICacheService>();
// Setup the GetOrSet method to take any string as its first parameter and
// any func which returns string as the 2nd parameter
// When the GetOrSet method is called with the above restrictions, return "someObject"
mockCacheService.Setup( x => x.GetOrSet( It.IsAny<string>(), It.IsAny<Func<string>>() ) )
.Returns( "someObject" );
// Setup the GetOrSet method and only when the first parameter argument is "Key1" and
// the second argument is a func which returns "item returned by func"
// then this method should return "someOtherObject"
mockCacheService.Setup( x => x.GetOrSet( "Key1", () => "item returned by func") )
.Returns( "someOtherObject" );
It
has many different methods such as IsIn
, IsInRange
, IsRegex
etc. See which one will suit your needs.
You will then need to verify something on your mock. For example, below I am verifying that the method was called with these exact arguments and only called once. If it was called with "Key1" as the first argument and a func which returns "item returned by func", then this will pass.
mockCacheService.Verify( x => x.GetOrSet( "Key1", () => "item returned by func" ), Times.Once() );
EDIT 1
This is important:
You probably know this but I hope you are not using this to test InMemoryCache.GetOrSet
method. The idea here is that you are testing some other class and that class, under certain conditions, better call this mock with that specific setup in the setup
method above. If your class under test does not call the mock with "Key1" and does not pass a func which returns "item retuned by func", then the test fails. Which means the logic in your class under test is wrong. NOT this class since you are mocking it all.
Upvotes: 3