Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse code

Refactoring all the test frameworks improving the #parse_results meth…

…ods via metaprogramming
  • Loading branch information...
commit b3202281cacd0aa417b8785ba9d20beb7f99374f 1 parent 08b344d
Tomas D'Stefano authored
61 lib/infinity_test/test_framework.rb
@@ -2,30 +2,71 @@ module InfinityTest
2 2 class TestFramework
3 3 attr_accessor :message
4 4
  5 + # Method used in the subclasses of TestFramework
  6 + #
  7 + # Example:
  8 + #
  9 + # class Rspec < TestFramework
  10 + # parse_results :example => /(\d+) example/, :failure => /(\d+) failure/, :pending => /(\d+) pending/
  11 + # end
  12 + #
  13 + # Then will create @examples, @failure and @pending instance variables with the values in the test result
  14 + #
  15 + # Or with Test::Unit:
  16 + #
  17 + # class TestUnit < TestFramework
  18 + # parse_results :tests => /(\d+) tests/, :assertions => /(\d+) assertions/, :failures => /(\d+) failures/, :errors => /(\d+) errors/
  19 + # end
  20 + #
  21 + # Then will create @tests, @assertions, @failures and @errors instance variables with the values in the test result
  22 + #
5 23 def self.parse_results(patterns)
6 24 raise(ArgumentError, 'patterns should not be empty') if patterns.empty?
7   - patterns.each do |attribute, pattern|
8   - attr_accessor attribute
9   - end
  25 + create_accessors(patterns)
10 26 define_method(:parse_results) do |results|
11   - shell_result = test_message(results)
12   - if shell_result =~ /example/ or shell_result =~ /tests/
  27 + shell_result = test_message(results, patterns)
  28 + if shell_result
13 29 create_pattern_instance_variables(patterns, shell_result)
14 30 else
  31 + patterns.each { |instance, pattern| instance_variable_set("@#{instance}", 1) } # set all to 1 to show that an error occurred
15 32 @message = "An exception occurred"
16 33 end
17 34 end
18 35 end
19 36
  37 + # Create accessors for keys of the Hash passed in argument
  38 + #
  39 + # create_accessors({ :example => '...', :failure => '...'}) # => attr_accessor :example, :failure
  40 + #
  41 + def self.create_accessors(hash)
  42 + hash.keys.each do |attribute|
  43 + attr_accessor attribute
  44 + end
  45 + end
  46 +
  47 + # Create the instance pass in the patterns options
  48 + #
  49 + # Useful for the parse results:
  50 + # parse_results :tests => /.../, :assertions => /.../
  51 + #
  52 + # Then will create @tests ans @assertions (the keys of the Hash)
  53 + #
