activerecord 4.2.11.1 → 5.0.0

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of activerecord might be problematic. Click here for more details.

Files changed (246) hide show
  1. checksums.yaml +5 -5
  2. data/CHANGELOG.md +1282 -1195
  3. data/MIT-LICENSE +2 -2
  4. data/README.rdoc +7 -8
  5. data/examples/performance.rb +2 -3
  6. data/examples/simple.rb +0 -1
  7. data/lib/active_record.rb +8 -4
  8. data/lib/active_record/aggregations.rb +35 -24
  9. data/lib/active_record/association_relation.rb +3 -3
  10. data/lib/active_record/associations.rb +317 -209
  11. data/lib/active_record/associations/alias_tracker.rb +19 -16
  12. data/lib/active_record/associations/association.rb +11 -9
  13. data/lib/active_record/associations/association_scope.rb +73 -102
  14. data/lib/active_record/associations/belongs_to_association.rb +21 -32
  15. data/lib/active_record/associations/builder/association.rb +28 -34
  16. data/lib/active_record/associations/builder/belongs_to.rb +43 -18
  17. data/lib/active_record/associations/builder/collection_association.rb +7 -19
  18. data/lib/active_record/associations/builder/has_and_belongs_to_many.rb +14 -11
  19. data/lib/active_record/associations/builder/has_many.rb +4 -4
  20. data/lib/active_record/associations/builder/has_one.rb +11 -6
  21. data/lib/active_record/associations/builder/singular_association.rb +3 -10
  22. data/lib/active_record/associations/collection_association.rb +49 -41
  23. data/lib/active_record/associations/collection_proxy.rb +67 -27
  24. data/lib/active_record/associations/foreign_association.rb +1 -1
  25. data/lib/active_record/associations/has_many_association.rb +20 -71
  26. data/lib/active_record/associations/has_many_through_association.rb +8 -47
  27. data/lib/active_record/associations/has_one_association.rb +12 -5
  28. data/lib/active_record/associations/join_dependency.rb +29 -19
  29. data/lib/active_record/associations/join_dependency/join_association.rb +16 -10
  30. data/lib/active_record/associations/preloader.rb +14 -4
  31. data/lib/active_record/associations/preloader/association.rb +46 -52
  32. data/lib/active_record/associations/preloader/collection_association.rb +0 -6
  33. data/lib/active_record/associations/preloader/has_many_through.rb +1 -1
  34. data/lib/active_record/associations/preloader/has_one.rb +0 -8
  35. data/lib/active_record/associations/preloader/through_association.rb +27 -14
  36. data/lib/active_record/associations/singular_association.rb +7 -1
  37. data/lib/active_record/associations/through_association.rb +11 -3
  38. data/lib/active_record/attribute.rb +68 -18
  39. data/lib/active_record/attribute/user_provided_default.rb +28 -0
  40. data/lib/active_record/attribute_assignment.rb +19 -140
  41. data/lib/active_record/attribute_decorators.rb +6 -5
  42. data/lib/active_record/attribute_methods.rb +76 -47
  43. data/lib/active_record/attribute_methods/before_type_cast.rb +1 -1
  44. data/lib/active_record/attribute_methods/dirty.rb +46 -86
  45. data/lib/active_record/attribute_methods/primary_key.rb +2 -2
  46. data/lib/active_record/attribute_methods/query.rb +2 -2
  47. data/lib/active_record/attribute_methods/read.rb +31 -59
  48. data/lib/active_record/attribute_methods/serialization.rb +13 -16
  49. data/lib/active_record/attribute_methods/time_zone_conversion.rb +61 -14
  50. data/lib/active_record/attribute_methods/write.rb +13 -37
  51. data/lib/active_record/attribute_mutation_tracker.rb +70 -0
  52. data/lib/active_record/attribute_set.rb +30 -3
  53. data/lib/active_record/attribute_set/builder.rb +6 -4
  54. data/lib/active_record/attributes.rb +199 -81
  55. data/lib/active_record/autosave_association.rb +49 -16
  56. data/lib/active_record/base.rb +32 -23
  57. data/lib/active_record/callbacks.rb +39 -43
  58. data/lib/active_record/coders/json.rb +1 -1
  59. data/lib/active_record/coders/yaml_column.rb +20 -8
  60. data/lib/active_record/collection_cache_key.rb +40 -0
  61. data/lib/active_record/connection_adapters/abstract/connection_pool.rb +452 -182
  62. data/lib/active_record/connection_adapters/abstract/database_limits.rb +3 -3
  63. data/lib/active_record/connection_adapters/abstract/database_statements.rb +65 -61
  64. data/lib/active_record/connection_adapters/abstract/query_cache.rb +2 -2
  65. data/lib/active_record/connection_adapters/abstract/quoting.rb +74 -10
  66. data/lib/active_record/connection_adapters/abstract/savepoints.rb +3 -3
  67. data/lib/active_record/connection_adapters/abstract/schema_creation.rb +61 -39
  68. data/lib/active_record/connection_adapters/abstract/schema_definitions.rb +236 -185
  69. data/lib/active_record/connection_adapters/abstract/schema_dumper.rb +72 -17
  70. data/lib/active_record/connection_adapters/abstract/schema_statements.rb +380 -141
  71. data/lib/active_record/connection_adapters/abstract/transaction.rb +51 -34
  72. data/lib/active_record/connection_adapters/abstract_adapter.rb +141 -59
  73. data/lib/active_record/connection_adapters/abstract_mysql_adapter.rb +401 -370
  74. data/lib/active_record/connection_adapters/column.rb +28 -43
  75. data/lib/active_record/connection_adapters/connection_specification.rb +15 -27
  76. data/lib/active_record/connection_adapters/determine_if_preparable_visitor.rb +22 -0
  77. data/lib/active_record/connection_adapters/mysql/column.rb +50 -0
  78. data/lib/active_record/connection_adapters/mysql/database_statements.rb +125 -0
  79. data/lib/active_record/connection_adapters/mysql/explain_pretty_printer.rb +70 -0
  80. data/lib/active_record/connection_adapters/mysql/quoting.rb +51 -0
  81. data/lib/active_record/connection_adapters/mysql/schema_creation.rb +67 -0
  82. data/lib/active_record/connection_adapters/mysql/schema_definitions.rb +93 -0
  83. data/lib/active_record/connection_adapters/mysql/schema_dumper.rb +54 -0
  84. data/lib/active_record/connection_adapters/mysql/type_metadata.rb +32 -0
  85. data/lib/active_record/connection_adapters/mysql2_adapter.rb +29 -166
  86. data/lib/active_record/connection_adapters/postgresql/column.rb +5 -10
  87. data/lib/active_record/connection_adapters/postgresql/database_statements.rb +10 -72
  88. data/lib/active_record/connection_adapters/postgresql/explain_pretty_printer.rb +42 -0
  89. data/lib/active_record/connection_adapters/postgresql/oid.rb +1 -6
  90. data/lib/active_record/connection_adapters/postgresql/oid/array.rb +27 -57
  91. data/lib/active_record/connection_adapters/postgresql/oid/bit.rb +2 -2
  92. data/lib/active_record/connection_adapters/postgresql/oid/bytea.rb +1 -1
  93. data/lib/active_record/connection_adapters/postgresql/oid/cidr.rb +3 -1
  94. data/lib/active_record/connection_adapters/postgresql/oid/date_time.rb +7 -22
  95. data/lib/active_record/connection_adapters/postgresql/oid/hstore.rb +3 -3
  96. data/lib/active_record/connection_adapters/postgresql/oid/json.rb +1 -26
  97. data/lib/active_record/connection_adapters/postgresql/oid/jsonb.rb +2 -2
  98. data/lib/active_record/connection_adapters/postgresql/oid/money.rb +0 -4
  99. data/lib/active_record/connection_adapters/postgresql/oid/point.rb +4 -4
  100. data/lib/active_record/connection_adapters/postgresql/oid/rails_5_1_point.rb +50 -0
  101. data/lib/active_record/connection_adapters/postgresql/oid/range.rb +31 -17
  102. data/lib/active_record/connection_adapters/postgresql/oid/specialized_string.rb +0 -4
  103. data/lib/active_record/connection_adapters/postgresql/oid/uuid.rb +2 -2
  104. data/lib/active_record/connection_adapters/postgresql/oid/vector.rb +1 -1
  105. data/lib/active_record/connection_adapters/postgresql/oid/xml.rb +1 -1
  106. data/lib/active_record/connection_adapters/postgresql/quoting.rb +26 -18
  107. data/lib/active_record/connection_adapters/postgresql/referential_integrity.rb +29 -10
  108. data/lib/active_record/connection_adapters/postgresql/schema_definitions.rb +107 -79
  109. data/lib/active_record/connection_adapters/postgresql/schema_dumper.rb +47 -0
  110. data/lib/active_record/connection_adapters/postgresql/schema_statements.rb +234 -148
  111. data/lib/active_record/connection_adapters/postgresql/type_metadata.rb +35 -0
  112. data/lib/active_record/connection_adapters/postgresql_adapter.rb +248 -160
  113. data/lib/active_record/connection_adapters/schema_cache.rb +36 -23
  114. data/lib/active_record/connection_adapters/sql_type_metadata.rb +32 -0
  115. data/lib/active_record/connection_adapters/sqlite3/explain_pretty_printer.rb +19 -0
  116. data/lib/active_record/connection_adapters/sqlite3/quoting.rb +48 -0
  117. data/lib/active_record/connection_adapters/sqlite3/schema_creation.rb +22 -0
  118. data/lib/active_record/connection_adapters/sqlite3_adapter.rb +149 -192
  119. data/lib/active_record/connection_adapters/statement_pool.rb +31 -12
  120. data/lib/active_record/connection_handling.rb +37 -14
  121. data/lib/active_record/core.rb +89 -107
  122. data/lib/active_record/counter_cache.rb +13 -24
  123. data/lib/active_record/dynamic_matchers.rb +1 -20
  124. data/lib/active_record/enum.rb +113 -76
  125. data/lib/active_record/errors.rb +87 -48
  126. data/lib/active_record/explain_registry.rb +1 -1
  127. data/lib/active_record/explain_subscriber.rb +1 -1
  128. data/lib/active_record/fixture_set/file.rb +26 -5
  129. data/lib/active_record/fixtures.rb +76 -40
  130. data/lib/active_record/gem_version.rb +4 -4
  131. data/lib/active_record/inheritance.rb +32 -40
  132. data/lib/active_record/integration.rb +4 -4
  133. data/lib/active_record/internal_metadata.rb +56 -0
  134. data/lib/active_record/legacy_yaml_adapter.rb +18 -2
  135. data/lib/active_record/locale/en.yml +3 -2
  136. data/lib/active_record/locking/optimistic.rb +15 -15
  137. data/lib/active_record/locking/pessimistic.rb +1 -1
  138. data/lib/active_record/log_subscriber.rb +43 -21
  139. data/lib/active_record/migration.rb +363 -133
  140. data/lib/active_record/migration/command_recorder.rb +59 -18
  141. data/lib/active_record/migration/compatibility.rb +126 -0
  142. data/lib/active_record/model_schema.rb +129 -41
  143. data/lib/active_record/nested_attributes.rb +58 -29
  144. data/lib/active_record/null_relation.rb +16 -8
  145. data/lib/active_record/persistence.rb +121 -80
  146. data/lib/active_record/query_cache.rb +15 -18
  147. data/lib/active_record/querying.rb +10 -9
  148. data/lib/active_record/railtie.rb +23 -16
  149. data/lib/active_record/railties/controller_runtime.rb +1 -1
  150. data/lib/active_record/railties/databases.rake +69 -46
  151. data/lib/active_record/readonly_attributes.rb +1 -1
  152. data/lib/active_record/reflection.rb +282 -115
  153. data/lib/active_record/relation.rb +176 -116
  154. data/lib/active_record/relation/batches.rb +139 -34
  155. data/lib/active_record/relation/batches/batch_enumerator.rb +67 -0
  156. data/lib/active_record/relation/calculations.rb +79 -108
  157. data/lib/active_record/relation/delegation.rb +7 -20
  158. data/lib/active_record/relation/finder_methods.rb +163 -81
  159. data/lib/active_record/relation/from_clause.rb +32 -0
  160. data/lib/active_record/relation/merger.rb +16 -42
  161. data/lib/active_record/relation/predicate_builder.rb +120 -107
  162. data/lib/active_record/relation/predicate_builder/array_handler.rb +11 -16
  163. data/lib/active_record/relation/predicate_builder/association_query_handler.rb +88 -0
  164. data/lib/active_record/relation/predicate_builder/base_handler.rb +17 -0
  165. data/lib/active_record/relation/predicate_builder/basic_object_handler.rb +17 -0
  166. data/lib/active_record/relation/predicate_builder/class_handler.rb +27 -0
  167. data/lib/active_record/relation/predicate_builder/polymorphic_array_handler.rb +57 -0
  168. data/lib/active_record/relation/predicate_builder/range_handler.rb +33 -0
  169. data/lib/active_record/relation/predicate_builder/relation_handler.rb +1 -1
  170. data/lib/active_record/relation/query_attribute.rb +19 -0
  171. data/lib/active_record/relation/query_methods.rb +308 -244
  172. data/lib/active_record/relation/record_fetch_warning.rb +49 -0
  173. data/lib/active_record/relation/spawn_methods.rb +4 -7
  174. data/lib/active_record/relation/where_clause.rb +174 -0
  175. data/lib/active_record/relation/where_clause_factory.rb +38 -0
  176. data/lib/active_record/result.rb +4 -3
  177. data/lib/active_record/runtime_registry.rb +1 -1
  178. data/lib/active_record/sanitization.rb +95 -66
  179. data/lib/active_record/schema.rb +26 -22
  180. data/lib/active_record/schema_dumper.rb +62 -38
  181. data/lib/active_record/schema_migration.rb +11 -14
  182. data/lib/active_record/scoping.rb +32 -15
  183. data/lib/active_record/scoping/default.rb +23 -9
  184. data/lib/active_record/scoping/named.rb +49 -28
  185. data/lib/active_record/secure_token.rb +38 -0
  186. data/lib/active_record/serialization.rb +2 -4
  187. data/lib/active_record/statement_cache.rb +16 -14
  188. data/lib/active_record/store.rb +8 -3
  189. data/lib/active_record/suppressor.rb +58 -0
  190. data/lib/active_record/table_metadata.rb +68 -0
  191. data/lib/active_record/tasks/database_tasks.rb +57 -43
  192. data/lib/active_record/tasks/mysql_database_tasks.rb +6 -14
  193. data/lib/active_record/tasks/postgresql_database_tasks.rb +11 -2
  194. data/lib/active_record/tasks/sqlite_database_tasks.rb +5 -1
  195. data/lib/active_record/timestamp.rb +20 -9
  196. data/lib/active_record/touch_later.rb +58 -0
  197. data/lib/active_record/transactions.rb +138 -56
  198. data/lib/active_record/type.rb +66 -17
  199. data/lib/active_record/type/adapter_specific_registry.rb +130 -0
  200. data/lib/active_record/type/date.rb +2 -45
  201. data/lib/active_record/type/date_time.rb +2 -49
  202. data/lib/active_record/type/internal/abstract_json.rb +29 -0
  203. data/lib/active_record/type/internal/timezone.rb +15 -0
  204. data/lib/active_record/type/serialized.rb +15 -14
  205. data/lib/active_record/type/time.rb +10 -16
  206. data/lib/active_record/type/type_map.rb +4 -4
  207. data/lib/active_record/type_caster.rb +7 -0
  208. data/lib/active_record/type_caster/connection.rb +29 -0
  209. data/lib/active_record/type_caster/map.rb +19 -0
  210. data/lib/active_record/validations.rb +33 -32
  211. data/lib/active_record/validations/absence.rb +23 -0
  212. data/lib/active_record/validations/associated.rb +10 -3
  213. data/lib/active_record/validations/length.rb +24 -0
  214. data/lib/active_record/validations/presence.rb +11 -12
  215. data/lib/active_record/validations/uniqueness.rb +30 -29
  216. data/lib/rails/generators/active_record/migration.rb +7 -0
  217. data/lib/rails/generators/active_record/migration/migration_generator.rb +7 -4
  218. data/lib/rails/generators/active_record/migration/templates/create_table_migration.rb +8 -3
  219. data/lib/rails/generators/active_record/migration/templates/migration.rb +8 -1
  220. data/lib/rails/generators/active_record/model/model_generator.rb +32 -15
  221. data/lib/rails/generators/active_record/model/templates/application_record.rb +5 -0
  222. data/lib/rails/generators/active_record/model/templates/model.rb +3 -0
  223. metadata +59 -34
  224. data/lib/active_record/connection_adapters/mysql_adapter.rb +0 -498
  225. data/lib/active_record/connection_adapters/postgresql/array_parser.rb +0 -93
  226. data/lib/active_record/connection_adapters/postgresql/oid/date.rb +0 -11
  227. data/lib/active_record/connection_adapters/postgresql/oid/float.rb +0 -21
  228. data/lib/active_record/connection_adapters/postgresql/oid/infinity.rb +0 -13
  229. data/lib/active_record/connection_adapters/postgresql/oid/integer.rb +0 -11
  230. data/lib/active_record/connection_adapters/postgresql/oid/time.rb +0 -11
  231. data/lib/active_record/serializers/xml_serializer.rb +0 -193
  232. data/lib/active_record/type/big_integer.rb +0 -13
  233. data/lib/active_record/type/binary.rb +0 -50
  234. data/lib/active_record/type/boolean.rb +0 -31
  235. data/lib/active_record/type/decimal.rb +0 -64
  236. data/lib/active_record/type/decimal_without_scale.rb +0 -11
  237. data/lib/active_record/type/decorator.rb +0 -14
  238. data/lib/active_record/type/float.rb +0 -19
  239. data/lib/active_record/type/integer.rb +0 -59
  240. data/lib/active_record/type/mutable.rb +0 -16
  241. data/lib/active_record/type/numeric.rb +0 -36
  242. data/lib/active_record/type/string.rb +0 -40
  243. data/lib/active_record/type/text.rb +0 -11
  244. data/lib/active_record/type/time_value.rb +0 -38
  245. data/lib/active_record/type/unsigned_integer.rb +0 -15
  246. data/lib/active_record/type/value.rb +0 -110
