Sha256: f6123d1e45fdd723c41978fc47fd718f7eeca93e1f0cb94dc87ca662d9702515
Contents?: true
Size: 1.74 KB
Versions: 1
Compression:
Stored size: 1.74 KB
Contents
# frozen_string_literal: true require 'activerecord-import' require 'rails_or' require 'atomically/patches/none' if not ActiveRecord::Base.respond_to?(:none) require 'atomically/patches/from' if Gem::Version.new(ActiveRecord::VERSION::STRING) < Gem::Version.new('4.0.0') class Atomically::QueryService def initialize(klass, relation: nil) @klass = klass @relation = relation || @klass end def create_or_plus(columns, data, update_columns) @klass.import(columns, data, on_duplicate_key_update: on_duplicate_key_plus_sql(update_columns)) end def pay_all(hash, update_columns, primary_key: :id) # { id => pay_count } return 0 if hash.blank? update_columns = update_columns.map(&method(:quote_column)) query = hash.inject(@klass.none) do |relation, (id, pay_count)| condition = @relation.where(primary_key => id) update_columns.each{|s| condition = condition.where("#{s} >= ?", pay_count) } next relation.or(condition) end raw_when_sql = hash.map{|id, pay_count| "WHEN #{sanitize(id)} THEN #{sanitize(-pay_count)}" }.join("\n") update_sqls = update_columns.map.with_index do |column, idx| value = idx == 0 ? "(@change := \nCASE #{quote_column(primary_key)}\n#{raw_when_sql}\nEND)" : '@change' next "#{column} = #{column} + #{value}" end return query.where("(#{@klass.from(query).select('COUNT(*)').to_sql}) = ?", hash.size) .update_all(update_sqls.join(', ')) end private def on_duplicate_key_plus_sql( columns) columns.lazy.map(&method(:quote_column)).map{|s| "#{s} = #{s} + VALUES(#{s})" }.force.join(', ') end def quote_column(column) @klass.connection.quote_column_name(column) end def sanitize(value) @klass.connection.quote(value) end end
Version data entries
1 entries across 1 versions & 1 rubygems
Version | Path |
---|---|
atomically-1.0.1 | lib/atomically/query_service.rb |