Speeding Up Rendering Rails Pages with render_async

Adding new code to Rails controllers can bring a couple of problems with it. Sometimes controller actions get really big, and they tend to do a lot of things. Another common problem is an increase in data over time, which can lead to slow page loading time. Adding new code to controller actions can also sometimes block the rendering of some actions if it fails, breaking user experience and user happiness.

Here at Semaphore, we came across these types of problems a couple of times. We usually resolved them by splitting controller actions into smaller actions, and rendering them asynchronously using plain Javascript.

After some time, we saw that this can be extracted to render_async, a gem that speeds up Rails pages for you – it loads content to your HTML asynchronously by making an AJAX call to your Rails server.

Imported from Disqus

Josh Arnold3 years ago

If you are not already doing so, you should look into taking advantage of caching as part of this gem! No sense in making an extra ajax call every time a popular page is rendered, if you can cache that partial for a certain period of time.

Without digging into source code, something along the lines of “if cache exists, render cache, else make ajax call”.

Nikola Đuza Josh Arnold3 years ago

You are totally right, I should add this to the gem, thanks.

Seems like someone already submitted a pull request with the caching idea => https://github.com/rendered…

mikeperitore Nikola Đuza3 years ago

The PR is for server side cache, which I’d think you’d want to leave in the hands of each app’s author, no? Just wondering… this article definitely made my day

Josh Arnold mikeperitore3 years ago • edited

I made the PR and it was just a rush proof of concept. Needs refined before approved. It for sure should accept a simple cache flag (defaulted to false). It utilizes rails fragment/view caching.

Nikola Đuza Josh Arnold3 years ago • edited

Awesome idea Josh, I agree with optional caching flag.

I was also thinking about adding an option to pass in the spinner to render_async so it gets shown before AJAX call is finished.

Avatar

Eric Allam3 years ago

Great article and this Gem looks great! One thing to keep in mind is that there are other problems with loading content from an external resource during the lifecycle of a rails request, such as blocking the queue of requests waiting for that action to finish. Of course that isn’t the only use case for this gem, but I figured it’d be good to mention

Avatar

antulik3 years ago • edited

There is another similar pagelet_rails gem. It does exactly the same and more. I’ve wrote a blog post about it last year http://antulik.com/2016-10-…

Nikola Đuza antulik3 years ago

Cool gem, it’s really robust and full of features. I was thinking of adding similar behaviour with placeholder.

But you really went far with this, making streams and caching, and controller helpers, great job, I will try it out!

antulik Nikola Đuza3 years ago

Thanks, let me know what you think about it.

Avatar

Matt Sears3 years ago

This looks pretty similar to render_sync: https://github.com/chrismcc…. Though, it doesn’t look like that project has been updated in a while. We’ve used it for a few projects at Littlelines and the concept of async partial loading works great.

Avatar

Todd3 years ago

Nice article, its a nice way to “abstract away” some JS from a Rails app. However, wouldn’t it be simpler to just have a js.erb template with some vanilla JS to make the AJAX call to the external service, and just supply the movie_rating_path to the view template? Is the tradeoff here just writing less JS vs having fewer gems in an application?

Nikola Đuza Todd3 years ago

Glad you like the article, Todd.

js.erb template sounds good, but then you still have to write boring JS that manipulates response from an external service, right?

Idea behind this gem is that you don’t have to write any JS and avoid code duplication throughout the app.

Avatar

Web Designer3 years ago

Does anyone have any examples of sites using this gem that load fast as tested on dareboost.com. Quite often I see claims about speed and then test it on dareboost and its still slow. Fastest site I have found so far for an ecommerce site (from aussie locations) is theiconic.com.au for rendering above the fold of their product pages.

Nikola Đuza Web Designer3 years ago

Hey Web Designer , thanks for commenting!

I can’t pin point exact websites using it, but I can help you out with the slowness you experienced on dareboost.com

Also, I’ve released new version of this gem that supports caching of your partials. If you need caching you should definitely check it out https://github.com/rendered…