activerecord 5.2.3.rc1 → 6.0.0.beta1

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 (240) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +326 -696
  3. data/MIT-LICENSE +3 -1
  4. data/README.rdoc +1 -1
  5. data/examples/performance.rb +1 -1
  6. data/lib/active_record.rb +2 -1
  7. data/lib/active_record/aggregations.rb +4 -2
  8. data/lib/active_record/associations.rb +16 -12
  9. data/lib/active_record/associations/association.rb +35 -19
  10. data/lib/active_record/associations/association_scope.rb +4 -6
  11. data/lib/active_record/associations/belongs_to_association.rb +36 -42
  12. data/lib/active_record/associations/belongs_to_polymorphic_association.rb +0 -4
  13. data/lib/active_record/associations/builder/belongs_to.rb +14 -50
  14. data/lib/active_record/associations/builder/collection_association.rb +1 -1
  15. data/lib/active_record/associations/builder/has_and_belongs_to_many.rb +17 -38
  16. data/lib/active_record/associations/collection_association.rb +11 -25
  17. data/lib/active_record/associations/collection_proxy.rb +32 -6
  18. data/lib/active_record/associations/foreign_association.rb +7 -0
  19. data/lib/active_record/associations/has_many_association.rb +1 -1
  20. data/lib/active_record/associations/has_many_through_association.rb +14 -14
  21. data/lib/active_record/associations/has_one_association.rb +28 -30
  22. data/lib/active_record/associations/has_one_through_association.rb +5 -5
  23. data/lib/active_record/associations/join_dependency.rb +15 -20
  24. data/lib/active_record/associations/join_dependency/join_association.rb +6 -0
  25. data/lib/active_record/associations/join_dependency/join_part.rb +2 -2
  26. data/lib/active_record/associations/preloader.rb +31 -28
  27. data/lib/active_record/associations/preloader/association.rb +1 -2
  28. data/lib/active_record/associations/singular_association.rb +2 -16
  29. data/lib/active_record/attribute_assignment.rb +7 -10
  30. data/lib/active_record/attribute_methods.rb +34 -56
  31. data/lib/active_record/attribute_methods/dirty.rb +64 -26
  32. data/lib/active_record/attribute_methods/primary_key.rb +8 -7
  33. data/lib/active_record/attribute_methods/read.rb +16 -48
  34. data/lib/active_record/attribute_methods/serialization.rb +1 -1
  35. data/lib/active_record/attribute_methods/time_zone_conversion.rb +1 -1
  36. data/lib/active_record/attribute_methods/write.rb +15 -16
  37. data/lib/active_record/autosave_association.rb +1 -1
  38. data/lib/active_record/base.rb +2 -2
  39. data/lib/active_record/callbacks.rb +3 -17
  40. data/lib/active_record/collection_cache_key.rb +1 -1
  41. data/lib/active_record/connection_adapters/abstract/connection_pool.rb +10 -14
  42. data/lib/active_record/connection_adapters/abstract/database_limits.rb +9 -0
  43. data/lib/active_record/connection_adapters/abstract/database_statements.rb +25 -84
  44. data/lib/active_record/connection_adapters/abstract/query_cache.rb +14 -11
  45. data/lib/active_record/connection_adapters/abstract/quoting.rb +5 -11
  46. data/lib/active_record/connection_adapters/abstract/schema_creation.rb +15 -11
  47. data/lib/active_record/connection_adapters/abstract/schema_definitions.rb +30 -13
  48. data/lib/active_record/connection_adapters/abstract/schema_dumper.rb +0 -2
  49. data/lib/active_record/connection_adapters/abstract/schema_statements.rb +40 -26
  50. data/lib/active_record/connection_adapters/abstract/transaction.rb +81 -52
  51. data/lib/active_record/connection_adapters/abstract_adapter.rb +95 -31
  52. data/lib/active_record/connection_adapters/abstract_mysql_adapter.rb +65 -90
  53. data/lib/active_record/connection_adapters/connection_specification.rb +52 -42
  54. data/lib/active_record/connection_adapters/determine_if_preparable_visitor.rb +5 -9
  55. data/lib/active_record/connection_adapters/mysql/database_statements.rb +29 -7
  56. data/lib/active_record/connection_adapters/mysql/quoting.rb +1 -1
  57. data/lib/active_record/connection_adapters/mysql/schema_creation.rb +3 -4
  58. data/lib/active_record/connection_adapters/mysql/schema_statements.rb +65 -10
  59. data/lib/active_record/connection_adapters/mysql2_adapter.rb +8 -4
  60. data/lib/active_record/connection_adapters/postgresql/column.rb +1 -2
  61. data/lib/active_record/connection_adapters/postgresql/database_statements.rb +16 -1
  62. data/lib/active_record/connection_adapters/postgresql/oid/array.rb +1 -1
  63. data/lib/active_record/connection_adapters/postgresql/oid/bit.rb +1 -4
  64. data/lib/active_record/connection_adapters/postgresql/oid/hstore.rb +1 -1
  65. data/lib/active_record/connection_adapters/postgresql/oid/legacy_point.rb +1 -1
  66. data/lib/active_record/connection_adapters/postgresql/oid/point.rb +1 -1
  67. data/lib/active_record/connection_adapters/postgresql/oid/type_map_initializer.rb +9 -7
  68. data/lib/active_record/connection_adapters/postgresql/quoting.rb +4 -4
  69. data/lib/active_record/connection_adapters/postgresql/schema_creation.rb +11 -36
  70. data/lib/active_record/connection_adapters/postgresql/schema_definitions.rb +9 -2
  71. data/lib/active_record/connection_adapters/postgresql/schema_statements.rb +38 -20
  72. data/lib/active_record/connection_adapters/postgresql/type_metadata.rb +2 -1
  73. data/lib/active_record/connection_adapters/postgresql_adapter.rb +75 -56
  74. data/lib/active_record/connection_adapters/schema_cache.rb +5 -0
  75. data/lib/active_record/connection_adapters/sqlite3/quoting.rb +5 -5
  76. data/lib/active_record/connection_adapters/sqlite3/schema_statements.rb +14 -9
  77. data/lib/active_record/connection_adapters/sqlite3_adapter.rb +93 -60
  78. data/lib/active_record/connection_handling.rb +132 -26
  79. data/lib/active_record/core.rb +76 -43
  80. data/lib/active_record/counter_cache.rb +4 -29
  81. data/lib/active_record/database_configurations.rb +184 -0
  82. data/lib/active_record/database_configurations/database_config.rb +37 -0
  83. data/lib/active_record/database_configurations/hash_config.rb +50 -0
  84. data/lib/active_record/database_configurations/url_config.rb +74 -0
  85. data/lib/active_record/enum.rb +22 -7
  86. data/lib/active_record/errors.rb +24 -21
  87. data/lib/active_record/explain.rb +1 -1
  88. data/lib/active_record/fixture_set/model_metadata.rb +33 -0
  89. data/lib/active_record/fixture_set/render_context.rb +17 -0
  90. data/lib/active_record/fixture_set/table_row.rb +153 -0
  91. data/lib/active_record/fixture_set/table_rows.rb +47 -0
  92. data/lib/active_record/fixtures.rb +140 -472
  93. data/lib/active_record/gem_version.rb +4 -4
  94. data/lib/active_record/inheritance.rb +12 -2
  95. data/lib/active_record/integration.rb +56 -16
  96. data/lib/active_record/internal_metadata.rb +5 -1
  97. data/lib/active_record/locking/optimistic.rb +2 -2
  98. data/lib/active_record/locking/pessimistic.rb +3 -3
  99. data/lib/active_record/log_subscriber.rb +7 -26
  100. data/lib/active_record/migration.rb +38 -37
  101. data/lib/active_record/migration/command_recorder.rb +35 -5
  102. data/lib/active_record/migration/compatibility.rb +34 -16
  103. data/lib/active_record/model_schema.rb +30 -9
  104. data/lib/active_record/nested_attributes.rb +2 -2
  105. data/lib/active_record/no_touching.rb +7 -0
  106. data/lib/active_record/persistence.rb +18 -7
  107. data/lib/active_record/query_cache.rb +11 -4
  108. data/lib/active_record/querying.rb +19 -11
  109. data/lib/active_record/railtie.rb +71 -42
  110. data/lib/active_record/railties/collection_cache_association_loading.rb +34 -0
  111. data/lib/active_record/railties/controller_runtime.rb +30 -35
  112. data/lib/active_record/railties/databases.rake +94 -43
  113. data/lib/active_record/reflection.rb +46 -34
  114. data/lib/active_record/relation.rb +150 -69
  115. data/lib/active_record/relation/batches.rb +13 -10
  116. data/lib/active_record/relation/calculations.rb +34 -23
  117. data/lib/active_record/relation/delegation.rb +4 -13
  118. data/lib/active_record/relation/finder_methods.rb +12 -25
  119. data/lib/active_record/relation/merger.rb +2 -6
  120. data/lib/active_record/relation/predicate_builder.rb +4 -6
  121. data/lib/active_record/relation/predicate_builder/array_handler.rb +5 -4
  122. data/lib/active_record/relation/predicate_builder/association_query_value.rb +1 -4
  123. data/lib/active_record/relation/predicate_builder/base_handler.rb +1 -2
  124. data/lib/active_record/relation/predicate_builder/basic_object_handler.rb +1 -2
  125. data/lib/active_record/relation/predicate_builder/polymorphic_array_value.rb +1 -4
  126. data/lib/active_record/relation/predicate_builder/range_handler.rb +3 -23
  127. data/lib/active_record/relation/query_attribute.rb +15 -12
  128. data/lib/active_record/relation/query_methods.rb +26 -47
  129. data/lib/active_record/relation/where_clause.rb +4 -0
  130. data/lib/active_record/relation/where_clause_factory.rb +1 -2
  131. data/lib/active_record/result.rb +30 -11
  132. data/lib/active_record/sanitization.rb +2 -39
  133. data/lib/active_record/schema.rb +1 -10
  134. data/lib/active_record/schema_dumper.rb +12 -6
  135. data/lib/active_record/schema_migration.rb +4 -0
  136. data/lib/active_record/scoping.rb +9 -8
  137. data/lib/active_record/scoping/default.rb +8 -1
  138. data/lib/active_record/scoping/named.rb +10 -14
  139. data/lib/active_record/statement_cache.rb +30 -3
  140. data/lib/active_record/store.rb +39 -8
  141. data/lib/active_record/table_metadata.rb +1 -4
  142. data/lib/active_record/tasks/database_tasks.rb +89 -23
  143. data/lib/active_record/tasks/mysql_database_tasks.rb +2 -4
  144. data/lib/active_record/tasks/postgresql_database_tasks.rb +5 -7
  145. data/lib/active_record/tasks/sqlite_database_tasks.rb +2 -8
  146. data/lib/active_record/test_databases.rb +38 -0
  147. data/lib/active_record/test_fixtures.rb +224 -0
  148. data/lib/active_record/timestamp.rb +4 -6
  149. data/lib/active_record/transactions.rb +2 -21
  150. data/lib/active_record/translation.rb +1 -1
  151. data/lib/active_record/type.rb +3 -4
  152. data/lib/active_record/type/adapter_specific_registry.rb +1 -8
  153. data/lib/active_record/type_caster/connection.rb +1 -6
  154. data/lib/active_record/type_caster/map.rb +1 -4
  155. data/lib/active_record/validations/uniqueness.rb +13 -25
  156. data/lib/arel.rb +44 -0
  157. data/lib/arel/alias_predication.rb +9 -0
  158. data/lib/arel/attributes.rb +22 -0
  159. data/lib/arel/attributes/attribute.rb +37 -0
  160. data/lib/arel/collectors/bind.rb +24 -0
  161. data/lib/arel/collectors/composite.rb +31 -0
  162. data/lib/arel/collectors/plain_string.rb +20 -0
  163. data/lib/arel/collectors/sql_string.rb +20 -0
  164. data/lib/arel/collectors/substitute_binds.rb +28 -0
  165. data/lib/arel/crud.rb +42 -0
  166. data/lib/arel/delete_manager.rb +18 -0
  167. data/lib/arel/errors.rb +9 -0
  168. data/lib/arel/expressions.rb +29 -0
  169. data/lib/arel/factory_methods.rb +49 -0
  170. data/lib/arel/insert_manager.rb +49 -0
  171. data/lib/arel/math.rb +45 -0
  172. data/lib/arel/nodes.rb +67 -0
  173. data/lib/arel/nodes/and.rb +32 -0
  174. data/lib/arel/nodes/ascending.rb +23 -0
  175. data/lib/arel/nodes/binary.rb +52 -0
  176. data/lib/arel/nodes/bind_param.rb +36 -0
  177. data/lib/arel/nodes/case.rb +55 -0
  178. data/lib/arel/nodes/casted.rb +50 -0
  179. data/lib/arel/nodes/count.rb +12 -0
  180. data/lib/arel/nodes/delete_statement.rb +45 -0
  181. data/lib/arel/nodes/descending.rb +23 -0
  182. data/lib/arel/nodes/equality.rb +18 -0
  183. data/lib/arel/nodes/extract.rb +24 -0
  184. data/lib/arel/nodes/false.rb +16 -0
  185. data/lib/arel/nodes/full_outer_join.rb +8 -0
  186. data/lib/arel/nodes/function.rb +44 -0
  187. data/lib/arel/nodes/grouping.rb +8 -0
  188. data/lib/arel/nodes/in.rb +8 -0
  189. data/lib/arel/nodes/infix_operation.rb +80 -0
  190. data/lib/arel/nodes/inner_join.rb +8 -0
  191. data/lib/arel/nodes/insert_statement.rb +37 -0
  192. data/lib/arel/nodes/join_source.rb +20 -0
  193. data/lib/arel/nodes/matches.rb +18 -0
  194. data/lib/arel/nodes/named_function.rb +23 -0
  195. data/lib/arel/nodes/node.rb +50 -0
  196. data/lib/arel/nodes/node_expression.rb +13 -0
  197. data/lib/arel/nodes/outer_join.rb +8 -0
  198. data/lib/arel/nodes/over.rb +15 -0
  199. data/lib/arel/nodes/regexp.rb +16 -0
  200. data/lib/arel/nodes/right_outer_join.rb +8 -0
  201. data/lib/arel/nodes/select_core.rb +63 -0
  202. data/lib/arel/nodes/select_statement.rb +41 -0
  203. data/lib/arel/nodes/sql_literal.rb +16 -0
  204. data/lib/arel/nodes/string_join.rb +11 -0
  205. data/lib/arel/nodes/table_alias.rb +27 -0
  206. data/lib/arel/nodes/terminal.rb +16 -0
  207. data/lib/arel/nodes/true.rb +16 -0
  208. data/lib/arel/nodes/unary.rb +44 -0
  209. data/lib/arel/nodes/unary_operation.rb +20 -0
  210. data/lib/arel/nodes/unqualified_column.rb +22 -0
  211. data/lib/arel/nodes/update_statement.rb +41 -0
  212. data/lib/arel/nodes/values.rb +16 -0
  213. data/lib/arel/nodes/values_list.rb +24 -0
  214. data/lib/arel/nodes/window.rb +126 -0
  215. data/lib/arel/nodes/with.rb +11 -0
  216. data/lib/arel/order_predications.rb +13 -0
  217. data/lib/arel/predications.rb +257 -0
  218. data/lib/arel/select_manager.rb +271 -0
  219. data/lib/arel/table.rb +110 -0
  220. data/lib/arel/tree_manager.rb +72 -0
  221. data/lib/arel/update_manager.rb +34 -0
  222. data/lib/arel/visitors.rb +20 -0
  223. data/lib/arel/visitors/depth_first.rb +199 -0
  224. data/lib/arel/visitors/dot.rb +292 -0
  225. data/lib/arel/visitors/ibm_db.rb +21 -0
  226. data/lib/arel/visitors/informix.rb +56 -0
  227. data/lib/arel/visitors/mssql.rb +143 -0
  228. data/lib/arel/visitors/mysql.rb +83 -0
  229. data/lib/arel/visitors/oracle.rb +159 -0
  230. data/lib/arel/visitors/oracle12.rb +67 -0
  231. data/lib/arel/visitors/postgresql.rb +116 -0
  232. data/lib/arel/visitors/sqlite.rb +39 -0
  233. data/lib/arel/visitors/to_sql.rb +913 -0
  234. data/lib/arel/visitors/visitor.rb +42 -0
  235. data/lib/arel/visitors/where_sql.rb +23 -0
  236. data/lib/arel/window_predications.rb +9 -0
  237. data/lib/rails/generators/active_record/migration.rb +14 -1
  238. data/lib/rails/generators/active_record/migration/migration_generator.rb +2 -5
  239. data/lib/rails/generators/active_record/model/model_generator.rb +1 -0
  240. metadata +101 -23
