Ruby on Rails Caching

Learn via video courses
Topics Covered

Overview

Caching rails is a key part of software development that enhances the performance of software applications. By saving data in temporary storage that can be retrieved quickly rather than having to go through the complete extraction process every time it is needed, it improves performance. Ruby on Rails employs its internal caching system to enhance the speed of its application.

This article will go through the various caching methods that Ruby on Rails supports, how to utilize them, and the benefits they offer. We will also go through the different cache stores that Rails provides as well as how to manage dependencies while using caching.

Caching in Ruby on Rails

Caching is a technique used in Ruby on Rails to store frequently accessed data in a faster memory, reducing the number of times the data must be queried from the database. This can result in significant speed gains, particularly in applications with a high volume of queries.

Rails provide different types of caching mechanisms, which can be used based on the requirements of the application. These mechanisms are:

  • Basic Caching
  • Page Caching
  • Action Caching
  • Fragment Caching
  • Russian Doll Caching
  • Shared Partial Caching
  • Low-Level Caching
  • SQL Caching

Let's discuss each of these in detail.

Basic Caching in Rails

Rails provide mainly three types of caching techniques: page, action, and fragment caching. Fragment caching is provided by default, however, page and action caching requires the actionpack-page_caching and actionpack-action_caching gems to be installed.

Rails caching is disabled in the default setup except in the production environment. However, in the development environment, you may experiment with caching by running rails dev:cache or setting config.action_controller.perform_caching to true in the config/environments/development.rb file.

Page Caching

Page caching is a Rails caching technique that allows a web server (such as Apache or NGINX) to provide a pre-generated HTML page without having to traverse the Rails stack. Because the page does not need to be built dynamically for each request, it may be loaded significantly faster.

Assume you have a blog with a homepage that shows the most recent blog posts. When page caching is enabled, the web server can deliver a pre-generated HTML file from the filesystem for the homepage instead of sending the request through the Rails stack to produce the HTML. This can considerably increase the site's performance, especially during high-traffic periods.

Page caching, on the other hand, is not suitable in many situations. Pages requiring user authentication, for example, cannot be cached in this way since the content must be generated dynamically for each user. Furthermore, because cached pages are provided directly from the disc, cache expiration is necessary to guarantee that users are not fed outdated and stale data.

Page caching was removed from Rails core and for using it we need to install the actionpack-page_caching gem.

Action Caching

Action Caching is a Ruby on Rails feature that caches the output of an entire action. It is similar to Page Caching, except it also allows you to execute prior filters before serving the cached content.

Let's say you have a website that shows a person's profile information, but only authenticated users can access it. It would be inefficient to retrieve information from the database for every request because profile data does not update frequently.

The profile data could be cached via Action Caching for a fixed period. The action is carried out, and the new data is cached for the following user if the cached data has expired or the user logs out.

Like Page Caching, Action Caching was also removed from Rails. To use it we need to install the actionpack-action_caching gem

Fragment Caching

In dynamic web applications where distinct elements of a page have varied caching requirements, the method of Fragment Caching is used. It enables developers to encapsulate a section of the code in a cache block and deliver the cached fragment from the cache store when a request is raised for a specific fragment.

Suppose you have a web page that displays a list of articles with their titles, authors, and publication dates. You want to cache each article separately to avoid the expensive database query to retrieve the article details.

You could use the following code to cache each article:

Upon receiving the first request, Rails will build a cache entry with a special key and hash digest depending on the information in the view fragment. The digest will update and the current cache entry will expire if the article details change.

Use cache_if or cache_unless if you only want to cache a fragment in specific circumstances. For example, let's say you only want to cache an article if it has been published. You could modify the code as follows:

The article fragment will only be cached if the published? method returns true. The fragment won't be cached in any other case.

This method of using fragment caching can decrease the number of database queries required to display each article's details, which can enhance the web page's performance.

Russian Doll Caching

Russian Doll caching is a caching method used in Rails to improve the performance of web applications. It involves nesting fragment caches based on their dependencies, resulting in faster page load times as only the necessary fragments are updated when data changes.

