Search code examples
javamultithreadingspringcachingservice

How should I implement a cache object/system in Spring?


I am working on an Spring application that has hundreds of users but has 100-1 million pieces of data that is being sent as a response to each individual user. As such, performance is a big issue for us. We utilise Java, JSP, jQuery, HTML and CSS. For the bit I am working on, I am building a notification system. For example, if a user has an item that has past their expiry date then we send a notification to the user. However, the problems are:

  • I am using jQuery/AJAX to poll the server every minute
  • Each query is VERY expensive as we are searching the database for 100s of thousands of data, every minute for each user. Moreover, there are hundreds of users.
  • We are not checking for last modified time, we are checking for whether this expiry date field is before current time.

The idea I have right now is to use a thread that will continuously check the database for newly updated items and if there are new items we update a representation of a cache object. The users will retrieve data from the cache.

How should I implement this with Spring? What data structures should I use? What should I use for the thread and for the cache object? Should I use a WeakHashMap for this?

Note: Our application does not support annotation driven mvc.


Solution

  • Spring introduced abstraction for Cache in 3.x RELEASE. You can read about it in official Spring documentation (the site is down today for some reason :)), or at this post for example.

    http://dzone.com/articles/spring-cache-abstraction-0

    With this abstraction, all you need to do to enable cache is to add some annotations to your services, like

    To add value to the cache

    @Cacheable("customers")
    public Customer findCustomer(long customerId) {...}
    

    To remove value to the cache

    @CacheEvict(value="customer", allEntries = true)
    public void removeAllCustomers(long customerId) {...}
    

    And enable cacheable spring configuration. Spring magic AOP takes care of the rest. And as everything with Spring you can use any implementation you want, and many implementation are supported out of the box. And you don't need to change allot of code for this, just add annotations, as needed:)

    Besides Spring native support, there is Guava Cache

    https://code.google.com/p/guava-libraries/wiki/CachesExplained

    You can choose what you want, and implement your requirement by for example specifying cache key life timeout, so it would be removed from cache after specific time, and recalculated on next call.