#!/usr/bin/env ruby

require 'jgrep'
require 'optparse'

options = {:flat => false, :start => nil, :field => []}

begin
    OptionParser.new do |opts|
        opts.banner = "Usage: jgrep [options] \"expression\""
        opts.on("-s", "--simple [FIELDS]", "Display only one or more fields from each of the resulting json documents") do |field|
            options[:field].concat(field.split(" "))
        end

        opts.on("-c", "--compact", "Display non pretty json") do
            options[:flat] = true
        end

        opts.on("-f", "--flatten", "Makes output as flat as possible") do
            JGrep::flatten_on
        end

        opts.on("-i", "--input [FILENAME]", "Specify input file to parse") do |filename|
            options[:file] = filename
        end

        opts.on("-q", "--quiet", "Quiet; don't write to stdout.  Exit with zero status if match found.") do
            options[:quiet] = true
        end

        opts.on("-v", "--verbose", "Verbose output") do
            JGrep::verbose_on
        end

        opts.on("--start [FIELD]", "Where in the data to start from") do |field|
            options[:start] = field
        end
    end.parse!
rescue OptionParser::InvalidOption => e
    puts e.to_s.capitalize
    exit 1
end

begin
    expression = nil

    #Identify the expression from command line arguments
    ARGV.each do |argument|
        if argument =~ /<|>|=|\+|-/
            expression = argument
            ARGV.delete(argument)
        end
    end

    expression = "" if expression.nil?

    #Load json from standard input if tty is false
    #else find and load file from command line arugments
    unless STDIN.tty?
        json = STDIN.read
    else
        if options[:file]
            json = File.read(options[:file])
        else
            raise "No json input specified"
        end
    end

    if options[:field].empty?
        result = JGrep::jgrep((json), expression, nil, options[:start])
        unless options[:quiet] == true
            (options[:flat] == false) ? puts(JSON.pretty_generate(result)) : puts(result.to_json)
        end
    else
        if options[:field].size > 1
            JGrep::validate_filters(options[:field])
            result = JGrep::jgrep((json), expression, options[:field], options[:start])
            unless result == [] or options[:quiet] == true
                puts(JSON.pretty_generate(result))
            end

        else
            JGrep::validate_filters(options[:field][0])
            result = JGrep::jgrep((json), expression, options[:field][0], options[:start])
            unless result.first.is_a?(Hash) || result.flatten.first.is_a?(Hash)
                unless options[:quiet] == true
                    result.map{|x| puts x unless x.nil?}
                end
            else
                unless options[:quiet] == true
                    puts(JSON.pretty_generate(result))
                end
            end
            unless result.length > 0
                exit 1
            end
        end
    end

rescue Exception => e
    if e.is_a?(SystemExit)
        exit e.status
    else
        STDERR.puts "Error - #{e}"
        exit 1
    end
end
