Show Me The Money: A Basic Cache Provider

Tuesday, May 27, 2014 @ 04:34

By Corey Adler

"There’s lots of things that can be solved with cash" - Danny Boyle

 

Although certainly not his intention, famous Hollywood director Danny Boyle’s quote above can also be true in the programming world—although with a little tweak in the spelling: There’s lots of things that can be solved with cache. Caching items into memory for future use is a very handy tool for programmers to use—especially in regards to creating web sites and applications. Although the ability to cache comes standard with web applications (through the use of the session), it is not so with desktop applications. In this post I will show you how to create a simple cache provider, as well as provide (pun intended) some tips and potential pitfalls using this cache provider.

For this example, I will be implementing 4 distinct methods in our cache provider, as shown in my ICacheProvider interface:

Code

  1. A Get() method which will grab the record from the cache given a key.
  2. A Set() method which will place a record into the cache given a key. This record will be removed from the cache after an amount of time, defaulted to 30 minutes.
  3. An IsSet() method which will check to see if a given key is present in the cache.
  4. An Invalidate() method which will remove an item from the cache given a key.
The implementation for the cache provider is based on the MemoryCache object type in .NET (MSDN documentation: http://bit.ly/RWotqf ). In fact, the cache provider uses the default MemoryCache instance itself as the basis for all of its methods. The actual implementation is as follows:

Code

One immediate thing to notice is the fact that the MemoryCache acts almost as a Dictionary (with one important exception mentioned below). The Get, IsSet, and Invalidate methods are exactly what you would use if your underlying data source were actually a Dictionary. The only difference is in the Set method. The Set method utilizes the CacheItemPolicy class, which allows you to setup when the record should expire, and be removed from the cache. In my implementation of the provider I have set up that it should absolutely expire some amount of minutes from now (default to 30). You can certainly change the default in the optional parameter, or even change it to a matter of seconds. You can also use the SlidingExpiration property in which the record will only expire if it has not been accessed in a given amount of time. Any other additions or changes are up to you; this is simply a beginning.

So there you have it: A very simple cache provider for your application to use. To conclude, let me share with you a couple of tips that I have had to learn the hard way in the hopes that you will not make the same mistakes that I have made.

The keys are not unique!

File this under “It’s like a Dictionary except…” In a Dictionary setting, if you were to attempt to insert a record with a key already found in a different record in that Dictionary, you would receive a lovely exception telling you about the big mistake that you’ve made. MemoryCache, on the other hand, is more forgiving, which can cause a fair number of headaches. It will allow the use of duplicate keys, grabbing only the first one that it finds. I’ve had it happen that the data showing on my screen was from a different record than anticipated because I had previously used that key for something else. Lesson learned: Always make sure that you’re not reusing key names!


Remember your scope!

Remember that your Cache Provider is based on a static variable. So if you use this provider throughout your application, you’d best be sure to remove items from the cache after you’re done with them! You could easily find yourself violating the first tip above simply by re-entering a screen you’d previously visited! Imagine: You’ve set up a few records in the cache for this one page showing some clients’ records. If you click away from that page without removing the records, and then go back in to the page for a different client, the page may show you the same data as the first client, simply because you never removed the old data from the cache! You can imagine some of the problems that that could easily lead to. So my tip for you is keep a tab on what keys each of your pages creates, and to remove them immediately after that page is changed. No muss, no fuss, no worries about possible switches.


Always have a backup plan!

No matter how good your intentions are, chances are that, at some point, a user is going to stay on a page for too long, and a record that needs to be found in the cache will have already expired. In such a case, make sure that you have plan for what should happen on a timeout—typically a redirect to different page, or a nice popup box telling the user that the session has expired etc. You should also make sure that the user has an easy way to get back to where he or she was before the timeout occurred, or you’ll have one upset user on your hands!

So there you have it! A basic implementation of a cache provider to use with desktop applications (such as WPF or WinForms), that you should feel free to play around with, and get more comfortable with. The more you get familiar with some of the concepts and classes mentioned here, the more valuable your knowledge will be!

Until next time, I wish you good coding.