activerecord 5.2.0.beta2 → 5.2.0.rc1

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 (80) hide show
  1. checksums.yaml +5 -5
  2. data/CHANGELOG.md +231 -2
  3. data/MIT-LICENSE +1 -1
  4. data/README.rdoc +1 -1
  5. data/lib/active_record.rb +1 -1
  6. data/lib/active_record/aggregations.rb +4 -5
  7. data/lib/active_record/association_relation.rb +2 -2
  8. data/lib/active_record/associations.rb +18 -12
  9. data/lib/active_record/associations/alias_tracker.rb +2 -10
  10. data/lib/active_record/associations/association.rb +1 -1
  11. data/lib/active_record/associations/belongs_to_association.rb +9 -9
  12. data/lib/active_record/associations/belongs_to_polymorphic_association.rb +1 -6
  13. data/lib/active_record/associations/builder/association.rb +2 -2
  14. data/lib/active_record/associations/builder/belongs_to.rb +7 -3
  15. data/lib/active_record/associations/collection_association.rb +2 -2
  16. data/lib/active_record/associations/collection_proxy.rb +1 -1
  17. data/lib/active_record/associations/has_many_association.rb +1 -1
  18. data/lib/active_record/associations/has_many_through_association.rb +4 -17
  19. data/lib/active_record/associations/has_one_through_association.rb +5 -6
  20. data/lib/active_record/associations/preloader.rb +1 -1
  21. data/lib/active_record/associations/preloader/association.rb +2 -2
  22. data/lib/active_record/associations/through_association.rb +22 -9
  23. data/lib/active_record/attribute_methods.rb +1 -5
  24. data/lib/active_record/attribute_methods/dirty.rb +2 -4
  25. data/lib/active_record/attributes.rb +1 -1
  26. data/lib/active_record/autosave_association.rb +3 -0
  27. data/lib/active_record/callbacks.rb +2 -2
  28. data/lib/active_record/collection_cache_key.rb +5 -6
  29. data/lib/active_record/connection_adapters/abstract/connection_pool.rb +1 -3
  30. data/lib/active_record/connection_adapters/abstract/database_statements.rb +57 -21
  31. data/lib/active_record/connection_adapters/abstract/schema_creation.rb +1 -0
  32. data/lib/active_record/connection_adapters/abstract/schema_definitions.rb +20 -3
  33. data/lib/active_record/connection_adapters/abstract/schema_statements.rb +55 -15
  34. data/lib/active_record/connection_adapters/abstract_adapter.rb +19 -6
  35. data/lib/active_record/connection_adapters/abstract_mysql_adapter.rb +55 -64
  36. data/lib/active_record/connection_adapters/mysql/database_statements.rb +8 -1
  37. data/lib/active_record/connection_adapters/mysql/schema_definitions.rb +0 -4
  38. data/lib/active_record/connection_adapters/mysql/schema_statements.rb +21 -6
  39. data/lib/active_record/connection_adapters/postgresql/oid/decimal.rb +1 -1
  40. data/lib/active_record/connection_adapters/postgresql/oid/range.rb +1 -1
  41. data/lib/active_record/connection_adapters/postgresql/quoting.rb +9 -1
  42. data/lib/active_record/connection_adapters/postgresql/schema_creation.rb +12 -0
  43. data/lib/active_record/connection_adapters/postgresql/schema_definitions.rb +13 -4
  44. data/lib/active_record/connection_adapters/postgresql/schema_statements.rb +170 -48
  45. data/lib/active_record/connection_adapters/postgresql_adapter.rb +15 -5
  46. data/lib/active_record/connection_adapters/schema_cache.rb +2 -2
  47. data/lib/active_record/connection_adapters/sqlite3_adapter.rb +63 -18
  48. data/lib/active_record/core.rb +12 -3
  49. data/lib/active_record/enum.rb +2 -0
  50. data/lib/active_record/fixtures.rb +28 -37
  51. data/lib/active_record/gem_version.rb +1 -1
  52. data/lib/active_record/inheritance.rb +3 -4
  53. data/lib/active_record/log_subscriber.rb +41 -0
  54. data/lib/active_record/migration.rb +138 -120
  55. data/lib/active_record/migration/compatibility.rb +20 -0
  56. data/lib/active_record/model_schema.rb +19 -16
  57. data/lib/active_record/persistence.rb +8 -11
  58. data/lib/active_record/railtie.rb +7 -2
  59. data/lib/active_record/railties/databases.rake +8 -11
  60. data/lib/active_record/reflection.rb +10 -13
  61. data/lib/active_record/relation.rb +27 -17
  62. data/lib/active_record/relation/calculations.rb +17 -12
  63. data/lib/active_record/relation/finder_methods.rb +30 -37
  64. data/lib/active_record/relation/merger.rb +30 -2
  65. data/lib/active_record/relation/predicate_builder.rb +12 -0
  66. data/lib/active_record/relation/predicate_builder/association_query_value.rb +1 -1
  67. data/lib/active_record/relation/predicate_builder/polymorphic_array_value.rb +1 -1
  68. data/lib/active_record/relation/query_methods.rb +14 -24
  69. data/lib/active_record/relation/spawn_methods.rb +1 -1
  70. data/lib/active_record/relation/where_clause.rb +16 -2
  71. data/lib/active_record/relation/where_clause_factory.rb +1 -2
  72. data/lib/active_record/sanitization.rb +130 -128
  73. data/lib/active_record/schema.rb +1 -1
  74. data/lib/active_record/schema_dumper.rb +12 -3
  75. data/lib/active_record/scoping/named.rb +6 -0
  76. data/lib/active_record/store.rb +1 -1
  77. data/lib/active_record/table_metadata.rb +10 -3
  78. data/lib/active_record/tasks/database_tasks.rb +4 -4
  79. data/lib/active_record/type_caster/map.rb +1 -1
  80. metadata +9 -9
