class RedMatryoshka::Cache
Public Class Methods
new(cache_klass)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 3 def initialize(cache_klass) @cache_klass = cache_klass end
Public Instance Methods
cache(object)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 13 def cache(object) key = cache_keys(object.id) doll = cache_doll(object) RedMatryoshka.configuration.redis.mapped_hmset key, doll.flatten doll.expand end
cache_doll(object)
click to toggle source
TODO: Right a test only for this method
# File lib/red_matryoshka/cache.rb, line 24 def cache_doll(object) RedMatryoshka::Doll.new( merge_dependent_hashes_and_main_hash( @cache_klass.to_hash(object), associate_object(object) ), @cache_klass ) end
delete(object_id)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 34 def delete(object_id) key = cache_keys(object_id) RedMatryoshka.configuration.redis.del key end
fetch(ids)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 7 def fetch(ids) @cache_klass.after_fetch( fetch_objects(ids) ) end
Private Instance Methods
associate_object(object)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 100 def associate_object(object) @cache_klass.classes_to_depends_on.inject({}) do |associates, dependence| d = associate_object_id(dependence) d_id = @cache_klass.to_hash(object)[associate_object_id(dependence)] return associates if d_id.nil? associate_object = associate_object_key_formatter( transform_class_name(dependence[0]), d_id, self.class.new( cache_klass_with_module(dependence[0]).constantize.new ).send(:fetch_objects, d_id) ) associates.merge(d => associate_object) end end
associate_object_field(dependence)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 119 def associate_object_field(dependence) base_fetch_class = cache_klass_with_module(dependence[0]).constantize.class_to_fetch_from associate_id = dependence[1][:for] || base_fetch_class.to_s + "_id" transform_class_name(associate_id) rescue NameError base_fetch_class.to_s + "_id" end
associate_object_id(dependence)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 128 def associate_object_id(dependence) associate_object_field(dependence).to_sym end
associate_object_key_formatter(dependence_name, dependence_id, fetch_object)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 132 def associate_object_key_formatter(dependence_name, dependence_id, fetch_object) if dependence_id.is_a? Array dependence_id.map.with_index do |id, i| object_formatter(dependence_name, id, fetch_object[i]) end else object_formatter(dependence_name, dependence_id, fetch_object.first) end end
cache_keys(*object_ids)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 78 def cache_keys(*object_ids) object_ids.map do |id| @cache_klass.cache_key id end end
cache_klass_with_module(klass)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 152 def cache_klass_with_module(klass) if RedMatryoshka.configuration.module.present? "#{RedMatryoshka.configuration.module}::#{klass}" else klass end end
fetch_objects(ids)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 41 def fetch_objects(ids) ids = [ids] unless ids.is_a? Array ids = ids[0] if ids[0].is_a? Array hashes = object_from_cache(*ids) keys_to_retrieve = object_id_to_retrieve_from_db(ids, hashes) fetch_objects_from_db(keys_to_retrieve).each do |object| i = ids.find_index(object.id) hashes[i] = cache(object) end hashes.map { |hash| RedMatryoshka::Doll.new(hash, @cache_klass).expand } end
fetch_objects_from_db(object_ids_to_fetch = [])
click to toggle source
# File lib/red_matryoshka/cache.rb, line 73 def fetch_objects_from_db(object_ids_to_fetch = []) return [] unless object_ids_to_fetch.any? @cache_klass.class_to_fetch_from.constantize.find(object_ids_to_fetch) end
merge_dependent_hashes_and_main_hash(hash, dependent_hashes)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 84 def merge_dependent_hashes_and_main_hash(hash, dependent_hashes) if dependent_hashes.any? && dependent_hashes.keys.any? dependent_hashes.each do |dependence| if dependent_hashes[dependence[0]].is_a?(Array) && dependent_hashes[dependence[0]].any? hash.merge! dependent_hashes[dependence[0]].inject(&:merge) elsif dependent_hashes[dependence[0]].is_a? Hash hash.merge! dependent_hashes[dependence[0]] end hash.delete dependence[0] end end hash end
object_formatter(dependence_name, dependence_id, fetch_object)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 142 def object_formatter(dependence_name, dependence_id, fetch_object) RedMatryoshka::Doll.new(fetch_object).flatten.inject({}) do |format_hash, (k, v)| format_hash.merge "#{dependence_name}:#{dependence_id}:#{k}" => v end end
object_from_cache(*object_ids)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 55 def object_from_cache(*object_ids) keys = cache_keys(*object_ids) keys = [keys] if keys.is_a? String RedMatryoshka.configuration.redis.multi do |redis| keys.each do |key| redis.hgetall(key) end end end
object_id_to_retrieve_from_db(object_ids, redis_objects_hash)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 66 def object_id_to_retrieve_from_db(object_ids, redis_objects_hash) redis_objects_hash.each_with_index.inject([]) do |keys, (v, i)| keys << object_ids[i] if v.empty? keys # Force return to avoid case where `keys` is empty end end
transform_class_name(klass_name)
click to toggle source
# File lib/red_matryoshka/cache.rb, line 148 def transform_class_name(klass_name) klass_name.to_s.split(/(?=[A-Z])/).map(&:downcase).join("_") end