@@ -5,7 +5,7 @@ module ActiveRecord
5
5
  # Enable the query cache within the block if Active Record is configured.
6
6
  # If it's not, it will execute the given block.
7
7
  def cache(&block)
8
- if ActiveRecord::Base.connected?
8
+ if connected?
9
9
  connection.cache(&block)
10
10
  else
11
11
  yield
@@ -15,7 +15,7 @@ module ActiveRecord
15
15
  # Disable the query cache within the block if Active Record is configured.
16
16
  # If it's not, it will execute the given block.
17
17
  def uncached(&block)
18
- if ActiveRecord::Base.connected?
18
+ if connected?
19
19
  connection.uncached(&block)
20
20
  else
21
21
  yield
@@ -23,34 +23,31 @@ module ActiveRecord
23
23
  end
24
24
  end
25
25
 
26
- def initialize(app)
27
- @app = app
28
- end
29
-
30
- def call(env)
26
+ def self.run
31
27
  connection = ActiveRecord::Base.connection
32
28
  enabled = connection.query_cache_enabled
33
29
  connection_id = ActiveRecord::Base.connection_id
34
30
  connection.enable_query_cache!
35
31
 
36
- response = @app.call(env)
37
- response[2] = Rack::BodyProxy.new(response[2]) do
38
- restore_query_cache_settings(connection_id, enabled)
39
- end
40
-
41
- response
42
- rescue Exception => e
43
- restore_query_cache_settings(connection_id, enabled)
44
- raise e
32
+ [enabled, connection_id]
45
33
  end