@@ -3,11 +3,7 @@
3
3
  module ActiveRecord
4
4
  class PredicateBuilder
5
5
  class RangeHandler # :nodoc:
6
- class RangeWithBinds < Struct.new(:begin, :end)
7
- def exclude_end?
8
- false
9
- end
10
- end
6
+ RangeWithBinds = Struct.new(:begin, :end, :exclude_end?)
11
7
 
12
8
  def initialize(predicate_builder)
13
9
  @predicate_builder = predicate_builder
@@ -16,26 +12,10 @@ module ActiveRecord
16
12
  def call(attribute, value)
17
13
  begin_bind = predicate_builder.build_bind_attribute(attribute.name, value.begin)
18
14
  end_bind = predicate_builder.build_bind_attribute(attribute.name, value.end)
19
-
20
- if begin_bind.value.infinity?
21
- if end_bind.value.infinity?
22
- attribute.not_in([])
23
- elsif value.exclude_end?
24
- attribute.lt(end_bind)
25
- else
26
- attribute.lteq(end_bind)
27
- end
28
- elsif end_bind.value.infinity?
29
- attribute.gteq(begin_bind)
30
- elsif value.exclude_end?
31
- attribute.gteq(begin_bind).and(attribute.lt(end_bind))
32
- else
33
- attribute.between(RangeWithBinds.new(begin_bind, end_bind))
34
- end
15
+ attribute.between(RangeWithBinds.new(begin_bind, end_bind, value.exclude_end?))
35
16
  end
