Friday, January 13, 2012

Scalability in Rails - Exploring Caching



Many of us when talk about Rails, are concerned with scalability of Rails applications.

I got a chance to improve scalability of a particular module in my application through Rails Caching.

Here's how it works in Rails 3.x series:

Rails, basically comes with a inbuilt Caching mechanism which is by default enabled in  production mode.
In each of the Modes of deploying a Rails app, i.e. Dev, Test, Prod we need to make sure caching is enabled in the respective app/environments/mode.rb file
i.e.

app/environments/development.rb
app/environments/test.rb
app/environments/production.rb

The command which will set Caching to true in these environments is:

config.action_controller.perform_caching = true


Now , Say if you are implementing Rails -> Action Caching, In your controller You need to enter:-

caches_action :index, :layout => false

def index
# your code goes in here
end

This means, Rails is going to cache the Index action for you. Of course , with Caching, we need to also consider Expiry of Cache.

What I gotta implement is not a Batch Process which regularly checks for Cache Expiry, but a more efficient approach which is within my controller itself. This way I am saving myself and others who use this code in the future from the overhead of managing and monitoring a batch process time and again.

This is how the Cache Expiry action can look:-

def clear_cache
t = Rails.cache.fetch('variable_used_to_check_expiry_time') || Time.now
t = Time.parse(t) if t.is_a?(String)
expire_action :action => :index if Time.now > t
end

Now, how do I call for clear_cache to check when it is actually time to clear the cache..? Well, this can be done efficiently , automatically using a before_filter method.. Like this..
before_filter => :clear_cache

Rails Cache, comes with a <b>Cache log</b> on which we can specify when the a page was first accessed as a result of the particular Rails action being called.

Now for e.g. if I access the index.html.erb at 20:29 pm, this gets stored in my Rails cache log through the following way:-

def index
# your code goes in here
Rails.cache.write('variable_used_to_check_expiry_time', Time.now + 6.hours)
end I'm setting my cache expiry time to current time  + 6 hrs..i.e. at 04:29am,

Now only if the page => index.html.erb if accessed after 04:29am the following day, the new cache expiry time can be set....

You might be wondering what is written into cache log when the controller method of clear cache is actually called for the first time? Thats a good question..:)

Well basically what happens is, the current time is set into var t, since t = current time, no clear cache action needs to be executed to worry us.

P.S:- Credits to Srikanth Jeeva for inputs on the clear cache approach..

No comments:

Post a Comment