active_record_host_pool 1.1.0 → 1.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 7baaf5e8c49a8308e3be6a9f52b41af880f0d8182a98a12be2ce8fa6d7ccbe60
4
- data.tar.gz: aa68d84f75c00f608d13d475761f936722171f3d3d59a4ede471513279e8cda2
3
+ metadata.gz: 2dc3e41230c1cc7b208056d7f6fe99abe717e190b55cdca3ff5df9f1513fcad1
4
+ data.tar.gz: 92f1982d46da0644184083a78d72ad878d54ff70413f347fcb67bc3890cfaeca
5
5
  SHA512:
6
- metadata.gz: 072b56581266326d5decfd1221ccb9bf2ffde945cd04e1ce52278dd89d3b9e84b4d59d0a8d8e21808352d25a0f360ed67a006f71dc112751b7937a42f21aa455
7
- data.tar.gz: c6075399e78ec309aeca872079044b042a5208dc1071c068eac01928a83b588d23cfc0d268907c0a9aa5c13a7d9b99005443e644b8142cb7ad9cb8a0e7cf013a
6
+ metadata.gz: b3e4c62f5aee3ae968622ca9a7fef59fd9974c4153c244c312715036f6753a0ec58ba3083247bb9a4b9479db3a3c55a8182c85ae320d273ad90a1084ea745b46
7
+ data.tar.gz: 1fcec2e7e23272e50894a19bd4fc195e0360089d3a5e44f98fc6a589723f3a6bb8dae2276dbeeec31f05f87f89641308909412b28f73f929bc2358605fe30937
@@ -0,0 +1,150 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'delegate'
4
+ require 'active_record'
5
+ require 'active_record_host_pool/connection_adapter_mixin'
6
+
7
+ # this module sits in between ConnectionHandler and a bunch of different ConnectionPools (one per host).
8
+ # when a connection is requested, it goes like:
9
+ # ActiveRecordClass -> ConnectionHandler#connection
10
+ # ConnectionHandler#connection -> (find or create PoolProxy)
11
+ # PoolProxy -> shared list of Pools
12
+ # Pool actually gives back a connection, then PoolProxy turns this
13
+ # into a ConnectionProxy that can inform (on execute) which db we should be on.
14
+
15
+ module ActiveRecordHostPool
16
+ # Sits between ConnectionHandler and a bunch of different ConnectionPools (one per host).
17
+ class PoolProxy < Delegator
18
+ def initialize(pool_config)
19
+ super(pool_config)
20
+ @pool_config = pool_config
21
+ @config = pool_config.db_config.configuration_hash
22
+ end
23
+
24
+ def __getobj__
25
+ _connection_pool
26
+ end
27
+
28
+ def __setobj__(pool_config)
29
+ @pool_config = pool_config
30
+ @config = pool_config.db_config.configuration_hash
31
+ @_pool_key = nil
32
+ end
33
+
34
+ attr_reader :pool_config
35
+
36
+ def connection(*args)
37
+ real_connection = _connection_pool.connection(*args)
38
+ _connection_proxy_for(real_connection, @config[:database])
39
+ rescue Mysql2::Error, ActiveRecord::NoDatabaseError
40
+ _connection_pools.delete(_pool_key)
41
+ Kernel.raise
42
+ end
43
+
44
+ # by the time we are patched into ActiveRecord, the current thread has already established
45
+ # a connection. thus we need to patch both connection and checkout/checkin
46
+ def checkout(*args, &block)
47
+ cx = _connection_pool.checkout(*args, &block)
48
+ _connection_proxy_for(cx, @config[:database])
49
+ end
50
+
51
+ def checkin(cx)
52
+ cx = cx.unproxied
53
+ _connection_pool.checkin(cx)
54
+ end
55
+
56
+ def with_connection
57
+ cx = checkout
58
+ yield cx
59
+ ensure
60
+ checkin cx
61
+ end
62
+
63
+ def disconnect!
64
+ p = _connection_pool(false)
65
+ return unless p
66
+
67
+ p.disconnect!
68
+ p.automatic_reconnect = true if p.respond_to?(:automatic_reconnect=)
69
+ _clear_connection_proxy_cache
70
+ end
71
+
72
+ def automatic_reconnect=(value)
73
+ p = _connection_pool(false)
74
+ return unless p
75
+
76
+ p.automatic_reconnect = value if p.respond_to?(:automatic_reconnect=)
77
+ end
78
+
79
+ def clear_reloadable_connections!
80
+ _connection_pool.clear_reloadable_connections!
81
+ _clear_connection_proxy_cache
82
+ end
83
+
84
+ def release_connection(*args)
85
+ p = _connection_pool(false)
86
+ return unless p
87
+
88
+ p.release_connection(*args)
89
+ end
90
+
91
+ def flush!
92
+ p = _connection_pool(false)
93
+ return unless p
94
+
95
+ p.flush!
96
+ end
97
+
98
+ def discard!
99
+ p = _connection_pool(false)
100
+ return unless p
101
+
102
+ p.discard!
103
+
104
+ # All connections in the pool (even if they're currently
105
+ # leased!) have just been discarded, along with the pool itself.
106
+ # Any further interaction with the pool (except #pool_config and #schema_cache)
107
+ # is undefined.
108
+ # Remove the connection for the given key so a new one can be created in its place
109
+ _connection_pools.delete(_pool_key)
110
+ end
111
+
112
+ private
113
+
114
+ def _connection_pools
115
+ @@_connection_pools ||= {}
116
+ end
117
+
118
+ def _pool_key
119
+ @_pool_key ||= "#{@config[:host]}/#{@config[:port]}/#{@config[:socket]}/" \
120
+ "#{@config[:username]}/#{replica_configuration? && 'replica'}"
121
+ end
122
+
123
+ def _connection_pool(auto_create = true)
124
+ pool = _connection_pools[_pool_key]
125
+ if pool.nil? && auto_create
126
+ pool = _connection_pools[_pool_key] = ActiveRecord::ConnectionAdapters::ConnectionPool.new(@pool_config)
127
+ end
128
+ pool
129
+ end
130
+
131
+ def _connection_proxy_for(connection, database)
132
+ @connection_proxy_cache ||= {}
133
+ key = [connection, database]
134
+
135
+ @connection_proxy_cache[key] ||= begin
136
+ cx = ActiveRecordHostPool::ConnectionProxy.new(connection, database)
137
+ cx.execute('select 1')
138
+ cx
139
+ end
140
+ end
141
+
142
+ def _clear_connection_proxy_cache
143
+ @connection_proxy_cache = {}
144
+ end
145
+
146
+ def replica_configuration?
147
+ @config[:replica] || @config[:slave]
148
+ end
149
+ end
150
+ end
@@ -0,0 +1,152 @@
1
+ # frozen_string_literal: true
2
+
3
+ # For versions of Rails < 6.1
4
+
5
+ require 'delegate'
6
+ require 'active_record'
7
+ require 'active_record_host_pool/connection_adapter_mixin'
8
+
9
+ # this module sits in between ConnectionHandler and a bunch of different ConnectionPools (one per host).
10
+ # when a connection is requested, it goes like:
11
+ # ActiveRecordClass -> ConnectionHandler#connection
12
+ # ConnectionHandler#connection -> (find or create PoolProxy)
13
+ # PoolProxy -> shared list of Pools
14
+ # Pool actually gives back a connection, then PoolProxy turns this
15
+ # into a ConnectionProxy that can inform (on execute) which db we should be on.
16
+
17
+ module ActiveRecordHostPool
18
+ # Sits between ConnectionHandler and a bunch of different ConnectionPools (one per host).
19
+ class PoolProxy < Delegator
20
+ def initialize(spec)
21
+ super(spec)
22
+ @spec = spec
23
+ @config = spec.config
24
+ end
25
+
26
+ def __getobj__
27
+ _connection_pool
28
+ end
29
+
30
+ def __setobj__(spec)
31
+ @spec = spec
32
+ @config = spec.config
33
+ @_pool_key = nil
34
+ end
35
+
36
+ attr_reader :spec
37
+
38
+ def connection(*args)
39
+ real_connection = _connection_pool.connection(*args)
40
+ _connection_proxy_for(real_connection, @config[:database])
41
+ rescue Mysql2::Error, ActiveRecord::NoDatabaseError
42
+ _connection_pools.delete(_pool_key)
43
+ Kernel.raise
44
+ end
45
+
46
+ # by the time we are patched into ActiveRecord, the current thread has already established
47
+ # a connection. thus we need to patch both connection and checkout/checkin
48
+ def checkout(*args, &block)
49
+ cx = _connection_pool.checkout(*args, &block)
50
+ _connection_proxy_for(cx, @config[:database])
51
+ end
52
+
53
+ def checkin(cx)
54
+ cx = cx.unproxied
55
+ _connection_pool.checkin(cx)
56
+ end
57
+
58
+ def with_connection
59
+ cx = checkout
60
+ yield cx
61
+ ensure
62
+ checkin cx
63
+ end
64
+
65
+ def disconnect!
66
+ p = _connection_pool(false)
67
+ return unless p
68
+
69
+ p.disconnect!
70
+ p.automatic_reconnect = true if p.respond_to?(:automatic_reconnect=)
71
+ _clear_connection_proxy_cache
72
+ end
73
+
74
+ def automatic_reconnect=(value)
75
+ p = _connection_pool(false)
76
+ return unless p
77
+
78
+ p.automatic_reconnect = value if p.respond_to?(:automatic_reconnect=)
79
+ end
80
+
81
+ def clear_reloadable_connections!
82
+ _connection_pool.clear_reloadable_connections!
83
+ _clear_connection_proxy_cache
84
+ end
85
+
86
+ def release_connection(*args)
87
+ p = _connection_pool(false)
88
+ return unless p
89
+
90
+ p.release_connection(*args)
91
+ end
92
+
93
+ def flush!
94
+ p = _connection_pool(false)
95
+ return unless p
96
+
97
+ p.flush!
98
+ end
99
+
100
+ def discard!
101
+ p = _connection_pool(false)
102
+ return unless p
103
+
104
+ p.discard!
105
+
106
+ # All connections in the pool (even if they're currently
107
+ # leased!) have just been discarded, along with the pool itself.
108
+ # Any further interaction with the pool (except #spec and #schema_cache)
109
+ # is undefined.
110
+ # Remove the connection for the given key so a new one can be created in its place
111
+ _connection_pools.delete(_pool_key)
112
+ end
113
+
114
+ private
115
+
116
+ def _connection_pools
117
+ @@_connection_pools ||= {}
118
+ end
119
+
120
+ def _pool_key
121
+ @_pool_key ||= "#{@config[:host]}/#{@config[:port]}/#{@config[:socket]}/" \
122
+ "#{@config[:username]}/#{replica_configuration? && 'replica'}"
123
+ end
124
+
125
+ def _connection_pool(auto_create = true)
126
+ pool = _connection_pools[_pool_key]
127
+ if pool.nil? && auto_create
128
+ pool = _connection_pools[_pool_key] = ActiveRecord::ConnectionAdapters::ConnectionPool.new(@spec)
129
+ end
130
+ pool
131
+ end
132
+
133
+ def _connection_proxy_for(connection, database)
134
+ @connection_proxy_cache ||= {}
135
+ key = [connection, database]
136
+
137
+ @connection_proxy_cache[key] ||= begin
138
+ cx = ActiveRecordHostPool::ConnectionProxy.new(connection, database)
139
+ cx.execute('select 1')
140
+ cx
141
+ end
142
+ end
143
+
144
+ def _clear_connection_proxy_cache
145
+ @connection_proxy_cache = {}
146
+ end
147
+
148
+ def replica_configuration?
149
+ @config[:replica] || @config[:slave]
150
+ end
151
+ end
152
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module ActiveRecordHostPool
4
- VERSION = "1.1.0"
4
+ VERSION = "1.1.1"
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: active_record_host_pool
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.0
4
+ version: 1.1.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Benjamin Quorning
@@ -163,6 +163,8 @@ files:
163
163
  - lib/active_record_host_pool/connection_adapter_mixin.rb
164
164
  - lib/active_record_host_pool/connection_proxy.rb
165
165
  - lib/active_record_host_pool/pool_proxy.rb
166
+ - lib/active_record_host_pool/pool_proxy_6_1.rb
167
+ - lib/active_record_host_pool/pool_proxy_legacy.rb
166
168
  - lib/active_record_host_pool/version.rb
167
169
  - test/database.yml
168
170
  - test/helper.rb