@@ -12,17 +12,20 @@ module ActiveRecord
12
12
  if record
13
13
  raise_on_type_mismatch!(record)
14
14
  update_counters_on_replace(record)
15
- replace_keys(record)
16
15
  set_inverse_instance(record)
17
16
  @updated = true
18
17
  else
19
18
  decrement_counters
20
- remove_keys
21
19
  end
22
20
 
23
21
  self.target = record
24
22
  end
25
23
 
24
+ def target=(record)
25
+ replace_keys(record)
26
+ super
27
+ end
28
+
26
29
  def default(&block)
27
30
  writer(owner.instance_exec(&block)) if reader.nil?
28
31
  end
@@ -49,9 +52,9 @@ module ActiveRecord
49
52
  def update_counters(by)
50
53
  if require_counter_update? && foreign_key_present?
51
54
  if target && !stale_target?
52
- target.increment!(reflection.counter_cache_column, by)
55
+ target.increment!(reflection.counter_cache_column, by, touch: reflection.options[:touch])
53
56
  else
54
- klass.update_counters(target_id, reflection.counter_cache_column => by)
57
+ klass.update_counters(target_id, reflection.counter_cache_column => by, touch: reflection.options[:touch])
55
58
  end
56
59
  end
57
60
  end
@@ -78,11 +81,8 @@ module ActiveRecord
78
81
  end
79
82
 
80
83
  def replace_keys(record)
81
- owner[reflection.foreign_key] = record._read_attribute(reflection.association_primary_key(record.class))
82
- end
83
-
84
- def remove_keys
85
- owner[reflection.foreign_key] = nil
84
+ owner[reflection.foreign_key] = record ?
85
+ record._read_attribute(reflection.association_primary_key(record.class)) : nil
86
86
  end
87
87
 
88
88
  def foreign_key_present?
@@ -13,12 +13,7 @@ module ActiveRecord
13
13
 
14
14
  def replace_keys(record)
15
15
  super
16
- owner[reflection.foreign_type] = record.class.base_class.name
17
- end
18
-
19
- def remove_keys
20
- super
21
- owner[reflection.foreign_type] = nil
16
+ owner[reflection.foreign_type] = record ? record.class.base_class.name : nil
22
17
  end
23
18
 
24
19
  def different_target?(record)
@@ -104,8 +104,8 @@ module ActiveRecord::Associations::Builder # :nodoc:
104
104
 
105
105
  def self.define_readers(mixin, name)
106
106
  mixin.class_eval <<-CODE, __FILE__, __LINE__ + 1
107
- def #{name}(*args)
108
- association(:#{name}).reader(*args)
107
+ def #{name}
108
+ association(:#{name}).reader
109
109
  end
110
110
  CODE
111
111
  end
@@ -114,9 +114,13 @@ module ActiveRecord::Associations::Builder # :nodoc:
114
114
  BelongsTo.touch_record(record, record.send(changes_method), foreign_key, n, touch, belongs_to_touch_method)
115
115
  }}
116
116
 
117
- model.after_save callback.(:saved_changes), if: :saved_changes?
118
- model.after_touch callback.(:changes_to_save)
119
- model.after_destroy callback.(:changes_to_save)
117
+ unless reflection.counter_cache_column
118
+ model.after_create callback.(:saved_changes), if: :saved_changes?
119
+ model.after_destroy callback.(:changes_to_save)
120
+ end
121
+
122
+ model.after_update callback.(:saved_changes), if: :saved_changes?
123
+ model.after_touch callback.(:changes_to_save)
120
124
  end
121
125
 
122
126
  def self.add_default_callbacks(model, reflection)
@@ -52,11 +52,11 @@ module ActiveRecord
52
52
 
53
53
  # Implements the ids writer method, e.g. foo.item_ids= for Foo.has_many :items
54
54
  def ids_writer(ids)
55
- pk_type = reflection.association_primary_key_type
55
+ primary_key = reflection.association_primary_key
56
+ pk_type = klass.type_for_attribute(primary_key)
56
57
  ids = Array(ids).reject(&:blank?)
57
58
  ids.map! { |i| pk_type.cast(i) }
58
59
 
59
- primary_key = reflection.association_primary_key
60
60
  records = klass.where(primary_key => ids).index_by do |r|
61
61
  r.public_send(primary_key)
62
62
  end.values_at(*ids).compact
@@ -32,7 +32,7 @@ module ActiveRecord
32
32
  class CollectionProxy < Relation
33
33
  def initialize(klass, association) #:nodoc:
34
34
  @association = association
35
- super klass, klass.arel_table, klass.predicate_builder
35
+ super klass
36
36
 
37
37
  extensions = association.extensions
38
38
  extend(*extensions) if extensions.any?
@@ -63,7 +63,7 @@ module ActiveRecord
63
63
  count = if reflection.has_cached_counter?
64
64
  owner._read_attribute(reflection.counter_cache_column).to_i
65
65
  else
66
- scope.count
66
+ scope.count(:all)
67
67
  end
68
68
 
69
69
  # If there's nothing in the database and @target has no new records
@@ -8,9 +8,7 @@ module ActiveRecord
8
8
 
9
9
  def initialize(owner, reflection)
10
10
  super
11
-
12
- @through_records = {}
13
- @through_association = nil
11
+ @through_records = {}
14
12
  end
15
13
 
16
14
  def concat(*records)
@@ -50,11 +48,6 @@ module ActiveRecord
50
48
  end
51
49
 
52
50
  private
53
-
54
- def through_association
55
- @through_association ||= owner.association(through_reflection.name)
56
- end
57
-
58
51
  # The through record (built with build_record) is temporarily cached
59
52
  # so that it may be reused if insert_record is subsequently called.
60
53
  #
@@ -140,21 +133,15 @@ module ActiveRecord
140
133
 
141
134
  scope = through_association.scope
142
135
  scope.where! construct_join_attributes(*records)
136
+ scope = scope.where(through_scope_attributes)
143
137
 
144
138
  case method
145
139
  when :destroy
146
140
  if scope.klass.primary_key
147
- count = scope.destroy_all.length
141
+ count = scope.destroy_all.count(&:destroyed?)
148
142
  else
149
143
  scope.each(&:_run_destroy_callbacks)
150
-
151
- arel = scope.arel
152
-
153
- stmt = Arel::DeleteManager.new
154
- stmt.from scope.klass.arel_table
155
- stmt.wheres = arel.constraints
156
-
157
- count = scope.klass.connection.delete(stmt, "SQL")
144
+ count = scope.delete_all
158
145
  end
159
146
  when :nullify
160
147
  count = scope.update_all(source_reflection.foreign_key => nil)
@@ -6,17 +6,16 @@ module ActiveRecord
6
6
  class HasOneThroughAssociation < HasOneAssociation #:nodoc:
7
7
  include ThroughAssociation
8
8
 
9
- def replace(record)
10
- create_through_record(record)
9
+ def replace(record, save = true)
10
+ create_through_record(record, save)
11
11
  self.target = record
12
12
  end
13
13
 
14
14
  private
15
-
16
- def create_through_record(record)
15
+ def create_through_record(record, save)
17
16
  ensure_not_nested
18
17
 
