How can I put (parts of) a large object graph in Rails.cache?

I have a class in which looking up an instance is expensive, so instances are cached:

class Foo
  def self.find(id)
    Rails.cache.fetch("Foo.#{id}") do
      // some expensive lookup, like an HTTParty request, or a long SQL query
      ...
    end
  end
end

That works fine until Foos have related Foos:

class Foo
  def children
    @child_foo_ids.map { |id| Foo.find(id) }
  end
end

I'd like to use ||= caching to save repeated trips:

class Foo
  def children
    @children ||= @child_foo_ids.map { |id| Foo.find(id) }
  end
end

But Rails.cache freezes the found Foos, so I can't set the instance variable after I create and cache the object. (i.e. this method raises a TypeError.)

One solution would be to pre-fetch the parent when I first do the expensive find, but that could end up loading a gigantic object graph when I only want one or two instances.

Answers


You can use ||= caching; you just have to use a little indirection:

class Foo
  def initialize
    @related_objects = {}
  end
  def children
    @related_objects[:children] ||= @child_foo_ids.map { |id| Foo.find(id) }
  end
end

Rails.cache won't freeze the instance variables of each Foo, so that Hash can be modified!

PS: yes, I did just post this question and the answer at essentially the same time. I figured the community could benefit from my struggle.


Need Your Help

Architecture for Web-App development aimed at aiding interoperability between CMS systems. Has it been done?

drupal architecture joomla content-management-system interop

I'm thinking about attempting to design a new framework architecture aimed at allowing a web app to later be easily ported into a system such as Drupal or Joomla while maintaining the independence ...

Case in WHERE clause for condition oracle

sql oracle plsql oracle11g

I have to write a query which have dynamic where clause. I have a column gap_value if the user sends a parameter 'P' then I need to fetch gap_value>0 else if 'N' it should be gap_value<0.

About UNIX Resources Network

Original, collect and organize Developers related documents, information and materials, contains jQuery, Html, CSS, MySQL, .NET, ASP.NET, SQL, objective-c, iPhone, Ruby on Rails, C, SQL Server, Ruby, Arrays, Regex, ASP.NET MVC, WPF, XML, Ajax, DataBase, and so on.