class ReplicaPools::ConnectionProxy
Attributes
current[RW]
current_pool[RW]
leader[RW]
leader_depth[RW]
replica_pools[RW]
Public Class Methods
generate_safe_delegations()
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 12 def generate_safe_delegations ReplicaPools.config.safe_methods.each do |method| generate_safe_delegation(method) unless instance_methods.include?(method) end end
new(leader, pools)
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 29 def initialize(leader, pools) @leader = leader @replica_pools = pools @leader_depth = 0 @current_pool = default_pool if ReplicaPools.config.defaults_to_leader @current = leader else @current = current_replica end # this ivar is for ConnectionAdapter compatibility # some gems (e.g. newrelic_rpm) will actually use # instance_variable_get(:@config) to find it. @config = current.connection_config end
Protected Class Methods
generate_safe_delegation(method)
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 20 def generate_safe_delegation(method) class_eval <<-END, __FILE__, __LINE__ + 1 def #{method}(*args, &block) route_to(current, :#{method}, *args, &block) end END end
Public Instance Methods
current_replica()
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 80 def current_replica current_pool.current end
next_replica!()
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 75 def next_replica! return if within_leader_block? self.current = current_pool.next end
transaction(*args, &block)
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 71 def transaction(*args, &block) with_leader { leader.transaction(*args, &block) } end
with_leader() { || ... }
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 57 def with_leader raise LeaderDisabled.new if ReplicaPools.config.disable_leader last_conn = self.current self.current = leader self.leader_depth += 1 yield ensure if last_conn self.leader_depth = [leader_depth - 1, 0].max self.current = last_conn end end
with_pool(pool_name = 'default') { || ... }
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 47 def with_pool(pool_name = 'default') last_conn, last_pool = self.current, self.current_pool self.current_pool = replica_pools[pool_name.to_sym] || default_pool self.current = current_replica unless within_leader_block? yield ensure self.current_pool = last_pool self.current = last_conn end
Protected Instance Methods
default_pool()
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 86 def default_pool replica_pools[:default] || replica_pools.values.first end
generate_unsafe_delegation(method)
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 102 def generate_unsafe_delegation(method) self.class_eval <<-END, __FILE__, __LINE__ + 1 def #{method}(*args, &block) route_to(leader, :#{method}, *args, &block) end END end
method_missing(method, *args, &block)
click to toggle source
Proxies any unknown methods to leader. Safe methods have been generated during `setup!`. Creates a method to speed up subsequent calls.
# File lib/replica_pools/connection_proxy.rb, line 93 def method_missing(method, *args, &block) generate_unsafe_delegation(method) send(method, *args, &block) end
route_to(conn, method, *args, &block)
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 110 def route_to(conn, method, *args, &block) raise ReplicaPools::LeaderDisabled.new if ReplicaPools.config.disable_leader && conn == leader conn.retrieve_connection.send(method, *args, &block) rescue => e ReplicaPools.log :error, "Error during ##{method}: #{e}" log_proxy_state raise e end
within_leader_block?()
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 98 def within_leader_block? leader_depth > 0 end
Private Instance Methods
log_proxy_state()
click to toggle source
# File lib/replica_pools/connection_proxy.rb, line 121 def log_proxy_state ReplicaPools.log :error, "Current Connection: #{current}" ReplicaPools.log :error, "Current Pool Name: #{current_pool.name}" ReplicaPools.log :error, "Current Pool Members: #{current_pool.replicas}" ReplicaPools.log :error, "Leader Depth: #{leader_depth}" end