rspec-core 2.0.0.beta.7 → 2.0.0.beta.8

Sign up to get free protection for your applications and to get access to all the features.
data/VERSION CHANGED
@@ -1 +1 @@
1
- 2.0.0.beta.7
1
+ 2.0.0.beta.8
@@ -4,4 +4,4 @@ rerun_opts = rerun.to_s.strip.empty? ? "--format progress features" : "--format
4
4
  std_opts = "#{rerun_opts} --require features --format rerun --out rerun.txt --strict --tags ~@wip"
5
5
  %>
6
6
  default: <%= std_opts %>
7
- wip: --tags @wip:3 --wip features
7
+ wip: --require features --tags @wip:3 --wip features
@@ -28,8 +28,8 @@ Feature: before and after hooks
28
28
  applied to all groups or subsets of all groups defined by example group
29
29
  types.
30
30
 
31
- Scenario: define before(:each) block in example group
32
- Given a file named "before_each_in_example_group_spec.rb" with:
31
+ Scenario: define before(:each) block
32
+ Given a file named "before_each_spec.rb" with:
33
33
  """
34
34
  require "rspec/expectations"
35
35
 
@@ -59,11 +59,11 @@ Feature: before and after hooks
59
59
  end
60
60
  end
61
61
  """
62
- When I run "rspec before_each_in_example_group_spec.rb"
62
+ When I run "rspec before_each_spec.rb"
63
63
  Then I should see "3 examples, 0 failures"
64
64
 
65
65
  Scenario: define before(:all) block in example group
66
- Given a file named "before_all_in_example_group_spec.rb" with:
66
+ Given a file named "before_all_spec.rb" with:
67
67
  """
68
68
  require "rspec/expectations"
69
69
 
@@ -93,9 +93,12 @@ Feature: before and after hooks
93
93
  end
94
94
  end
95
95
  """
96
- When I run "rspec before_all_in_example_group_spec.rb"
96
+ When I run "rspec before_all_spec.rb"
97
97
  Then I should see "3 examples, 0 failures"
98
98
 
99
+ When I run "rspec before_all_spec.rb:15"
100
+ Then I should see "1 example, 0 failures"
101
+
99
102
  @wip
100
103
  Scenario: define before and after blocks in configuration
101
104
  Given a file named "befores_in_configuration_spec.rb" with:
@@ -135,21 +138,11 @@ Feature: before and after hooks
135
138
  When I run "rspec befores_in_configuration_spec.rb"
136
139
  Then I should see "3 examples, 0 failures"
137
140
 
138
- @wip
139
141
  Scenario: before/after blocks are run in order
140
142
  Given a file named "ensure_block_order_spec.rb" with:
141
143
  """
142
144
  require "rspec/expectations"
143
145
 
144
- Rspec.configure do |config|
145
- config.before(:suite) do
146
- puts "before suite"
147
- end
148
- config.after(:suite) do
149
- puts "after suite"
150
- end
151
- end
152
-
153
146
  describe "before and after callbacks" do
154
147
  before(:all) do
155
148
  puts "before all"
@@ -173,5 +166,38 @@ Feature: before and after hooks
173
166
  end
174
167
  """
175
168
  When I run "rspec ensure_block_order_spec.rb"
176
- Then I should see /before suite\nbefore all\nbefore each\nafter each\n\.after all\n.*after suite/m
169
+ Then I should see matching "before all\nbefore each\nafter each\n.after all"
170
+
171
+ @wip
172
+ Scenario: before/after all blocks are run once
173
+ Given a file named "before_and_after_all_spec.rb" with:
174
+ """
175
+ describe "before and after callbacks" do
176
+ before(:all) do
177
+ puts "before all"
178
+ end
179
+
180
+ after(:all) do
181
+ puts "after all"
182
+ end
183
+
184
+ example "in outer group" do
185
+
186
+ end
187
+
188
+ describe "nested group" do
189
+
190
+ example "in nested group" do
191
+
192
+ end
193
+
194
+ end
195
+
196
+ end
197
+ """
198
+ When I run "rspec before_and_after_all_spec.rb:16"
199
+ Then I should see matching "before all\n.after all"
200
+
201
+ When I run "rspec before_and_after_all_spec.rb"
202
+ Then I should see matching "before all\n..after all"
177
203
 
@@ -1,4 +1,3 @@
1
- @wip
2
1
  Feature: pending examples
3
2
 
4
3
  Rspec offers three ways to indicate that an example is disabled pending
@@ -8,10 +7,10 @@ Feature: pending examples
8
7
  Given a file named "example_without_block_spec.rb" with:
