Class: ActiveRecord::InsertAll

Inherits:
Object
  • Object
show all
Defined in:
lib/active_record/insert_all.rb

Overview

:nodoc:

Defined Under Namespace

Classes: Builder

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(relation, connection, inserts, on_duplicate:, update_only: nil, returning: nil, unique_by: nil, record_timestamps: nil) ⇒ InsertAll

Returns a new instance of InsertAll.



18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
# File 'lib/active_record/insert_all.rb', line 18

def initialize(relation, connection, inserts, on_duplicate:, update_only: nil, returning: nil, unique_by: nil, record_timestamps: nil)
  @relation = relation
  @model, @connection, @inserts = relation.model, connection, inserts.map(&:stringify_keys)
  @on_duplicate, @update_only, @returning, @unique_by = on_duplicate, update_only, returning, unique_by
  @record_timestamps = record_timestamps.nil? ? model.record_timestamps : record_timestamps

  disallow_raw_sql!(on_duplicate)
  disallow_raw_sql!(returning)

  if @inserts.empty?
    @keys = []
  else
    resolve_sti
    resolve_attribute_aliases
    @keys = @inserts.first.keys
  end

  @scope_attributes = relation.scope_for_create.except(@model.inheritance_column)
  @keys |= @scope_attributes.keys
  @keys = @keys.to_set

  @returning = (connection.supports_insert_returning? ? primary_keys : false) if @returning.nil?
  @returning = false if @returning == []

  @unique_by = find_unique_index_for(@unique_by)

  configure_on_duplicate_update_logic
  ensure_valid_options_for_connection!
end

Instance Attribute Details

#connectionObject (readonly)

Returns the value of attribute connection.



7
8
9
# File 'lib/active_record/insert_all.rb', line 7

def connection
  @connection
end

#insertsObject (readonly)

Returns the value of attribute inserts.



7
8
9
# File 'lib/active_record/insert_all.rb', line 7

def inserts
  @inserts
end

#keysObject (readonly)

Returns the value of attribute keys.



7
8
9
# File 'lib/active_record/insert_all.rb', line 7

def keys
  @keys
end

#modelObject (readonly)

Returns the value of attribute model.



7
8
9
# File 'lib/active_record/insert_all.rb', line 7

def model
  @model
end

#on_duplicateObject (readonly)

Returns the value of attribute on_duplicate.



8
9
10
# File 'lib/active_record/insert_all.rb', line 8

def on_duplicate
  @on_duplicate
end

#returningObject (readonly)

Returns the value of attribute returning.



8
9
10
# File 'lib/active_record/insert_all.rb', line 8

def returning
  @returning
end

#unique_byObject (readonly)

Returns the value of attribute unique_by.



8
9
10
# File 'lib/active_record/insert_all.rb', line 8

def unique_by
  @unique_by
end

#update_onlyObject (readonly)

Returns the value of attribute update_only.



8
9
10
# File 'lib/active_record/insert_all.rb', line 8

def update_only
  @update_only
end

#update_sqlObject (readonly)

Returns the value of attribute update_sql.



8
9
10
# File 'lib/active_record/insert_all.rb', line 8

def update_sql
  @update_sql
end

Class Method Details

.execute(relation) ⇒ Object



11
12
13
14
15
# File 'lib/active_record/insert_all.rb', line 11

def execute(relation, ...)
  relation.model.with_connection do |c|
    new(relation, c, ...).execute
  end
end

Instance Method Details

#executeObject



48
49
50
51
52
53
54
55
# File 'lib/active_record/insert_all.rb', line 48

def execute
  return ActiveRecord::Result.empty if inserts.empty?

  message = +"#{model} "
  message << "Bulk " if inserts.many?
  message << (on_duplicate == :update ? "Upsert" : "Insert")
  connection.exec_insert_all to_sql, message
end

#keys_including_timestampsObject

TODO: Consider renaming this method, as it only conditionally extends keys, not always



92
93
94
95
96
97
98
# File 'lib/active_record/insert_all.rb', line 92

def keys_including_timestamps
  @keys_including_timestamps ||= if record_timestamps?
    keys + model.all_timestamp_attributes_in_model
  else
    keys
  end
end

#map_key_with_valueObject



73
74
75
76
77
78
79
80
81
82
83
84
85
# File 'lib/active_record/insert_all.rb', line 73

def map_key_with_value
  inserts.map do |attributes|
    attributes = attributes.stringify_keys
    attributes.merge!(@scope_attributes)
    attributes.reverse_merge!(timestamps_for_create) if record_timestamps?

    verify_attributes(attributes)

    keys_including_timestamps.map do |key|
      yield key, attributes[key]
    end
  end
end

#primary_keysObject



61
62
63
# File 'lib/active_record/insert_all.rb', line 61

def primary_keys
  Array(@model.schema_cache.primary_keys(model.table_name))
end

#record_timestamps?Boolean

Returns:

  • (Boolean)


87
88
89
# File 'lib/active_record/insert_all.rb', line 87

def record_timestamps?
  @record_timestamps
end

#skip_duplicates?Boolean

Returns:

  • (Boolean)


65
66
67
# File 'lib/active_record/insert_all.rb', line 65

def skip_duplicates?
  on_duplicate == :skip
end

#updatable_columnsObject



57
58
59
# File 'lib/active_record/insert_all.rb', line 57

def updatable_columns
  @updatable_columns ||= keys - readonly_columns - unique_by_columns
end

#update_duplicates?Boolean

Returns:

  • (Boolean)


69
70
71
# File 'lib/active_record/insert_all.rb', line 69

def update_duplicates?
  on_duplicate == :update
end