36
17
 
37
- protected
38
-
18
+ private
39
19
  attr_reader :predicate_builder
40
20
  end
41
21
  end
@@ -18,26 +18,29 @@ module ActiveRecord
18
18
  end
19
19
 
20
20
  def nil?
21
- unless value_before_type_cast.is_a?(StatementCache::Substitute)
22
- value_before_type_cast.nil? ||
23
- type.respond_to?(:subtype, true) && value_for_database.nil?
24
- end
21
+ !value_before_type_cast.is_a?(StatementCache::Substitute) &&
22
+ (value_before_type_cast.nil? || value_for_database.nil?)
23
+ rescue ::RangeError
25
24
  end
26
25
 
27
- def boundable?
28
- return @_boundable if defined?(@_boundable)
29
- value_for_database unless value_before_type_cast.is_a?(StatementCache::Substitute)
30
- @_boundable = true
26
+ def infinite?
27
+ infinity?(value_before_type_cast) || infinity?(value_for_database)
31
28
  rescue ::RangeError
32
- @_boundable = false
33
29
  end
34
30
 
35
- def infinity?
36
- _infinity?(value_before_type_cast) || boundable? && _infinity?(value_for_database)
31
+ def unboundable?
32
+ if defined?(@_unboundable)
33
+ @_unboundable
34
+ else
35
+ value_for_database
36
+ @_unboundable = nil
37
+ end
38
+ rescue ::RangeError
39
+ @_unboundable = type.cast(value_before_type_cast) <=> 0
37
40
  end