9
8
  """
10
9
  describe "an example" do
11
- it "has not yet been implemented"
10
+ it "is a pending example"
12
11
  end
13
12
  """
14
- When I run "spec example_without_block_spec.rb"
13
+ When I run "rspec example_without_block_spec.rb"
15
14
  Then the exit status should be 0
16
15
  And I should see "1 example, 0 failures, 1 pending"
17
16
  And I should see "Not Yet Implemented"
@@ -23,10 +22,11 @@ Feature: pending examples
23
22
  describe "an example" do
24
23
  it "is implemented but waiting" do
25
24
  pending("something else getting finished")
25
+ this_should_not_get_executed
26
26
  end
27
27
  end
28
28
  """
29
- When I run "spec pending_without_block_spec.rb"
29
+ When I run "rspec pending_without_block_spec.rb"
30
30
  Then the exit status should be 0
31
31
  And I should see "1 example, 0 failures, 1 pending"
32
32
  And I should see "(something else getting finished)"
@@ -43,7 +43,7 @@ Feature: pending examples
43
43
  end
44
44
  end
45
45
  """
46
- When I run "spec pending_with_failing_block_spec.rb"
46
+ When I run "rspec pending_with_failing_block_spec.rb"
47
47
  Then the exit status should be 0
48
48
  And I should see "1 example, 0 failures, 1 pending"
49
49
  And I should see "(something else getting finished)"
@@ -60,7 +60,7 @@ Feature: pending examples
60
60
  end
61
61
  end
62
62
  """
63
- When I run "spec pending_with_passing_block_spec.rb"
63
+ When I run "rspec pending_with_passing_block_spec.rb"
64
64
  Then the exit status should not be 0
65
65
  And I should see "1 example, 1 failure"
66
66
  And I should see "FIXED"
@@ -34,19 +34,18 @@ Feature: explicit subject
34
34
  When I run "rspec nested_subject_spec.rb"
35
35
  Then I should see "1 example, 0 failures"
36
36
 
37
- @wip
38
37
  Scenario: access subject from before block
39
38
  Given a file named "top_level_subject_spec.rb" with:
40
39
  """
41
40
  describe Array, "with some elements" do
42
41
  subject { [] }
43
- before { subject += [1,2,3] }
42
+ before { subject.push(1,2,3) }
44
43
  it "should have the prescribed elements" do
45
44
  subject.should == [1,2,3]
46
45
  end
47
46
  end
48
47
  """
49
- When I run "spec top_level_subject_spec.rb"
48
+ When I run "rspec top_level_subject_spec.rb"
50
49
  Then I should see "1 example, 0 failures"
51
50
 
52
51
  Scenario: subject using helper method
@@ -7,8 +7,6 @@ Feature: implicit subject
7
7
  Scenario: subject in top level group
8
8
  Given a file named "top_level_subject_spec.rb" with:
9
9
  """
10
- require 'rspec/expectations'
11
-
12
10
  describe Array, "when first created" do
13
11
  it "should be empty" do
14
12
  subject.should == []
@@ -21,8 +19,6 @@ Feature: implicit subject
21
19
  Scenario: subject in a nested group
22
20
  Given a file named "nested_subject_spec.rb" with:
