class Dentaku::AST::Comparator

def self.precedence

def self.precedence
  5
end

def cast(val)

def cast(val)
  return val unless val.is_a?(::String)
  return val unless val.match?(Arithmetic::DECIMAL) || val.match?(Arithmetic::INTEGER)
  v = BigDecimal(val, Float::DIG + 1)
  v = v.to_i if v.frac.zero?
  v
end

def operator

def operator
  raise NotImplementedError
end

def type

def type
  :logical
end

def validate_value(value)

def validate_value(value)
  unless value.respond_to?(operator)
    raise Dentaku::ArgumentError.for(:invalid_operator, operation: self.class, operator: operator),
          "#{ self.class } requires operands that respond to #{operator}"
  end
  value
end

def value(context = {})

def value(context = {})
  l = validate_value(cast(left.value(context)))
  r = validate_value(cast(right.value(context)))
  l.public_send(operator, r)
rescue ::ArgumentError => e
  raise Dentaku::ArgumentError.for(:incompatible_type, value: r, for: l.class), e.message
end