Module: ActiveRecord::Refined::Writes

Defined in:
lib/active_record/refined.rb

Overview

The writing statements, which live on Relation rather than in QueryMethods. What a block adds here is the one thing their arguments cannot carry: a value worked out from the row rather than given.

Instance Method Summary collapse

Instance Method Details

#update_all(updates = nil, &block) ⇒ Object

update_all(likes: :likes) sets the column to the symbol; the block reads a symbol as the column it names, as every other block here does, which is what lets the new value be built from the old:

Post.where { ... }.update_all { { likes: :likes + 1 } }


571
572
573
574
575
576
577
578
579
580
581
# File 'lib/active_record/refined.rb', line 571

def update_all(updates = nil, &block)
  return super(updates) unless block
  if updates
    raise ArgumentError, "update_all takes updates or a block, not both"
  end
  result = evaluate_block(&block)
  unless result.is_a?(::Hash)
    raise ArgumentError, "the block gives update_all a hash of column => value"
  end
  super(result.transform_values {|value| to_arel_field(value) })
end

#upsert_all(attributes, **options, &block) ⇒ Object

upsert_all's on_duplicate takes SQL text and nothing else, so this is the one place the DSL writes the SQL out itself rather than handing Arel a tree. excluded is the row that could not be inserted:

Post.upsert_all(rows, unique_by: :title) {
{ likes: :likes + excluded(:likes) }
}


590
591
592
593
594
595
596
597
598
599
600
601
602
603
# File 'lib/active_record/refined.rb', line 590

def upsert_all(attributes, **options, &block)
  return super(attributes, **options) unless block
  if options.key?(:on_duplicate)
    raise ArgumentError, "upsert_all takes on_duplicate: or a block, not both"
  end
  result = evaluate_block(&block)
  unless result.is_a?(::Hash)
    raise ArgumentError, "the block gives upsert_all a hash of column => value"
  end
  if result.empty?
    raise ArgumentError, "the block gives upsert_all at least one column to set"
  end
  super(attributes, on_duplicate: Arel.sql(set_clause(result)), **options)
end