46
34
 
47
- private
35
+ def self.complete(state)
36
+ enabled, connection_id = state
48
37
 
49
- def restore_query_cache_settings(connection_id, enabled)
50
38
  ActiveRecord::Base.connection_id = connection_id
51
39
  ActiveRecord::Base.connection.clear_query_cache
52
40
  ActiveRecord::Base.connection.disable_query_cache! unless enabled
53
41
  end
54
42
 
43
+ def self.install_executor_hooks(executor = ActiveSupport::Executor)
44
+ executor.register_hook(self)
45
+
46
+ executor.to_complete do
47
+ unless ActiveRecord::Base.connection.transaction_open?
48
+ ActiveRecord::Base.clear_active_connections!
49
+ end
50
+ end
51
+ end
55
52
  end
56
53
  end
@@ -1,13 +1,13 @@
1
1
  module ActiveRecord
2
2
  module Querying
3
- delegate :find, :take, :take!, :first, :first!, :last, :last!, :exists?, :any?, :many?, to: :all
4
- delegate :second, :second!, :third, :third!, :fourth, :fourth!, :fifth, :fifth!, :forty_two, :forty_two!, to: :all
3
+ delegate :find, :take, :take!, :first, :first!, :last, :last!, :exists?, :any?, :many?, :none?, :one?, to: :all
4
+ delegate :second, :second!, :third, :third!, :fourth, :fourth!, :fifth, :fifth!, :forty_two, :forty_two!, :third_to_last, :third_to_last!, :second_to_last, :second_to_last!, to: :all
5
5
  delegate :first_or_create, :first_or_create!, :first_or_initialize, to: :all
