19750e409Sopenharmony_ci# ==========================================
29750e409Sopenharmony_ci#   Unity Project - A Test Framework for C
39750e409Sopenharmony_ci#   Copyright (c) 2007 Mike Karlesky, Mark VanderVoord, Greg Williams
49750e409Sopenharmony_ci#   [Released under MIT License. Please refer to license.txt for details]
59750e409Sopenharmony_ci# ==========================================
69750e409Sopenharmony_ci
79750e409Sopenharmony_ci# !/usr/bin/ruby
89750e409Sopenharmony_ci#
99750e409Sopenharmony_ci# unity_test_summary.rb
109750e409Sopenharmony_ci#
119750e409Sopenharmony_cirequire 'fileutils'
129750e409Sopenharmony_cirequire 'set'
139750e409Sopenharmony_ci
149750e409Sopenharmony_ciclass UnityTestSummary
159750e409Sopenharmony_ci  include FileUtils::Verbose
169750e409Sopenharmony_ci
179750e409Sopenharmony_ci  attr_reader :report, :total_tests, :failures, :ignored
189750e409Sopenharmony_ci  attr_writer :targets, :root
199750e409Sopenharmony_ci
209750e409Sopenharmony_ci  def initialize(_opts = {})
219750e409Sopenharmony_ci    @report = ''
229750e409Sopenharmony_ci    @total_tests = 0
239750e409Sopenharmony_ci    @failures = 0
249750e409Sopenharmony_ci    @ignored = 0
259750e409Sopenharmony_ci  end
269750e409Sopenharmony_ci
279750e409Sopenharmony_ci  def run
289750e409Sopenharmony_ci    # Clean up result file names
299750e409Sopenharmony_ci    results = @targets.map { |target| target.tr('\\', '/') }
309750e409Sopenharmony_ci
319750e409Sopenharmony_ci    # Dig through each result file, looking for details on pass/fail:
329750e409Sopenharmony_ci    failure_output = []
339750e409Sopenharmony_ci    ignore_output = []
349750e409Sopenharmony_ci
359750e409Sopenharmony_ci    results.each do |result_file|
369750e409Sopenharmony_ci      lines = File.readlines(result_file).map(&:chomp)
379750e409Sopenharmony_ci
389750e409Sopenharmony_ci      raise "Empty test result file: #{result_file}" if lines.empty?
399750e409Sopenharmony_ci
409750e409Sopenharmony_ci      output = get_details(result_file, lines)
419750e409Sopenharmony_ci      failure_output << output[:failures] unless output[:failures].empty?
429750e409Sopenharmony_ci      ignore_output  << output[:ignores]  unless output[:ignores].empty?
439750e409Sopenharmony_ci      tests, failures, ignored = parse_test_summary(lines)
449750e409Sopenharmony_ci      @total_tests += tests
459750e409Sopenharmony_ci      @failures += failures
469750e409Sopenharmony_ci      @ignored += ignored
479750e409Sopenharmony_ci    end
489750e409Sopenharmony_ci
499750e409Sopenharmony_ci    if @ignored > 0
509750e409Sopenharmony_ci      @report += "\n"
519750e409Sopenharmony_ci      @report += "--------------------------\n"
529750e409Sopenharmony_ci      @report += "UNITY IGNORED TEST SUMMARY\n"
539750e409Sopenharmony_ci      @report += "--------------------------\n"
549750e409Sopenharmony_ci      @report += ignore_output.flatten.join("\n")
559750e409Sopenharmony_ci    end
569750e409Sopenharmony_ci
579750e409Sopenharmony_ci    if @failures > 0
589750e409Sopenharmony_ci      @report += "\n"
599750e409Sopenharmony_ci      @report += "--------------------------\n"
609750e409Sopenharmony_ci      @report += "UNITY FAILED TEST SUMMARY\n"
619750e409Sopenharmony_ci      @report += "--------------------------\n"
629750e409Sopenharmony_ci      @report += failure_output.flatten.join("\n")
639750e409Sopenharmony_ci    end
649750e409Sopenharmony_ci
659750e409Sopenharmony_ci    @report += "\n"
669750e409Sopenharmony_ci    @report += "--------------------------\n"
679750e409Sopenharmony_ci    @report += "OVERALL UNITY TEST SUMMARY\n"
689750e409Sopenharmony_ci    @report += "--------------------------\n"
699750e409Sopenharmony_ci    @report += "#{@total_tests} TOTAL TESTS #{@failures} TOTAL FAILURES #{@ignored} IGNORED\n"
709750e409Sopenharmony_ci    @report += "\n"
719750e409Sopenharmony_ci  end
729750e409Sopenharmony_ci
739750e409Sopenharmony_ci  def usage(err_msg = nil)
749750e409Sopenharmony_ci    puts "\nERROR: "
759750e409Sopenharmony_ci    puts err_msg if err_msg
769750e409Sopenharmony_ci    puts "\nUsage: unity_test_summary.rb result_file_directory/ root_path/"
779750e409Sopenharmony_ci    puts '     result_file_directory - The location of your results files.'
789750e409Sopenharmony_ci    puts '                             Defaults to current directory if not specified.'
799750e409Sopenharmony_ci    puts '                             Should end in / if specified.'
809750e409Sopenharmony_ci    puts '     root_path - Helpful for producing more verbose output if using relative paths.'
819750e409Sopenharmony_ci    exit 1
829750e409Sopenharmony_ci  end
839750e409Sopenharmony_ci
849750e409Sopenharmony_ci  protected
859750e409Sopenharmony_ci
869750e409Sopenharmony_ci  def get_details(_result_file, lines)
879750e409Sopenharmony_ci    results = { failures: [], ignores: [], successes: [] }
889750e409Sopenharmony_ci    lines.each do |line|
899750e409Sopenharmony_ci      _src_file, _src_line, _test_name, status, _msg = line.split(/:/)
909750e409Sopenharmony_ci      line_out = (@root && (@root != 0) ? "#{@root}#{line}" : line).gsub(/\//, '\\')
919750e409Sopenharmony_ci      case status
929750e409Sopenharmony_ci      when 'IGNORE' then results[:ignores]   << line_out
939750e409Sopenharmony_ci      when 'FAIL'   then results[:failures]  << line_out
949750e409Sopenharmony_ci      when 'PASS'   then results[:successes] << line_out
959750e409Sopenharmony_ci      end
969750e409Sopenharmony_ci    end
979750e409Sopenharmony_ci    results
989750e409Sopenharmony_ci  end
999750e409Sopenharmony_ci
1009750e409Sopenharmony_ci  def parse_test_summary(summary)
1019750e409Sopenharmony_ci    raise "Couldn't parse test results: #{summary}" unless summary.find { |v| v =~ /(\d+) Tests (\d+) Failures (\d+) Ignored/ }
1029750e409Sopenharmony_ci    [Regexp.last_match(1).to_i, Regexp.last_match(2).to_i, Regexp.last_match(3).to_i]
1039750e409Sopenharmony_ci  end
1049750e409Sopenharmony_ci
1059750e409Sopenharmony_ci  def here
1069750e409Sopenharmony_ci    File.expand_path(File.dirname(__FILE__))
1079750e409Sopenharmony_ci  end
1089750e409Sopenharmony_ciend
1099750e409Sopenharmony_ci
1109750e409Sopenharmony_ciif $0 == __FILE__
1119750e409Sopenharmony_ci
1129750e409Sopenharmony_ci  # parse out the command options
1139750e409Sopenharmony_ci  opts, args = ARGV.partition { |v| v =~ /^--\w+/ }
1149750e409Sopenharmony_ci  opts.map! { |v| v[2..-1].to_sym }
1159750e409Sopenharmony_ci
1169750e409Sopenharmony_ci  # create an instance to work with
1179750e409Sopenharmony_ci  uts = UnityTestSummary.new(opts)
1189750e409Sopenharmony_ci
1199750e409Sopenharmony_ci  begin
1209750e409Sopenharmony_ci    # look in the specified or current directory for result files
1219750e409Sopenharmony_ci    args[0] ||= './'
1229750e409Sopenharmony_ci    targets = "#{ARGV[0].tr('\\', '/')}**/*.test*"
1239750e409Sopenharmony_ci    results = Dir[targets]
1249750e409Sopenharmony_ci    raise "No *.testpass, *.testfail, or *.testresults files found in '#{targets}'" if results.empty?
1259750e409Sopenharmony_ci    uts.targets = results
1269750e409Sopenharmony_ci
1279750e409Sopenharmony_ci    # set the root path
1289750e409Sopenharmony_ci    args[1] ||= Dir.pwd + '/'
1299750e409Sopenharmony_ci    uts.root = ARGV[1]
1309750e409Sopenharmony_ci
1319750e409Sopenharmony_ci    # run the summarizer
1329750e409Sopenharmony_ci    puts uts.run
1339750e409Sopenharmony_ci  rescue StandardError => e
1349750e409Sopenharmony_ci    uts.usage e.message
1359750e409Sopenharmony_ci  end
1369750e409Sopenharmony_ciend
137