switchman 1.5.3 → 1.5.4

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
  SHA1:
3
- metadata.gz: 657642d7cee67361f96f71c662754e3045797d54
4
- data.tar.gz: b812153caf29c4699863e85c3fd65f1146b1ba83
3
+ metadata.gz: afbf29688ae3158c8e0a6e02d5dd27355d33fcc9
4
+ data.tar.gz: 104a872cbf73ba12f5a9bdc74d25db7d25d68c59
5
5
  SHA512:
6
- metadata.gz: 85b96aae81f8939ab5625d582ede7a46e795db85b6fc60c04207dde636701ff8dca25d1517ceb794c232f39309a45df8f3e00a812e91c63776471883da53eea0
7
- data.tar.gz: 081fd47e581206a4b628ff13d3eff837c8a4fbc9f143b08ae32cabfeff53153a78d733eb904048bcf4f23bd7aab6dfbb8fa1e2049388882e7cb060e6af9eea5f
6
+ metadata.gz: 453bb244bc91a04501f5952f629a964ebcb338629a6ba4e3530954a71325bb268acbc514619e1ca06d68c6d56d333e24575dc6eb053c8c86a22506462882c0ca
7
+ data.tar.gz: 9f39e116166e29ce9bfaf22aff35d84821f8d8ccbd2ff93032cb8dfbabd77c695e4a4a1aaf4608ca5171b31b17a66325357f16a85b9b6aeb83bb1aa9c8f84941
@@ -470,6 +470,7 @@ module Switchman
470
470
  end
471
471
 
472
472
  def shard_for(any_id, source_shard = nil)
473
+ return any_id.shard if any_id.is_a?(::ActiveRecord::Base)
473
474
  _, shard = local_id_for(any_id)
474
475
  shard || source_shard || Shard.current
475
476
  end
@@ -103,7 +103,7 @@ module Switchman
103
103
  # for belongs_to, it's the shard of the foreign_key
104
104
  partition_proc = ->(owner) do
105
105
  if owner.class.sharded_column?(owner_key_name)
106
- Shard.shard_for(owner, owner[owner_key_name])
106
+ Shard.shard_for(owner[owner_key_name], owner.shard)
107
107
  else
108
108
  Shard.current
109
109
  end
@@ -1,3 +1,5 @@
1
+ require 'switchman/errors'
2
+
1
3
  module Switchman
2
4
  module ActiveRecord
3
5
  module ConnectionPool
@@ -26,6 +28,7 @@ module Switchman
26
28
 
27
29
  def connection
28
30
  conn = super
31
+ raise NonExistentShardError if shard.new_record?
29
32
  switch_database(conn) if conn.shard != self.shard
30
33
  conn
31
34
  end
@@ -11,6 +11,7 @@ module Switchman
11
11
  def global_id_for(local_id); local_id; end
12
12
  def database_server_id; nil; end
13
13
  def database_server; DatabaseServer.find(nil); end
14
+ def new_record?; false; end
14
15
  def name
15
16
  unless instance_variable_defined?(:@name)
16
17
  @name = nil # prevent taking this branch on recursion
