mirror of
https://github.com/ditkrg/active_model_serializers.git
synced 2026-01-22 22:06:50 +00:00
Add basic caching
This commit is contained in:
parent
6408b73e3c
commit
b4395f281b
@ -69,7 +69,15 @@ module ActiveModel
|
||||
class_attribute :use_default_render_json
|
||||
self.use_default_render_json = false
|
||||
|
||||
class_attribute :cache
|
||||
class_attribute :perform_caching
|
||||
|
||||
class << self
|
||||
# set peform caching like root
|
||||
def cache(value = true)
|
||||
self.perform_caching = value
|
||||
end
|
||||
|
||||
# Define attributes to be used in the serialization.
|
||||
def attributes(*attrs)
|
||||
|
||||
@ -266,6 +274,16 @@ module ActiveModel
|
||||
hash[meta_key] = @options[:meta] if @options.has_key?(:meta)
|
||||
end
|
||||
|
||||
def to_json(*args)
|
||||
if perform_caching?
|
||||
cache.fetch expand_cache_key([self.class.to_s.underscore, object.cache_key, 'to-json']) do
|
||||
super
|
||||
end
|
||||
else
|
||||
super
|
||||
end
|
||||
end
|
||||
|
||||
# Returns a json representation of the serializable
|
||||
# object including the root.
|
||||
def as_json(options={})
|
||||
@ -284,10 +302,15 @@ module ActiveModel
|
||||
# Returns a hash representation of the serializable
|
||||
# object without the root.
|
||||
def serializable_hash
|
||||
return nil if @object.nil?
|
||||
@node = attributes
|
||||
include_associations! if _embed
|
||||
@node
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
if perform_caching?
|
||||
cache.fetch expand_cache_key([self.class.to_s.underscore, object.cache_key, 'serializable-hash']) do
|
||||
_serializable_hash
|
||||
end
|
||||
else
|
||||
_serializable_hash
|
||||
end
|
||||
end
|
||||
|
||||
def include_associations!
|
||||
@ -400,6 +423,31 @@ module ActiveModel
|
||||
|
||||
alias :read_attribute_for_serialization :send
|
||||
|
||||
# def _serializable_hash
|
||||
# instrument(:serialize, :serializer => self.class.name) do
|
||||
# node = attributes
|
||||
# instrument :associations do
|
||||
# include_associations!(node) if _embed
|
||||
# end
|
||||
# node
|
||||
# end
|
||||
# end
|
||||
|
||||
def _serializable_hash
|
||||
return nil if @object.nil?
|
||||
@node = attributes
|
||||
include_associations! if _embed
|
||||
@node
|
||||
end
|
||||
|
||||
def perform_caching?
|
||||
perform_caching && cache && object.respond_to?(:cache_key)
|
||||
end
|
||||
|
||||
def expand_cache_key(*args)
|
||||
ActiveSupport::Cache.expand_cache_key(args)
|
||||
end
|
||||
|
||||
# Use ActiveSupport::Notifications to send events to external systems.
|
||||
# The event name is: name.class_name.serializer
|
||||
def instrument(name, payload = {}, &block)
|
||||
|
||||
97
test/caching_test.rb
Normal file
97
test/caching_test.rb
Normal file
@ -0,0 +1,97 @@
|
||||
require "test_helper"
|
||||
|
||||
class CachingTest < ActiveModel::TestCase
|
||||
class NullStore
|
||||
def fetch(key)
|
||||
return store[key] if store[key]
|
||||
|
||||
store[key] = yield
|
||||
end
|
||||
|
||||
def clear
|
||||
store.clear
|
||||
end
|
||||
|
||||
def store
|
||||
@store ||= {}
|
||||
end
|
||||
|
||||
def read(key)
|
||||
store[key]
|
||||
end
|
||||
end
|
||||
|
||||
class Programmer
|
||||
def name
|
||||
'Adam'
|
||||
end
|
||||
|
||||
def skills
|
||||
%w(ruby)
|
||||
end
|
||||
|
||||
def cache_key
|
||||
name
|
||||
end
|
||||
|
||||
def read_attribute_for_serialization(name)
|
||||
send name
|
||||
end
|
||||
end
|
||||
|
||||
def test_serializers_have_a_cache_store
|
||||
ActiveModel::Serializer.cache = NullStore.new
|
||||
|
||||
assert ActiveModel::Serializer.cache
|
||||
end
|
||||
|
||||
def test_serializers_can_enable_caching
|
||||
serializer = Class.new(ActiveModel::Serializer) do
|
||||
cache true
|
||||
end
|
||||
|
||||
assert serializer.perform_caching
|
||||
end
|
||||
|
||||
def test_serializers_cache_serializable_hash
|
||||
serializer = Class.new(ActiveModel::Serializer) do
|
||||
cache true
|
||||
attributes :name, :skills
|
||||
|
||||
def self.to_s
|
||||
'serializer'
|
||||
end
|
||||
end
|
||||
|
||||
serializer.cache = NullStore.new
|
||||
instance = serializer.new Programmer.new
|
||||
|
||||
instance.to_json
|
||||
|
||||
assert_equal({
|
||||
:name => 'Adam',
|
||||
:skills => ['ruby'],
|
||||
}, serializer.cache.read('serializer/Adam/serializable-hash'))
|
||||
end
|
||||
|
||||
def test_serializers_cache_to_json
|
||||
serializer = Class.new(ActiveModel::Serializer) do
|
||||
cache true
|
||||
attributes :name, :skills
|
||||
|
||||
def self.to_s
|
||||
'serializer'
|
||||
end
|
||||
end
|
||||
|
||||
serializer.cache = NullStore.new
|
||||
instance = serializer.new Programmer.new
|
||||
|
||||
instance.to_json
|
||||
|
||||
assert_equal({
|
||||
:name => 'Adam',
|
||||
:skills => ['ruby'],
|
||||
}.to_json, serializer.cache.read('serializer/Adam/to-json'))
|
||||
end
|
||||
end
|
||||
Loading…
Reference in New Issue
Block a user