class RqlParser::Services::Parse

Service that performs the parse operation

Constants

AND_STRICT_DELIMITERS
BRACES_REGEX
COMMA_DELIMITER
DELIMITERS
FUNCTION_ARGS
FUNCTION_IDENTIFIER
FUNCTION_REGEX
OR_DELIMITERS
VALUE_REGEX

Public Instance Methods

execute() click to toggle source
# File lib/rql_parser/services/parse.rb, line 17
def execute
  formatted = perform(Format.run(inputs))
  expression(formatted) || errors.add(:rql) unless errors.any?
end

Private Instance Methods

and_expression(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 41
def and_expression(str)
  result = repeat_pattern(str, COMMA_DELIMITER) { |s| function(s) || group(s) || and_strict(s) }
  return false unless result

  result.size > 1 ? { type: :function, identifier: :and, args: result } : result.first
end
and_strict(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 48
def and_strict(str)
  result = repeat_pattern(str, AND_STRICT_DELIMITERS) { |s| function(s) || group(s) }
  return false unless result

  result.size > 1 ? { type: :function, identifier: :and, args: result } : result.first
end
arg(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 70
def arg(str)
  expression(str) || array_of_values(str) || value(str)
end
args(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 66
def args(str)
  repeat_pattern(str, COMMA_DELIMITER) { |s| arg(s) }
end
array_of_values(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 74
def array_of_values(str)
  return false unless BRACES_REGEX.match?(str)

  result = repeat_pattern(str[1..-2], COMMA_DELIMITER) { |s| value(s) }
  return false unless result

  { arg_array: result }
end
compose_char(regex) click to toggle source
# File lib/rql_parser/services/parse.rb, line 108
def compose_char(regex)
  DELIMITERS.match(regex)[0]
end
expression(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 24
def expression(str)
  group(str) || or_expression(str)
end
function(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 55
def function(str)
  return false unless FUNCTION_REGEX.match?(str)

  identifier = str.match(FUNCTION_IDENTIFIER)[1]
  args = args(str.match(FUNCTION_ARGS)[1])

  return false unless args

  { type: :function, identifier: identifier.to_sym, args: args }
end
group(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 28
def group(str)
  return false unless BRACES_REGEX.match?(str)

  or_expression(str[1..-2]) || false
end
or_expression(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 34
def or_expression(str)
  result = repeat_pattern(str, OR_DELIMITERS) { |s| and_expression(s) }
  return false unless result

  result.size > 1 ? { type: :function, identifier: :or, args: result } : result.first
end
repeat_pattern(str, split_regex) { |expression| ... } click to toggle source
# File lib/rql_parser/services/parse.rb, line 91
def repeat_pattern(str, split_regex)
  split = str.split(split_regex)
  result = []
  expression = ''
  while split.any?
    expression += split.shift
    bin_tree = yield(expression)
    if bin_tree
      result.push(bin_tree)
      expression = ''
    else
      expression += compose_char(split_regex)
    end
  end
  expression.blank? && result
end
value(str) click to toggle source
# File lib/rql_parser/services/parse.rb, line 83
def value(str)
  if str.match?(VALUE_REGEX)
    { arg: str }
  else
    false
  end
end