@@ -0,0 +1,203 @@
1
+ module Switchman
2
+ class Engine < ::Rails::Engine
3
+ require 'byebug'
4
+ debugger
5
+ isolate_namespace Switchman
6
+
7
+ config.autoload_once_paths << File.expand_path(File.join(__FILE__, "../../../app/models"))
8
+
9
+ def self.lookup_stores(cache_store_config)
10
+ result = {}
11
+ cache_store_config.each do |key, value|
12
+ next if value.is_a?(String)
13
+ result[key] = ::ActiveSupport::Cache.lookup_store(value)
14
+ end
15
+
16
+ cache_store_config.each do |key, value|
17
+ next unless value.is_a?(String)
18
+ result[key] = result[value]
19
+ end
20
+ result
21
+ end
22
+
23
+ initializer 'switchman.initialize_cache', :before => 'initialize_cache' do
24
+ require "switchman/active_support/cache"
25
+ ::ActiveSupport::Cache.singleton_class.prepend(ActiveSupport::Cache::ClassMethods)
26
+
27
+ # if we haven't already setup our cache map out-of-band, set it up from
28
+ # config.cache_store now. behaves similarly to Rails' default
29
+ # initialize_cache initializer, but for each value in the map, rather
30
+ # than just Rails.cache. if config.cache_store is a flat value, uses it
31
+ # to fill just the Rails.env entry in the cache map.
32
+ unless Switchman.config[:cache_map].present?
33
+ cache_store_config = ::Rails.configuration.cache_store
34
+ unless cache_store_config.is_a?(Hash)
35
+ cache_store_config = {::Rails.env => cache_store_config}
36
+ end
37
+
38
+ Switchman.config[:cache_map] = Engine.lookup_stores(cache_store_config)
39
+ end
40
+
41
+ # if the configured cache map (either from before, or as populated from
42
+ # config.cache_store) didn't have an entry for Rails.env, add one using
43
+ # lookup_store(nil); matches the behavior of Rails' default
44
+ # initialize_cache initializer when config.cache_store is nil.
45
+ unless Switchman.config[:cache_map].has_key?(::Rails.env)
46
+ value = ::ActiveSupport::Cache.lookup_store(nil)
47
+ Switchman.config[:cache_map][::Rails.env] = value
48
+ end
49
+
50
+ middlewares = Switchman.config[:cache_map].values.map do |store|
51
+ store.middleware if store.respond_to?(:middleware)
52
+ end.compact.uniq
53
+ middlewares.each do |middleware|
54
+ config.middleware.insert_before("Rack::Runtime", middleware)
55
+ end
56
+
57
+ # prevent :initialize_cache from trying to (or needing to) set
58
+ # Rails.cache. once our switchman.extend_ar initializer (below) runs
59
+ # Rails.cache will be overridden to pull appropriate values from the
60
+ # cache map, but between now and then, Rails.cache should return the
61
+ # Rails.env entry in the cache map.
62
+ ::Rails.cache = Switchman.config[:cache_map][::Rails.env]
63
+
64
+ require "switchman/rails"
65
+ ::Rails.singleton_class.prepend(Rails::ClassMethods)
66
+ end
67
+
68
+ initializer 'switchman.asplode', :after => "active_record.initialize_database" do
69
+ ::Rails.cache
70
+ end
71
+
72
+ initializer 'switchman.extend_ar', :before => "active_record.initialize_database" do
73
+ ::ActiveSupport.on_load(:active_record) do
74
+ require 'byebug'
75
+ debugger
76
+ require "switchman/active_record/abstract_adapter"
77
+ require "switchman/active_record/association"
78
+ require "switchman/active_record/attribute_methods"
79
+ require "switchman/active_record/base"
80
+ require "switchman/active_record/calculations"
81
+ require "switchman/active_record/connection_handler"
82
+ require "switchman/active_record/connection_pool"
83
+ require "switchman/active_record/finder_methods"
84
+ require "switchman/active_record/log_subscriber"
85
+ require "switchman/active_record/model_schema"
86
+ require "switchman/active_record/persistence"
87
+ require "switchman/active_record/predicate_builder"
88
+ require "switchman/active_record/query_cache"
89
+ require "switchman/active_record/query_methods"
90
+ require "switchman/active_record/reflection"
91
+ require "switchman/active_record/relation"
92
+ require "switchman/active_record/spawn_methods"
93
+ require "switchman/active_record/where_clause_factory"
94
+ require "switchman/active_record/type_caster"
95
+ require "switchman/arel"
96
+ require "switchman/shackles/relation"
97
+
98
+ include ActiveRecord::Base
99
+ include ActiveRecord::AttributeMethods
100
+ include ActiveRecord::Persistence
101
+ singleton_class.prepend ActiveRecord::ModelSchema::ClassMethods
102
+
103
+ if ::Rails.version > '4.2'
104
+ require "switchman/active_record/statement_cache"
105
+ ::ActiveRecord::StatementCache.prepend(ActiveRecord::StatementCache)
106
+ ::ActiveRecord::StatementCache::BindMap.prepend(ActiveRecord::StatementCache::BindMap)
107
+ ::ActiveRecord::StatementCache::Substitute.send(:attr_accessor, :primary, :sharded)
108
+
109
+ ::ActiveRecord::Associations::CollectionAssociation.prepend(ActiveRecord::CollectionAssociation)
110
+ ::ActiveRecord::PredicateBuilder.singleton_class.prepend(ActiveRecord::PredicateBuilder)
111
+ end
112
+
113
+ if ::Rails.version > '4.1'
114
+ prepend(ActiveRecord::AutosaveAssociation)
115
+ end
116
+
117
+ ::ActiveRecord::Associations::Association.prepend(ActiveRecord::Association)
118
+ ::ActiveRecord::Associations::BelongsToAssociation.prepend(ActiveRecord::BelongsToAssociation)
119
+ ::ActiveRecord::Associations::CollectionProxy.include(ActiveRecord::CollectionProxy)
120
+ if ::Rails.version < '5'
121
+ ::ActiveRecord::Associations::Builder::CollectionAssociation.include(ActiveRecord::Builder::CollectionAssociation)
122
+ end
123
+
124
+ ::ActiveRecord::Associations::Preloader::Association.prepend(ActiveRecord::Preloader::Association)
125
+ ::ActiveRecord::ConnectionAdapters::AbstractAdapter.prepend(ActiveRecord::AbstractAdapter)
126
+ ::ActiveRecord::ConnectionAdapters::ConnectionHandler.prepend(ActiveRecord::ConnectionHandler)
127
+ ::ActiveRecord::ConnectionAdapters::ConnectionPool.prepend(ActiveRecord::ConnectionPool)
128
+ ::ActiveRecord::ConnectionAdapters::AbstractAdapter.prepend(ActiveRecord::QueryCache)
129
+ # when we call super in Switchman::ActiveRecord::QueryCache#select_all,
130
+ # we want it to find the definition from
131
+ # ActiveRecord::ConnectionAdapters::DatabaseStatements, not
132
+ # ActiveRecord::ConnectionAdapters::QueryCache
133
+ ::ActiveRecord::ConnectionAdapters::QueryCache.send(:remove_method, :select_all)
134
+
135
+ ::ActiveRecord::LogSubscriber.prepend(ActiveRecord::LogSubscriber)
136
+ ::ActiveRecord::Reflection::AssociationReflection.prepend(ActiveRecord::Reflection::AssociationReflection)
137
+ ::ActiveRecord::Relation.prepend(ActiveRecord::Calculations)
138
+ ::ActiveRecord::Relation.include(ActiveRecord::FinderMethods)
139
+ ::ActiveRecord::Relation.include(ActiveRecord::QueryMethods)
140
+ ::ActiveRecord::Relation.prepend(ActiveRecord::Relation)
141
+ ::ActiveRecord::Relation.include(ActiveRecord::SpawnMethods)
142
+ ::ActiveRecord::Relation.prepend(Shackles::Relation)
143
+
144
+ if ::Rails.version >= '5'
145
+ ::ActiveRecord::Relation::WhereClauseFactory.prepend(ActiveRecord::WhereClauseFactory)
146
+ ::ActiveRecord::PredicateBuilder::AssociationQueryValue.prepend(ActiveRecord::PredicateBuilder::AssociationQueryValue)
147
+ ::ActiveRecord::TypeCaster::Map.include(ActiveRecord::TypeCaster::Map)
148
+ ::ActiveRecord::TypeCaster::Connection.include(ActiveRecord::TypeCaster::Connection)
149
+ end
150
+
151
+ ::Arel::Table.prepend(Arel::Table)
152
+ ::Arel::Visitors::ToSql.prepend(Arel::Visitors::ToSql)
153
+ ::Arel::Visitors::PostgreSQL.include(Arel::Visitors::PostgreSQL) if ::Rails.version < '4.2'
154
+ end
155
+ end
156
+
157
+ def self.foreign_key_check(name, type, options)
158
+ if name.to_s =~ /_id\z/ && type.to_s == 'integer' && options[:limit].to_i < 8
159
+ puts "WARNING: All foreign keys need to be 8-byte integers. #{name} looks like a foreign key. If so, please add the option: `:limit => 8`"
160
+ end
161
+ end
162
+
163
+ initializer 'switchman.extend_connection_adapters', :after => "active_record.initialize_database" do
164
+ ::ActiveSupport.on_load(:active_record) do
165
+ ::ActiveRecord::ConnectionAdapters::AbstractAdapter.descendants.each do |klass|
166
+ klass.prepend(ActiveRecord::AbstractAdapter::ForeignKeyCheck)
167
+ end
168
+
169
+ require 'switchman/active_record/table_definition'
170
+ ::ActiveRecord::ConnectionAdapters::TableDefinition.prepend(ActiveRecord::TableDefinition)
171
+
172
+ if defined?(::ActiveRecord::ConnectionAdapters::PostgreSQLAdapter)
173
+ require "switchman/active_record/postgresql_adapter"
174
+ ::ActiveRecord::ConnectionAdapters::PostgreSQLAdapter.prepend(ActiveRecord::PostgreSQLAdapter)
175
+ end
176
+ end
177
+ end
178
+
179
+ initializer 'switchman.eager_load' do
180
+ ::ActiveSupport.on_load(:before_eager_load) do
181
+ # This needs to be loaded before Switchman::Shard, otherwise it won't autoload it correctly
182
+ require 'active_record/base'
183
+ end
184
+ end
185
+
186
+ initializer 'switchman.extend_shackles', :before => "switchman.extend_ar" do
187
+ ::ActiveSupport.on_load(:active_record) do
188
+ require "switchman/shackles"
189
+
190
+ ::Shackles.singleton_class.prepend(Shackles::ClassMethods)
191
+ end
192
+ end
193
+
194
+ initializer 'switchman.extend_controller', :after => "shackles.extend_ar" do
195
+ ::ActiveSupport.on_load(:action_controller) do
196
+ require "switchman/action_controller/caching"
197
+
198
+ ::ActionController::Base.include(ActionController::Caching)
199
+ end
200
+ end
201
+
202
+ end
203
+ end
@@ -0,0 +1,3 @@
1
+ module Switchman
2
+ class NonExistentShardError < RuntimeError; end
3
+ end
@@ -1,3 +1,3 @@
1
1
  module Switchman