6
6
  delegate :find_or_create_by, :find_or_create_by!, :find_or_initialize_by, to: :all
7
7
  delegate :find_by, :find_by!, to: :all
8
8
  delegate :destroy, :destroy_all, :delete, :delete_all, :update, :update_all, to: :all
9
- delegate :find_each, :find_in_batches, to: :all
10
- delegate :select, :group, :order, :except, :reorder, :limit, :offset, :joins,
9
+ delegate :find_each, :find_in_batches, :in_batches, to: :all
10
+ delegate :select, :group, :order, :except, :reorder, :limit, :offset, :joins, :left_joins, :left_outer_joins, :or,
11
11
  :where, :rewhere, :preload, :eager_load, :includes, :from, :lock, :readonly,
12
12
  :having, :create_with, :uniq, :distinct, :references, :none, :unscope, to: :all
13
13
  delegate :count, :average, :minimum, :maximum, :sum, :calculate, to: :all
@@ -35,8 +35,8 @@ module ActiveRecord
35
35
  #
36
36
  # Post.find_by_sql ["SELECT title FROM posts WHERE author = ? AND created > ?", author_id, start_date]
37
37
  # Post.find_by_sql ["SELECT body FROM comments WHERE author = :user_id OR approved_by = :user_id", { :user_id => user_id }]
38
- def find_by_sql(sql, binds = [])
39
- result_set = connection.select_all(sanitize_sql(sql), "#{name} Load", binds)
38
+ def find_by_sql(sql, binds = [], preparable: nil)
39
+ result_set = connection.select_all(sanitize_sql(sql), "#{name} Load", binds, preparable: preparable)
40
40
  column_types = result_set.column_types.dup
41
41
  columns_hash.each_key { |k| column_types.delete k }
42
42
  message_bus = ActiveSupport::Notifications.instrumenter
@@ -55,11 +55,12 @@ module ActiveRecord
55
55
  # The use of this method should be restricted to complicated SQL queries that can't be executed
56
56
  # using the ActiveRecord::Calculations class methods. Look into those before using this.
57
57
  #
58
- # ==== Parameters
58
+ # Product.count_by_sql "SELECT COUNT(*) FROM sales s, customers c WHERE s.customer_id = c.id"
59
+ # # => 12
59
60
  #
60
- # * +sql+ - An SQL statement which should return a count query from the database, see the example below.
61
+ # ==== Parameters
61
62
  #
62
- # Product.count_by_sql "SELECT COUNT(*) FROM sales s, customers c WHERE s.customer_id = c.id"
63
+ # * +sql+ - An SQL statement which should return a count query from the database, see the example above.
63
64
  def count_by_sql(sql)
64
65
  sql = sanitize_conditions(sql)