38
41
 
39
42
  private
40
- def _infinity?(value)
43
+ def infinity?(value)
41
44
  value.respond_to?(:infinite?) && value.infinite?
42
45
  end
43
46
  end
@@ -231,6 +231,7 @@ module ActiveRecord
231
231
  end
232
232
 
233
233
  def _select!(*fields) # :nodoc:
234
+ fields.reject!(&:blank?)
234
235
  fields.flatten!
235
236
  fields.map! do |field|
236
237
  klass.attribute_alias?(field) ? klass.attribute_alias(field).to_sym : field
@@ -898,26 +899,28 @@ module ActiveRecord
898
899
  self
899
900
  end
900
901
 
902
+ def skip_preloading! # :nodoc:
903
+ self.skip_preloading_value = true
904
+ self
905
+ end
906
+
901
907
  # Returns the Arel object associated with the relation.
902
908
  def arel(aliases = nil) # :nodoc:
903
909
  @arel ||= build_arel(aliases)
904
910
  end
905
911
 
906
- # Returns a relation value with a given name
907
- def get_value(name) # :nodoc:
908
- @values.fetch(name, DEFAULT_VALUES[name])
909
- end
910
-
911
- protected
912
+ private
913
+ # Returns a relation value with a given name
914
+ def get_value(name)
915
+ @values.fetch(name, DEFAULT_VALUES[name])
916
+ end
912
917
 