19
- through_proxy = owner.association(through_reflection.name)
18
+ through_proxy = through_association
20
19
  through_record = through_proxy.load_target
21
20
 
22
21
  if through_record && !record
@@ -30,7 +29,7 @@ module ActiveRecord
30
29
 
31
30
  if through_record
32
31
  through_record.update(attributes)
33
- elsif owner.new_record?
32
+ elsif owner.new_record? || !save
34
33
  through_proxy.build(attributes)
35
34
  else
36
35
  through_proxy.create(attributes)
@@ -83,7 +83,7 @@ module ActiveRecord
83
83
  # { author: :avatar }
84
84
  # [ :books, { author: :avatar } ]
85
85
  def preload(records, associations, preload_scope = nil)
86
- records = records.compact
86
+ records = Array.wrap(records).compact
87
87
 
88
88
  if records.empty?
89
89
  []
@@ -82,11 +82,11 @@ module ActiveRecord
82
82
  end
83
83
 
84
84
  def association_key_type
85
- @klass.type_for_attribute(association_key_name.to_s).type
85
+ @klass.type_for_attribute(association_key_name).type
86
86
  end
87
87
 
88
88
  def owner_key_type
89
- @model.type_for_attribute(owner_key_name.to_s).type
89
+ @model.type_for_attribute(owner_key_name).type
90
90
  end
91
91
 
92
92
  def load_records(&block)
@@ -4,9 +4,24 @@ module ActiveRecord
4
4
  module Associations
5
5
  # = Active Record Through Association
6
6
  module ThroughAssociation #:nodoc:
7
- delegate :source_reflection, :through_reflection, to: :reflection
7
+ delegate :source_reflection, to: :reflection
8
8
 
9
9
  private
10
+ def through_reflection
11
+ @through_reflection ||= begin
12
+ refl = reflection.through_reflection
13
+
14
+ while refl.through_reflection?
15
+ refl = refl.through_reflection
16
+ end
17
+
18
+ refl
19
+ end
20
+ end
21
+
22
+ def through_association
23
+ @through_association ||= owner.association(through_reflection.name)
24
+ end
10
25
 
11
26
  # We merge in these scopes for two reasons:
12
27
  #
@@ -38,24 +53,22 @@ module ActiveRecord
38
53
  def construct_join_attributes(*records)
39
54
  ensure_mutable
40
55
 
41
- if source_reflection.association_primary_key(reflection.klass) == reflection.klass.primary_key
56
+ association_primary_key = source_reflection.association_primary_key(reflection.klass)
57
+
58
+ if association_primary_key == reflection.klass.primary_key && !options[:source_type]
42
59
  join_attributes = { source_reflection.name => records }
43
60
  else
44
61
  join_attributes = {
45
- source_reflection.foreign_key =>
46
- records.map { |record|
47
- record.send(source_reflection.association_primary_key(reflection.klass))
48
- }
62
+ source_reflection.foreign_key => records.map(&association_primary_key.to_sym)
49
63
  }
50
64
  end
51
65
 
52
66
  if options[:source_type]
53
- join_attributes[source_reflection.foreign_type] =
54
- records.map { |record| record.class.base_class.name }
67
+ join_attributes[source_reflection.foreign_type] = [ options[:source_type] ]
55
68
  end
56
69
 
57
70
  if records.count == 1
58
- Hash[join_attributes.map { |k, v| [k, v.first] }]
71
+ join_attributes.transform_values!(&:first)
59
72
  else
60
73
  join_attributes
61
74
  end
@@ -456,7 +456,7 @@ module ActiveRecord
456
456
  arel_table = self.class.arel_table
457
457
 
458
458
  attribute_names.each do |name|
459
- attrs[arel_table[name]] = typecasted_attribute_value(name)
459
+ attrs[arel_table[name]] = _read_attribute(name)
460
460
  end
461
461
  attrs
462
462
  end
@@ -483,9 +483,5 @@ module ActiveRecord
483
483
  def pk_attribute?(name)
484
484
  name == self.class.primary_key
485
485
  end
486
-
487
- def typecasted_attribute_value(name)
488
- _read_attribute(name)
489
- end
490
486
  end
491
487
  end
@@ -32,9 +32,7 @@ module ActiveRecord
32
32
  # <tt>reload</tt> the record and clears changed attributes.
33
33
  def reload(*)
34
34
  super.tap do
35
- @previously_changed = ActiveSupport::HashWithIndifferentAccess.new
36
35
  @mutations_before_last_save = nil
