class QueryHelper::Filter

Attributes

aggregate[RW]
bind_variable[RW]
comparate[RW]
criterion[RW]
operator[RW]
operator_code[RW]

Public Class Methods

new( operator_code:, criterion:, comparate:, aggregate: false ) click to toggle source
# File lib/query_helper/filter.rb, line 8
def initialize(
  operator_code:,
  criterion:,
  comparate:,
  aggregate: false
)
  @operator_code = operator_code
  @criterion = criterion # Converts to a string to be inserted into sql.
  @comparate = comparate
  @aggregate = aggregate
  @bind_variable = ('a'..'z').to_a.shuffle[0,20].join.to_sym

  translate_operator_code()
  mofify_criterion()
  modify_comparate()
  validate_criterion()
end

Public Instance Methods

sql_string() click to toggle source
# File lib/query_helper/filter.rb, line 26
def sql_string
  case operator_code
  when "in", "notin"
    "#{comparate} #{operator} (:#{bind_variable})"
  when "null"
    "#{comparate} #{operator}"
  else
    "#{comparate} #{operator} :#{bind_variable}"
  end

end

Private Instance Methods

invalid_criterion_error() click to toggle source
# File lib/query_helper/filter.rb, line 117
def invalid_criterion_error
  raise InvalidQueryError.new("'#{criterion}' is not a valid criterion for the '#{@operator}' operator")
end
modify_comparate() click to toggle source
# File lib/query_helper/filter.rb, line 82
def modify_comparate
  # lowercase strings for comparison
  if (criterion.class == String && 
      criterion.scan(/[a-zA-Z]/).any? && 
      !["true", "false"].include?(criterion)) ||
      (criterion.class == Array && 
      criterion.to_s.scan(/[a-zA-Z]/).any?)
    @comparate = "lower(#{@comparate})" 
  end 
end
mofify_criterion() click to toggle source
# File lib/query_helper/filter.rb, line 71
def mofify_criterion
  # lowercase strings for comparison
  @criterion.downcase! if @criterion.class == String && @criterion.scan(/[a-zA-Z]/).any?

  # turn the criterion into an array for in and notin comparisons
  @criterion = @criterion.split(",") if ["in", "notin"].include?(@operator_code) && @criterion.class == String

  # Add wildcards for like comparisons
  @criterion = "%#{@criterion}%" if @operator_code == "like"
end
translate_operator_code() click to toggle source
# File lib/query_helper/filter.rb, line 40
def translate_operator_code
  @operator = case operator_code
    when "gte"
      ">="
    when "lte"
      "<="
    when "gt"
      ">"
    when "lt"
      "<"
    when "eql"
      "="
    when "noteql"
      "!="
    when "in"
      "in"
    when "like"
      "like"
    when "notin"
      "not in"
    when "null"
      if criterion.to_s == "true"
        "is null"
      else
        "is not null"
      end
    else
      raise InvalidQueryError.new("Invalid operator code: '#{operator_code}'")
  end
end
validate_criterion() click to toggle source
# File lib/query_helper/filter.rb, line 93
def validate_criterion
  case operator_code
    when "gte", "lte", "gt", "lt"
      begin
        Time.parse(criterion.to_s)
      rescue
        begin
          Date.parse(criterion.to_s)
        rescue
          begin
            Float(criterion.to_s)
          rescue
            invalid_criterion_error()
          end
        end
      end
    when "in", "notin"
      invalid_criterion_error() unless criterion.class == Array
    when "null"
      invalid_criterion_error() unless ["true", "false"].include?(criterion.to_s)
  end
  true
end