mspec 1.1.1 → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -43,36 +43,30 @@ EOH
43
43
  print "</ul>\n</div>\n"
44
44
  end
45
45
 
46
+ def exception(exception)
47
+ super
48
+ outcome = exception.failure? ? "FAILED" : "ERROR"
49
+ print %[<li class="fail">- #{exception.it} (<a href="#details-#{@count}">]
50
+ print %[#{outcome} - #{@count}</a>)</li>\n]
51
+ end
52
+
46
53
  def after(state)
47
- desc = "- #{state.it}"
48
- if state.exception?
49
- @states << state
50
- count = @counter.failures + @counter.errors - state.exceptions.size
51
- state.exceptions.each do |msg, exc|
52
- outcome = state.failure?(exc) ? "FAILED" : "ERROR"
53
- count += 1
54
- print %[<li class="fail">#{desc} (<a href="#details-#{count}">#{outcome} - #{count}</a>)</li>\n]
55
- end
56
- else
57
- print %[<li class="pass">#{desc}</li>\n]
58
- end
54
+ print %[<li class="pass">- #{state.it}</li>\n] unless exception?
59
55
  end
60
56
 
61
57
  def finish
62
- success = @states.empty?
58
+ success = @exceptions.empty?
63
59
  unless success
64
60
  print "<hr>\n"
65
61
  print %[<ol id="details">]
66
62
  count = 0
67
- @states.each do |state|
68
- state.exceptions.each do |msg, exc|
69
- outcome = failure?(state) ? "FAILED" : "ERROR"
70
- print %[\n<li id="details-#{count += 1}"><p>#{escape(state.description)} #{outcome}</p>\n<p>]
71
- print escape(message(exc))
72
- print "</p>\n<pre>\n"
73
- print escape(backtrace(exc))
74
- print "</pre>\n</li>\n"
75
- end
63
+ @exceptions.each do |exc|
64
+ outcome = exc.failure? ? "FAILED" : "ERROR"
65
+ print %[\n<li id="details-#{count += 1}"><p>#{escape(exc.description)} #{outcome}</p>\n<p>]
66
+ print escape(exc.message)
67
+ print "</p>\n<pre>\n"
68
+ print escape(exc.backtrace)
69
+ print "</pre>\n</li>\n"
76
70
  end
77
71
  print "</ol>\n"
78
72
  end
@@ -7,21 +7,34 @@ class SpecdocFormatter < DottedFormatter
7
7
  MSpec.register :enter, self
8
8
  end
9
9
 
10
+ # Callback for the MSpec :enter event. Prints the
11
+ # +describe+ block string.
10
12
  def enter(describe)
11
13
  print "\n#{describe}\n"
12
14
  end
13
15
 
16
+ # Callback for the MSpec :before event. Prints the
17
+ # +it+ block string.
18
+ def before(state)
19
+ print "- #{state.it}"
20
+ end
21
+
22
+ # Callback for the MSpec :exception event. Prints
23
+ # either 'ERROR - X' or 'FAILED - X' where _X_ is
24
+ # the sequential number of the exception raised. If
25
+ # there has already been an exception raised while
26
+ # evaluating this example, it prints another +it+
27
+ # block description string so that each discription
28
+ # string has an associated 'ERROR' or 'FAILED'
29
+ def exception(exception)
30
+ print "\n- #{exception.it}" if exception?
31
+ super
32
+ print " (#{exception.failure? ? 'FAILED' : 'ERROR'} - #{@count})"
33
+ end
34
+
35
+ # Callback for the MSpec :after event. Prints a
36
+ # newline to finish the description string output.
14
37
  def after(state)
15
- desc = "- #{state.it}"
16
- if state.exception?
17
- @states << state
18
- count = @counter.failures + @counter.errors - state.exceptions.size
19
- state.exceptions.each do |msg, exc|
20
- outcome = state.failure?(exc) ? "FAILED" : "ERROR"
21
- print "#{desc} (#{outcome} - #{count += 1})\n"
22
- end
23
- else
24
- print "#{desc}\n"
25
- end
38
+ print "\n"
26
39
  end
27
40
  end
@@ -9,11 +9,13 @@ class SpinnerFormatter < DottedFormatter
9
9
  MIN = 60
10
10
 
11
11
  def initialize(out=nil)
12
+ @exception = @failure = false
13
+ @exceptions = []
14
+ @count = 0
12
15
  @out = $stdout
13
16
 
14
- @states = []
15
17
  @which = 0
16
- @count = 0
18
+ @loaded = 0
17
19
  self.length = 40
18
20
  @percent = 0
19
21
  @start = Time.now
@@ -51,7 +53,7 @@ class SpinnerFormatter < DottedFormatter
51
53
  end
52
54
 
53
55
  def percentage
54
- @percent = @count * 100 / @total
56
+ @percent = @loaded * 100 / @total
55
57
  bar = ("=" * (@percent / @ratio)).ljust @length
56
58
  label = "%d%%" % @percent
57
59
  bar[@position, label.size] = label
@@ -69,21 +71,29 @@ class SpinnerFormatter < DottedFormatter
69
71
  end
70
72
  end
71
73
 
74
+ # Callback for the MSpec :start event. Stores the total
75
+ # number of files that will be processed.
72
76
  def start
73
77
  @total = MSpec.retrieve(:files).size
74
78
  end
75
79
 
80
+ # Callback for the MSpec :load event. Increments the number
81
+ # of files that have been loaded.
76
82
  def load
77
- @count += 1
83
+ @loaded += 1
78
84
  end
79
85
 
80
- def after(state)
81
- if state.exception?
82
- @fail_color = "31" if @counter.failures > 0
83
- @error_color = "33" if @counter.errors > 0
84
- @states << state
85
- end
86
+ # Callback for the MSpec :exception event. Changes the color
87
+ # used to display the tally of errors and failures
88
+ def exception(exception)
89
+ super
90
+ @fail_color = "31" if exception.failure?
91
+ @error_color = "33" unless exception.failure?
92
+ end
86
93
 
94
+ # Callback for the MSpec :after event. Updates the spinner
95
+ # and progress bar.
96
+ def after(state)
87
97
  spin
88
98
  end
89
99
  end
@@ -2,7 +2,10 @@ require 'mspec/expectations/expectations'
2
2
  require 'mspec/runner/formatters/dotted'
3
3
 
4
4
  class SummaryFormatter < DottedFormatter
5
+ # Callback for the MSpec :after event. Overrides the
6
+ # callback provided by +DottedFormatter+ and does not
7
+ # print any output for each example evaluated.
5
8
  def after(state)
6
- @states << state if state.exception?
9
+ # do nothing
7
10
  end
8
11
  end
@@ -5,15 +5,11 @@ class UnitdiffFormatter < DottedFormatter
5
5
  def finish
6
6
  print "\n\n#{@timer.format}\n"
7
7
  count = 0
8
- @states.each do |state|
9
- state.exceptions.each do |msg, exc|
10
- outcome = failure?(state) ? "FAILED" : "ERROR"
11
- print "\n#{count += 1})\n#{state.description} #{outcome}\n"
12
- print "Exception occurred during: #{msg}\n" if msg
13
- print((exc.message.empty? ? "<No message>" : exc.message) + ": \n")
14
- print backtrace(exc)
15
- print "\n"
16
- end
8
+ @exceptions.each do |exc|
9
+ outcome = exc.failure? ? "FAILED" : "ERROR"
10
+ print "\n#{count += 1})\n#{exc.description} #{outcome}\n"
11
+ print exc.message, ": \n"
12
+ print exc.backtrace, "\n"
17
13
  end
18
14
  print "\n#{@tally.format}\n"
19
15
  end
@@ -3,7 +3,9 @@ require 'mspec/runner/formatters/dotted'
3
3
 
4
4
  class YamlFormatter < DottedFormatter
5
5
  def initialize(out=nil)
6
- @states = []
6
+ @exception = @failure = false
7
+ @exceptions = []
8
+ @count = 0
7
9
  @out = $stdout
8
10
 
9
11
  if out.nil?
@@ -17,20 +19,19 @@ class YamlFormatter < DottedFormatter
17
19
  @out = @finish
18
20
  end
19
21
 
22
+ def after(state)
23
+ end
24
+
20
25
  def finish
21
26
  switch
22
27
 
23
28
  print "---\n"
24
29
  print "exceptions:\n"
25
- @states.each do |state|
26
- state.exceptions.each do |msg, exc|
27
- outcome = failure?(state) ? "FAILED" : "ERROR"
28
- str = "#{state.description} #{outcome}\n"
29
- str << "#{exc.class.name} occurred during: #{msg}\n" if msg
30
- str << message(exc)
31
- str << backtrace(exc)
32
- print "- ", str.inspect, "\n"
33
- end
30
+ @exceptions.each do |exc|
31
+ outcome = exc.failure? ? "FAILED" : "ERROR"
32
+ str = "#{exc.description} #{outcome}\n"
33
+ str << exc.message << "\n" << exc.backtrace
34
+ print "- ", str.inspect, "\n"
34
35
  end
35
36
 
36
37
  print "time: ", @timer.elapsed, "\n"
@@ -1,4 +1,5 @@
1
- require 'mspec/runner/state'
1
+ require 'mspec/runner/context'
2
+ require 'mspec/runner/exception'
2
3
  require 'mspec/runner/tag'
3
4
  require 'fileutils'
4
5
 
@@ -21,7 +22,7 @@ module MSpec
21
22
  @expectation = nil
22
23
 
23
24
  def self.describe(mod, msg=nil, &block)
24
- stack.push RunState.new
25
+ stack.push ContextState.new
25
26
 
26
27
  current.describe(mod, msg, &block)
27
28
  current.process
@@ -55,6 +56,17 @@ module MSpec
55
56
  actions.each { |obj| obj.send action, *args } if actions
56
57
  end
57
58
 
59
+ def self.protect(location, &block)
60
+ begin
61
+ @env.instance_eval(&block)
62
+ return true
63
+ rescue Exception => exc
64
+ register_exit 1
65
+ actions :exception, ExceptionState.new(current && current.state, location, exc)
66
+ return false
67
+ end
68
+ end
69
+
58
70
  def self.register_exit(code)
59
71
  store :exit, code
60
72
  end
@@ -97,6 +109,7 @@ module MSpec
97
109
  # :enter before a describe block is run
98
110
  # :before before a single spec is run
99
111
  # :expectation before a 'should', 'should_receive', etc.
112
+ # :exception after an exception is rescued
100
113
  # :after after a single spec is run
101
114
  # :leave after a describe block is run
102
115
  # :unload after a spec file is run
@@ -125,20 +138,6 @@ module MSpec
125
138
  end
126
139
  end
127
140
 
128
- def self.protect(msg, &block)
129
- begin
130
- @env.instance_eval(&block)
131
- rescue Exception => e
132
- register_exit 1
133
- if current and current.state
134
- current.state.exceptions << [msg, e]
135
- else
136
- STDERR.write "\nAn exception occurred in #{msg}:\n#{e.class}: #{e.message.inspect}\n"
137
- STDERR.write "#{e.backtrace.join "\n"}"
138
- end
139
- end
140
- end
141
-
142
141
  def self.stack
143
142
  @stack ||= []
144
143
  end
data/lib/mspec/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module MSpec
2
- VERSION = '1.1.1'
2
+ VERSION = '1.2.0'
3
3
  end
@@ -1,7 +1,7 @@
1
1
  require File.dirname(__FILE__) + '/../../spec_helper'
2
2
  require 'mspec/runner/actions/debug'
3
3
  require 'mspec/runner/mspec'
4
- require 'mspec/runner/state'
4
+ require 'mspec/runner/example'
5
5
 
6
6
  describe DebugAction do
7
7
  before :each do
@@ -18,7 +18,7 @@ end
18
18
  describe DebugAction, "#before" do
19
19
  before :each do
20
20
  MSpec.stub!(:read_tags).and_return([])
21
- @state = SpecState.new "Catch#me", "if you can"
21
+ @state = ExampleState.new "Catch#me", "if you can"
22
22
  end
23
23
 
24
24
  it "does not invoke the debugger if the description does not match" do
@@ -1,7 +1,7 @@
1
1
  require File.dirname(__FILE__) + '/../../spec_helper'
2
2
  require 'mspec/runner/actions/gdb'
3
3
  require 'mspec/runner/mspec'
4
- require 'mspec/runner/state'
4
+ require 'mspec/runner/example'
5
5
 
6
6
  describe GdbAction do
7
7
  before :each do
@@ -18,7 +18,7 @@ end
18
18
  describe GdbAction, "#before" do
19
19
  before :each do
20
20
  MSpec.stub!(:read_tags).and_return([])
21
- @state = SpecState.new "Catch#me", "if you can"
21
+ @state = ExampleState.new "Catch#me", "if you can"
22
22
  end
23
23
 
24
24
  it "does not invoke the debugger if the description does not match" do
@@ -1,7 +1,7 @@
1
1
  require File.dirname(__FILE__) + '/../../spec_helper'
2
2
  require 'mspec/runner/actions/tag'
3
3
  require 'mspec/runner/mspec'
4
- require 'mspec/runner/state'
4
+ require 'mspec/runner/example'
5
5
  require 'mspec/runner/tag'
6
6
 
7
7
  describe TagAction do
@@ -38,49 +38,83 @@ describe TagAction, "#===" do
38
38
  end
39
39
  end
40
40
 
41
+ describe TagAction, "#exception?" do
42
+ before :each do
43
+ @action = TagAction.new :add, :fail, nil, nil, nil, nil
44
+ end
45
+
46
+ it "returns false if no exception has been raised while evaluating an example" do
47
+ @action.exception?.should be_false
48
+ end
49
+
50
+ it "returns true if an exception was raised while evaluating an example" do
51
+ @action.exception ExceptionState.new nil, nil, Exception.new("failed")
52
+ @action.exception?.should be_true
53
+ end
54
+ end
55
+
41
56
  describe TagAction, "#outcome?" do
42
57
  before :each do
43
58
  MSpec.stub!(:read_tags).and_return([])
44
- @state = SpecState.new "describe", "it"
45
- @exception = [nil, Exception.new("failed")]
59
+ @exception = ExceptionState.new nil, nil, Exception.new("failed")
46
60
  end
47
61
 
48
62
  it "returns true if outcome is :fail and the spec fails" do
49
63
  action = TagAction.new :add, :fail, nil, nil, nil, nil
50
- @state.exceptions << @exception
51
- action.outcome?(@state).should == true
64
+ action.exception @exception
65
+ action.outcome?.should == true
52
66
  end
53
67
 
54
68
  it "returns false if the outcome is :fail and the spec passes" do
55
69
  action = TagAction.new :add, :fail, nil, nil, nil, nil
56
- action.outcome?(@state).should == false
70
+ action.outcome?.should == false
57
71
  end
58
72
 
59
73
  it "returns true if the outcome is :pass and the spec passes" do
60
74
  action = TagAction.new :del, :pass, nil, nil, nil, nil
61
- action.outcome?(@state).should == true
75
+ action.outcome?.should == true
62
76
  end
63
77
 
64
78
  it "returns false if the outcome is :pass and the spec fails" do
65
79
  action = TagAction.new :del, :pass, nil, nil, nil, nil
66
- @state.exceptions << @exception
67
- action.outcome?(@state).should == false
80
+ action.exception @exception
81
+ action.outcome?.should == false
68
82
  end
69
83
 
70
84
  it "returns true if the outcome is :all" do
71
85
  action = TagAction.new :add, :all, nil, nil, nil, nil
72
- @state.exceptions << @exception
73
- action.outcome?(@state).should == true
86
+ action.exception @exception
87
+ action.outcome?.should == true
88
+ end
89
+ end
90
+
91
+ describe TagAction, "#before" do
92
+ it "resets the #exception? flag to false" do
93
+ action = TagAction.new :add, :fail, nil, nil, nil, nil
94
+ action.exception?.should be_false
95
+ action.exception ExceptionState.new(nil, nil, Exception.new("Fail!"))
96
+ action.exception?.should be_true
97
+ action.before(ExampleState.new("describe", "it"))
98
+ action.exception?.should be_false
99
+ end
100
+ end
101
+
102
+ describe TagAction, "#exception" do
103
+ it "sets the #exception? flag" do
104
+ action = TagAction.new :add, :fail, nil, nil, nil, nil
105
+ action.exception?.should be_false
106
+ action.exception ExceptionState.new(nil, nil, Exception.new("Fail!"))
107
+ action.exception?.should be_true
74
108
  end
75
109
  end
76
110
 
77
111
  describe TagAction, "#after when action is :add" do
78
112
  before :each do
79
113
  MSpec.stub!(:read_tags).and_return([])
80
- @state = SpecState.new "Catch#me", "if you can"
114
+ @state = ExampleState.new "Catch#me", "if you can"
81
115
  @tag = SpecTag.new "tag(comment):Catch#me if you can"
82
116
  SpecTag.stub!(:new).and_return(@tag)
83
- @exception = [nil, Exception.new("failed")]
117
+ @exception = ExceptionState.new nil, nil, Exception.new("failed")
84
118
  end
85
119
 
86
120
  it "does not write a tag if the description does not match" do
@@ -98,14 +132,14 @@ describe TagAction, "#after when action is :add" do
98
132
  it "writes a tag if the outcome is :fail and the spec failed" do
99
133
  MSpec.should_receive(:write_tag).with(@tag)
100
134
  action = TagAction.new :add, :fail, "tag", "comment", nil, "can"
101
- @state.exceptions << @exception
135
+ action.exception @exception
102
136
  action.after @state
103
137
  end
104
138
 
105
139
  it "does not write a tag if outcome is :pass and the spec failed" do
106
140
  MSpec.should_not_receive(:write_tag)
107
141
  action = TagAction.new :add, :pass, "tag", "comment", nil, "can"
108
- @state.exceptions << @exception
142
+ action.exception @exception
109
143
  action.after @state
110
144
  end
111
145
 
@@ -125,10 +159,10 @@ end
125
159
  describe TagAction, "#after when action is :del" do
126
160
  before :each do
127
161
  MSpec.stub!(:read_tags).and_return([])
128
- @state = SpecState.new "Catch#me", "if you can"
162
+ @state = ExampleState.new "Catch#me", "if you can"
129
163
  @tag = SpecTag.new "tag(comment):Catch#me if you can"
130
164
  SpecTag.stub!(:new).and_return(@tag)
131
- @exception = [nil, Exception.new("failed")]
165
+ @exception = ExceptionState.new nil, nil, Exception.new("failed")
132
166
  end
133
167
 
134
168
  it "does not delete a tag if the description does not match" do
@@ -146,14 +180,14 @@ describe TagAction, "#after when action is :del" do
146
180
  it "deletes a tag if the outcome is :fail and the spec failed" do
147
181
  MSpec.should_receive(:delete_tag).with(@tag)
148
182
  action = TagAction.new :del, :fail, "tag", "comment", nil, "can"
149
- @state.exceptions << @exception
183
+ action.exception @exception
150
184
  action.after @state
151
185
  end
152
186
 
153
187
  it "does not delete a tag if outcome is :pass and the spec failed" do
154
188
  MSpec.should_not_receive(:delete_tag)
155
189
  action = TagAction.new :del, :pass, "tag", "comment", nil, "can"
156
- @state.exceptions << @exception
190
+ action.exception @exception
157
191
  action.after @state
158
192
  end
159
193
 
@@ -173,7 +207,7 @@ end
173
207
  describe TagAction, "#finish" do
174
208
  before :each do
175
209
  $stdout = @out = IOStub.new
176
- @state = SpecState.new "Catch#me", "if you can"
210
+ @state = ExampleState.new "Catch#me", "if you can"
177
211
  MSpec.stub!(:write_tag).and_return(true)
178
212
  MSpec.stub!(:delete_tag).and_return(true)
179
213
  end
@@ -232,8 +266,17 @@ describe TagAction, "#register" do
232
266
  @action = TagAction.new :add, :all, nil, nil, nil, nil
233
267
  end
234
268
 
235
- it "registers itself with MSpec for the :after action" do
269
+ it "registers itself with MSpec for the :after event" do
236
270
  MSpec.should_receive(:register).with(:after, @action)
271
+ @action.register
272
+ end
273
+
274
+ it "registers itself with MSpec for the :exception event" do
275
+ MSpec.should_receive(:register).with(:exception, @action)
276
+ @action.register
277
+ end
278
+
279
+ it "registers itself with MSpec for the :finish event" do
237
280
  MSpec.should_receive(:register).with(:finish, @action)
238
281
  @action.register
239
282
  end
@@ -246,8 +289,19 @@ describe TagAction, "#unregister" do
246
289
  @action = TagAction.new :add, :all, nil, nil, nil, nil
247
290
  end
248
291
 
249
- it "unregisters itself with MSpec for the :after action" do
292
+ it "unregisters itself with MSpec for the :after event" do
293
+ MSpec.should_receive(:unregister).with(:exception, @action)
250
294
  MSpec.should_receive(:unregister).with(:after, @action)
251
295
  @action.unregister
252
296
  end
297
+
298
+ it "unregisters itself with MSpec for the :exception event" do
299
+ MSpec.should_receive(:unregister).with(:exception, @action)
300
+ @action.unregister
301
+ end
302
+
303
+ it "unregisters itself with MSpec for the :finish event" do
304
+ MSpec.should_receive(:unregister).with(:finish, @action)
305
+ @action.unregister
306
+ end
253
307
  end