Skip to content
Permalink

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: jruby/jruby
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: 9319c37ea9e5
Choose a base ref
...
head repository: jruby/jruby
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: 2a3dc1f37978
Choose a head ref
  • 3 commits
  • 5 files changed
  • 1 contributor

Commits on Feb 24, 2015

  1. Copy the full SHA
    a5d6868 View commit details
  2. 1
    Copy the full SHA
    8ff6afa View commit details
  3. [Truffle] Added a jUnit-based mspec formatter to track spec execution…

    … time and skipped spec percentage.
    nirvdrum committed Feb 24, 2015
    Copy the full SHA
    2a3dc1f View commit details
21 changes: 18 additions & 3 deletions spec/mspec/lib/mspec/runner/actions/tally.rb
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
class Tally
attr_accessor :files, :examples, :expectations, :failures, :errors, :guards
attr_accessor :files, :examples, :expectations, :failures, :errors, :guards, :tagged

def initialize
@files = @examples = @expectations = @failures = @errors = @guards = 0
@files = @examples = @expectations = @failures = @errors = @guards = @tagged = 0
end

def files!(add=1)
@@ -29,6 +29,10 @@ def guards!(add=1)
@guards += add
end

def tagged!(add=1)
@tagged += add
end

def file
pluralize files, "file"
end
@@ -53,8 +57,12 @@ def guard
pluralize guards, "guard"
end

def tag
"#{tagged} tagged"
end

def format
results = [ file, example, expectation, failure, error ]
results = [ file, example, expectation, failure, error, tag ]
results << guard if [:report, :report_on, :verify].any? { |m| MSpec.mode? m }
results.join(", ")
end
@@ -79,13 +87,15 @@ def register
MSpec.register :exception, self
MSpec.register :example, self
MSpec.register :expectation, self
MSpec.register :tagged, self
end

def unregister
MSpec.unregister :load, self
MSpec.unregister :exception, self
MSpec.unregister :example, self
MSpec.unregister :expectation, self
MSpec.unregister :tagged, self
end

def load
@@ -110,6 +120,11 @@ def example(state, block)
@counter.examples!
end

def tagged(state)
@counter.examples!
@counter.tagged!
end

def format
@counter.format
end
11 changes: 10 additions & 1 deletion spec/mspec/lib/mspec/runner/context.rb
Original file line number Diff line number Diff line change
@@ -182,7 +182,16 @@ def protect(what, blocks, check=true)
# Removes filtered examples. Returns true if there are examples
# left to evaluate.
def filter_examples
@examples.reject! { |ex| ex.filtered? }
filtered = @examples.select do |ex|
ex.filtered?
end

filtered.each do |ex|
MSpec.actions :tagged, ex
end

@examples -= filtered

not @examples.empty?
end

1 change: 1 addition & 0 deletions spec/mspec/lib/mspec/runner/formatters/yaml.rb
Original file line number Diff line number Diff line change
@@ -40,5 +40,6 @@ def finish
print "expectations: ", @tally.counter.expectations, "\n"
print "failures: ", @tally.counter.failures, "\n"
print "errors: ", @tally.counter.errors, "\n"
print "tagged: ", @tally.counter.tagged, "\n"
end
end
17 changes: 14 additions & 3 deletions spec/mspec/lib/mspec/utils/options.rb
Original file line number Diff line number Diff line change
@@ -293,9 +293,20 @@ def formatters
when 'j', 'junit'
config[:formatter] = JUnitFormatter
else
puts "Unknown format: #{o}"
puts @parser
exit
if File.exist?(o)
require o

if defined?(CUSTOM_MSPEC_FORMATTER)
config[:formatter] = CUSTOM_MSPEC_FORMATTER
else
puts "You must define CUSTOM_MSPEC_FORMATTER in your custom formatter file"
exit
end
else
puts "Unknown format: #{o}"
puts @parser
exit
end
end
end

186 changes: 186 additions & 0 deletions spec/truffle/truffle_formatter.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,186 @@
require 'mspec/expectations/expectations'
require 'mspec/utils/ruby_name'
require 'mspec/runner/formatters/dotted'

class TruffleFormatter < DottedFormatter
def initialize(out=nil)
super
@tests = []
end

def register
super
MSpec.register :start, self
MSpec.register :before, self
MSpec.register :load, self
MSpec.register :unload, self
MSpec.register :tagged, self
end