37
- @attributes_changed_by_setter = ActiveSupport::HashWithIndifferentAccess.new
38
36
  @mutations_from_database = nil
39
37
  end
40
38
  end
@@ -114,12 +112,12 @@ module ActiveRecord
114
112
 
115
113
  # Alias for +changed+
116
114
  def changed_attribute_names_to_save
117
- changes_to_save.keys
115
+ mutations_from_database.changed_attribute_names
118
116
  end
119
117
 
120
118
  # Alias for +changed_attributes+
121
119
  def attributes_in_database
122
- changes_to_save.transform_values(&:first)
120
+ mutations_from_database.changed_values
123
121
  end
124
122
 
125
123
  private
@@ -57,7 +57,7 @@ module ActiveRecord
57
57
  # store_listing = StoreListing.new(price_in_cents: '10.1')
58
58
  #
59
59
  # # before
60
- # store_listing.price_in_cents # => BigDecimal.new(10.1)
60
+ # store_listing.price_in_cents # => BigDecimal(10.1)
61
61
  #
62
62
  # class StoreListing < ActiveRecord::Base
63
63
  # attribute :price_in_cents, :integer
@@ -436,6 +436,9 @@ module ActiveRecord
436
436
  if (autosave && record.changed_for_autosave?) || new_record? || record_changed?(reflection, record, key)
437
437
  unless reflection.through_reflection
438
438
  record[reflection.foreign_key] = key
439
+ if inverse_reflection = reflection.inverse_of
440
+ record.association(inverse_reflection.name).loaded!
441
+ end
439
442
  end
440
443
 
441
444
  saved = record.save(validate: !autosave)
@@ -232,7 +232,7 @@ module ActiveRecord
232
232
  #
233
233
  # For example:
234
234
  #
235
- # class Topic
235
+ # class Topic < ActiveRecord::Base
236
236
  # has_many :children
237
237
  #
238
238
  # after_save :log_children
@@ -257,7 +257,7 @@ module ActiveRecord
257
257
  #
258
258
  # For example:
259
259
  #
260
- # class Topic
260
+ # class Topic < ActiveRecord::Base
261
261
  # has_many :children
262
262
  #
263
263
  # after_commit :log_children
@@ -3,11 +3,11 @@
3
3
  module ActiveRecord
4
4
  module CollectionCacheKey
5
5
  def collection_cache_key(collection = all, timestamp_column = :updated_at) # :nodoc:
6
- query_signature = Digest::MD5.hexdigest(collection.to_sql)
6
+ query_signature = ActiveSupport::Digest.hexdigest(collection.to_sql)
7
7
  key = "#{collection.model_name.cache_key}/query-#{query_signature}"
8
8
 
9
- if collection.loaded?
10
- size = collection.size
9
+ if collection.loaded? || collection.distinct_value
10
+ size = collection.records.size
11
11
  if size > 0
12
12
  timestamp = collection.max_by(&timestamp_column)._read_attribute(timestamp_column)
13
13
  end
@@ -15,13 +15,12 @@ module ActiveRecord
15
15
  if collection.eager_loading?
16
16
  collection = collection.send(:apply_join_dependency)
17
17
  end
18
- column_type = type_for_attribute(timestamp_column.to_s)
18
+ column_type = type_for_attribute(timestamp_column)
19
19
  column = connection.column_name_from_arel_node(collection.arel_attribute(timestamp_column))
20
20
  select_values = "COUNT(*) AS #{connection.quote_column_name("size")}, MAX(%s) AS timestamp"
21
21
 
22
22
  if collection.has_limit_or_offset?
23
- query = collection.spawn
24
- query.select_values = [column]
23
+ query = collection.select(column)
25
24
  subquery_alias = "subquery_for_cache_key"
26
25
  subquery_column = "#{subquery_alias}.#{timestamp_column}"
27
26
  subquery = query.arel.as(subquery_alias)
@@ -1005,9 +1005,7 @@ module ActiveRecord
1005
1005
  def retrieve_connection(spec_name) #:nodoc:
1006
1006
  pool = retrieve_connection_pool(spec_name)
1007
1007
  raise ConnectionNotEstablished, "No connection pool with '#{spec_name}' found." unless pool
1008
- conn = pool.connection
1009
- raise ConnectionNotEstablished, "No connection for '#{spec_name}' in connection pool" unless conn
1010
- conn
1008
+ pool.connection
1011
1009
  end
