Simple way to implement caching in ASP.NET Web API



This article is not about caching the output of APIControllers.
Often in ASP.NET Web API you will have a need to cache something temporarily in memory probably to improve performance.

There are several nice libraries that allow you to do just that.

One very popular is CacheCow and here you will find a very nice article how to use this library.

But what if you want to do caching without third party library in a very simple way?
 
If you want to learn more about ASP.NET Web API I recommend a great book that I love written by real experts:
 
BookWebAPIEvolvable
Designing Evolvable Web APIs with ASP.NET 

Caching without third party library in a very simple way

I had a need for this. I implemented some basic authentication for the ASP.NET Web API with Tokens and wanted to cache Tokens temporarily in memory to avoid going into the database for every HTTP request.

The solution is very simple.
You just need to use Microsoft class for this called MemoryCache which resides in System.Runtime.Caching dll.

 

I created a simple helper class for caching with few lines of code:

 

public class MemoryCacher
{
  public object GetValue(string key)
  {
    MemoryCache memoryCache = MemoryCache.Default;
    return memoryCache.Get(key);
  }

  public bool Add(string key, object value, DateTimeOffset absExpiration)
  {
    MemoryCache memoryCache = MemoryCache.Default;
    return memoryCache.Add(key, value, absExpiration);
  }

  public void Delete(string key)
  {
    MemoryCache memoryCache = MemoryCache.Default;
    if (memoryCache.Contains(key))
    {
       memoryCache.Remove(key);
    }
  }
}

When you want to cache something:

memCacher.Add(token, userId, DateTimeOffset.UtcNow.AddHours(1));

 

And to get something from the cache:

var result = memCacher.GetValue(token);

 

 
NOTE: You should be aware that MemoryCache will be disposed every time IIS do app pool recycle.

If your Web API :

  • Does not receive any request for more that 20 minutes
  • Or hit default IIS pool interval 1740 minutes
  • Or you copy a new version of your ASP.NET Web API project into an IIS folder (this will auto-trigger app pool recycle)

So you should have a workaround for this. If you don’t get value from the cache you should grab it for example from a database and then store it again in the cache:

 

 var result = memCacher.GetValue(token);
 if (result == null)
 {
     // for example get token from database and put grabbed token
     // again in memCacher Cache
 }

 

And if you liked this post, go ahead and subscribe here to my RSS Feed to make sure you don’t miss other content like this.

 
 

  • Bernd Viehmann

    Thank you very much. I found this article and will give your solution a try 🙂

    • Thanks Bernd. I use it in production project so it should be fine.
      Don’t forget to subscribe to my blog and make sure you don’t miss some great content I’m planning for this year.

  • pooranspress

    Why does the cache invalidate if it did not receive any request for more that 20 minutes. how can we extend it?

  • Vino Spartan

    Hi Man,

    I’ve implemented the same and it is doing its job great…but the prob is every time i’m gettin http header as 200 instead of 304 when response from cache..could u pl hlp me…..

    • Hi Vino. That is easy. Just implement something similar to this :

      var result = memCacher.GetValue(token);

      if(result==null)

      {

      // we grab fresh value from database

      return request.CreateResponse(HttpStatusCode.OK, result);

      }

      // we return result from cache and return status code 304 notModified
      return request.CreateResponse(HttpStatusCode. NotModified, result);

      • Vino Spartan

        Hi,
        Thanks for your response. As i said above, i’ve implemented your way for cachin in my API. I do confirm values retrieved from cache when same reqs handled(by debugging)
        But i’ve come with few issues as listed,
        1)It is not specified as Cached when i try in Fiddler/PostMan.(Image uploaded FYR)
        2)As you advised above, i’ve tried to modify my return but i can’t. i snaped my method and uploaded FYR.

        Could you please help me how can i implement and resolve above two issues.

        (Probable it might be simple but i jst kicked myself in API…..:) )

        Thanks,
        Vino

  • siah

    Hi, nice and clean and efficient way of caching.

    Can you also please explain the memory constraints of caching in iis app pool. How to limit the caching size etc. This will help in deciding the right caching strategy. Particularly in hosting in azure.

    Many thanks in advance

  • Sumanta

    Hi, nice and clean and efficient way of caching.

    Can you also please explain the memory constraints of caching in iis app pool. How to limit the caching size etc. This will help in deciding the right caching strategy. Particularly in hosting in azure.

    Many thanks in advance

  • Nerdy Beast

    We use the built in web cache class in many of our web api projects. It’s about as simple as it gets, check it out here: https://msdn.microsoft.com/en-us/library/system.web.helpers.webcache(v=vs.111).aspx