913
918
  # Sets the relation value with the given name
914
- def set_value(name, value) # :nodoc:
919
+ def set_value(name, value)
915
920
  assert_mutability!
916
921
  @values[name] = value
917
922
  end
918
923
 
919
- private
920
-
921
924
  def assert_mutability!
922
925
  raise ImmutableRelation if @loaded
923
926
  raise ImmutableRelation if defined?(@arel) && @arel
@@ -933,7 +936,7 @@ module ActiveRecord
933
936
  arel.having(having_clause.ast) unless having_clause.empty?
934
937
  if limit_value
935
938
  limit_attribute = ActiveModel::Attribute.with_cast_value(
936
- "LIMIT".freeze,
939
+ "LIMIT",
937
940
  connection.sanitize_limit(limit_value),
938
941
  Type.default_value,
939
942
  )
@@ -941,7 +944,7 @@ module ActiveRecord
941
944
  end
942
945
  if offset_value
943
946
  offset_attribute = ActiveModel::Attribute.with_cast_value(
944
- "OFFSET".freeze,
947
+ "OFFSET",
945
948
  offset_value.to_i,
946
949
  Type.default_value,
947
950
  )
@@ -1020,9 +1023,7 @@ module ActiveRecord
1020
1023
  join_list = join_nodes + convert_join_strings_to_ast(string_joins)
1021
1024
  alias_tracker = alias_tracker(join_list, aliases)
1022
1025
 
1023
- join_dependency = ActiveRecord::Associations::JoinDependency.new(
1024
- klass, table, association_joins
1025
- )
1026
+ join_dependency = construct_join_dependency(association_joins)
1026
1027
 
