Matchu
e42de795dd
That is, once we get our list of IDs from the search engine, only fetch records whose JSON we don't already have cached. It's simpler here to use as_json, but it'd probably be even faster if I figure out how to serve a plain JSON string from a Rails controller. In the meantime, requests of entirely cached items are coming in at about 85ms on average on my box (dev, cache classes, many items), about 10ms better than the last iteration.
45 lines
No EOL
1.2 KiB
Ruby
45 lines
No EOL
1.2 KiB
Ruby
class Item
|
|
class Proxy
|
|
include FragmentLocalization
|
|
|
|
attr_reader :id
|
|
attr_writer :item
|
|
|
|
def initialize(id)
|
|
@id = id
|
|
@known_method_outputs = {}
|
|
end
|
|
|
|
def method_cached?(method_name)
|
|
# TODO: is there a way to cache nil? Right now we treat is as a miss.
|
|
# We eagerly read the cache rather than just check if the value exists,
|
|
# which will usually cut down on cache requests.
|
|
@known_method_outputs[method_name] ||= Rails.cache.read(
|
|
method_fragment_key(method_name))
|
|
!@known_method_outputs[method_name].nil?
|
|
end
|
|
|
|
def as_json(options={})
|
|
cache_method(:as_json)
|
|
end
|
|
|
|
private
|
|
|
|
def cache_method(method_name, &block)
|
|
# Two layers of cache: a local copy, in case the method is called again,
|
|
# and then the Rails cache, before we hit the actual method call.
|
|
@known_method_outputs[method_name] ||= begin
|
|
key = method_fragment_key(method_name)
|
|
Rails.cache.fetch(key) { item.send(method_name) }
|
|
end
|
|
end
|
|
|
|
def item
|
|
@item ||= Item.find(@id)
|
|
end
|
|
|
|
def method_fragment_key(method_name)
|
|
localize_fragment_key("item/#{@id}##{method_name}", I18n.locale)
|
|
end
|
|
end
|
|
end |