23
21
  """
24
- require 'rspec/expectations'
25
-
26
22
  describe Array do
27
23
  describe "when first created" do
28
24
  it "should be empty" do
@@ -5,7 +5,7 @@ require 'aruba'
5
5
  module ArubaOverrides
6
6
  def detect_ruby_script(cmd)
7
7
  if cmd =~ /^rspec /
8
- "ruby -I../../lib -S ../../bin/#{cmd}"
8
+ "ruby -I. -I../../lib -S ../../bin/#{cmd}"
9
9
  else
10
10
  super(cmd)
11
11
  end
@@ -5,6 +5,7 @@ require 'rspec/core/hooks'
5
5
  require 'rspec/core/subject'
6
6
  require 'rspec/core/let'
7
7
  require 'rspec/core/metadata'
8
+ require 'rspec/core/pending'
8
9
 
9
10
  require 'rspec/core/around_proxy'
10
11
  require 'rspec/core/world'
@@ -18,6 +19,7 @@ require 'rspec/core/example_group'
18
19
  require 'rspec/core/formatters'
19
20
  require 'rspec/core/backward_compatibility'
20
21
  require 'rspec/core/version'
22
+ require 'rspec/core/errors'
21
23
 
22
24
  module Rspec
23
25
  module Core
@@ -0,0 +1,14 @@
1
+ module Rspec
2
+ module Core
3
+ # If Test::Unit is loaed, we'll use its error as baseclass, so that Test::Unit
4
+ # will report unmet RSpec expectations as failures rather than errors.
5
+ superclass = ['Test::Unit::AssertionFailedError', '::StandardError'].map do |c|
6
+ eval(c) rescue nil
7
+ end.compact.first
8
+
9
+ class PendingExampleFixedError < superclass
10
+ end
11
+ end
12
+ end
13
+
14
+
@@ -4,55 +4,90 @@ module Rspec
4
4
 
5
5
  attr_reader :metadata, :example_block
6
6
 
7
- def example_group
8
- @example_group_class
7
+ def self.delegate_to_metadata(*keys)
8
+ keys.each do |key|
9
+ define_method(key) {@metadata[key]}
10
+ end
9
11
  end
10
12
 
11
- alias_method :behaviour, :example_group
13
+ delegate_to_metadata :description, :full_description, :execution_result, :file_path, :pending
14
+
15
+ alias_method :inspect, :full_description
16
+ alias_method :to_s, :full_description
12
17
 
13
18
  def initialize(example_group_class, desc, options, example_block=nil)
14
19
  @example_group_class, @options, @example_block = example_group_class, options, example_block
15
20
  @metadata = @example_group_class.metadata.for_example(desc, options)
16
21
  end
17
22
 
18
- def description
19
- @metadata[:description]
23
+ def example_group
24
+ @example_group_class
20
25
  end
21
26
 
22
- def record_results(results={})
23
- @metadata[:execution_result].update(results)
24
- end
27
+ alias_method :behaviour, :example_group
25
28
 
26
- def execution_result
27
- @metadata[:execution_result]
28
- end
29
+ def run(example_group_instance, reporter)
30
+ @example_group_instance = example_group_instance
31
+ @example_group_instance.running_example = self
29
32
 
30
- def file_path
31
- @metadata[:file_path] || example_group.file_path
32
- end
33
+ run_started
33
34
 
34
- def inspect
35
- @metadata[:full_description]
36
- end
35
+ exception = nil
36
+
37
+ begin
38
+ run_before_each
39
+ pending_declared_in_example = catch(:pending_declared_in_example) do
40
+ if @example_group_class.around_eachs.empty?
41
+ @example_group_instance.instance_eval(&example_block) unless pending
42
+ else
43
+ @example_group_class.around_eachs.first.call(AroundProxy.new(self, &example_block))
44
+ end
45
+ throw :pending_declared_in_example, false
46
+ end
47
+ rescue Exception => e
48
+ exception = e
49
+ ensure
50
+ assign_auto_description
51
+ end
52
+
53
+ begin
54
+ run_after_each
55
+ rescue Exception => e
56
+ exception ||= e
57
+ ensure
58
+ @example_group_instance.running_example = nil
59
+ end
37
60
 
38
- def to_s
39
- inspect
61
+ if exception
62
+ run_failed(reporter, exception)
63
+ elsif pending_declared_in_example
64
+ run_pending(reporter, pending_declared_in_example)
65
+ elsif pending
66
+ run_pending(reporter, 'Not Yet Implemented')
67
+ else
68
+ run_passed(reporter)
69
+ end
40
70
  end
41
71
 
72
+ private
73
+
42
74
  def run_started
43
75
  record_results :started_at => Time.now
44
76
  end
45
77
 
46
78
  def run_passed(reporter=nil)
47
79
  run_finished reporter, 'passed'
80
+ true
48
81
  end
49
82
 
50
- def run_pending(reporter=nil, message='Not yet implemented')
83
+ def run_pending(reporter, message)
51
84
  run_finished reporter, 'pending', :pending_message => message
85
+ true
52
86
  end
53
87
 
54
88
  def run_failed(reporter, exception)
55
89
  run_finished reporter, 'failed', :exception_encountered => exception
90
+ false
56
91
  end
57
92
 
58
93
  def run_finished(reporter, status, results={})
@@ -81,52 +116,10 @@ module Rspec
81
116
  end
82
117
  end
83
118
 
84
- def runnable?
85
- !metadata[:pending]
86
- end
87
-
88
- def run(example_group_instance, reporter)
89
- @example_group_instance = example_group_instance
90
- @example_group_instance.running_example = self
91
-
92
- run_started
93
-
94
- all_systems_nominal = true
95
- exception_encountered = nil
96
-
97
- begin
98
- run_before_each
99
- if @example_group_class.around_eachs.empty?
100
- @example_group_instance.instance_eval(&example_block) if runnable?
101
- else
102
- @example_group_class.around_eachs.first.call(AroundProxy.new(self, &example_block))
103
- end
104
- rescue Exception => e
105
- exception_encountered = e
106
- all_systems_nominal = false
107
- end
108
-
109
- assign_auto_description
110
-
111
- begin
112
- run_after_each
113
- rescue Exception => e
114
- exception_encountered ||= e
115
- all_systems_nominal = false
116
- ensure
117
- @example_group_instance.running_example = nil
118
- end
119
-
120
- if exception_encountered
121
- run_failed(reporter, exception_encountered)
122
- else
123
- runnable? ? run_passed(reporter) : run_pending(reporter)
124
- end
125
-
126
- all_systems_nominal
119
+ def record_results(results={})
120
+ execution_result.update(results)
127
121
  end
128
122
 
129
123
  end
130
-
131
124
  end
132
125
  end
@@ -4,6 +4,7 @@ module Rspec
4
4
  extend Hooks
5
5
  include Subject
6
6
  include Let
7
+ include Pending
7
8
 
8
9
  attr_accessor :running_example
9
10
 
@@ -12,9 +13,21 @@ module Rspec
12
13
  Rspec::Core.world.example_groups << klass
13
14
  end
14
15
 
16
+ class << self
17
+ def self.delegate_to_metadata(*names)
18
+ names.each do |name|
19
+ define_method name do
20
+ metadata[:example_group][name]
21
+ end
22
+ end
23
+ end
24
+
25
+ delegate_to_metadata :description, :describes, :file_path
26
+ alias_method :display_name, :description
27
+ end
28
+
15
29
  def self.extended_modules #:nodoc:
16
- ancestors = class << self; ancestors end
17
- ancestors.select { |mod| mod.class == Module } - [ Object, Kernel ]
30
+ @extended_modules ||= ancestors.select { |mod| mod.class == Module } - [ Object, Kernel ]
18
31
  end
19
32
 
20
33
  def self.define_example_method(name, extra_options={})
@@ -24,6 +37,7 @@ module Rspec
24
37
  options.update(:caller => caller)
25
38
  options.update(#{extra_options.inspect})
26
39
  examples << Rspec::Core::Example.new(self, desc, options, block)
40
+ examples.last
27
41
  end
28
42
  END_RUBY
29
43
  end
@@ -82,69 +96,34 @@ module Rspec
82
96
  @metadata
83
97
  end
84
98
 
85
- def self.display_name
86
- metadata[:example_group][:description]
87
- end
88
-
89
- def self.description
90
- metadata[:example_group][:description]
91
- end
92
-
93
- def self.describes
94
- metadata[:example_group][:describes]
95
- end
96
-
97
- def self.file_path
98
- metadata[:example_group][:file_path]
99
- end
100
-
101
99
  def self.describe(*args, &example_group_block)
102
- raise(ArgumentError, "No arguments given. You must a least supply a type or description") if args.empty?
103
- raise(ArgumentError, "You must supply a block when calling describe") if example_group_block.nil?
104
100
  @_subclass_count ||= 0
105
101
  @_subclass_count += 1
102
+ args << {} unless args.last.is_a?(Hash)
103
+ args.last.update(:example_group_block => example_group_block)
104
+ args.last.update(:caller => caller)
105
+ args.unshift Rspec.configuration unless args.first.is_a?(Rspec::Core::Configuration)
106
106
  const_set(
107
107
  "Nested_#{@_subclass_count}",
108
- _build(Class.new(self), caller, args, &example_group_block)
108
+ subclass(self, args, &example_group_block)
109
109
  )
110
110
  end
111
111
 
112
- def self.create(*args, &example_group_block)
113
- _build(dup, caller, args, &example_group_block)
112
+ def self.subclass(parent, args, &example_group_block)
113
+ subclass = Class.new(parent)
114
+ subclass.set_it_up(*args)
115
+ subclass.module_eval(&example_group_block) if example_group_block
116
+ subclass
114
117
  end
115
118
 
116
- def self._build(klass, given_caller, args, &example_group_block)
117
- args << {} unless args.last.is_a?(Hash)
118
- args.last.update(:example_group_block => example_group_block, :caller => given_caller)
119
- args.unshift Rspec.configuration unless args.first.is_a?(Rspec::Core::Configuration)
120
- klass.set_it_up(*args)
121
- klass.module_eval(&example_group_block) if example_group_block
122
- klass
119
+ def self.ancestors
120
+ @_ancestors ||= super().select {|a| a < Rspec::Core::ExampleGroup}
123
121
  end
124
122
 
125
123
  class << self
126
124
  alias_method :context, :describe
127
125
  end
128
126
 
129
- def self.ancestors(superclass_last=false)
130
- current_class = self
131
-
132
- classes = []
133
- while current_class < Rspec::Core::ExampleGroup
134
- superclass_last ? classes << current_class : classes.unshift(current_class)
135
- current_class = current_class.superclass
136
- end
137
- classes
138
- end
139
-
140
- def self.before_ancestors
141
- @_before_ancestors ||= ancestors
142
- end
143
-
144
- def self.after_ancestors
145
- @_after_ancestors ||= ancestors(true)
146
- end
147
-
148
127
  def self.before_all_ivars
149
128
  @before_all_ivars ||= {}
150
129
  end
@@ -155,43 +134,55 @@ module Rspec
155
134
  end
156
135
  configuration.find_hook(:before, :all, self).each { |blk| running_example.instance_eval(&blk) }
157
136
 
158
- before_alls.each { |blk| running_example.instance_eval(&blk) }
137
+ ancestors.reverse.each do |ancestor|
138
+ until ancestor.before_alls.empty?
139
+ running_example.instance_eval &ancestor.before_alls.shift
140
+ end
141
+ end
159
142
  running_example.instance_variables.each { |ivar| before_all_ivars[ivar] = running_example.instance_variable_get(ivar) }
160
143
  end
161
144
 
162
145
  def self.eval_before_eachs(running_example)
163
146
  configuration.find_hook(:before, :each, self).each { |blk| running_example.instance_eval(&blk) }
164
- before_ancestors.each { |ancestor| ancestor.before_eachs.each { |blk| running_example.instance_eval(&blk) } }
147
+ ancestors.reverse.each { |ancestor| ancestor.before_eachs.each { |blk| running_example.instance_eval(&blk) } }
148
+ end
149
+
150
+ def self.eval_after_eachs(running_example)
151
+ ancestors.each { |ancestor| ancestor.after_eachs.each { |blk| running_example.instance_eval(&blk) } }
152
+ configuration.find_hook(:after, :each, self).each { |blk| running_example.instance_eval(&blk) }
165
153
  end
166
154
 
167
155
  def self.eval_after_alls(running_example)
168
- after_alls.each { |blk| running_example.instance_eval(&blk) }
156
+ ancestors.each do |ancestor|
157
+ after_alls = ancestor.after_alls.dup
158
+ until after_alls.empty?
159
+ running_example.instance_eval &after_alls.shift
160
+ end
161
+ end
169
162
  configuration.find_hook(:after, :all, self).each { |blk| running_example.instance_eval(&blk) }
170
163
  before_all_ivars.keys.each { |ivar| before_all_ivars[ivar] = running_example.instance_variable_get(ivar) }
171
164
  end
172
165
 
173
- def self.eval_after_eachs(running_example)
174
- after_ancestors.each { |ancestor| ancestor.after_eachs.each { |blk| running_example.instance_eval(&blk) } }
175
- configuration.find_hook(:after, :each, self).each { |blk| running_example.instance_eval(&blk) }
176
- end
177
-
178
166
  def self.run(reporter)
179
167
  example_group_instance = new
180
168
  reporter.add_example_group(self)
181
- eval_before_alls(example_group_instance)
182
- success = run_examples(example_group_instance, reporter)
183
- eval_after_alls(example_group_instance)
184
-
185
- success
169
+ begin
170
+ eval_before_alls(example_group_instance)
171
+ run_examples(example_group_instance, reporter)
172
+ ensure
173
+ eval_after_alls(example_group_instance)
174
+ end
186
175
  end
187
176
 
188
177
  # Runs all examples, returning true only if all of them pass
189
178
  def self.run_examples(instance, reporter)
190
179
  examples_to_run.map do |example|
191
- success = example.run(instance, reporter)
192
- instance.__reset__
193
- before_all_ivars.each {|k, v| instance.instance_variable_set(k, v)}
194
- success
180
+ begin
181
+ example.run(instance, reporter)
182
+ ensure
183
+ instance.__reset__
184
+ before_all_ivars.each {|k, v| instance.instance_variable_set(k, v)}
185
+ end
195
186
  end.all?
196
187
  end
197
188
 
@@ -208,6 +199,10 @@ module Rspec
208
199
  examples.collect {|e| e.metadata[:line_number]}
209
200
  end
210
201
 
202
+ def self.top_level_description
203
+ ancestors.last.description
204
+ end
205
+
211
206
  def described_class
212
207
  self.class.describes
213
208
  end