20 54 def create_pattern_instance_variables(patterns, shell_result)
21 55 patterns.each do |key, pattern|
22   - instance_variable_set("@#{key}", shell_result[pattern, 1].to_i)
23   - end
24   - @message = shell_result
  56 + number = shell_result[pattern, 1].to_i
  57 + instance_variable_set("@#{key}", number)
  58 + end
  59 + @message = shell_result.gsub(/\e\[\d+?m/, '')
25 60 end
26 61
27   - def test_message(output)
28   - output.split("\n").last
  62 + # Return the message of the tests
  63 + #
  64 + # test_message('0 examples, 0 failures', { :example => /(\d) example/}) # => '0 examples, 0 failures'
  65 + # test_message('....\n4 examples, 0 failures', { :examples => /(\d) examples/}) # => '4 examples, 0 failures'
  66 + #
  67 + def test_message(output, patterns)
  68 + lines = output.split("\n")
  69 + lines.select { |line| line =~ patterns.values.first }.first
29 70 end
30 71
31 72 end
28 lib/infinity_test/test_library/bacon.rb
@@ -2,6 +2,7 @@ module InfinityTest
2 2 module TestLibrary
3 3 class Bacon < TestFramework
4 4
  5 + parse_results :specifications => /(\d+) specifications/, :requirements => /(\d+) requirements/, :failures => /(\d+) failure/, :errors => /(\d+) errors/
5 6
6 7 #
7 8 # test_pattern = 'spec/**/*_spec.rb'
@@ -20,7 +21,7 @@ class Bacon < TestFramework
20 21 # end
21 22 # end
22 23 #
23   - # parse_results :examples => /(\d+) example/, :failures => /(\d+) failure/, :pending => /(\d+) pending/
  24 + #
24 25 #
25 26
26 27 include BinaryPath
@@ -58,7 +59,7 @@ def construct_rubies_commands(file=nil)
58 59 unless have_binary?(bacon_binary)
59 60 print_message('bacon', ruby_version)
60 61 else
61   - results[ruby_version] = "rvm #{ruby_version} ruby #{bacon_binary} #{decide_files(file)}"
  62 + results[ruby_version] = "rvm #{ruby_version} ruby #{bacon_binary} -Ilib -d #{decide_files(file)}"
62 63 end
63 64 end
64 65 results
@@ -74,31 +75,14 @@ def decide_files(file)
74 75 def search_bacon(environment)
75 76 search_binary('bacon', :environment => environment)
76 77 end
77   -
78   - def parse_results(results)
79   - shell_result = results.split("\n").last
80   - if shell_result =~ /example/
81   - @example = shell_result[/(\d+) example/, 1].to_i
82   - @failure = shell_result[/(\d+) failure/, 1].to_i
83   - @pending = shell_result[/(\d+) pending/, 1].to_i
84   - @message = "#{@example} examples, #{@failure} failures, #{@pending} pending"
85   - else
86   - @example, @pending, @failure = 0, 0, 1
87   - @message = "An exception occurred"
88   - end
89   - end
90   -
  78 +
91 79 def sucess?
92   - return false if failure? or pending?
  80 + return false if failure?
93 81 true
94 82 end
95 83
96 84 def failure?
97   - @failure > 0
98   - end
99   -
100   - def pending?
101   - @pending > 0 and not failure?
  85 + @failures > 0
102 86 end
103 87
104 88 end
20 lib/infinity_test/test_library/rspec.rb
... ... @@ -1,10 +1,13 @@
1 1 module InfinityTest
2 2 module TestLibrary
3   - class Rspec
  3 + class Rspec < TestFramework
  4 +
4 5 include BinaryPath
5 6 attr_accessor :rubies, :test_directory_pattern, :message, :test_pattern,
6 7 :failure, :sucess, :pending
7 8
  9 + parse_results :examples => /(\d+) example/, :failures => /(\d+) failure/, :pending => /(\d+) pending/
  10 +
8 11 #
9 12 # rspec = InfinityTest::Rspec.new(:rubies => '1.9.1,1.9.2')
10 13 # rspec.rubies # => '1.9.1,1.9.2'
@@ -58,26 +61,13 @@ def search_rspec_one(environment)
58 61 search_binary('spec', :environment => environment)
59 62 end
60 63
61   - def parse_results(results)
62   - shell_result = results.split("\n").last
63   - if shell_result =~ /example/
64   - @example = shell_result[/(\d+) example/, 1].to_i
65   - @failure = shell_result[/(\d+) failure/, 1].to_i
66   - @pending = shell_result[/(\d+) pending/, 1].to_i
67   - @message = "#{@example} examples, #{@failure} failures, #{@pending} pending"
68   - else
69   - @example, @pending, @failure = 0, 0, 1
70   - @message = "An exception occurred"
71   - end
72   - end
73   -
74 64 def sucess?
75 65 return false if failure? or pending?
76 66 true
77 67 end
78 68
79 69 def failure?
80   - @failure > 0
  70 + @failures > 0
81 71 end
82 72
83 73 def pending?
23 lib/infinity_test/test_library/test_unit.rb
... ... @@ -1,9 +1,11 @@
1 1 module InfinityTest
2 2 module TestLibrary
3   - class TestUnit
4   - attr_reader :rubies, :message, :test_directory_pattern, :tests,
5   - :assertions, :failures, :errors
  3 + class TestUnit < TestFramework
6 4
  5 + attr_reader :rubies, :message, :test_directory_pattern, :tests, :assertions, :failures, :errors
  6 +
  7 + parse_results :tests => /(\d+) tests/, :assertions => /(\d+) assertions/, :failures => /(\d+) failures/, :errors => /(\d+) errors/
  8 +
7 9 def initialize(options={})
8 10 @rubies = options[:rubies] || []
9 11 @test_directory_pattern = "^test/*/(.*)_test.rb"
@@ -48,21 +50,6 @@ def test_loader
48 50 end
49 51 end
50 52
51   - def parse_results(results)
52   - shell_result = results.split("\n")
53   - shell_result = shell_result.select { |line| line =~ /(\d+) tests/}.first
54   - if shell_result
55   - @tests = shell_result[/(\d+) tests/, 1].to_i
56   - @assertions = shell_result[/(\d+) assertions/, 1].to_i
57   - @failures = shell_result[/(\d+) failures/, 1].to_i
58   - @errors = shell_result[/(\d+) errors/, 1].to_i
59   - @message = shell_result
60   - else
61   - @tests, @assertions, @failures, @errors = 0, 0, 1, 1
62   - @message = "An exception ocurred"
63   - end
64   - end
65   -
66 53 def failure?
67 54 @failures > 0 or @errors > 0
68 55 end
20 spec/infinity_test/test_framework_spec.rb
@@ -54,8 +54,8 @@ class OtherFramework < TestFramework
54 54 end
55 55
56 56 it "should create a message based in the keys of framework" do
57   - some_framework.parse_results(".....\n200 examples, 0 failues, 1 pending")
58   - some_framework.message.should == "200 examples, 0 failues, 1 pending"
  57 + some_framework.parse_results(".....\n200 examples, 0 failures, 1 pending")
  58 + some_framework.message.should == "200 examples, 0 failures, 1 pending"
59 59 end
60 60
61 61 it "should create a error message to runtime errors and similars" do
@@ -63,6 +63,22 @@ class OtherFramework < TestFramework
63 63 some_framework.message.should == "An exception occurred"
64 64 end
65 65
  66 + it "should parse the results correctly(when not have in last line)" do
  67 + other_framework.parse_results("....\n10 tests, 35 assertions, 0 failures, 0 errors\nTest run options: --seed 18841")
  68 + other_framework.tests.should == 10
  69 + other_framework.assertions.should == 35
  70 + end
  71 +
  72 + it "should clear the term ansi colors strings" do
  73 + other_framework.parse_results("seconds\n\e[33m406 tests, 34 assertions, 0 failures, 2 pending\e[0m\n")
  74 + other_framework.message.should == "406 tests, 34 assertions, 0 failures, 2 pending"
  75 + end
  76 +
  77 + it "should clear the term ansi colors strings" do
  78 + some_framework.parse_results("seconds\n\e[33m406 examples, 0 failures, 2 pending\e[0m\n")
  79 + some_framework.message.should == "406 examples, 0 failures, 2 pending"
  80 + end
  81 +
66 82 it "should raise error when not have patterns" do
67 83 lambda {
68 84 class Abc < TestFramework
67 spec/infinity_test/test_library/bacon_spec.rb
@@ -78,35 +78,29 @@ module TestLibrary
78 78 end
79 79
80 80 it "should handle a example that succeed" do
81   - results = "........Finished in 0.299817 seconds\n\n105 examples, 0 failures, 0 pending\n"
  81 + results = "should be true\n\n2 specifications (2 requirements), 0 failures, 0 errors\n"
82 82 @bacon.parse_results(results)
83   - @bacon.message.should == "105 examples, 0 failures, 0 pending"
  83 + @bacon.message.should == "2 specifications (2 requirements), 0 failures, 0 errors"
84 84 end
85 85
86 86 it "should parse without the terminal ansi color" do
87   - results = "ork\e[0m\n\e[90m # No reason given\e[0m\n\e[90m # ./spec/infinity_test/configuration_spec.rb:31\e[0m\n\nFinished in 0.10487 seconds\n\e[33m406 examples, 5 failures, 2 pending\e[0m\n"
  87 + results = "should be true\n\n3 specifications (2 requirements), 0 failures, 0 errors\n"
88 88 @bacon.parse_results(results)
89   - @bacon.message.should == "406 examples, 5 failures, 2 pending"
  89 + @bacon.message.should == "3 specifications (2 requirements), 0 failures, 0 errors"
90 90 end
91 91
92 92 it "should handle a example that succeed and return false for failure?" do
93   - results = "........Finished in 0.299817 seconds\n\n105 examples, 0 failures, 0 pending\n"
  93 + results = "3 specifications (2 requirements), 0 failures, 0 errors"
94 94 @bacon.parse_results(results)
95 95 @bacon.failure?.should equal false
96 96 end
97 97
98 98 it "should parse without the terminal ansi color and grep the failure" do
99   - results = "ork\e[0m\n\e[90m # No reason given\e[0m\n\e[90m # ./spec/infinity_test/configuration_spec.rb:31\e[0m\n\nFinished in 0.10487 seconds\n\e[33m406 examples, 5 failures, 2 pending\e[0m\n"
  99 + results = "\n\e[33m3 specifications (2 requirements), 10 failures, 0 errors\e[0m\n"
100 100 @bacon.parse_results(results)
101 101 @bacon.failure?.should be_true
102 102 end
103 103
104   - it "should parse without the terminal ansi color and grep the pending" do
105   - results = "ork\e[0m\n\e[90m # No reason given\e[0m\n\e[90m # ./spec/infinity_test/configuration_spec.rb:31\e[0m\n\nFinished in 0.10487 seconds\n\e[33m406 examples, 0 failures, 2 pending\e[0m\n"
106   - @bacon.parse_results(results)
107   - @bacon.pending?.should be_true
108   - end
109   -
110 104 it "should parse bacon tests errors" do
111 105 results = "/Users/tomas/.rvm/gems/ruby-1.9.2@infinity_test/gems/my_class/bin/klass:2:in `require': no such file to load -- MyClass (LoadError)"
112 106 @bacon.parse_results(results)
@@ -123,69 +117,26 @@ module TestLibrary
123 117 results = "/Users/tomas/.rvm/gems/ruby-1.9.2@infinity_test/gems/my_class/bin/klass:2:in `require': no such file to load -- MyClass (LoadError)"
124 118 @bacon.parse_results(results)
125 119 @bacon.sucess?.should equal false
126   - end
127   -
128   - it "should parse bacon tests errors" do
129   - results = "/Users/tomas/.rvm/gems/ruby-1.9.2@infinity_test/gems/my_class/bin/klass:2:in `require': no such file to load -- MyClass (LoadError)"
130   - @bacon.parse_results(results)
131   - @bacon.pending?.should equal false
132   - end
  120 + end
133 121 end
134 122
135 123 describe '#sucess?' do
136 124 before { @bacon = Bacon.new }
137 125
138 126 it "should return false when have failures" do
139   - results = "ork\e[0m\n\e[90m # No reason given\e[0m\n\e[90m # ./spec/infinity_test/configuration_spec.rb:31\e[0m\n\nFinished in 0.10487 seconds\n\e[33m406 examples, 5 failures, 2 pending\e[0m\n"
  127 + results = "3 specifications (3 requirements), 3 failures, 0 errors"
140 128 @bacon.parse_results(results)
141 129 @bacon.sucess?.should equal false
142 130 end
143   -
144   - it "should return false when have pending" do
145   - results = "ork\e[0m\n\e[90m # No reason given\e[0m\n\e[90m # ./spec/infinity_test/configuration_spec.rb:31\e[0m\n\nFinished in 0.10487 seconds\n\e[33m806 examples, 0 failures, 2 pending\e[0m\n"
146   - @bacon.parse_results(results)
147   - @bacon.sucess?.should be_false
148   - end
149 131
150 132 it "should return true when have zero failures and zero pending" do
151   - results = "........Finished in 0.299817 seconds\n\n105 examples, 0 failures, 0 pending\n"
  133 + results = "13 specifications (20 requirements), 0 failures, 0 errors"
152 134 @bacon.parse_results(results)
153 135 @bacon.sucess?.should be_true
154 136 end
155 137
156 138 end
157 139
158   - describe '#pending?' do
159   - let(:bacon) { Bacon.new }
160   -
161   - it "should return true when have pending" do
162   - bacon.pending = 1
163   - bacon.failure = 0
164   - bacon.pending?.should be_true
165   - end
166   -
167   - it "should return false when have pending bu thave failures" do
168   - bacon.pending = 1
169   - bacon.failure = 1
170   - bacon.pending?.should equal false
171   - end
172   -
173   - end
174   -
175   - def redefine_const(name,value)
176   - if Object.const_defined?(name)
177   - old_value = Object.const_get(name)
178   - Object.send(:remove_const, name)
179   - else
180   - old_value = value
181   - end
182   - Object.const_set(name,value)
183   - yield
184   - ensure
185   - Object.send(:remove_const, name)
186   - Object.const_set(name, old_value)
187   - end
188   -
189 140 end
190 141 end
191 142 end
4 spec/infinity_test/test_library/rspec_spec.rb
@@ -160,13 +160,13 @@ module TestLibrary
160 160
161 161 it "should return true when have pending" do
162 162 rspec.pending = 1
163   - rspec.failure = 0
  163 + rspec.failures = 0
164 164 rspec.pending?.should be_true
165 165 end
166 166
167 167 it "should return false when have pending bu thave failures" do
168 168 rspec.pending = 1
169   - rspec.failure = 1
  169 + rspec.failures = 1
170 170 rspec.pending?.should equal false
171 171 end
172 172
6 spec/infinity_test/test_library/test_unit_spec.rb
@@ -77,7 +77,7 @@ module TestLibrary
77 77
78 78 it "should parse when have a exception" do
79 79 @test_unit.parse_results("")
80   - @test_unit.message.should == "An exception ocurred"
  80 + @test_unit.message.should == "An exception occurred"
81 81 end
82 82
83 83 it "should parse and set correctly the tests" do
@@ -131,8 +131,8 @@ module TestLibrary
131 131 it "should parse when have a exception and set failure to 1" do
132 132 @test_unit.parse_results("")
133 133 @test_unit.failures.should == 1
134   - @test_unit.tests.should == 0
135   - @test_unit.assertions.should == 0
  134 + @test_unit.tests.should == 1
  135 + @test_unit.assertions.should == 1
136 136 @test_unit.errors.should == 1
137 137 end
138 138

0 comments on commit b320228

Please sign in to comment.
Something went wrong with that request. Please try again.