For example, in a blog application where multiple users view and comment on posts, the comments area can cause slow page load times if it is regenerated each time the content is shown. By using Russian Doll caching, the article view and comment view can be cached separately and nested within each other. This way, when a new comment is added or updated, only the comment view cache is regenerated while the article view cache remains unchanged, resulting in better application performance.

Shared Partial Caching

Shared partial caching in Rails is a way to cache a partial view based on a key and share it across multiple views. This can be helpful for partial views that are reused on various pages but have dynamic content. By caching the partial view, the performance of the application can be improved as the partial view does not need to be regenerated with each request.

An example use case for shared partial Rails caching is in an e-commerce application where users can search for and view product details. If multiple users view the same product, the related information section, such as reviews and related products, will be regenerated each time, causing a slowdown in page load time. To address this, the related information section can be cached separately and shared between the search results view and product details view as a shared partial. This way, only the related information section cache needs to be expired and regenerated if a review is added or updated, while the other cached views remain unchanged.

Managing Dependencies

When utilizing Rails caching, it's critical to handle the relationships between cached objects such that the cached objects are invalidated when their dependents change. Cache keys, cache sweepers, and cache digests are among the tools available in Rails for managing dependencies.

Low-Level Caching

Low-Level Caching is a Rails caching system that uses the Rails.cache.fetch function to cache specific values or query results, which can significantly improve application performance by minimizing the time spent searching the database and creating views. For example, an e-commerce website can cache the list of all available items using a cache key that expires after a specific duration, enabling users to quickly access the cached list instead of conducting a database query.

SQL Caching

SQL caching involves storing the results of SQL queries in the cache to improve application performance by minimizing the amount of SQL queries that must be run. This method is particularly useful in scenarios such as an e-commerce application that needs to display a product’s total sales, where caching the result set can significantly reduce the number of SQL queries.

Rails Cache Stores

Rails cache stores are storage engines used by Rails to store cached data. Rails support a variety of cache stores, including in-memory, file-based, and distributed cache stores, as well as custom cache stores.

We can set the config.cache_store configuration option to configure your application's default cache-store. Other options can be supplied to the cache store's constructor as arguments:

We can access the cache by calling Rails.cache.

Rails Cache Keys

Cache keys are used in Rails to identify a specific cache entry. Any object that responds to cache_key or to_param can be used as a key. Custom cache keys can be constructed if necessary by implementing the cache_key function on a class. Hashes and arrays of values can also be used as cache keys.

It is crucial to remember that the keys used with Rails.cache may differ from those used with the actual storage engine, since they may be adjusted to match technical backend requirements or include a namespace. This implies that values saved using Rails.cache cannot be retrieved using other Rails caching tools such as dalli. However, this also implies that the developer does not have to worry about exceeding the memcached size limit or breaking syntax rules.

FAQs

Q: What is Rails caching?

A: Rails caching is the technique of storing frequently visited data in a cache so that it may be retrieved quickly and returned when the data is requested again.

Q: Why use caching in Ruby on Rails?

A: Caching in Ruby on Rails can improve web application performance by reducing the number of database queries and expensive calculations required to generate a response. Thus it can also help to reduce the load on the application server and database while increasing application scalability.

Q: What types of caching are available in Ruby on Rails?

A: Ruby on Rails provides several types of caching, including page caching, action caching, fragment caching, Russian doll caching, and low-level caching.

Conclusion

  • Rails caching is the process of storing frequently accessed data in a cache to improve application performance.
  • Page caching, action caching, fragment caching, Russian doll caching, and low-level caching are just a few of the caching options offered by Ruby on Rails.
  • Rails caching may be used to increase the overall performance and scalability of web applications, as well as to decrease the amount of database queries and costly calculations needed to create a response.
  • In Rails, cache sweepers and cache digests can be used to invalidate caches when dependencies change.
  • Rails offers an adaptable and user-friendly caching architecture that can be customized to fit the requirements of any application.