65
66
  connection.select_value(sql, "#{name} Count").to_i
@@ -16,12 +16,6 @@ module ActiveRecord
16
16
  config.app_generators.orm :active_record, :migration => true,
17
17
  :timestamps => true
18
18
 
19
- config.app_middleware.insert_after "::ActionDispatch::Callbacks",
20
- "ActiveRecord::QueryCache"
21
-
22
- config.app_middleware.insert_after "::ActionDispatch::Callbacks",
23
- "ActiveRecord::ConnectionAdapters::ConnectionManagement"
24
-
25
19
  config.action_dispatch.rescue_responses.merge!(
26
20
  'ActiveRecord::RecordNotFound' => :not_found,
27
21
  'ActiveRecord::StaleObjectError' => :conflict,
@@ -40,7 +34,7 @@ module ActiveRecord
40
34
  task :load_config do
41
35
  ActiveRecord::Tasks::DatabaseTasks.database_configuration = Rails.application.config.database_configuration
42
36
 
43
- if defined?(ENGINE_PATH) && engine = Rails::Engine.find(ENGINE_PATH)
37
+ if defined?(ENGINE_ROOT) && engine = Rails::Engine.find(ENGINE_ROOT)
44
38
  if engine.paths['db/migrate'].existent
45
39
  ActiveRecord::Tasks::DatabaseTasks.migrations_paths += engine.paths['db/migrate'].to_a
46
40
  end
@@ -80,8 +74,8 @@ module ActiveRecord
80
74
 
81
75
  initializer "active_record.migration_error" do
82
76
  if config.active_record.delete(:migration_error) == :page_load
83
- config.app_middleware.insert_after "::ActionDispatch::Callbacks",
84
- "ActiveRecord::Migration::CheckPending"
77
+ config.app_middleware.insert_after ::ActionDispatch::Callbacks,
78
+ ActiveRecord::Migration::CheckPending
85
79
  end
86
80
  end
87
81
 
@@ -95,6 +89,7 @@ module ActiveRecord
95
89
  cache = Marshal.load File.binread filename
96
90
  if cache.version == ActiveRecord::Migrator.current_version
97
91
  self.connection.schema_cache = cache
92
+ self.connection_pool.schema_cache = cache.dup
98
93
  else
99
94
  warn "Ignoring db/schema_cache.dump because it has expired. The current schema version is #{ActiveRecord::Migrator.current_version}, but the one in the cache is #{cache.version}."
100
95
  end
@@ -104,6 +99,14 @@ module ActiveRecord
104
99
  end
105
100
  end
106
101
 
102
+ initializer "active_record.warn_on_records_fetched_greater_than" do
103
+ if config.active_record.warn_on_records_fetched_greater_than
104
+ ActiveSupport.on_load(:active_record) do
105
+ require 'active_record/relation/record_fetch_warning'
106
+ end
107
+ end
108
+ end
109
+
107
110
  initializer "active_record.set_configs" do |app|
108
111
  ActiveSupport.on_load(:active_record) do
109
112
  app.config.active_record.each do |k,v|
@@ -114,7 +117,7 @@ module ActiveRecord
114
117
 
115
118
  # This sets the database configuration from Configuration#database_configuration
116
119
  # and then establishes the connection.
117
- initializer "active_record.initialize_database" do |app|
120
+ initializer "active_record.initialize_database" do
118
121
  ActiveSupport.on_load(:active_record) do
119
122
  self.configurations = Rails.application.config.database_configuration
120
123
 
@@ -127,8 +130,8 @@ Oops - You have a database configured, but it doesn't exist yet!
127
130
  Here's how to get started:
128
131
 
129
132
  1. Configure your database in config/database.yml.
130
- 2. Run `bin/rake db:create` to create the database.
131
- 3. Run `bin/rake db:setup` to load your database schema.
133
+ 2. Run `bin/rails db:create` to create the database.
134
+ 3. Run `bin/rails db:setup` to load your database schema.
132
135
  end_warning
133
136
  raise
134
137
  end
@@ -143,11 +146,9 @@ end_warning
143
146
  end
144
147
  end
145
148
 
146
- initializer "active_record.set_reloader_hooks" do |app|
147
- hook = app.config.reload_classes_only_on_change ? :to_prepare : :to_cleanup
148
-
149
+ initializer "active_record.set_reloader_hooks" do
149
150
  ActiveSupport.on_load(:active_record) do
150
- ActionDispatch::Reloader.send(hook) do
151
+ ActiveSupport::Reloader.before_class_unload do
151
152
  if ActiveRecord::Base.connected?
152
153
  ActiveRecord::Base.clear_cache!
153
154
  ActiveRecord::Base.clear_reloadable_connections!
@@ -156,6 +157,12 @@ end_warning
156
157
  end
157
158
  end
158
159
 
160
+ initializer "active_record.set_executor_hooks" do
161
+ ActiveSupport.on_load(:active_record) do
162
+ ActiveRecord::QueryCache.install_executor_hooks
163
+ end
164
+ end
165
+
159
166
  initializer "active_record.add_watchable_files" do |app|
160
167
  path = app.paths["db"].first
161
168
  config.watchable_files.concat ["#{path}/schema.rb", "#{path}/structure.sql"]
@@ -19,7 +19,7 @@ module ActiveRecord
19
19
  end
20
20
 
21
21
  def cleanup_view_runtime
22
- if ActiveRecord::Base.connected?
22
+ if logger.info? && ActiveRecord::Base.connected?
23
23
  db_rt_before_render = ActiveRecord::LogSubscriber.reset_runtime
24
24
  self.db_runtime = (db_runtime || 0) + db_rt_before_render
25
25
  runtime = super
@@ -1,6 +1,16 @@
1
1
  require 'active_record'
2
2
 
3
3
  db_namespace = namespace :db do
4
+ desc "Set the environment value for the database"
5
+ task "environment:set" => [:environment, :load_config] do
6
+ ActiveRecord::InternalMetadata.create_table
7
+ ActiveRecord::InternalMetadata[:environment] = ActiveRecord::Migrator.current_environment
8
+ end
9
+
10
+ task :check_protected_environments => [:environment, :load_config] do
11
+ ActiveRecord::Tasks::DatabaseTasks.check_protected_environments!
12
+ end
13
+
4
14
  task :load_config do
5
15
  ActiveRecord::Base.configurations = ActiveRecord::Tasks::DatabaseTasks.database_configuration || {}
6
16
  ActiveRecord::Migrator.migrations_paths = ActiveRecord::Tasks::DatabaseTasks.migrations_paths
@@ -12,30 +22,34 @@ db_namespace = namespace :db do
12
22
  end
13
23
  end
14
24
 
15
- desc 'Creates the database from DATABASE_URL or config/database.yml for the current RAILS_ENV (use db:create:all to create all databases in the config). Without RAILS_ENV it defaults to creating the development and test databases.'
25
+ desc 'Creates the database from DATABASE_URL or config/database.yml for the current RAILS_ENV (use db:create:all to create all databases in the config). Without RAILS_ENV or when RAILS_ENV is development, it defaults to creating the development and test databases.'
16
26
  task :create => [:load_config] do
17
27
  ActiveRecord::Tasks::DatabaseTasks.create_current
18
28
  end
19
29
 
20
30
  namespace :drop do
21
- task :all => :load_config do
31
+ task :all => [:load_config, :check_protected_environments] do
22
32
  ActiveRecord::Tasks::DatabaseTasks.drop_all
23
33
  end
24
34
  end
25
35
 
26
- desc 'Drops the database from DATABASE_URL or config/database.yml for the current RAILS_ENV (use db:drop:all to drop all databases in the config). Without RAILS_ENV it defaults to dropping the development and test databases.'
27
- task :drop => [:load_config] do
36
+ desc 'Drops the database from DATABASE_URL or config/database.yml for the current RAILS_ENV (use db:drop:all to drop all databases in the config). Without RAILS_ENV or when RAILS_ENV is development, it defaults to dropping the development and test databases.'
37
+ task :drop => [:load_config, :check_protected_environments] do
38
+ db_namespace["drop:_unsafe"].invoke
39
+ end
40
+
41
+ task "drop:_unsafe" => [:load_config] do
28
42
  ActiveRecord::Tasks::DatabaseTasks.drop_current
29
43
  end
30
44
 
31
45
  namespace :purge do
32
- task :all => :load_config do
46
+ task :all => [:load_config, :check_protected_environments] do
33
47
  ActiveRecord::Tasks::DatabaseTasks.purge_all
34
48
  end
35
49
  end
36
50
 
37
- # desc "Empty the database from DATABASE_URL or config/database.yml for the current RAILS_ENV (use db:drop:all to drop all databases in the config). Without RAILS_ENV it defaults to purging the development and test databases."
38
- task :purge => [:load_config] do
51
+ # desc "Empty the database from DATABASE_URL or config/database.yml for the current RAILS_ENV (use db:purge:all to purge all databases in the config). Without RAILS_ENV it defaults to purging the development and test databases."
52
+ task :purge => [:load_config, :check_protected_environments] do
39
53
  ActiveRecord::Tasks::DatabaseTasks.purge_current
40
54
  end
41
55
 
@@ -63,8 +77,6 @@ db_namespace = namespace :db do
63
77
  namespace :migrate do
64
78
  # desc 'Rollbacks the database one migration and re migrate up (options: STEP=x, VERSION=x).'
65
79
  task :redo => [:environment, :load_config] do
66
- raise "Empty VERSION provided" if ENV["VERSION"] && ENV["VERSION"].empty?
67
-
68
80
  if ENV['VERSION']
69
81
  db_namespace['migrate:down'].invoke
70
82
  db_namespace['migrate:up'].invoke
@@ -79,18 +91,17 @@ db_namespace = namespace :db do
79
91
 
80
92
  # desc 'Runs the "up" for a given migration VERSION.'
81
93
  task :up => [:environment, :load_config] do
82
- raise "VERSION is required" if ENV["VERSION"] && ENV["VERSION"].empty?
83
-
84
94
  version = ENV['VERSION'] ? ENV['VERSION'].to_i : nil
85
- ActiveRecord::Migrator.run(:up, ActiveRecord::Migrator.migrations_paths, version)
95
+ raise 'VERSION is required' unless version
96
+ ActiveRecord::Migrator.run(:up, ActiveRecord::Tasks::DatabaseTasks.migrations_paths, version)
86
97
  db_namespace['_dump'].invoke
87
98
  end
88
99
 
89
100
  # desc 'Runs the "down" for a given migration VERSION.'
90
101
  task :down => [:environment, :load_config] do
91
- raise "VERSION is required - To go down one migration, use db:rollback" if ENV["VERSION"] && ENV["VERSION"].empty?
92
102
  version = ENV['VERSION'] ? ENV['VERSION'].to_i : nil
93
- ActiveRecord::Migrator.run(:down, ActiveRecord::Migrator.migrations_paths, version)
103
+ raise 'VERSION is required - To go down one migration, run db:rollback' unless version
104
+ ActiveRecord::Migrator.run(:down, ActiveRecord::Tasks::DatabaseTasks.migrations_paths, version)
94
105
  db_namespace['_dump'].invoke
95
106
  end
96
107
 
@@ -99,13 +110,28 @@ db_namespace = namespace :db do
99
110
  unless ActiveRecord::SchemaMigration.table_exists?
100
111
  abort 'Schema migrations table does not exist yet.'
101
112
  end
113
+ db_list = ActiveRecord::SchemaMigration.normalized_versions
114
+
115
+ file_list =
116
+ ActiveRecord::Tasks::DatabaseTasks.migrations_paths.flat_map do |path|
117
+ Dir.foreach(path).map do |file|
118
+ next unless ActiveRecord::Migrator.match_to_migration_filename?(file)
119
+
120
+ version, name, scope = ActiveRecord::Migrator.parse_migration_filename(file)
121
+ version = ActiveRecord::SchemaMigration.normalize_migration_number(version)
122
+ status = db_list.delete(version) ? 'up' : 'down'
123
+ [status, version, (name + scope).humanize]
124
+ end.compact
125
+ end
102
126
 
127
+ db_list.map! do |version|
128
+ ['up', version, '********** NO FILE **********']
129
+ end
103
130
  # output
104
131
  puts "\ndatabase: #{ActiveRecord::Base.connection_config[:database]}\n\n"
105
132
  puts "#{'Status'.center(8)} #{'Migration ID'.ljust(14)} Migration Name"
106
133
  puts "-" * 50
107
- paths = ActiveRecord::Tasks::DatabaseTasks.migrations_paths
108
- ActiveRecord::Migrator.migrations_status(paths).each do |status, version, name|
134
+ (db_list + file_list).sort_by { |_, version, _| version }.each do |status, version, name|
109
135
  puts "#{status.center(8)} #{version.ljust(14)} #{name}"
110
136
  end
111
137
  puts
@@ -115,22 +141,19 @@ db_namespace = namespace :db do
115
141
  desc 'Rolls the schema back to the previous version (specify steps w/ STEP=n).'
116
142
  task :rollback => [:environment, :load_config] do
117
143
  step = ENV['STEP'] ? ENV['STEP'].to_i : 1
118
- ActiveRecord::Migrator.rollback(ActiveRecord::Migrator.migrations_paths, step)
144
+ ActiveRecord::Migrator.rollback(ActiveRecord::Tasks::DatabaseTasks.migrations_paths, step)
119
145
  db_namespace['_dump'].invoke
120
146
  end
121
147
 
122
148
  # desc 'Pushes the schema to the next version (specify steps w/ STEP=n).'
123
149
  task :forward => [:environment, :load_config] do
124
150
  step = ENV['STEP'] ? ENV['STEP'].to_i : 1
125
- ActiveRecord::Migrator.forward(ActiveRecord::Migrator.migrations_paths, step)
151
+ ActiveRecord::Migrator.forward(ActiveRecord::Tasks::DatabaseTasks.migrations_paths, step)
126
152
  db_namespace['_dump'].invoke
127
153
  end
128
154
 
129
155
  # desc 'Drops and recreates the database from db/schema.rb for the current environment and loads the seeds.'
130
- task :reset => [:environment, :load_config] do
131
- db_namespace["drop"].invoke
132
- db_namespace["setup"].invoke
133
- end
156
+ task :reset => [ 'db:drop', 'db:setup' ]
134
157
 
135
158
  # desc "Retrieves the charset for the current environment's database"
136
159
  task :charset => [:environment, :load_config] do
@@ -152,29 +175,29 @@ db_namespace = namespace :db do
152
175
  end
153
176
 
154
177
  # desc "Raises an error if there are pending migrations"
155
- task :abort_if_pending_migrations => :environment do
156
- pending_migrations = ActiveRecord::Migrator.open(ActiveRecord::Migrator.migrations_paths).pending_migrations
178
+ task :abort_if_pending_migrations => [:environment, :load_config] do
179
+ pending_migrations = ActiveRecord::Migrator.open(ActiveRecord::Tasks::DatabaseTasks.migrations_paths).pending_migrations
157
180
 
158
181
  if pending_migrations.any?
159
182
  puts "You have #{pending_migrations.size} pending #{pending_migrations.size > 1 ? 'migrations:' : 'migration:'}"
160
183
  pending_migrations.each do |pending_migration|
161
184
  puts ' %4d %s' % [pending_migration.version, pending_migration.name]
162
185
  end
163
- abort %{Run `rake db:migrate` to update your database then try again.}
186
+ abort %{Run `rails db:migrate` to update your database then try again.}
164
187
  end
165
188
  end
166
189
 
167
- desc 'Create the database, load the schema, and initialize with the seed data (use db:reset to also drop the database first)'
190
+ desc 'Creates the database, loads the schema, and initializes with the seed data (use db:reset to also drop the database first)'
168
191
  task :setup => ['db:schema:load_if_ruby', 'db:structure:load_if_sql', :seed]
169
192
 
170
- desc 'Load the seed data from db/seeds.rb'
193
+ desc 'Loads the seed data from db/seeds.rb'
171
194
  task :seed do
172
195
  db_namespace['abort_if_pending_migrations'].invoke
173
196
  ActiveRecord::Tasks::DatabaseTasks.load_seed
174
197
  end
175
198
 
176
199
  namespace :fixtures do
177
- desc "Load fixtures into the current environment's database. Load specific fixtures using FIXTURES=x,y. Load from subdirectory in test/fixtures using FIXTURES_DIR=z. Specify an alternative path (eg. spec/fixtures) using FIXTURES_PATH=spec/fixtures."
200
+ desc "Loads fixtures into the current environment's database. Load specific fixtures using FIXTURES=x,y. Load from subdirectory in test/fixtures using FIXTURES_DIR=z. Specify an alternative path (eg. spec/fixtures) using FIXTURES_PATH=spec/fixtures."
178
201
  task :load => [:environment, :load_config] do
179
202
  require 'active_record/fixtures'
180
203
 
@@ -222,7 +245,7 @@ db_namespace = namespace :db do
222
245
  end
223
246
 
224
247
  namespace :schema do
225
- desc 'Create a db/schema.rb file that is portable against any DB supported by AR'
248
+ desc 'Creates a db/schema.rb file that is portable against any DB supported by Active Record'
226
249
  task :dump => [:environment, :load_config] do
227
250
  require 'active_record/schema_dumper'
228
251
  filename = ENV['SCHEMA'] || File.join(ActiveRecord::Tasks::DatabaseTasks.db_dir, 'schema.rb')
@@ -232,8 +255,8 @@ db_namespace = namespace :db do
232
255
  db_namespace['schema:dump'].reenable
233
256
  end
234
257
 
235
- desc 'Load a schema.rb file into the database'
236
- task :load => [:environment, :load_config] do
258
+ desc 'Loads a schema.rb file into the database'
259
+ task :load => [:environment, :load_config, :check_protected_environments] do
237
260
  ActiveRecord::Tasks::DatabaseTasks.load_schema_current(:ruby, ENV['SCHEMA'])
238
261
  end
239
262
 
@@ -242,29 +265,29 @@ db_namespace = namespace :db do
242
265
  end
243
266
 
244
267
  namespace :cache do
245
- desc 'Create a db/schema_cache.dump file.'
268
+ desc 'Creates a db/schema_cache.dump file.'
246
269
  task :dump => [:environment, :load_config] do
247
270
  con = ActiveRecord::Base.connection
248
271
  filename = File.join(ActiveRecord::Tasks::DatabaseTasks.db_dir, "schema_cache.dump")
249
272
 
250
273
  con.schema_cache.clear!
251
- con.tables.each { |table| con.schema_cache.add(table) }
274
+ con.data_sources.each { |table| con.schema_cache.add(table) }
252
275
  open(filename, 'wb') { |f| f.write(Marshal.dump(con.schema_cache)) }
253
276
  end
254
277
 
255
- desc 'Clear a db/schema_cache.dump file.'
278
+ desc 'Clears a db/schema_cache.dump file.'
256
279
  task :clear => [:environment, :load_config] do
257
280
  filename = File.join(ActiveRecord::Tasks::DatabaseTasks.db_dir, "schema_cache.dump")
258
- FileUtils.rm(filename) if File.exist?(filename)
281
+ rm_f filename, verbose: false
259
282
  end
260
283
  end
261
284
 
262
285
  end
263
286
 
264
287
  namespace :structure do
265
- desc 'Dump the database structure to db/structure.sql. Specify another file with DB_STRUCTURE=db/my_structure.sql'
288
+ desc 'Dumps the database structure to db/structure.sql. Specify another file with SCHEMA=db/my_structure.sql'
266
289
  task :dump => [:environment, :load_config] do
267
- filename = ENV['DB_STRUCTURE'] || File.join(ActiveRecord::Tasks::DatabaseTasks.db_dir, "structure.sql")
290
+ filename = ENV['SCHEMA'] || File.join(ActiveRecord::Tasks::DatabaseTasks.db_dir, "structure.sql")
268
291
  current_config = ActiveRecord::Tasks::DatabaseTasks.current_config
269
292
  ActiveRecord::Tasks::DatabaseTasks.structure_dump(current_config, filename)
270
293
 
@@ -278,9 +301,9 @@ db_namespace = namespace :db do
278
301
  db_namespace['structure:dump'].reenable
279
302
  end
280
303
 
281
- desc "Recreate the databases from the structure.sql file"
282
- task :load => [:load_config] do
283
- ActiveRecord::Tasks::DatabaseTasks.load_schema_current(:sql, ENV['DB_STRUCTURE'])
304
+ desc "Recreates the databases from the structure.sql file"
305
+ task :load => [:environment, :load_config, :check_protected_environments] do
306
+ ActiveRecord::Tasks::DatabaseTasks.load_schema_current(:sql, ENV['SCHEMA'])
284
307
  end
285
308
 
286
309
  task :load_if_sql => ['db:create', :environment] do
@@ -312,7 +335,7 @@ db_namespace = namespace :db do
312
335
  begin
313
336
  should_reconnect = ActiveRecord::Base.connection_pool.active_connection?
314
337
  ActiveRecord::Schema.verbose = false
315
- ActiveRecord::Tasks::DatabaseTasks.load_schema_for ActiveRecord::Base.configurations['test'], :ruby, ENV['SCHEMA']
338
+ ActiveRecord::Tasks::DatabaseTasks.load_schema ActiveRecord::Base.configurations['test'], :ruby, ENV['SCHEMA']
316
339
  ensure
317
340
  if should_reconnect
318
341
  ActiveRecord::Base.establish_connection(ActiveRecord::Base.configurations[ActiveRecord::Tasks::DatabaseTasks.env])
@@ -322,7 +345,7 @@ db_namespace = namespace :db do
322
345
 
323
346
  # desc "Recreate the test database from an existent structure.sql file"
324
347
  task :load_structure => %w(db:test:purge) do
325
- ActiveRecord::Tasks::DatabaseTasks.load_schema_for ActiveRecord::Base.configurations['test'], :sql, ENV['SCHEMA']
348
+ ActiveRecord::Tasks::DatabaseTasks.load_schema ActiveRecord::Base.configurations['test'], :sql, ENV['SCHEMA']
326
349
  end
327
350
 
328
351
  # desc "Recreate the test database from a fresh schema"
@@ -342,11 +365,11 @@ db_namespace = namespace :db do
342
365
  task :clone_structure => %w(db:test:deprecated db:structure:dump db:test:load_structure)
343
366
 
344
367
  # desc "Empty the test database"
345
- task :purge => %w(environment load_config) do
368
+ task :purge => %w(environment load_config check_protected_environments) do
346
369
  ActiveRecord::Tasks::DatabaseTasks.purge ActiveRecord::Base.configurations['test']
347
370
  end
348
371
 
349
- # desc 'Check for pending migrations and load the test schema'
372
+ # desc 'Load the test schema'
350
373
  task :prepare => %w(environment load_config) do
351
374
  unless ActiveRecord::Base.configurations.blank?
352
375
  db_namespace['test:load'].invoke
@@ -359,7 +382,7 @@ namespace :railties do
359
382
  namespace :install do
360
383
  # desc "Copies missing migrations from Railties (e.g. engines). You can specify Railties to use with FROM=railtie1,railtie2"
361
384
  task :migrations => :'db:load_config' do
362
- to_load = ENV['FROM'].blank? ? :all : ENV['FROM'].split(",").map {|n| n.strip }
385
+ to_load = ENV['FROM'].blank? ? :all : ENV['FROM'].split(",").map(&:strip)
363
386
  railties = {}
364
387
  Rails.application.migration_railties.each do |railtie|
365
388
  next unless to_load == :all || to_load.include?(railtie.railtie_name)
@@ -377,7 +400,7 @@ namespace :railties do
377
400
  puts "Copied migration #{migration.basename} from #{name}"
378
401
  end
379
402
 
380
- ActiveRecord::Migration.copy(ActiveRecord::Migrator.migrations_paths.first, railties,
403
+ ActiveRecord::Migration.copy(ActiveRecord::Tasks::DatabaseTasks.migrations_paths.first, railties,
381
404
  :on_skip => on_skip, :on_copy => on_copy)
382
405
  end
383
406
  end