Backo
Backo

Reputation: 18871

How to retrieve database data by disabling the Ruby on Rails cache system only for one case?

I am using Ruby on Rails v3.2.2 and I would like to retrieve database data by disabling the system cache only in a case. That is, in my view file I have something like the following:

<h1>Random articles 1</h1>
<%= Article.order('RAND()').limit(3).inspect %>
...
<h1>Random articles 2</h1>
<%= Article.order('RAND()').limit(3).inspect %>

When the view file is rendered it outputs the same data for both under "Random articles 1" and "Random articles 2". It happens because the Ruby on Rails cache system (by "default"/"convention") tries to hit the database as less as possible for performance reasons.

How can I prevent this behavior (just for the above explained case) so to output different data for finder methods in my view file?

Upvotes: 3

Views: 561

Answers (2)

apeiros
apeiros

Reputation: 1705

I tried to reproduce your issue, but could not (Rails 3.2.2 too, using sqlite3 adapter, code below). But try this anyway:

Article.uncached do Article.order('RAND()').limit(3).inspect end

The following is how I tried to reproduce your issue in an empty Rails project, for me it yielded the articles in a different order all the time, though:

ActiveRecord::Migration.create_table :articles do |t| t.string :name end
class Article < ActiveRecord::Base; end
20.times do |i| Article.create :name => "Article#{i}" end
# sqlite doesn't have a RAND() function, emulate it
Article.connection.instance_variable_get(:@connection).define_function 'RAND' do rand end
p *Article.order('RAND()').limit(3)

Maybe you spot a mistake in how I tried to reproduce your issue.

Upvotes: 0

KL-7
KL-7

Reputation: 47648

There is uncached method in ActiveRecord. Looks like you can use it like that:

articles = Article.uncached do
  Article.order('RAND()').limit(3)
end

but you better extract that into class method of your model.

See this article for more information

Upvotes: 6

Related Questions