1027
1028
  joins = join_dependency.join_constraints(stashed_joins, join_type, alias_tracker)
1028
1029
  joins.each { |join| manager.from(join) }
@@ -1051,13 +1052,11 @@ module ActiveRecord
1051
1052
 
1052
1053
  def arel_columns(columns)
1053
1054
  columns.flat_map do |field|
1054
- case field
1055
- when Symbol
1056
- field = field.to_s
1057
- arel_column(field) { connection.quote_table_name(field) }
1058
- when String
1059
- arel_column(field) { field }
1060
- when Proc
1055
+ if (Symbol === field || String === field) && (klass.has_attribute?(field) || klass.attribute_alias?(field)) && !from_clause.value
1056
+ arel_attribute(field)
1057
+ elsif Symbol === field
1058
+ connection.quote_table_name(field.to_s)
1059
+ elsif Proc === field
1061
1060
  field.call
1062
1061
  else
1063
1062
  field
@@ -1065,21 +1064,6 @@ module ActiveRecord
1065
1064
  end
1066
1065
  end
1067
1066
 
1068
- def arel_column(field)
1069
- field = klass.attribute_alias(field) if klass.attribute_alias?(field)
1070
- from = from_clause.name || from_clause.value
1071
-
1072
- if klass.columns_hash.key?(field) && (!from || table_name_matches?(from))
1073
- arel_attribute(field)
1074
- else
1075
- yield
1076
- end
1077
- end
1078
-
1079
- def table_name_matches?(from)
1080
- /(?:\A|(?<!FROM)\s)(?:\b#{table.name}\b|#{connection.quote_table_name(table.name)})(?!\.)/i.match?(from.to_s)
1081
- end
1082
-
1083
1067
  def reverse_sql_order(order_query)
1084
1068
  if order_query.empty?
1085
1069
  return [arel_attribute(primary_key).desc] if primary_key
@@ -1146,9 +1130,9 @@ module ActiveRecord
1146
1130
  end
1147
1131
  order_args.flatten!
1148
1132
 
1149
- @klass.enforce_raw_sql_whitelist(
1133
+ @klass.disallow_raw_sql!(
1150
1134
  order_args.flat_map { |a| a.is_a?(Hash) ? a.keys : a },
1151
- whitelist: AttributeMethods::ClassMethods::COLUMN_NAME_ORDER_WHITELIST
1135
+ permit: AttributeMethods::ClassMethods::COLUMN_NAME_WITH_ORDER
1152
1136
  )
1153
1137
 
1154
1138
  validate_order_args(order_args)
@@ -1161,20 +1145,14 @@ module ActiveRecord
1161
1145
  order_args.map! do |arg|
1162
1146
  case arg
1163
1147
  when Symbol
1164
- arg = arg.to_s
1165
- arel_column(arg) {
1166
- Arel.sql(connection.quote_table_name(arg))
1167
- }.asc
1148
+ arel_attribute(arg).asc
1168
1149
  when Hash
1169
1150
  arg.map { |field, dir|
1170
1151
  case field
1171
1152
  when Arel::Nodes::SqlLiteral
1172
1153
  field.send(dir.downcase)
1173
1154
  else
1174
- field = field.to_s
1175
- arel_column(field) {
1176
- Arel.sql(connection.quote_table_name(field))
1177
- }.send(dir.downcase)
1155
+ arel_attribute(field).send(dir.downcase)
1178
1156
  end
1179
1157
  }
1180
1158
  else
@@ -1207,8 +1185,9 @@ module ActiveRecord
1207
1185
 
1208
1186
  STRUCTURAL_OR_METHODS = Relation::VALUE_METHODS - [:extending, :where, :having, :unscope, :references]
1209
1187
  def structurally_incompatible_values_for_or(other)
1188
+ values = other.values
1210
1189
  STRUCTURAL_OR_METHODS.reject do |method|
1211
- get_value(method) == other.get_value(method)
1190
+ get_value(method) == values.fetch(method, DEFAULT_VALUES[method])
1212
1191
  end
1213
1192
  end
1214
1193
 
@@ -125,6 +125,10 @@ module ActiveRecord
125
125
  raise ArgumentError, "Invalid argument for .where.not(), got nil."
126
126
  when Arel::Nodes::In
127
127
  Arel::Nodes::NotIn.new(node.left, node.right)
128
+ when Arel::Nodes::IsNotDistinctFrom
129
+ Arel::Nodes::IsDistinctFrom.new(node.left, node.right)
130
+ when Arel::Nodes::IsDistinctFrom
131
+ Arel::Nodes::IsNotDistinctFrom.new(node.left, node.right)
128
132
  when Arel::Nodes::Equality
129
133
  Arel::Nodes::NotEqual.new(node.left, node.right)
130
134
  when String
@@ -26,8 +26,7 @@ module ActiveRecord
26
26
  WhereClause.new(parts)
27
27
  end
28
28
 
29
- protected
30
-
29
+ private
31
30
  attr_reader :klass, :predicate_builder
32
31
  end
33
32
  end
@@ -21,7 +21,7 @@ module ActiveRecord
21
21
  # ]
22
22
  #
23
23
  # # Get an array of hashes representing the result (column => value):
24
- # result.to_hash
24
+ # result.to_a
25
25
  # # => [{"id" => 1, "title" => "title_1", "body" => "body_1"},
26
26
  # {"id" => 2, "title" => "title_2", "body" => "body_2"},
27
27
  # ...
@@ -43,6 +43,11 @@ module ActiveRecord
43
43
  @column_types = column_types
44
44
  end
45
45
 
46
+ # Returns true if this result set includes the column named +name+
47
+ def includes_column?(name)
48
+ @columns.include? name
49
+ end
50
+
46
51
  # Returns the number of elements in the rows array.
47
52
  def length
48
53
  @rows.length
@@ -60,9 +65,12 @@ module ActiveRecord
60
65
  end
61
66
  end
62
67
 
63
- # Returns an array of hashes representing each row record.
64
68
  def to_hash
65
- hash_rows
69
+ ActiveSupport::Deprecation.warn(<<-MSG.squish)
70
+ `ActiveRecord::Result#to_hash` has been renamed to `to_a`.
71
+ `to_hash` is deprecated and will be removed in Rails 6.1.
72
+ MSG
73
+ to_a
66
74
  end
67
75
 
68
76
  alias :map! :map
@@ -78,6 +86,8 @@ module ActiveRecord
78
86
  hash_rows
79
87
  end
80
88
 
89
+ alias :to_a :to_ary
90
+
81
91
  def [](idx)
82
92
  hash_rows[idx]
83
93
  end
@@ -97,12 +107,21 @@ module ActiveRecord
97
107
  end
98
108
 
99
109
  def cast_values(type_overrides = {}) # :nodoc:
100
- types = columns.map { |name| column_type(name, type_overrides) }
101
- result = rows.map do |values|
102
- types.zip(values).map { |type, value| type.deserialize(value) }
103
- end
110
+ if columns.one?
111
+ # Separated to avoid allocating an array per row
112
+
113
+ type = column_type(columns.first, type_overrides)
104
114
 
105
- columns.one? ? result.map!(&:first) : result
115
+ rows.map do |(value)|
116
+ type.deserialize(value)
117
+ end
118
+ else
119
+ types = columns.map { |name| column_type(name, type_overrides) }
120
+
121
+ rows.map do |values|
122
+ Array.new(values.size) { |i| types[i].deserialize(values[i]) }
123
+ end
124
+ end
106
125
  end
107
126
 
108
127
  def initialize_copy(other)
@@ -125,7 +144,9 @@ module ActiveRecord
125
144
  begin
126
145
  # We freeze the strings to prevent them getting duped when
127
146
  # used as keys in ActiveRecord::Base's @attributes hash
128
- columns = @columns.map { |c| c.dup.freeze }
147
+ columns = @columns.map(&:-@)
148
+ length = columns.length
149
+
129
150
  @rows.map { |row|
130
151
  # In the past we used Hash[columns.zip(row)]
131
152
  # though elegant, the verbose way is much more efficient
@@ -134,8 +155,6 @@ module ActiveRecord
134
155
  hash = {}
135
156
 
136
157
  index = 0
137
- length = columns.length
138
-
139
158
  while index < length
140
159
  hash[columns[index]] = row[index]
141
160
  index += 1
@@ -61,8 +61,8 @@ module ActiveRecord
61
61
  # # => "id ASC"
62
62
  def sanitize_sql_for_order(condition)
63
63
  if condition.is_a?(Array) && condition.first.to_s.include?("?")
64
- enforce_raw_sql_whitelist([condition.first],
65
- whitelist: AttributeMethods::ClassMethods::COLUMN_NAME_ORDER_WHITELIST
64
+ disallow_raw_sql!([condition.first],
65
+ permit: AttributeMethods::ClassMethods::COLUMN_NAME_WITH_ORDER
66
66
  )
67
67
 
68
68
  # Ensure we aren't dealing with a subclass of String that might
@@ -134,43 +134,6 @@ module ActiveRecord
134
134
  end
135
135
 
136
136
  private
137
- # Accepts a hash of SQL conditions and replaces those attributes
138
- # that correspond to a {#composed_of}[rdoc-ref:Aggregations::ClassMethods#composed_of]
139
- # relationship with their expanded aggregate attribute values.
140
- #
141
- # Given:
142
- #
143
- # class Person < ActiveRecord::Base
144
- # composed_of :address, class_name: "Address",
145
- # mapping: [%w(address_street street), %w(address_city city)]
146
- # end
147
- #
148
- # Then:
149
- #
150
- # { address: Address.new("813 abc st.", "chicago") }
151
- # # => { address_street: "813 abc st.", address_city: "chicago" }
152
- def expand_hash_conditions_for_aggregates(attrs) # :doc:
153
- expanded_attrs = {}
154
- attrs.each do |attr, value|
155
- if aggregation = reflect_on_aggregation(attr.to_sym)
156
- mapping = aggregation.mapping
157
- mapping.each do |field_attr, aggregate_attr|
158
- expanded_attrs[field_attr] = if value.is_a?(Array)
159
- value.map { |it| it.send(aggregate_attr) }
160
- elsif mapping.size == 1 && !value.respond_to?(aggregate_attr)
161
- value
162
- else
163
- value.send(aggregate_attr)
164
- end
165
- end
166
- else
167
- expanded_attrs[attr] = value
168
- end
169
- end
170
- expanded_attrs
171
- end
172
- deprecate :expand_hash_conditions_for_aggregates
173
-
174
137
  def replace_bind_variables(statement, values)
175
138
  raise_if_bind_arity_mismatch(statement, statement.count("?"), values.size)
176
139
  bound = values.dup
@@ -51,20 +51,11 @@ module ActiveRecord
51
51
 
52
52
  if info[:version].present?
53
53
  ActiveRecord::SchemaMigration.create_table
54
- connection.assume_migrated_upto_version(info[:version], migrations_paths)
54
+ connection.assume_migrated_upto_version(info[:version])
55
55
  end
56
56
 
57
57
  ActiveRecord::InternalMetadata.create_table
58
58
  ActiveRecord::InternalMetadata[:environment] = connection.migration_context.current_environment
59
59
  end
60
-
61
- private
62
- # Returns the migrations paths.
63
- #
64
- # ActiveRecord::Schema.new.migrations_paths
65
- # # => ["db/migrate"] # Rails migration path by default.
66
- def migrations_paths
67
- ActiveRecord::Migrator.migrations_paths
68
- end
69
60
  end
70
61
  end
@@ -17,6 +17,12 @@ module ActiveRecord
17
17
  # Only strings are accepted if ActiveRecord::Base.schema_format == :sql.
18
18
  cattr_accessor :ignore_tables, default: []
19
19
 
20
+ ##
21
+ # :singleton-method:
22
+ # Specify a custom regular expression matching foreign keys which name
23
+ # should not be dumped to db/schema.rb.
24
+ cattr_accessor :fk_ignore_pattern, default: /^fk_rails_[0-9a-f]{10}$/
25
+
20
26
  class << self
21
27
  def dump(connection = ActiveRecord::Base.connection, stream = STDOUT, config = ActiveRecord::Base)
22
28
  connection.create_schema_dumper(generate_options(config)).dump(stream)
@@ -65,11 +71,11 @@ module ActiveRecord
65
71
  # of editing this file, please use the migrations feature of Active Record to
66
72
  # incrementally modify your database, and then regenerate this schema definition.
67
73
  #
68
- # Note that this schema.rb definition is the authoritative source for your
69
- # database schema. If you need to create the application database on another
70
- # system, you should be using db:schema:load, not running all the migrations
71
- # from scratch. The latter is a flawed and unsustainable approach (the more migrations
72
- # you'll amass, the slower it'll run and the greater likelihood for issues).
74
+ # This file is the source Rails uses to define your schema when running `rails
75
+ # db:schema:load`. When creating a new database, `rails db:schema:load` tends to
76
+ # be faster and is potentially less error prone than running all of your
77
+ # migrations from scratch. Old migrations may fail to apply correctly if those
78
+ # migrations use external dependencies or application code.
73
79
  #
74
80
  # It's strongly recommended that you check this file into your version control system.
75
81
 
@@ -210,7 +216,7 @@ HEADER
210
216
  parts << "primary_key: #{foreign_key.primary_key.inspect}"
211
217
  end
212
218
 
213
- if foreign_key.name !~ /^fk_rails_[0-9a-f]{10}$/
219
+ if foreign_key.export_name_on_schema_dump?
214
220
  parts << "name: #{foreign_key.name.inspect}"
215
221
  end
216
222