2
- VERSION = "1.5.3"
2
+ VERSION = "1.5.4"
3
3
  end
@@ -225,6 +225,20 @@ module Switchman
225
225
  run_cmd('pg_dump', args, 'dumping')
226
226
  File.open(filename, "a") { |f| f << "SET search_path TO #{serialized_search_path};\n\n" }
227
227
  end
228
+
229
+ if ::Rails.version < '4.2.5'
230
+ # These methods are backported from rails 4.2.5 to work with the above
231
+ def run_cmd(cmd, args, action)
232
+ fail run_cmd_error(cmd, args, action) unless Kernel.system(cmd, *args)
233
+ end
234
+
235
+ def run_cmd_error(cmd, args, action)
236
+ msg = "failed to execute:\n"
237
+ msg << "#{cmd} #{args.join(' ')}\n\n"
238
+ msg << "Please check the output above for any errors and make sure that `#{cmd}` is installed in your PATH and has proper permissions.\n\n"
239
+ msg
240
+ end
241
+ end
228
242
  end
229
243
  end
230
244
  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: 1.5.3
4
+ version: 1.5.4
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: 2016-03-28 00:00:00.000000000 Z
13
+ date: 2016-05-04 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: railties
@@ -192,7 +192,9 @@ files:
192
192
  - lib/switchman/database_server.rb
193
193
  - lib/switchman/default_shard.rb
194
194
  - lib/switchman/engine.rb
195
+ - lib/switchman/engine.rb~
195
196
  - lib/switchman/environment.rb
197
+ - lib/switchman/errors.rb
196
198
  - lib/switchman/r_spec_helper.rb
197
199
  - lib/switchman/rails.rb
198
200
  - lib/switchman/schema_cache.rb
@@ -222,9 +224,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
222
224
  version: '0'
223
225
  requirements: []
224
226
  rubyforge_project:
225
- rubygems_version: 2.5.1
227
+ rubygems_version: 2.6.4
226
228
  signing_key:
227
229
  specification_version: 4
228
230
  summary: Rails 4 sharding magic
229
231
  test_files: []
230
- has_rdoc: