module ActiveScaffold::Actions::BatchUpdate

Constants

DateOperators
GenericOperators
NumericOperators
NumericOptions

Public Class Methods

included(base) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 24
def self.included(base)
  base.before_filter :batch_update_authorized_filter, :only => [:batch_edit, :batch_update]
  base.helper_method :batch_update_values
  base.helper_method :batch_update_columns
end

Public Instance Methods

batch_edit() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 30
def batch_edit
  do_batch_edit
  respond_to_action(:batch_edit)
end
batch_update() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 35
def batch_update
  batch_action
end

Protected Instance Methods

batch_edit_formats() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 318
def batch_edit_formats
  (default_formats + active_scaffold_config.formats).uniq
end
batch_edit_respond_to_html() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 41
def batch_edit_respond_to_html
  if batch_successful?
    render(:action => 'batch_update')
  else
    return_to_main
  end
end
batch_edit_respond_to_js() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 49
def batch_edit_respond_to_js
  render(:partial => 'batch_update_form')
end
batch_update_all_value_for_decimal(column, calculation_info)
batch_update_all_value_for_float(column, calculation_info)
batch_update_all_value_for_integer(column, calculation_info)
batch_update_all_value_for_numeric(column, calculation_info) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 248
def batch_update_all_value_for_numeric(column, calculation_info)
  if ActiveScaffold::Actions::BatchUpdate::GenericOperators.include?(calculation_info[:operator]) || ActiveScaffold::Actions::BatchUpdate::NumericOperators.include?(calculation_info[:operator])
    operand =  active_scaffold_config.model.quote_value(self.class.condition_value_for_numeric(column, calculation_info[:value]))
    if calculation_info[:opt] == 'PERCENT'#
      operand = "#{active_scaffold_config.model.connection.quote_column_name(column.name)} / 100.0 * #{operand}"
    end
    case calculation_info[:operator]
    when 'REPLACE' then operand
    when 'NULL' then active_scaffold_config.model.quote_value(nil)
    when 'PLUS' then "#{active_scaffold_config.model.connection.quote_column_name(column.name)} + #{operand}"
    when 'MINUS' then "#{active_scaffold_config.model.connection.quote_column_name(column.name)} - #{operand}"
    when 'TIMES' then "#{active_scaffold_config.model.connection.quote_column_name(column.name)} * #{operand}"
    when 'DIVISION' then "#{active_scaffold_config.model.connection.quote_column_name(column.name)} / #{operand}"
    else
      nil
    end
  else
    nil
  end
end
batch_update_attribute_values_from_params(columns, attributes) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 205
def batch_update_attribute_values_from_params(columns, attributes)
  values = {}
  attributes = {} unless attributes.is_a?(Hash)
  columns.each :for => new_model, :crud_type => :update, :flatten => true do |column|
    values[column.name] = {:column => column, :value => attributes[column.name].merge(:value => column_value_from_param_value(nil, column, attributes[column.name][:value]))} if selected_columns.include? column.name
  end
  values
end
batch_update_authorized?(record = nil) click to toggle source

The default security delegates to ActiveRecordPermissions. You may override the method to customize.

# File lib/active_scaffold/actions/batch_update.rb, line 217
def batch_update_authorized?(record = nil)
  authorized_for?(:crud_type => :update)
end
batch_update_authorized_filter() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 313
def batch_update_authorized_filter
  link = active_scaffold_config.batch_update.link || active_scaffold_config.batch_update.class.link
  raise ActiveScaffold::ActionNotAllowed unless self.send(link.security_method)
end
batch_update_columns() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 322
def batch_update_columns
  active_scaffold_config.batch_update.columns
end
batch_update_columns_names() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 326
def batch_update_columns_names
  batch_update_columns.collect(&:name)
end
batch_update_ignore?(record = nil) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 221
def batch_update_ignore?(record = nil)
  false
end
batch_update_listed() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 110
def batch_update_listed
  case active_scaffold_config.batch_update.process_mode
  when :update then
    each_record_in_scope {|record| update_record(record) if authorized_for_job?(record)}
  when :update_all then
    updates = updates_for_update_all
    unless updates.first.empty?
      do_search if respond_to? :do_search, true
      # all_conditions might fail cause joins are not working in update_all
      active_scaffold_config.model.update_all(updates, all_conditions)
    end
  else
    Rails.logger.error("Unknown process_mode: #{active_scaffold_config.batch_update.process_mode} for action batch_update")
  end
  
end
batch_update_marked() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 127
def batch_update_marked
  case active_scaffold_config.batch_update.process_mode
  when :update then
    active_scaffold_config.model.marked.each {|record| update_record(record) if authorized_for_job?(record)}
  when :update_all then
    updates = updates_for_update_all
    unless updates.first.empty?
      active_scaffold_config.model.marked.update_all(updates)
      do_demark_all
    end
  else
    Rails.logger.error("Unknown process_mode: #{active_scaffold_config.batch_update.process_mode} for action batch_update")
  end
end
batch_update_respond_to_html() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 70
def batch_update_respond_to_html
  if params[:iframe]=='true' # was this an iframe post ?
    responds_to_parent do
      render :action => 'on_batch_update.js', :layout => false
    end
  else # just a regular post
    if batch_successful?
      flash[:info] = as_(:updated_model, :model => @record.to_label)
      return_to_main
    else
      render(:action => 'batch_update')
    end
  end
end
batch_update_respond_to_js() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 85
def batch_update_respond_to_js
  render :action => 'on_batch_update'
end
batch_update_set_record_attribute(column, attribute, value) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 171
def batch_update_set_record_attribute(column, attribute, value)
  form_ui = colunm_form_ui(column)
  if form_ui && override_batch_update_value?(form_ui)
    @record.send("#{attribute}=", send(override_batch_update_value(form_ui), column, @record, value))
  else
    @record.send("#{attribute}=", value[:operator] == 'NULL' ? nil : value[:value])
  end
end
batch_update_value_for_calendar_date_select(column, record, calculation_info)
batch_update_value_for_date_picker(column, record, calculation_info) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 272
def batch_update_value_for_date_picker(column, record, calculation_info)
  current_value = record.send(column.name)
  {"number"=>"", "unit"=>"DAYS", "value"=>"November 16, 2010", "operator"=>"REPLACE"}
  if ActiveScaffold::Actions::BatchUpdate::GenericOperators.include?(calculation_info[:operator]) || ActiveScaffold::Actions::BatchUpdate::DateOperators.include?(calculation_info[:operator])
    operand = self.class.condition_value_for_datetime(calculation_info[:value], column.column.type == :date ? :to_date : :to_time)
    case calculation_info[:operator]
    when 'REPLACE' then operand
    when 'NULL' then nil
    when 'PLUS' then
      trend_number = [calculation_info['number'].to_i,  1].max
      current_value.in((trend_number).send(calculation_info['unit'].downcase.singularize.to_sym))
    when 'MINUS' then
      trend_number = [calculation_info['number'].to_i,  1].max
      current_value.ago((trend_number).send(calculation_info['unit'].downcase.singularize.to_sym))
    else
      current_value
    end
  else
    current_value
  end
end
batch_update_value_for_decimal(column, record, calculation_info)
batch_update_value_for_float(column, record, calculation_info)
batch_update_value_for_integer(column, record, calculation_info)
batch_update_value_for_numeric(column, record, calculation_info) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 225
def batch_update_value_for_numeric(column, record, calculation_info)
  current_value = record.send(column.name)
  if ActiveScaffold::Actions::BatchUpdate::GenericOperators.include?(calculation_info[:operator]) || ActiveScaffold::Actions::BatchUpdate::NumericOperators.include?(calculation_info[:operator])
    operand = self.class.condition_value_for_numeric(column, calculation_info[:value])
    operand = current_value / 100 * operand  if calculation_info[:opt] == 'PERCENT'
    case calculation_info[:operator]
    when 'REPLACE' then operand
    when 'NULL' then nil
    when 'PLUS' then current_value.present? ? current_value + operand : nil
    when 'MINUS' then current_value.present? ? current_value - operand : nil
    when 'TIMES' then current_value.present? ? current_value * operand : nil
    when 'DIVISION' then current_value.present? ? current_value / operand : nil
    else
      current_value
    end
  else
    current_value
  end