1012
1010
 
1013
1011
  # Returns true if a connection that's accessible to this class has
@@ -356,35 +356,33 @@ module ActiveRecord
356
356
  # Inserts a set of fixtures into the table. Overridden in adapters that require
357
357
  # something beyond a simple insert (eg. Oracle).
358
358
  def insert_fixtures(fixtures, table_name)
359
+ ActiveSupport::Deprecation.warn(<<-MSG.squish)
360
+ `insert_fixtures` is deprecated and will be removed in the next version of Rails.
361
+ Consider using `insert_fixtures_set` for performance improvement.
362
+ MSG
359
363
  return if fixtures.empty?
360
364
 
361
- columns = schema_cache.columns_hash(table_name)
365
+ execute(build_fixture_sql(fixtures, table_name), "Fixtures Insert")
366
+ end
362
367
 
363
- values = fixtures.map do |fixture|
364
- fixture = fixture.stringify_keys
368
+ def insert_fixtures_set(fixture_set, tables_to_delete = [])
369
+ fixture_inserts = fixture_set.map do |table_name, fixtures|
370
+ next if fixtures.empty?
365
371
 
366
- unknown_columns = fixture.keys - columns.keys
367
- if unknown_columns.any?
368
- raise Fixture::FixtureError, %(table "#{table_name}" has no columns named #{unknown_columns.map(&:inspect).join(', ')}.)
369
- end
372
+ build_fixture_sql(fixtures, table_name)
373
+ end.compact
370
374
 
371
- columns.map do |name, column|
372
- if fixture.key?(name)
373
- type = lookup_cast_type_from_column(column)
374
- bind = Relation::QueryAttribute.new(name, fixture[name], type)
375
- with_yaml_fallback(bind.value_for_database)
376
- else
377
- Arel.sql("DEFAULT")
375
+ table_deletes = tables_to_delete.map { |table| "DELETE FROM #{quote_table_name table}".dup }
376
+ total_sql = Array.wrap(combine_multi_statements(table_deletes + fixture_inserts))
377
+
378
+ disable_referential_integrity do
379
+ transaction(requires_new: true) do
380
+ total_sql.each do |sql|
381
+ execute sql, "Fixtures Load"
382
+ yield if block_given?
378
383
  end
379
384
  end
380
385
  end
381
-
382
- table = Arel::Table.new(table_name)
383
- manager = Arel::InsertManager.new
384
- manager.into(table)
385
- columns.each_key { |column| manager.columns << table[column] }
386
- manager.values = manager.create_values_list(values)
387
- execute manager.to_sql, "Fixtures Insert"
388
386
  end
389
387
 
390
388
  def empty_insert_statement_value
@@ -416,6 +414,44 @@ module ActiveRecord
416
414
  alias join_to_delete join_to_update
417
415
 
418
416
  private
417
+ def default_insert_value(column)
418
+ Arel.sql("DEFAULT")
419
+ end
420
+
421
+ def build_fixture_sql(fixtures, table_name)
422
+ columns = schema_cache.columns_hash(table_name)
423
+
424
+ values = fixtures.map do |fixture|
425
+ fixture = fixture.stringify_keys
426
+
427
+ unknown_columns = fixture.keys - columns.keys
428
+ if unknown_columns.any?
429
+ raise Fixture::FixtureError, %(table "#{table_name}" has no columns named #{unknown_columns.map(&:inspect).join(', ')}.)
430
+ end
431
+
432
+ columns.map do |name, column|
433
+ if fixture.key?(name)
434
+ type = lookup_cast_type_from_column(column)
435
+ bind = Relation::QueryAttribute.new(name, fixture[name], type)
436
+ with_yaml_fallback(bind.value_for_database)
437
+ else
438
+ default_insert_value(column)
439
+ end
440
+ end
441
+ end
442
+
443
+ table = Arel::Table.new(table_name)
444
+ manager = Arel::InsertManager.new
445
+ manager.into(table)
446
+ columns.each_key { |column| manager.columns << table[column] }
447
+ manager.values = manager.create_values_list(values)
448
+
449
+ manager.to_sql
450
+ end
451
+
452
+ def combine_multi_statements(total_sql)
453
+ total_sql.join(";\n")
454
+ end
419
455
 
420
456
  # Returns a subquery for the given key using the join information.
421
457
  def subquery_for(key, select)