aboutsummaryrefslogtreecommitdiffstats
path: root/activesupport/lib/active_support/cache/strategy
diff options
context:
space:
mode:
Diffstat (limited to 'activesupport/lib/active_support/cache/strategy')
-rw-r--r--activesupport/lib/active_support/cache/strategy/local_cache.rb99
-rw-r--r--activesupport/lib/active_support/cache/strategy/local_cache_middleware.rb19
2 files changed, 76 insertions, 42 deletions
diff --git a/activesupport/lib/active_support/cache/strategy/local_cache.rb b/activesupport/lib/active_support/cache/strategy/local_cache.rb
index fe5bc82c30..39b32fc7f6 100644
--- a/activesupport/lib/active_support/cache/strategy/local_cache.rb
+++ b/activesupport/lib/active_support/cache/strategy/local_cache.rb
@@ -1,6 +1,8 @@
-require 'active_support/core_ext/object/duplicable'
-require 'active_support/core_ext/string/inflections'
-require 'active_support/per_thread_registry'
+# frozen_string_literal: true
+
+require "active_support/core_ext/object/duplicable"
+require "active_support/core_ext/string/inflections"
+require "active_support/per_thread_registry"
module ActiveSupport
module Cache
@@ -9,7 +11,7 @@ module ActiveSupport
# duration of a block. Repeated calls to the cache for the same key will hit the
# in-memory cache for faster access.
module LocalCache
- autoload :Middleware, 'active_support/cache/strategy/local_cache_middleware'
+ autoload :Middleware, "active_support/cache/strategy/local_cache_middleware"
# Class for storing and registering the local caches.
class LocalCacheRegistry # :nodoc:
@@ -52,6 +54,17 @@ module ActiveSupport
@data[key]
end
+ def read_multi_entries(keys, options)
+ values = {}
+
+ keys.each do |name|
+ entry = read_entry(name, options)
+ values[name] = entry.value if entry
+ end
+
+ values
+ end
+
def write_entry(key, value, options)
@data[key] = value
true
@@ -60,12 +73,17 @@ module ActiveSupport
def delete_entry(key, options)
!!@data.delete(key)
end
+
+ def fetch_entry(key, options = nil) # :nodoc:
+ @data.fetch(key) { @data[key] = yield }
+ end
end
# Use a local cache for the duration of block.
def with_local_cache
use_temporary_local_cache(LocalStore.new) { yield }
end
+
# Middleware class can be inserted as a Rack handler to be local cache for the
# duration of request.
def middleware
@@ -75,67 +93,82 @@ module ActiveSupport
end
def clear(options = nil) # :nodoc:
- local_cache.clear(options) if local_cache
+ return super unless cache = local_cache
+ cache.clear(options)
super
end
def cleanup(options = nil) # :nodoc:
- local_cache.clear(options) if local_cache
+ return super unless cache = local_cache
+ cache.clear
super
end
def increment(name, amount = 1, options = nil) # :nodoc:
- value = bypass_local_cache{super}
- set_cache_value(value, name, amount, options)
+ return super unless local_cache
+ value = bypass_local_cache { super }
+ write_cache_value(name, value, options)
value
end
def decrement(name, amount = 1, options = nil) # :nodoc:
- value = bypass_local_cache{super}
- set_cache_value(value, name, amount, options)
+ return super unless local_cache
+ value = bypass_local_cache { super }
+ write_cache_value(name, value, options)
value
end
- protected
- def read_entry(key, options) # :nodoc:
- if local_cache
- entry = local_cache.read_entry(key, options)
- unless entry
- entry = super
- local_cache.write_entry(key, entry, options)
- end
- entry
+ private
+ def read_entry(key, options)
+ if cache = local_cache
+ cache.fetch_entry(key) { super }
else
super
end
end
- def write_entry(key, entry, options) # :nodoc:
- local_cache.write_entry(key, entry, options) if local_cache
+ def read_multi_entries(keys, options)
+ return super unless local_cache
+
+ local_entries = local_cache.read_multi_entries(keys, options)
+ missed_keys = keys - local_entries.keys
+
+ if missed_keys.any?
+ local_entries.merge!(super(missed_keys, options))
+ else
+ local_entries
+ end
+ end
+
+ def write_entry(key, entry, options)
+ if options[:unless_exist]
+ local_cache.delete_entry(key, options) if local_cache
+ else
+ local_cache.write_entry(key, entry, options) if local_cache
+ end
+
super
end
- def delete_entry(key, options) # :nodoc:
+ def delete_entry(key, options)
local_cache.delete_entry(key, options) if local_cache
super
end
- def set_cache_value(value, name, amount, options) # :nodoc:
- if local_cache
- local_cache.mute do
- if value
- local_cache.write(name, value, options)
- else
- local_cache.delete(name, options)
- end
+ def write_cache_value(name, value, options)
+ name = normalize_key(name, options)
+ cache = local_cache
+ cache.mute do
+ if value
+ cache.write(name, value, options)
+ else
+ cache.delete(name, options)
end
end
end
- private
-
def local_cache_key
- @local_cache_key ||= "#{self.class.name.underscore}_local_cache_#{object_id}".gsub(/[\/-]/, '_').to_sym
+ @local_cache_key ||= "#{self.class.name.underscore}_local_cache_#{object_id}".gsub(/[\/-]/, "_").to_sym
end
def local_cache
diff --git a/activesupport/lib/active_support/cache/strategy/local_cache_middleware.rb b/activesupport/lib/active_support/cache/strategy/local_cache_middleware.rb
index a6f24b1a3c..62542bdb22 100644
--- a/activesupport/lib/active_support/cache/strategy/local_cache_middleware.rb
+++ b/activesupport/lib/active_support/cache/strategy/local_cache_middleware.rb
@@ -1,11 +1,12 @@
-require 'rack/body_proxy'
-require 'rack/utils'
+# frozen_string_literal: true
+
+require "rack/body_proxy"
+require "rack/utils"
module ActiveSupport
module Cache
module Strategy
module LocalCache
-
#--
# This class wraps up local storage for middlewares. Only the middleware method should
# construct them.
@@ -13,9 +14,9 @@ module ActiveSupport
attr_reader :name, :local_cache_key
def initialize(name, local_cache_key)
- @name = name
+ @name = name
@local_cache_key = local_cache_key
- @app = nil
+ @app = nil
end
def new(app)
@@ -29,13 +30,13 @@ module ActiveSupport
response[2] = ::Rack::BodyProxy.new(response[2]) do
LocalCacheRegistry.set_cache_for(local_cache_key, nil)
end
+ cleanup_on_body_close = true
response
rescue Rack::Utils::InvalidParameterError
- LocalCacheRegistry.set_cache_for(local_cache_key, nil)
[400, {}, []]
- rescue Exception
- LocalCacheRegistry.set_cache_for(local_cache_key, nil)
- raise
+ ensure
+ LocalCacheRegistry.set_cache_for(local_cache_key, nil) unless
+ cleanup_on_body_close
end
end
end