end
batch_update_values() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 66
def batch_update_values
  @batch_update_values || {}
end
before_do_batch_update() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 94
def before_do_batch_update
  update_columns = active_scaffold_config.batch_update.columns
  @batch_update_values = batch_update_attribute_values_from_params(update_columns, params[:record])
end
colunm_form_ui(column) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 180
def colunm_form_ui(column)
  form_ui = column.form_ui
  form_ui = column.column.type if form_ui.nil? && column.column
end
do_batch_edit() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 89
def do_batch_edit
  self.successful = true
  do_new
end
get_update_all_attribute(column, attribute, value) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 185
def get_update_all_attribute(column, attribute, value)
  form_ui = column.form_ui
  form_ui = column.column.type if form_ui.nil? && column.column
  
  if form_ui && override_batch_update_all_value?(form_ui)
    update_value =  send(override_batch_update_all_value(form_ui), column, value)
    if update_value.nil?
      sql_set = nil
    else
      sql_set = "#{attribute} = #{update_value}"
      update_value = nil
    end
  else
    sql_set = "#{attribute} = ?"
    update_value = value[:operator] == 'NULL' ? nil : value[:value]
  end
  
  return sql_set, update_value
end
override_batch_update_all_value(form_ui) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 309
def override_batch_update_all_value(form_ui)
  "batch_update_all_value_for_#{form_ui}"
end
override_batch_update_all_value?(form_ui) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 305
def override_batch_update_all_value?(form_ui)
  respond_to?(override_batch_update_all_value(form_ui), true)
end
override_batch_update_value(form_ui) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 301
def override_batch_update_value(form_ui)
  "batch_update_value_for_#{form_ui}"
end
override_batch_update_value?(form_ui) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 297
def override_batch_update_value?(form_ui)
  respond_to?(override_batch_update_value(form_ui), true)
end
prepare_error_record() click to toggle source

in case of an error we have to prepare @record object to have assigned all defined batch_update values, however, do not set those ones with an override these ones will manage on their own

# File lib/active_scaffold/actions/batch_update.rb, line 102
def prepare_error_record
  do_new
  batch_update_values.each do |attribute, value|
    form_ui = colunm_form_ui(value[:column])
    batch_update_set_record_attribute(value[:column], attribute, value[:value]) unless form_ui && override_batch_update_value?(form_ui)
  end
end
selected_columns() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 53
def selected_columns
  if @selected_columns.nil?
    @selected_columns = []
    if params[:record] && params[:record].is_a?(Hash)
      params[:record].each do |key, value|
        @selected_columns << key.to_sym if value[:operator] != 'NO_UPDATE'
      end
    end
  end
  @selected_columns
end
update_record(record) click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 155
def update_record(record)
  @successful = nil
  @record = record

  batch_update_values.each do |attribute, value|
    batch_update_set_record_attribute(value[:column], attribute, value[:value])
  end
  
  update_save({:no_record_param_update => true})
  if successful?
    @record.marked = false if batch_scope == 'MARKED'
  else
    error_records << @record
  end
end
updates_for_update_all() click to toggle source
# File lib/active_scaffold/actions/batch_update.rb, line 142
def updates_for_update_all()
  update_all = [[]]
  batch_update_values.each do |attribute, value|
    sql_set, value = get_update_all_attribute(value[:column], attribute, value[:value])
    unless sql_set.nil?
      update_all.first << sql_set
      update_all << value if sql_set.include?('?')
    end
  end
  update_all[0] = update_all.first.join(',')
  update_all
end