def start
# TODO (nirvdrum 23-Feb-15) Remove this hack when Truffle supports deleting directories with files and can do so synchronously.
system("rm -r tmp/*")
sleep(1)
end

def load
parts = MSpec.retrieve(:file).sub(Dir.pwd + '/', '').split('/')

@spec_type = parts[0...2].join('.')
@classname = parts[2...-1].join('_')
@filename_base = parts[-1].split('.rb').first.split('_spec').first

@tests.clear
@file_time = current_time

(@local_tally = TallyAction.new).register

@testsuite_name = [@spec_type, @classname, @filename_base].compact.join('.')
@dir = File.join('tmp', @spec_type, @classname)

mkdir_p(@dir)

@filename = File.expand_path(File.join(@dir, "TEST-#{@filename_base}.xml"))
@file = File.open(@filename, 'w')
end

def before(state = nil)
@spec_time = current_time
end

def after(state = nil)
super
@tests << {:test => state, :exception => false, :tagged => false, :time => current_time - @spec_time} unless exception?
end

def exception(exception)
super
@tests << {:test => exception, :exception => true, :tagged => false, :time => current_time - @spec_time}
end

def tagged(state = nil)
@tests << {:test => state, :exception => false, :tagged => true, :time => 0.0}
end

def unload
start = current_time

tests = @local_tally.counter.examples
errors = @local_tally.counter.errors
failures = @local_tally.counter.failures
tagged = @local_tally.counter.tagged

skipped_stats = if tagged > 0
# TODO (nirvdrum 23-Feb-15) Clean this up when Truffle supports Float#round(int)
skipped_percentage = ((tagged / tests.to_f) * 1000).round / 10.0
"#{skipped_percentage}% Skipped"
else
''
end

@file.puts <<-XML
<testsuite
tests="#{tests}"
errors="#{errors}"
failures="#{failures}"
skipped="#{tagged}"
time="#{current_time - @file_time}"
hostname="#{skipped_stats}"
name="#{@testsuite_name}">
XML

@tests.each do |h|
description = encode_for_xml h[:test].description

@file.puts <<-XML
<testcase classname="#{@classname}" name="#{description}" time="#{h[:time]}">
XML

if h[:exception]
outcome = h[:test].failure? ? "failure" : "error"
message = encode_for_xml h[:test].message
backtrace = encode_for_xml h[:test].backtrace
@file.puts <<-XML
<#{outcome} message="error in #{description}" type="#{outcome}">
#{message}
#{backtrace}
</#{outcome}>
XML
end

if h[:tagged]
@file.puts <<-XML
<skipped message="tagged"></skipped>
XML
end

@file.puts <<-XML
</testcase>
XML
end


@file.puts "</testsuite>"
@file.close

@local_tally.unregister
end

private
LT = "&lt;"
GT = "&gt;"
QU = "&quot;"
AP = "&apos;"
AM = "&amp;"
TARGET_ENCODING = "ISO-8859-1"

def filename(describe)
normalized = describe.gsub(' ', '_')

"TEST-#{normalized}.xml"
end

def encode_for_xml(str)
encode_as_latin1(str).gsub("&", AM).gsub("<", LT).gsub(">", GT).
gsub('"', QU).gsub("'", AP).
gsub(/[#{Regexp.escape("\0\1\2\3\4\5\6\7\8")}]/, "?")
end

if defined? Encoding
def encode_as_latin1(str)
str.encode(TARGET_ENCODING, :undef => :replace, :invalid => :replace)
end
else
require 'iconv'
def encode_as_latin1(str)
Iconv.conv("#{TARGET_ENCODING}//TRANSLIT//IGNORE", "UTF-8", str)
end
end

begin
Process.clock_gettime(Process::CLOCK_MONOTONIC)

def current_time
Process.clock_gettime(Process::CLOCK_MONOTONIC)
end
rescue Exception
def current_time
Time.now
end
end

def mkdir_p(dir)
sub_path = Dir.pwd
parts = dir.split('/')

parts.each do |part|
sub_path = File.join(sub_path, part)

puts "#{sub_path} exists?: #{Dir.exist?(sub_path)}"

Dir.mkdir(sub_path) unless Dir.exist?(sub_path)
end
end
end

CUSTOM_MSPEC_FORMATTER = TruffleFormatter