Pre-Build View Cache in Rails

Is there a way to pre-create the page cache without invoking the actual page via an HTTP request?

I looked at solutions like this and, but they do not generate a cache.

I have a relatively complicated view, and I want to cache all of this. I want to pre-create this cached version in the application, so when the user actually hits it, it will already be there.

thanks

+6
source share
2 answers

We needed to do something similar from the rake task — we had a partial one, which was supposed to display a very long list of entities (~ 700), which were somewhat context specific and which, due to a series of databases, had structure and user problems sorting criteria, it would be easy to take> 25 seconds to make the first time before entering the cache> This would often be a timeout, because our HTTP servers were configured to stop HTTP requests without response after 30 seconds and pre-cache it The list was a solution.

What you need to do is create an instance of ActiveController :: Base or one of your controllers if you need helper methods or other objects, and then pass the lookup_context link to a new instance of ActionView.Renderer.

In our rake team, we performed the following

namespace :rake_for_time_consuming_nonsense do task :pre_cache_long_list do PreCacher.pre_fetch_partials end end class PreCacher def self.pre_fetch_partials the_controller = ActionController::Base.new # Set any instance variables required by your partial in the controller, # they will be passed to the partial with the view_context reference the_controller.instance_variable_set "@cache_key", cache_key the_controller.instance_variable_set "@the_object", MyModel.first view_renderer = ActionView::Renderer.new the_controller.lookup_context view_renderer.render the_controller.view_context, {partial: 'my_model/the_partial', layout: false} end end 

This works in Rails 3.2.13.

+2
source

I think the following link should give you a good start. How to get the displayed result of the controller’s action without visiting a web page?

I am trying to do the same and, as far as I can see, your fake request should have the correct host, because the cache key contains host information.

I performed caching with ActionController :: Integration :: Session

 ais = ActionController::Integration::Session.new ais.host = host ais.xml_http_request(:post, url, params, headers) 

I have one more:

 class FakeRequest include ActionController::UrlWriter def initialize(url, params, session, host) @url = url @params = params @session = session default_url_options[:host] = URI.parse(host).host end def post process(:post) end def get process(:get) end def xhr process(:post, true) end def process(method, ajax = false) uri = URI.parse(url_for(@url)) request = ActionController::TestRequest.new({'HTTP_HOST' => uri.host,'rack.input' => '','rack.url_scheme' => 'http'}) request.query_parameters = @params request.path = uri.path request.host = uri.host request.env['REQUEST_METHOD'] = method.to_s.upcase if ajax request.headers['X-Requested-With'] = 'XMLHttpRequest' end @session.each_pair do |k,v| request.session[k] = v end response = ActionController::TestResponse.new controller = ActionController::Routing::Routes.recognize(request).new return controller.process(request, response) end end 

This also returns a response object.

0
source

Source: https://habr.com/ru/post/893636/


All Articles