Tips & tricks for unit testing in .NET Core 3: Using and mocking ISystemClock instead of using DateTime
Introduction
I discovered not long ago that a way to inject DateTime by dependency in my classes. Result, I was able to get rid of DateTime used directly in my services and I could greatly facilitate the testing unit of these services. The interface allowing me to do this is ISystemClock and I can mock it. This interface is found in the Microsoft.Extensions.Internal assembly of the Microsoft.Extensions.Caching.Abstractions package. It also exists in Microsoft.AspNetCore.Authentication package.
It also exists in Microsoft.AspNetCore.Authentication assembly. The Nuget package has the same name. It’s up to you to choose which package you want to use.
We will see in this article, from a scenario, how to make a service testable using DateTime.
Use case
Here is an any type object caching service. The latter uses a distributed cache service to which I pass options for caching. My service takes as a parameter a cache duration in minutes, while the cache option (AbsoluteExpiration), it is a DateTime.
So I’m going to need to add my cache time to the present time to calculate the absolute expiration. If I want to make the calculation of this absolute expiration testable I will need to use ISystemClock to generate a date and add it a duration in minutes as follows:
To activate it, don’t forget to add it in the DI:
Testing
Using tools that I really like and that I will not introduce again (see my article here: http://anthonygiretti.com/2019/06/15/asp-net-core-2-best-practices-and-practical-tools-for-testing-part-1/), I will be able to reach my goals and test if the calculation of my absolute expiration is correct:
Here we are! We are now able to improve or testing efficiency by using ISystemClock to manage DateTimes
Hope this article will help you as it has helped me 😉