require "../util.cr" require "./among_us.cr" struct AmongUs::Parser def initialize(code_io : IO) @raw_code = code_io.gets_to_end code_io.close end def parse : Array(Instruction) tokens = @raw_code.split instructions = [] of Instruction color_seen = false sus_safe = false tokens.each do |token| case token.upcase when "WHO?" instructions << Command::WHO when "WHERE?" instructions << Command::WHERE else i = parse_instruction(token) if i.nil? raise Util::ParserError.new("Failed to parse command/color '#{token}'") end instructions << i end color_seen = true if instructions[-1].is_a?(Color) if instructions[-1] == Command::SUS && !sus_safe unless color_seen raise Util::ParserError.new("Provided program uses SUS command, but no colors are provided before first SUS") end sus_safe = true end end return instructions end private def parse_instruction(str : String) : Instruction? i = Command.parse?(str) return i unless i.nil? Color.parse?(str) end end