Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add support for OCUnit test reports and update the builder.test method
- Loading branch information
Showing
8 changed files
with
302 additions
and
31 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,5 @@ | ||
source "http://rubygems.org" | ||
|
||
gemspec | ||
gem 'rspec' | ||
gem 'rspec' | ||
gem 'builder' |
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,172 @@ | ||
require 'time' | ||
require 'FileUtils' | ||
require 'socket' | ||
require 'builder' | ||
|
||
module Xcode | ||
module Test | ||
module Formatters | ||
class JunitFormatter | ||
def initialize(dir) | ||
@dir = dir | ||
end | ||
|
||
def string_to_xml(s) | ||
s.gsub(/&/, '&').gsub(/'/, '"').gsub(/</, '<') | ||
end | ||
|
||
def write(report) | ||
if report.end_time.nil? | ||
raise "Report #{report} #{report.name} has a nil end time!?" | ||
end | ||
xml = ::Builder::XmlMarkup.new( :indent => 2 ) | ||
xml.instruct! :xml, :encoding => "UTF-8" | ||
xml.testsuite(:errors => report.total_error_tests, | ||
:failures => report.total_failed_tests, | ||
:hostname => Socket.gethostname, | ||
:name => report.name, | ||
:tests => report.tests.count, | ||
:time => (report.end_time - report.start_time), | ||
:timestamp => report.end_time | ||
) do |p| | ||
|
||
report.tests.each do |t| | ||
p.testcase(:classname => report.name, | ||
:name => t.name, | ||
:time => t.time | ||
) do |e| | ||
|
||
if t.error? | ||
e.failure t.error_location, :message => t.error_message, :type => 'Failure' | ||
end | ||
end | ||
end | ||
end | ||
|
||
File.open("#{@dir}/TEST-#{report.name}.xml", 'w') do |current_file| | ||
current_file.write xml.target! | ||
end | ||
|
||
end | ||
end | ||
end | ||
|
||
class SuiteReport | ||
attr_accessor :tests, :name, :start_time, :end_time | ||
|
||
def initialize(name, start_time) | ||
@name = name | ||
@start_time = start_time | ||
@tests = [] | ||
end | ||
|
||
def finish(time) | ||
raise "Time is nil" if time.nil? | ||
@end_time = time | ||
end | ||
|
||
def total_error_tests | ||
@tests.select {|t| t.error? }.count | ||
end | ||
|
||
def total_passed_tests | ||
@tests.select {|t| t.passed? }.count | ||
end | ||
|
||
def total_failed_tests | ||
@tests.select {|t| t.failed? }.count | ||
end | ||
|
||
end | ||
|
||
class CaseReport | ||
attr_reader :name, :time, :error_message, :error_location | ||
|
||
def initialize(name) | ||
@name = name | ||
end | ||
|
||
def passed? | ||
@passed | ||
end | ||
|
||
def failed? | ||
error? or !@passed | ||
end | ||
|
||
def error? | ||
!@error_message.nil? | ||
end | ||
|
||
def passed(time) | ||
@passed = true | ||
@time = time | ||
end | ||
|
||
def failed(time) | ||
@passed = false | ||
@time = time | ||
end | ||
|
||
def error(error_message,error_location) | ||
@error_message = error_message | ||
@error_location = error_location | ||
end | ||
end | ||
|
||
class ReportParser | ||
|
||
attr_reader :exit_code, :reports | ||
|
||
def initialize | ||
@exit_code = 0 | ||
@reports = [] | ||
end | ||
|
||
def write(dir, format=:junit) | ||
dir = File.expand_path(dir) | ||
FileUtils.mkdir_p(dir) | ||
|
||
formatter = Formatters.const_get("#{format.capitalize}Formatter").new(dir) | ||
@reports.each do |r| | ||
formatter.write(r) | ||
end | ||
end | ||
|
||
def <<(piped_row) | ||
case piped_row | ||
|
||
when /Test Suite '(\S+)'.*started at\s+(.*)/ | ||
name = $1 | ||
time = Time.parse($2) | ||
@reports << SuiteReport.new(name, time) unless name=~/\// # ignore if its a file path | ||
|
||
when /Test Suite '(\S+)'.*finished at\s+(.*)./ | ||
@reports.last.finish(Time.parse($2)) | ||
|
||
when /Test Case '-\[\S+\s+(\S+)\]' started./ | ||
test = CaseReport.new($1) | ||
@reports.last.tests << test | ||
|
||
when /Test Case '-\[\S+\s+(\S+)\]' passed \((.*) seconds\)/ | ||
@reports.last.tests.last.passed($2.to_f) | ||
|
||
when /(.*): error: -\[(\S+) (\S+)\] : (.*)/ | ||
@reports.last.tests.last.error(error_message,error_location) | ||
@exit_code = 1 # should terminate | ||
|
||
when /Test Case '-\[\S+ (\S+)\]' failed \((\S+) seconds\)/ | ||
@reports.last.tests.last.failed($2.to_f) | ||
@exit_code = 1 # should terminate | ||
|
||
when /failed with exit code (\d+)/ | ||
@exit_code = $1.to_i | ||
|
||
when | ||
/BUILD FAILED/ | ||
@exit_code = -1; | ||
end | ||
end | ||
end | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,3 +1,3 @@ | ||
module Xcode | ||
VERSION = "0.0.17" | ||
VERSION = "0.0.18" | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
require 'rspec' | ||
require 'xcoder' | ||
|
||
describe Xcode::Test::ReportParser do | ||
|
||
def example_report | ||
t = Xcode::Test::ReportParser.new | ||
t << "Run test suite AnExampleTestSuite" | ||
t << "Test Suite 'AnExampleTestSuite' started at 2012-02-10 00:37:04 +0000" | ||
|
||
t << "Run test case anExampleTest1" | ||
t << "Test Case '-[AnExampleTestSuite anExampleTest1]' started." | ||
t << "Test Case '-[AnExampleTestSuite anExampleTest1]' passed (0.003 seconds)." | ||
|
||
t << "Run test case anExampleTest2" | ||
t << "Test Case '-[AnExampleTestSuite anExampleTest2]' started." | ||
t << "Test Case '-[AnExampleTestSuite anExampleTest2]' passed (0.003 seconds)." | ||
|
||
yield(t) if block_given? | ||
|
||
t << "Test Suite 'AnExampleTestSuite' finished at 2012-02-10 00:37:04 +0000." | ||
t << "Executed 1 test, with 0 failures (0 unexpected) in 0.000 (0.000) seconds" | ||
|
||
t | ||
end | ||
|
||
def example_failing_report | ||
example_report do |t| | ||
t << "Test Case '-[AnExampleTestSuite aFailingTest]' started." | ||
t << "Test Case '-[AnExampleTestSuite aFailingTest]' failed (2 seconds)." | ||
end | ||
end | ||
|
||
it "should create a test case" do | ||
t = example_report | ||
t.reports.count.should==1 | ||
t.reports.first.name.should=="AnExampleTestSuite" | ||
t.reports.first.start_time.should==Time.parse("2012-02-10 00:37:04 +0000") | ||
t.reports.first.end_time.should==Time.parse("2012-02-10 00:37:04 +0000") | ||
end | ||
|
||
it "should set the exist status to 0" do | ||
t = example_report | ||
t.exit_code.should==0 | ||
end | ||
|
||
it "should set the exit status to non 0" do | ||
t = example_failing_report | ||
t.exit_code.should_not==0 | ||
end | ||
|
||
it "should record a failure" do | ||
t = example_failing_report | ||
t.reports.first.total_failed_tests.should==1 | ||
end | ||
|
||
it "should create a test case with some tests" do | ||
t = example_report | ||
|
||
t.reports.count.should==1 | ||
t.reports.first.tests.count.should==2 | ||
t.reports.first.tests[0].name.should=='anExampleTest1' | ||
t.reports.first.tests[0].time.should==0.003 | ||
t.reports.first.tests[0].passed?.should==true | ||
|
||
t.reports.first.tests[1].name.should=='anExampleTest2' | ||
t.reports.first.tests[1].time.should==0.003 | ||
t.reports.first.tests[1].passed?.should==true | ||
end | ||
|
||
it "should write out reports in junit format" do | ||
report_dir = "#{File.dirname(__FILE__)}/test-reports" | ||
FileUtils.rm_rf report_dir | ||
|
||
t = example_report | ||
t.write(report_dir, :junit) | ||
|
||
files = Dir["#{report_dir}/*.xml"] | ||
files.count.should==1 | ||
files.first.should=~/TEST-AnExampleTestSuite.xml$/ | ||
|
||
# FIXME: parse the report | ||
end | ||
|
||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters