Skip to content

Commit

Permalink
Setup the cache in an initializer (#67)
Browse files Browse the repository at this point in the history
The cache cannot be setup until ActiveRecord has been initialized. We'll
configure it in an after_initialize hook to avoid the hit of building
the consistent hash on the first cache lookup.
  • Loading branch information
djmb authored Sep 13, 2023
1 parent df2b80d commit a8e6f8c
Show file tree
Hide file tree
Showing 4 changed files with 35 additions and 24 deletions.
50 changes: 26 additions & 24 deletions lib/solid_cache/cluster/connection_handling.rb
Original file line number Diff line number Diff line change
Expand Up @@ -15,17 +15,40 @@ def initialize(options = {})
end

# Done lazily as the cache maybe created before ActionRecord initialization
@shards_initialized = false
@setup = false
end

def setup?
@setup
end

def setup!
return if setup?

case @shard_options
when Array, NilClass
@shards = @shard_options || SolidCache.all_shard_keys || []
@nodes = @shards.to_h { |shard| [ shard, shard ] }
when Hash
@shards = @shard_options.keys
@nodes = @shard_options.invert
end

if @shards.count > 1
@consistent_hash = MaglevHash.new(@nodes.keys)
end

@setup = true
end

def shards
initialize_shards unless shards_initialized?
setup!

@shards
end

def nodes
initialize_shards unless shards_initialized?
setup!

@nodes
end
Expand Down Expand Up @@ -71,27 +94,6 @@ def reading_shard(normalized_key:)
private
attr_reader :consistent_hash

def shards_initialized?
@shards_initialized
end

def initialize_shards
case @shard_options
when Array, NilClass
@shards = @shard_options || SolidCache.all_shard_keys || []
@nodes = @shards.to_h { |shard| [ shard, shard ] }
when Hash
@shards = @shard_options.keys
@nodes = @shard_options.invert
end

if @shards.count > 1
@consistent_hash = MaglevHash.new(@nodes.keys)
end

@shards_initialized = true
end

def with_shard(shard)
if shard
Record.connected_to(shard: shard) { yield }
Expand Down
4 changes: 4 additions & 0 deletions lib/solid_cache/engine.rb
Original file line number Diff line number Diff line change
Expand Up @@ -13,5 +13,9 @@ class Engine < ::Rails::Engine
SolidCache.executor = config.solid_cache.executor
SolidCache.connects_to = config.solid_cache.connects_to
end

config.after_initialize do
Rails.cache.setup! if Rails.cache.is_a?(Store)
end
end
end
4 changes: 4 additions & 0 deletions lib/solid_cache/store.rb
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,10 @@ def initialize(options = {})
@primary_cluster = clusters.first
end

def setup!
clusters.each(&:setup!)
end

def delete_matched(matcher, options = {})
instrument :delete_matched, matcher do
raise ArgumentError, "Only strings are supported: #{matcher.inspect}" unless String === matcher
Expand Down
1 change: 1 addition & 0 deletions test/unit/cluster_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ class ClusterTest < ActiveSupport::TestCase

@primary_cache.delete("foo")
@cache.fetch("foo") { 2 }
sleep 0.1

assert_equal 2, @cache.read("foo")
assert_equal 2, @primary_cache.read("foo")
Expand Down

0 comments on commit a8e6f8c

Please sign in to comment.