switchman 3.4.2 → 3.6.7
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Rakefile +15 -14
- data/db/migrate/20180828183945_add_default_shard_index.rb +1 -1
- data/db/migrate/20190114212900_add_unique_name_indexes.rb +10 -4
- data/lib/switchman/active_record/abstract_adapter.rb +4 -2
- data/lib/switchman/active_record/associations.rb +89 -16
- data/lib/switchman/active_record/attribute_methods.rb +67 -22
- data/lib/switchman/active_record/base.rb +112 -22
- data/lib/switchman/active_record/calculations.rb +93 -37
- data/lib/switchman/active_record/connection_handler.rb +18 -0
- data/lib/switchman/active_record/connection_pool.rb +18 -14
- data/lib/switchman/active_record/database_configurations.rb +37 -15
- data/lib/switchman/active_record/finder_methods.rb +44 -14
- data/lib/switchman/active_record/log_subscriber.rb +11 -5
- data/lib/switchman/active_record/migration.rb +28 -9
- data/lib/switchman/active_record/pending_migration_connection.rb +17 -0
- data/lib/switchman/active_record/persistence.rb +22 -0
- data/lib/switchman/active_record/postgresql_adapter.rb +11 -10
- data/lib/switchman/active_record/predicate_builder.rb +2 -2
- data/lib/switchman/active_record/query_cache.rb +49 -20
- data/lib/switchman/active_record/query_methods.rb +93 -30
- data/lib/switchman/active_record/relation.rb +22 -11
- data/lib/switchman/active_record/spawn_methods.rb +2 -2
- data/lib/switchman/active_record/statement_cache.rb +2 -2
- data/lib/switchman/active_record/tasks/database_tasks.rb +6 -1
- data/lib/switchman/active_record/test_fixtures.rb +26 -16
- data/lib/switchman/active_support/cache.rb +9 -4
- data/lib/switchman/arel.rb +34 -18
- data/lib/switchman/call_super.rb +2 -8
- data/lib/switchman/database_server.rb +68 -21
- data/lib/switchman/default_shard.rb +14 -3
- data/lib/switchman/engine.rb +39 -19
- data/lib/switchman/environment.rb +2 -2
- data/lib/switchman/errors.rb +4 -1
- data/lib/switchman/guard_rail/relation.rb +1 -2
- data/lib/switchman/parallel.rb +5 -5
- data/lib/switchman/r_spec_helper.rb +11 -11
- data/lib/switchman/shard.rb +166 -64
- data/lib/switchman/sharded_instrumenter.rb +7 -3
- data/lib/switchman/standard_error.rb +4 -0
- data/lib/switchman/test_helper.rb +2 -2
- data/lib/switchman/version.rb +1 -1
- data/lib/switchman.rb +27 -15
- data/lib/tasks/switchman.rake +117 -51
- metadata +19 -44
data/lib/switchman.rb
CHANGED
@@ -1,12 +1,12 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
require
|
4
|
-
require
|
3
|
+
require "guard_rail"
|
4
|
+
require "zeitwerk"
|
5
5
|
|
6
6
|
class SwitchmanInflector < Zeitwerk::GemInflector
|
7
7
|
def camelize(basename, abspath)
|
8
8
|
if basename =~ /\Apostgresql_(.*)/
|
9
|
-
|
9
|
+
"PostgreSQL" + super($1, abspath)
|
10
10
|
else
|
11
11
|
super
|
12
12
|
end
|
@@ -18,21 +18,33 @@ loader.inflector = SwitchmanInflector.new(__FILE__)
|
|
18
18
|
loader.setup
|
19
19
|
|
20
20
|
module Switchman
|
21
|
-
|
22
|
-
# TODO: load from yaml
|
23
|
-
@config ||= {}
|
24
|
-
end
|
21
|
+
Deprecation = ::ActiveSupport::Deprecation.new("4.0", "Switchman")
|
25
22
|
|
26
|
-
|
27
|
-
|
28
|
-
end
|
23
|
+
class << self
|
24
|
+
attr_writer :cache
|
29
25
|
|
30
|
-
|
31
|
-
|
32
|
-
|
26
|
+
def config
|
27
|
+
# TODO: load from yaml
|
28
|
+
@config ||= {}
|
29
|
+
end
|
30
|
+
|
31
|
+
def cache
|
32
|
+
(@cache.respond_to?(:call) ? @cache.call : @cache) || ::Rails.cache
|
33
|
+
end
|
34
|
+
|
35
|
+
def region
|
36
|
+
config[:region]
|
37
|
+
end
|
33
38
|
|
34
|
-
|
35
|
-
|
39
|
+
def foreign_key_check(name, type, limit: nil)
|
40
|
+
return unless name.to_s.end_with?("_id") && type.to_s == "integer" && limit.to_i < 8
|
41
|
+
|
42
|
+
puts <<~TEXT.squish
|
43
|
+
WARNING: All foreign keys need to be 8-byte integers.
|
44
|
+
#{name} looks like a foreign key.
|
45
|
+
If so, please add the option: `:limit => 8`
|
46
|
+
TEXT
|
47
|
+
end
|
36
48
|
end
|
37
49
|
|
38
50
|
class OrderOnMultiShardQuery < RuntimeError; end
|
data/lib/tasks/switchman.rake
CHANGED
@@ -2,8 +2,8 @@
|
|
2
2
|
|
3
3
|
# In rails 7.0+ if you have only 1 db in the env it doesn't try to do explicit activation
|
4
4
|
# (and for rails purposes we only have one db per env because each database server is a separate env)
|
5
|
-
if Rails.version <
|
6
|
-
task_prefix = Rake::Task.task_defined?(
|
5
|
+
if Rails.version < "7.0"
|
6
|
+
task_prefix = Rake::Task.task_defined?("app:db:migrate") ? "app:db" : "db"
|
7
7
|
Rake::Task["#{task_prefix}:migrate"].clear_actions.enhance do
|
8
8
|
ActiveRecord::Tasks::DatabaseTasks.migrate
|
9
9
|
# Ensure this doesn't blow up when running inside the dummy app
|
@@ -13,28 +13,29 @@ end
|
|
13
13
|
|
14
14
|
module Switchman
|
15
15
|
module Rake
|
16
|
-
def self.filter_database_servers
|
17
|
-
|
18
|
-
|
16
|
+
def self.filter_database_servers
|
17
|
+
# use a local variable so that the current chain is closed over in the following lambda
|
18
|
+
chain = filter_database_servers_chain
|
19
|
+
@filter_database_servers_chain = ->(servers) { yield(servers, chain) }
|
19
20
|
end
|
20
21
|
|
21
22
|
def self.scope(base_scope = Shard,
|
22
|
-
database_server: ENV.fetch(
|
23
|
-
shard: ENV.fetch(
|
23
|
+
database_server: ENV.fetch("DATABASE_SERVER", nil),
|
24
|
+
shard: ENV.fetch("SHARD", nil))
|
24
25
|
servers = DatabaseServer.all
|
25
26
|
|
26
27
|
if database_server
|
27
28
|
servers = database_server
|
28
|
-
if servers.first ==
|
29
|
+
if servers.first == "-"
|
29
30
|
negative = true
|
30
31
|
servers = servers[1..]
|
31
32
|
end
|
32
|
-
servers = servers.split(
|
33
|
-
open = servers.delete(
|
33
|
+
servers = servers.split(",")
|
34
|
+
open = servers.delete("open")
|
34
35
|
|
35
|
-
servers = servers.
|
36
|
+
servers = servers.filter_map { |server| DatabaseServer.find(server) }
|
36
37
|
if open
|
37
|
-
open_servers = DatabaseServer.
|
38
|
+
open_servers = DatabaseServer.select { |server| server.config[:open] }
|
38
39
|
servers.concat(open_servers)
|
39
40
|
servers << DatabaseServer.find(nil) if open_servers.empty?
|
40
41
|
servers.uniq!
|
@@ -42,9 +43,22 @@ module Switchman
|
|
42
43
|
servers = DatabaseServer.all - servers if negative
|
43
44
|
end
|
44
45
|
|
46
|
+
ENV["REGION"]&.split(",")&.each do |region|
|
47
|
+
method = :select!
|
48
|
+
if region[0] == "-"
|
49
|
+
method = :reject!
|
50
|
+
region = region[1..]
|
51
|
+
end
|
52
|
+
if region == "self"
|
53
|
+
servers.send(method, &:in_current_region?)
|
54
|
+
else
|
55
|
+
servers.send(method) { |server| server.in_region?(region) }
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
45
59
|
servers = filter_database_servers_chain.call(servers)
|
46
60
|
|
47
|
-
scope = base_scope.order(::Arel.sql(
|
61
|
+
scope = base_scope.order(::Arel.sql("database_server_id IS NOT NULL, database_server_id, id"))
|
48
62
|
if servers != DatabaseServer.all
|
49
63
|
database_server_ids = servers.map(&:id)
|
50
64
|
database_server_ids << nil if servers.include?(Shard.default.database_server)
|
@@ -57,36 +71,81 @@ module Switchman
|
|
57
71
|
end
|
58
72
|
|
59
73
|
def self.options
|
60
|
-
{ parallel: ENV[
|
74
|
+
{ exception: (ENV["FAIL_FAST"] == "0") ? :defer : :raise, parallel: ENV["PARALLEL"].to_i }
|
61
75
|
end
|
62
76
|
|
63
77
|
# classes - an array or proc, to activate as the current shard during the
|
64
78
|
# task.
|
65
79
|
def self.shardify_task(task_name, classes: [::ActiveRecord::Base])
|
80
|
+
log_format = ENV.fetch("LOG_FORMAT", nil)
|
66
81
|
old_task = ::Rake::Task[task_name]
|
67
82
|
old_actions = old_task.actions.dup
|
68
83
|
old_task.actions.clear
|
69
84
|
|
70
85
|
old_task.enhance do |*task_args|
|
71
86
|
if ::Rails.env.test?
|
72
|
-
require
|
87
|
+
require "switchman/test_helper"
|
73
88
|
TestHelper.recreate_persistent_test_shards(dont_create: true)
|
74
89
|
end
|
75
90
|
|
76
91
|
::GuardRail.activate(:deploy) do
|
77
92
|
Shard.default.database_server.unguard do
|
78
93
|
classes = classes.call if classes.respond_to?(:call)
|
79
|
-
|
94
|
+
|
95
|
+
# We don't want the shard status messages to be wrapped using a custom log transfomer
|
96
|
+
original_stderr = $stderr
|
97
|
+
original_stdout = $stdout
|
98
|
+
output = if log_format == "json"
|
99
|
+
lambda { |msg|
|
100
|
+
JSON.dump(shard: Shard.current.id,
|
101
|
+
database_server: Shard.current.database_server.id,
|
102
|
+
type: "log",
|
103
|
+
message: msg)
|
104
|
+
}
|
105
|
+
else
|
106
|
+
nil
|
107
|
+
end
|
108
|
+
Shard.with_each_shard(scope, classes, output: output, **options) do
|
80
109
|
shard = Shard.current
|
81
|
-
|
110
|
+
|
111
|
+
if log_format == "json"
|
112
|
+
original_stdout.puts JSON.dump(
|
113
|
+
shard: shard.id,
|
114
|
+
database_server: shard.database_server.id,
|
115
|
+
type: "started"
|
116
|
+
)
|
117
|
+
else
|
118
|
+
original_stdout.puts "#{shard.id}: #{shard.description}"
|
119
|
+
end
|
82
120
|
|
83
121
|
shard.database_server.unguard do
|
84
122
|
old_actions.each { |action| action.call(*task_args) }
|
85
123
|
end
|
124
|
+
|
125
|
+
if log_format == "json"
|
126
|
+
original_stdout.puts JSON.dump(
|
127
|
+
shard: shard.id,
|
128
|
+
database_server: shard.database_server.id,
|
129
|
+
type: "completed"
|
130
|
+
)
|
131
|
+
end
|
86
132
|
nil
|
133
|
+
rescue => e
|
134
|
+
if log_format == "json"
|
135
|
+
original_stderr.puts JSON.dump(
|
136
|
+
shard: shard.id,
|
137
|
+
database_server: shard.database_server.id,
|
138
|
+
type: "failed",
|
139
|
+
message: e.full_message
|
140
|
+
)
|
141
|
+
end
|
142
|
+
|
143
|
+
raise
|
87
144
|
end
|
88
145
|
rescue => e
|
89
|
-
|
146
|
+
if options[:parallel] != 0
|
147
|
+
warn "Exception from #{e.current_shard.id}: #{e.current_shard.description}:\n#{e.full_message}"
|
148
|
+
end
|
90
149
|
raise
|
91
150
|
end
|
92
151
|
end
|
@@ -98,7 +157,7 @@ module Switchman
|
|
98
157
|
end
|
99
158
|
|
100
159
|
def self.shard_scope(scope, raw_shard_ids)
|
101
|
-
raw_shard_ids = raw_shard_ids.split(
|
160
|
+
raw_shard_ids = raw_shard_ids.split(",")
|
102
161
|
|
103
162
|
shard_ids = []
|
104
163
|
negative_shard_ids = []
|
@@ -108,13 +167,13 @@ module Switchman
|
|
108
167
|
|
109
168
|
raw_shard_ids.each do |id|
|
110
169
|
case id
|
111
|
-
when
|
170
|
+
when "default"
|
112
171
|
shard_ids << Shard.default.id
|
113
|
-
when
|
172
|
+
when "-default"
|
114
173
|
negative_shard_ids << Shard.default.id
|
115
|
-
when
|
174
|
+
when "primary"
|
116
175
|
shard_ids.concat(Shard.primary.pluck(:id))
|
117
|
-
when
|
176
|
+
when "-primary"
|
118
177
|
negative_shard_ids.concat(Shard.primary.pluck(:id))
|
119
178
|
when /^(-?)(\d+)?\.\.(\.)?(\d+)?$/
|
120
179
|
negative, start, open, finish = $1.present?, $2, $3.present?, $4
|
@@ -122,8 +181,8 @@ module Switchman
|
|
122
181
|
|
123
182
|
range = []
|
124
183
|
range << "id>=#{start}" if start
|
125
|
-
range << "id<#{
|
126
|
-
(negative ? negative_ranges : ranges) << "(#{range.join(
|
184
|
+
range << "id<#{"=" unless open}#{finish}" if finish
|
185
|
+
(negative ? negative_ranges : ranges) << "(#{range.join(" AND ")})"
|
127
186
|
when /^-(\d+)$/
|
128
187
|
negative_shard_ids << $1.to_i
|
129
188
|
when /^\d+$/
|
@@ -151,21 +210,21 @@ module Switchman
|
|
151
210
|
select = []
|
152
211
|
if index != 1
|
153
212
|
subscope = subscope.offset(per_chunk * (index - 1))
|
154
|
-
select <<
|
213
|
+
select << "MIN(id) AS min_id"
|
155
214
|
end
|
156
215
|
if index != denominator
|
157
216
|
subscope = subscope.limit(per_chunk)
|
158
|
-
select <<
|
217
|
+
select << "MAX(id) AS max_id"
|
159
218
|
end
|
160
219
|
|
161
|
-
result = Shard.from(subscope).select(select.join(
|
220
|
+
result = Shard.from(subscope).select(select.join(", ")).to_a.first
|
162
221
|
range = case index
|
163
222
|
when 1
|
164
|
-
"id<=#{result[
|
223
|
+
"id<=#{result["max_id"]}"
|
165
224
|
when denominator
|
166
|
-
"id>=#{result[
|
225
|
+
"id>=#{result["min_id"]}"
|
167
226
|
else
|
168
|
-
"(id>=#{result[
|
227
|
+
"(id>=#{result["min_id"]} AND id<=#{result["max_id"]})"
|
169
228
|
end
|
170
229
|
|
171
230
|
(numerator.negative? ? negative_ranges : ranges) << range
|
@@ -186,16 +245,16 @@ module Switchman
|
|
186
245
|
|
187
246
|
conditions = []
|
188
247
|
positive_queries = []
|
189
|
-
positive_queries << ranges.join(
|
248
|
+
positive_queries << ranges.join(" OR ") unless ranges.empty?
|
190
249
|
unless shard_ids.empty?
|
191
|
-
positive_queries <<
|
250
|
+
positive_queries << "id IN (?)"
|
192
251
|
conditions << shard_ids
|
193
252
|
end
|
194
|
-
positive_query = positive_queries.join(
|
253
|
+
positive_query = positive_queries.join(" OR ")
|
195
254
|
scope = scope.where(positive_query, *conditions) unless positive_queries.empty?
|
196
255
|
|
197
|
-
scope = scope.where("NOT (#{negative_ranges.join(
|
198
|
-
scope = scope.where(
|
256
|
+
scope = scope.where("NOT (#{negative_ranges.join(" OR")})") unless negative_ranges.empty?
|
257
|
+
scope = scope.where("id NOT IN (?)", negative_shard_ids) unless negative_shard_ids.empty?
|
199
258
|
scope
|
200
259
|
end
|
201
260
|
|
@@ -206,21 +265,28 @@ module Switchman
|
|
206
265
|
|
207
266
|
module ActiveRecord
|
208
267
|
module PostgreSQLDatabaseTasks
|
209
|
-
|
210
|
-
|
211
|
-
|
212
|
-
|
213
|
-
|
214
|
-
|
215
|
-
|
216
|
-
|
217
|
-
|
218
|
-
|
219
|
-
|
220
|
-
|
221
|
-
|
222
|
-
|
223
|
-
|
268
|
+
if ::Rails.version < "7.0"
|
269
|
+
def structure_dump(filename, extra_flags = nil)
|
270
|
+
set_psql_env
|
271
|
+
args = ["--schema-only", "--no-privileges", "--no-owner", "--file", filename]
|
272
|
+
args.concat(Array(extra_flags)) if extra_flags
|
273
|
+
shard = Shard.current.name
|
274
|
+
serialized_search_path = shard
|
275
|
+
args << "--schema=#{Shellwords.escape(shard)}"
|
276
|
+
|
277
|
+
ignore_tables = ::ActiveRecord::SchemaDumper.ignore_tables
|
278
|
+
args += ignore_tables.flat_map { |table| ["-T", table] } if ignore_tables.any?
|
279
|
+
|
280
|
+
args << db_config.database
|
281
|
+
run_cmd("pg_dump", args, "dumping")
|
282
|
+
remove_sql_header_comments(filename)
|
283
|
+
File.open(filename, "a") { |f| f << "SET search_path TO #{serialized_search_path};\n\n" }
|
284
|
+
end
|
285
|
+
else
|
286
|
+
def structure_dump(...)
|
287
|
+
::ActiveRecord.dump_schemas = Switchman::Shard.current.name
|
288
|
+
super
|
289
|
+
end
|
224
290
|
end
|
225
291
|
end
|
226
292
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: switchman
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.
|
4
|
+
version: 3.6.7
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Cody Cutrer
|
@@ -10,7 +10,7 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date:
|
13
|
+
date: 2024-09-11 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: activerecord
|
@@ -21,7 +21,7 @@ dependencies:
|
|
21
21
|
version: 6.1.4
|
22
22
|
- - "<"
|
23
23
|
- !ruby/object:Gem::Version
|
24
|
-
version: '7.
|
24
|
+
version: '7.2'
|
25
25
|
type: :runtime
|
26
26
|
prerelease: false
|
27
27
|
version_requirements: !ruby/object:Gem::Requirement
|
@@ -31,7 +31,7 @@ dependencies:
|
|
31
31
|
version: 6.1.4
|
32
32
|
- - "<"
|
33
33
|
- !ruby/object:Gem::Version
|
34
|
-
version: '7.
|
34
|
+
version: '7.2'
|
35
35
|
- !ruby/object:Gem::Dependency
|
36
36
|
name: guardrail
|
37
37
|
requirement: !ruby/object:Gem::Requirement
|
@@ -69,7 +69,7 @@ dependencies:
|
|
69
69
|
version: '6.1'
|
70
70
|
- - "<"
|
71
71
|
- !ruby/object:Gem::Version
|
72
|
-
version: '7.
|
72
|
+
version: '7.2'
|
73
73
|
type: :runtime
|
74
74
|
prerelease: false
|
75
75
|
version_requirements: !ruby/object:Gem::Requirement
|
@@ -79,35 +79,21 @@ dependencies:
|
|
79
79
|
version: '6.1'
|
80
80
|
- - "<"
|
81
81
|
- !ruby/object:Gem::Version
|
82
|
-
version: '7.
|
82
|
+
version: '7.2'
|
83
83
|
- !ruby/object:Gem::Dependency
|
84
|
-
name:
|
84
|
+
name: debug
|
85
85
|
requirement: !ruby/object:Gem::Requirement
|
86
86
|
requirements:
|
87
87
|
- - "~>"
|
88
88
|
- !ruby/object:Gem::Version
|
89
|
-
version:
|
89
|
+
version: '1.8'
|
90
90
|
type: :development
|
91
91
|
prerelease: false
|
92
92
|
version_requirements: !ruby/object:Gem::Requirement
|
93
93
|
requirements:
|
94
94
|
- - "~>"
|
95
95
|
- !ruby/object:Gem::Version
|
96
|
-
version:
|
97
|
-
- !ruby/object:Gem::Dependency
|
98
|
-
name: byebug
|
99
|
-
requirement: !ruby/object:Gem::Requirement
|
100
|
-
requirements:
|
101
|
-
- - ">="
|
102
|
-
- !ruby/object:Gem::Version
|
103
|
-
version: '0'
|
104
|
-
type: :development
|
105
|
-
prerelease: false
|
106
|
-
version_requirements: !ruby/object:Gem::Requirement
|
107
|
-
requirements:
|
108
|
-
- - ">="
|
109
|
-
- !ruby/object:Gem::Version
|
110
|
-
version: '0'
|
96
|
+
version: '1.8'
|
111
97
|
- !ruby/object:Gem::Dependency
|
112
98
|
name: pg
|
113
99
|
requirement: !ruby/object:Gem::Requirement
|
@@ -122,20 +108,6 @@ dependencies:
|
|
122
108
|
- - "~>"
|
123
109
|
- !ruby/object:Gem::Version
|
124
110
|
version: '1.2'
|
125
|
-
- !ruby/object:Gem::Dependency
|
126
|
-
name: pry
|
127
|
-
requirement: !ruby/object:Gem::Requirement
|
128
|
-
requirements:
|
129
|
-
- - ">="
|
130
|
-
- !ruby/object:Gem::Version
|
131
|
-
version: '0'
|
132
|
-
type: :development
|
133
|
-
prerelease: false
|
134
|
-
version_requirements: !ruby/object:Gem::Requirement
|
135
|
-
requirements:
|
136
|
-
- - ">="
|
137
|
-
- !ruby/object:Gem::Version
|
138
|
-
version: '0'
|
139
111
|
- !ruby/object:Gem::Dependency
|
140
112
|
name: rake
|
141
113
|
requirement: !ruby/object:Gem::Requirement
|
@@ -170,14 +142,14 @@ dependencies:
|
|
170
142
|
requirements:
|
171
143
|
- - "~>"
|
172
144
|
- !ruby/object:Gem::Version
|
173
|
-
version: '
|
145
|
+
version: '6.0'
|
174
146
|
type: :development
|
175
147
|
prerelease: false
|
176
148
|
version_requirements: !ruby/object:Gem::Requirement
|
177
149
|
requirements:
|
178
150
|
- - "~>"
|
179
151
|
- !ruby/object:Gem::Version
|
180
|
-
version: '
|
152
|
+
version: '6.0'
|
181
153
|
- !ruby/object:Gem::Dependency
|
182
154
|
name: rubocop
|
183
155
|
requirement: !ruby/object:Gem::Requirement
|
@@ -193,19 +165,19 @@ dependencies:
|
|
193
165
|
- !ruby/object:Gem::Version
|
194
166
|
version: '1.10'
|
195
167
|
- !ruby/object:Gem::Dependency
|
196
|
-
name: rubocop-
|
168
|
+
name: rubocop-inst
|
197
169
|
requirement: !ruby/object:Gem::Requirement
|
198
170
|
requirements:
|
199
171
|
- - "~>"
|
200
172
|
- !ruby/object:Gem::Version
|
201
|
-
version: '1
|
173
|
+
version: '1'
|
202
174
|
type: :development
|
203
175
|
prerelease: false
|
204
176
|
version_requirements: !ruby/object:Gem::Requirement
|
205
177
|
requirements:
|
206
178
|
- - "~>"
|
207
179
|
- !ruby/object:Gem::Version
|
208
|
-
version: '1
|
180
|
+
version: '1'
|
209
181
|
- !ruby/object:Gem::Dependency
|
210
182
|
name: rubocop-rake
|
211
183
|
requirement: !ruby/object:Gem::Requirement
|
@@ -269,6 +241,7 @@ files:
|
|
269
241
|
- lib/switchman/active_record/attribute_methods.rb
|
270
242
|
- lib/switchman/active_record/base.rb
|
271
243
|
- lib/switchman/active_record/calculations.rb
|
244
|
+
- lib/switchman/active_record/connection_handler.rb
|
272
245
|
- lib/switchman/active_record/connection_pool.rb
|
273
246
|
- lib/switchman/active_record/database_configurations.rb
|
274
247
|
- lib/switchman/active_record/database_configurations/database_config.rb
|
@@ -276,6 +249,7 @@ files:
|
|
276
249
|
- lib/switchman/active_record/log_subscriber.rb
|
277
250
|
- lib/switchman/active_record/migration.rb
|
278
251
|
- lib/switchman/active_record/model_schema.rb
|
252
|
+
- lib/switchman/active_record/pending_migration_connection.rb
|
279
253
|
- lib/switchman/active_record/persistence.rb
|
280
254
|
- lib/switchman/active_record/postgresql_adapter.rb
|
281
255
|
- lib/switchman/active_record/predicate_builder.rb
|
@@ -315,6 +289,7 @@ licenses:
|
|
315
289
|
- MIT
|
316
290
|
metadata:
|
317
291
|
rubygems_mfa_required: 'true'
|
292
|
+
source_code_uri: https://github.com/instructure/switchman
|
318
293
|
post_install_message:
|
319
294
|
rdoc_options: []
|
320
295
|
require_paths:
|
@@ -323,14 +298,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
323
298
|
requirements:
|
324
299
|
- - ">="
|
325
300
|
- !ruby/object:Gem::Version
|
326
|
-
version: '
|
301
|
+
version: '3.0'
|
327
302
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
328
303
|
requirements:
|
329
304
|
- - ">="
|
330
305
|
- !ruby/object:Gem::Version
|
331
306
|
version: '0'
|
332
307
|
requirements: []
|
333
|
-
rubygems_version: 3.
|
308
|
+
rubygems_version: 3.2.33
|
334
309
|
signing_key:
|
335
310
|
specification_version: 4
|
336
311
|
summary: Rails sharding magic
|