rspec-core 2.0.0.beta.22 → 2.6.4
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.
- data/.gitignore +1 -0
- data/.rspec +0 -1
- data/.travis.yml +9 -0
- data/Changelog.md +305 -0
- data/Gemfile +45 -20
- data/Guardfile +5 -0
- data/License.txt +2 -1
- data/{README.markdown → README.md} +23 -5
- data/Rakefile +63 -32
- data/bin/autospec +13 -0
- data/bin/rspec +24 -2
- data/cucumber.yml +1 -1
- data/features/.nav +57 -0
- data/features/Autotest.md +38 -0
- data/features/README.md +17 -0
- data/features/Upgrade.md +320 -0
- data/features/command_line/README.md +28 -0
- data/features/command_line/configure.feature +18 -15
- data/features/command_line/example_name_option.feature +37 -23
- data/features/command_line/exit_status.feature +16 -31
- data/features/command_line/format_option.feature +73 -0
- data/features/command_line/line_number_appended_to_path.feature +25 -27
- data/features/command_line/line_number_option.feature +11 -10
- data/features/command_line/rake_task.feature +68 -0
- data/features/command_line/tag.feature +90 -0
- data/features/configuration/alias_example_to.feature +48 -0
- data/features/configuration/custom_settings.feature +8 -10
- data/features/configuration/fail_fast.feature +77 -0
- data/features/configuration/read_options_from_file.feature +42 -26
- data/features/example_groups/basic_structure.feature +55 -0
- data/features/example_groups/shared_context.feature +74 -0
- data/features/example_groups/shared_example_group.feature +56 -41
- data/features/expectation_framework_integration/configure_expectation_framework.feature +73 -0
- data/features/filtering/exclusion_filters.feature +69 -9
- data/features/filtering/if_and_unless.feature +168 -0
- data/features/filtering/inclusion_filters.feature +58 -26
- data/features/filtering/run_all_when_everything_filtered.feature +46 -0
- data/features/formatters/custom_formatter.feature +17 -13
- data/features/formatters/text_formatter.feature +43 -0
- data/features/helper_methods/arbitrary_methods.feature +40 -0
- data/features/helper_methods/let.feature +50 -0
- data/features/helper_methods/modules.feature +149 -0
- data/features/hooks/around_hooks.feature +99 -69
- data/features/hooks/before_and_after_hooks.feature +74 -40
- data/features/hooks/filtering.feature +227 -0
- data/features/metadata/current_example.feature +17 -0
- data/features/metadata/described_class.feature +17 -0
- data/features/metadata/user_defined.feature +111 -0
- data/features/mock_framework_integration/use_any_framework.feature +106 -0
- data/features/mock_framework_integration/use_flexmock.feature +84 -11
- data/features/mock_framework_integration/use_mocha.feature +85 -11
- data/features/mock_framework_integration/use_rr.feature +86 -11
- data/features/mock_framework_integration/use_rspec.feature +85 -11
- data/features/pending/pending_examples.feature +143 -5
- data/features/spec_files/arbitrary_file_suffix.feature +2 -2
- data/features/step_definitions/additional_cli_steps.rb +30 -0
- data/features/subject/attribute_of_subject.feature +93 -15
- data/features/subject/explicit_subject.feature +28 -17
- data/features/subject/implicit_receiver.feature +29 -0
- data/features/subject/implicit_subject.feature +9 -10
- data/features/support/env.rb +6 -1
- data/lib/autotest/discover.rb +1 -0
- data/lib/autotest/rspec2.rb +15 -11
- data/lib/rspec/autorun.rb +2 -0
- data/lib/rspec/core/backward_compatibility.rb +32 -3
- data/lib/rspec/core/command_line.rb +4 -28
- data/lib/rspec/core/command_line_configuration.rb +16 -16
- data/lib/rspec/core/configuration.rb +286 -89
- data/lib/rspec/core/configuration_options.rb +74 -40
- data/lib/rspec/core/deprecation.rb +1 -1
- data/lib/rspec/core/drb_command_line.rb +5 -11
- data/lib/rspec/core/dsl.rb +11 -0
- data/lib/rspec/core/example.rb +63 -39
- data/lib/rspec/core/example_group.rb +109 -59
- data/lib/rspec/core/expecting/with_rspec.rb +9 -0
- data/lib/rspec/core/expecting/with_stdlib.rb +9 -0
- data/lib/rspec/core/extensions/kernel.rb +1 -1
- data/lib/rspec/core/extensions.rb +0 -1
- data/lib/rspec/core/formatters/base_formatter.rb +30 -15
- data/lib/rspec/core/formatters/base_text_formatter.rb +68 -40
- data/lib/rspec/core/formatters/documentation_formatter.rb +4 -2
- data/lib/rspec/core/formatters/helpers.rb +0 -4
- data/lib/rspec/core/formatters/html_formatter.rb +146 -41
- data/lib/rspec/core/formatters/progress_formatter.rb +1 -0
- data/lib/rspec/core/formatters/snippet_extractor.rb +1 -1
- data/lib/rspec/core/formatters/text_mate_formatter.rb +3 -1
- data/lib/rspec/core/hooks.rb +56 -17
- data/lib/rspec/core/metadata.rb +75 -64
- data/lib/rspec/core/metadata_hash_builder.rb +93 -0
- data/lib/rspec/core/mocking/with_flexmock.rb +2 -0
- data/lib/rspec/core/mocking/with_mocha.rb +2 -0
- data/lib/rspec/core/mocking/with_rr.rb +2 -0
- data/lib/rspec/core/mocking/with_rspec.rb +3 -1
- data/lib/rspec/core/option_parser.rb +49 -7
- data/lib/rspec/core/pending.rb +22 -4
- data/lib/rspec/core/rake_task.rb +64 -28
- data/lib/rspec/core/reporter.rb +6 -5
- data/lib/rspec/core/ruby_project.rb +2 -2
- data/lib/rspec/core/runner.rb +50 -6
- data/lib/rspec/core/shared_context.rb +16 -0
- data/lib/rspec/core/shared_example_group.rb +19 -4
- data/lib/rspec/core/subject.rb +92 -65
- data/lib/rspec/core/version.rb +1 -1
- data/lib/rspec/core/world.rb +85 -27
- data/lib/rspec/core.rb +55 -24
- data/lib/rspec/monkey/spork/test_framework/rspec.rb +1 -0
- data/rspec-core.gemspec +4 -25
- data/script/FullBuildRakeFile +63 -0
- data/script/cucumber +1 -0
- data/script/full_build +1 -0
- data/script/spec +1 -0
- data/spec/autotest/discover_spec.rb +19 -0
- data/spec/autotest/failed_results_re_spec.rb +25 -9
- data/spec/autotest/rspec_spec.rb +32 -41
- data/spec/rspec/core/command_line_spec.rb +62 -7
- data/spec/rspec/core/configuration_options_spec.rb +216 -148
- data/spec/rspec/core/configuration_spec.rb +419 -108
- data/spec/rspec/core/deprecations_spec.rb +38 -1
- data/spec/rspec/core/drb_command_line_spec.rb +21 -56
- data/spec/rspec/core/example_group_spec.rb +366 -127
- data/spec/rspec/core/example_spec.rb +125 -45
- data/spec/rspec/core/formatters/base_formatter_spec.rb +61 -1
- data/spec/rspec/core/formatters/base_text_formatter_spec.rb +134 -97
- data/spec/rspec/core/formatters/documentation_formatter_spec.rb +7 -6
- data/spec/rspec/core/formatters/helpers_spec.rb +1 -1
- data/spec/rspec/core/formatters/html_formatted-1.8.6.html +199 -81
- data/spec/rspec/core/formatters/html_formatted-1.8.7-jruby.html +195 -83
- data/spec/rspec/core/formatters/html_formatted-1.8.7.html +199 -81
- data/spec/rspec/core/formatters/html_formatted-1.9.1.html +206 -81
- data/spec/rspec/core/formatters/html_formatted-1.9.2.html +206 -61
- data/spec/rspec/core/formatters/html_formatter_spec.rb +17 -9
- data/spec/rspec/core/formatters/progress_formatter_spec.rb +1 -1
- data/spec/rspec/core/formatters/text_mate_formatted-1.8.6.html +199 -81
- data/spec/rspec/core/formatters/text_mate_formatted-1.8.7-jruby.html +195 -81
- data/spec/rspec/core/formatters/text_mate_formatted-1.8.7.html +199 -81
- data/spec/rspec/core/formatters/text_mate_formatted-1.9.1.html +206 -81
- data/spec/rspec/core/formatters/text_mate_formatted-1.9.2.html +206 -81
- data/spec/rspec/core/formatters/text_mate_formatter_spec.rb +22 -7
- data/spec/rspec/core/hooks_filtering_spec.rb +128 -5
- data/spec/rspec/core/hooks_spec.rb +90 -4
- data/spec/rspec/core/metadata_spec.rb +176 -163
- data/spec/rspec/core/option_parser_spec.rb +73 -6
- data/spec/rspec/core/pending_example_spec.rb +137 -35
- data/spec/rspec/core/rake_task_spec.rb +62 -29
- data/spec/rspec/core/reporter_spec.rb +20 -4
- data/spec/rspec/core/resources/formatter_specs.rb +25 -1
- data/spec/rspec/core/rspec_matchers_spec.rb +45 -0
- data/spec/rspec/core/runner_spec.rb +60 -10
- data/spec/rspec/core/shared_context_spec.rb +30 -0
- data/spec/rspec/core/shared_example_group_spec.rb +59 -23
- data/spec/rspec/core/subject_spec.rb +136 -0
- data/spec/rspec/core/world_spec.rb +211 -68
- data/spec/rspec/core_spec.rb +28 -0
- data/spec/spec_helper.rb +41 -24
- data/spec/support/matchers.rb +44 -13
- data/spec/support/shared_example_groups.rb +41 -0
- data/spec/support/spec_files.rb +44 -0
- data/spec.txt +1126 -0
- metadata +100 -170
- data/.treasure_map.rb +0 -23
- data/History.md +0 -30
- data/Upgrade.markdown +0 -150
- data/autotest/discover.rb +0 -2
- data/features/README.markdown +0 -12
- data/features/example_groups/describe_aliases.feature +0 -25
- data/features/example_groups/nested_groups.feature +0 -44
- data/features/hooks/described_class.feature +0 -14
- data/features/hooks/halt.feature +0 -26
- data/lib/rspec/core/around_proxy.rb +0 -14
- data/lib/rspec/core/extensions/object.rb +0 -15
- data/lib/rspec/core/formatters.rb +0 -8
- data/spec/ruby_forker.rb +0 -13
- data/specs.watchr +0 -59
|
@@ -11,18 +11,12 @@ module RSpec
|
|
|
11
11
|
|
|
12
12
|
def run(err, out)
|
|
13
13
|
begin
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
DRb.start_service("druby://:0")
|
|
18
|
-
end
|
|
19
|
-
spec_server = DRbObject.new_with_uri("druby://127.0.0.1:#{drb_port}")
|
|
20
|
-
spec_server.run(@options.drb_argv, err, out)
|
|
21
|
-
true
|
|
22
|
-
rescue DRb::DRbConnError
|
|
23
|
-
err.puts "No DRb server is running. Running in local process instead ..."
|
|
24
|
-
false
|
|
14
|
+
DRb.start_service("druby://localhost:0")
|
|
15
|
+
rescue SocketError, Errno::EADDRNOTAVAIL
|
|
16
|
+
DRb.start_service("druby://:0")
|
|
25
17
|
end
|
|
18
|
+
spec_server = DRbObject.new_with_uri("druby://127.0.0.1:#{drb_port}")
|
|
19
|
+
spec_server.run(@options.drb_argv, err, out)
|
|
26
20
|
end
|
|
27
21
|
end
|
|
28
22
|
end
|
data/lib/rspec/core/example.rb
CHANGED
|
@@ -2,7 +2,7 @@ module RSpec
|
|
|
2
2
|
module Core
|
|
3
3
|
class Example
|
|
4
4
|
|
|
5
|
-
attr_reader :metadata, :options
|
|
5
|
+
attr_reader :metadata, :options, :example_group_instance
|
|
6
6
|
|
|
7
7
|
def self.delegate_to_metadata(*keys)
|
|
8
8
|
keys.each do |key|
|
|
@@ -10,34 +10,31 @@ module RSpec
|
|
|
10
10
|
end
|
|
11
11
|
end
|
|
12
12
|
|
|
13
|
-
delegate_to_metadata :description, :full_description, :execution_result, :file_path, :pending
|
|
13
|
+
delegate_to_metadata :description, :full_description, :execution_result, :file_path, :pending, :location
|
|
14
14
|
|
|
15
15
|
def initialize(example_group_class, desc, options, example_block=nil)
|
|
16
16
|
@example_group_class, @options, @example_block = example_group_class, options, example_block
|
|
17
17
|
@metadata = @example_group_class.metadata.for_example(desc, options)
|
|
18
18
|
@exception = nil
|
|
19
|
-
@pending_declared_in_example =
|
|
19
|
+
@pending_declared_in_example = false
|
|
20
20
|
end
|
|
21
21
|
|
|
22
22
|
def example_group
|
|
23
23
|
@example_group_class
|
|
24
24
|
end
|
|
25
25
|
|
|
26
|
-
def
|
|
27
|
-
|
|
28
|
-
example_group
|
|
26
|
+
def around_hooks
|
|
27
|
+
@around_hooks ||= example_group.around_hooks_for(self)
|
|
29
28
|
end
|
|
30
29
|
|
|
31
|
-
def
|
|
32
|
-
@
|
|
30
|
+
def apply?(predicate, filters)
|
|
31
|
+
@metadata.apply?(predicate, filters) ||
|
|
32
|
+
@example_group_class.apply?(predicate, filters)
|
|
33
33
|
end
|
|
34
34
|
|
|
35
|
-
|
|
36
|
-
!!pending
|
|
37
|
-
end
|
|
35
|
+
alias_method :pending?, :pending
|
|
38
36
|
|
|
39
37
|
def run(example_group_instance, reporter)
|
|
40
|
-
return if RSpec.wants_to_quit
|
|
41
38
|
@example_group_instance = example_group_instance
|
|
42
39
|
@example_group_instance.example = self
|
|
43
40
|
|
|
@@ -45,26 +42,32 @@ module RSpec
|
|
|
45
42
|
|
|
46
43
|
begin
|
|
47
44
|
unless pending
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
run_after_each
|
|
59
|
-
end
|
|
45
|
+
with_around_hooks do
|
|
46
|
+
begin
|
|
47
|
+
run_before_each
|
|
48
|
+
@example_group_instance.instance_eval(&@example_block)
|
|
49
|
+
rescue Pending::PendingDeclaredInExample => e
|
|
50
|
+
@pending_declared_in_example = e.message
|
|
51
|
+
rescue Exception => e
|
|
52
|
+
set_exception(e)
|
|
53
|
+
ensure
|
|
54
|
+
run_after_each
|
|
60
55
|
end
|
|
61
56
|
end
|
|
62
57
|
end
|
|
63
58
|
rescue Exception => e
|
|
64
59
|
set_exception(e)
|
|
65
60
|
ensure
|
|
66
|
-
@example_group_instance.
|
|
67
|
-
|
|
61
|
+
@example_group_instance.instance_variables.each do |ivar|
|
|
62
|
+
@example_group_instance.instance_variable_set(ivar, nil)
|
|
63
|
+
end
|
|
64
|
+
@example_group_instance = nil
|
|
65
|
+
|
|
66
|
+
begin
|
|
67
|
+
assign_auto_description
|
|
68
|
+
rescue Exception => e
|
|
69
|
+
set_exception(e)
|
|
70
|
+
end
|
|
68
71
|
end
|
|
69
72
|
|
|
70
73
|
finish(reporter)
|
|
@@ -80,17 +83,31 @@ module RSpec
|
|
|
80
83
|
finish(reporter)
|
|
81
84
|
end
|
|
82
85
|
|
|
83
|
-
|
|
86
|
+
def self.procsy(metadata, &block)
|
|
87
|
+
Proc.new(&block).extend(Procsy).with(metadata)
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
module Procsy
|
|
91
|
+
attr_reader :metadata
|
|
84
92
|
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
93
|
+
def self.extended(object)
|
|
94
|
+
def object.run; call; end
|
|
95
|
+
end
|
|
96
|
+
|
|
97
|
+
def with(metadata)
|
|
98
|
+
@metadata = metadata
|
|
99
|
+
self
|
|
89
100
|
end
|
|
90
101
|
end
|
|
91
102
|
|
|
92
|
-
|
|
93
|
-
|
|
103
|
+
private
|
|
104
|
+
|
|
105
|
+
def with_around_hooks(&block)
|
|
106
|
+
if around_hooks.empty?
|
|
107
|
+
yield
|
|
108
|
+
else
|
|
109
|
+
@example_group_class.eval_around_eachs(self, Example.procsy(metadata, &block)).call
|
|
110
|
+
end
|
|
94
111
|
end
|
|
95
112
|
|
|
96
113
|
def start(reporter)
|
|
@@ -100,7 +117,7 @@ module RSpec
|
|
|
100
117
|
|
|
101
118
|
def finish(reporter)
|
|
102
119
|
if @exception
|
|
103
|
-
record_finished 'failed', :
|
|
120
|
+
record_finished 'failed', :exception => @exception
|
|
104
121
|
reporter.example_failed self
|
|
105
122
|
false
|
|
106
123
|
elsif @pending_declared_in_example
|
|
@@ -125,20 +142,27 @@ module RSpec
|
|
|
125
142
|
|
|
126
143
|
def run_before_each
|
|
127
144
|
@example_group_instance.setup_mocks_for_rspec if @example_group_instance.respond_to?(:setup_mocks_for_rspec)
|
|
128
|
-
@example_group_class.eval_before_eachs(
|
|
145
|
+
@example_group_class.eval_before_eachs(self)
|
|
129
146
|
end
|
|
130
147
|
|
|
131
148
|
def run_after_each
|
|
132
|
-
@example_group_class.eval_after_eachs(
|
|
149
|
+
@example_group_class.eval_after_eachs(self)
|
|
133
150
|
@example_group_instance.verify_mocks_for_rspec if @example_group_instance.respond_to?(:verify_mocks_for_rspec)
|
|
134
151
|
ensure
|
|
135
152
|
@example_group_instance.teardown_mocks_for_rspec if @example_group_instance.respond_to?(:teardown_mocks_for_rspec)
|
|
136
153
|
end
|
|
137
154
|
|
|
138
155
|
def assign_auto_description
|
|
139
|
-
if description.empty?
|
|
140
|
-
|
|
141
|
-
|
|
156
|
+
if description.empty? and !pending?
|
|
157
|
+
if RSpec.configuration.expecting_with_rspec?
|
|
158
|
+
metadata[:description] = RSpec::Matchers.generated_description
|
|
159
|
+
RSpec::Matchers.clear_generated_description
|
|
160
|
+
else
|
|
161
|
+
raise NotImplementedError.new(
|
|
162
|
+
"Generated descriptions are only supported when you use rspec-expectations. " +
|
|
163
|
+
"You must give every example an explicit description."
|
|
164
|
+
)
|
|
165
|
+
end
|
|
142
166
|
end
|
|
143
167
|
end
|
|
144
168
|
|
|
@@ -1,17 +1,20 @@
|
|
|
1
1
|
module RSpec
|
|
2
2
|
module Core
|
|
3
3
|
class ExampleGroup
|
|
4
|
+
extend MetadataHashBuilder::WithDeprecationWarning
|
|
4
5
|
extend Extensions::ModuleEvalWithArgs
|
|
5
|
-
|
|
6
|
+
extend Subject::ClassMethods
|
|
6
7
|
extend Hooks
|
|
7
|
-
|
|
8
|
-
include
|
|
8
|
+
|
|
9
|
+
include Extensions::InstanceEvalWithArgs
|
|
10
|
+
include Subject::InstanceMethods
|
|
9
11
|
include Pending
|
|
12
|
+
include Let
|
|
10
13
|
|
|
11
14
|
attr_accessor :example
|
|
12
15
|
|
|
13
16
|
def running_example
|
|
14
|
-
RSpec.deprecate(
|
|
17
|
+
RSpec.deprecate("running_example", "example")
|
|
15
18
|
example
|
|
16
19
|
end
|
|
17
20
|
|
|
@@ -19,8 +22,8 @@ module RSpec
|
|
|
19
22
|
RSpec.world
|
|
20
23
|
end
|
|
21
24
|
|
|
22
|
-
def self.
|
|
23
|
-
world.
|
|
25
|
+
def self.register
|
|
26
|
+
world.register(self)
|
|
24
27
|
end
|
|
25
28
|
|
|
26
29
|
class << self
|
|
@@ -39,9 +42,9 @@ module RSpec
|
|
|
39
42
|
|
|
40
43
|
def self.define_example_method(name, extra_options={})
|
|
41
44
|
module_eval(<<-END_RUBY, __FILE__, __LINE__)
|
|
42
|
-
def self.#{name}(desc=nil,
|
|
45
|
+
def self.#{name}(desc=nil, *args, &block)
|
|
46
|
+
options = build_metadata_hash_from(args)
|
|
43
47
|
options.update(:pending => true) unless block
|
|
44
|
-
options.update(:caller => caller)
|
|
45
48
|
options.update(#{extra_options.inspect})
|
|
46
49
|
examples << RSpec::Core::Example.new(self, desc, options, block)
|
|
47
50
|
examples.last
|
|
@@ -57,18 +60,20 @@ module RSpec
|
|
|
57
60
|
|
|
58
61
|
alias_example_to :it
|
|
59
62
|
alias_example_to :specify
|
|
60
|
-
alias_example_to :focused, :focused => true
|
|
63
|
+
alias_example_to :focused, :focused => true, :focus => true
|
|
64
|
+
alias_example_to :focus, :focused => true, :focus => true
|
|
61
65
|
alias_example_to :pending, :pending => true
|
|
66
|
+
alias_example_to :xit, :pending => true
|
|
62
67
|
|
|
63
|
-
def self.
|
|
68
|
+
def self.define_nested_shared_group_method(new_name, report_label=nil)
|
|
64
69
|
module_eval(<<-END_RUBY, __FILE__, __LINE__)
|
|
65
70
|
def self.#{new_name}(name, *args, &customization_block)
|
|
66
71
|
shared_block = world.shared_example_groups[name]
|
|
67
72
|
raise "Could not find shared example group named \#{name.inspect}" unless shared_block
|
|
68
73
|
|
|
69
74
|
group = describe("#{report_label || "it should behave like"} \#{name}") do
|
|
70
|
-
module_eval_with_args
|
|
71
|
-
module_eval
|
|
75
|
+
module_eval_with_args(*args, &shared_block)
|
|
76
|
+
module_eval(&customization_block) if customization_block
|
|
72
77
|
end
|
|
73
78
|
group.metadata[:shared_group_name] = name
|
|
74
79
|
group
|
|
@@ -76,14 +81,22 @@ module RSpec
|
|
|
76
81
|
END_RUBY
|
|
77
82
|
end
|
|
78
83
|
|
|
79
|
-
|
|
84
|
+
define_nested_shared_group_method :it_should_behave_like
|
|
80
85
|
|
|
81
86
|
class << self
|
|
82
|
-
alias_method :alias_it_should_behave_like_to, :
|
|
87
|
+
alias_method :alias_it_should_behave_like_to, :define_nested_shared_group_method
|
|
83
88
|
end
|
|
84
89
|
|
|
85
90
|
alias_it_should_behave_like_to :it_behaves_like, "behaves like"
|
|
86
91
|
|
|
92
|
+
def self.include_context(name)
|
|
93
|
+
module_eval(&world.shared_example_groups[name])
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
class << self
|
|
97
|
+
alias_method :include_examples, :include_context
|
|
98
|
+
end
|
|
99
|
+
|
|
87
100
|
def self.examples
|
|
88
101
|
@examples ||= []
|
|
89
102
|
end
|
|
@@ -93,7 +106,7 @@ module RSpec
|
|
|
93
106
|
end
|
|
94
107
|
|
|
95
108
|
def self.descendant_filtered_examples
|
|
96
|
-
filtered_examples + children.
|
|
109
|
+
@descendant_filtered_examples ||= filtered_examples + children.inject([]){|l,c| l + c.descendant_filtered_examples}
|
|
97
110
|
end
|
|
98
111
|
|
|
99
112
|
def self.metadata
|
|
@@ -101,7 +114,7 @@ module RSpec
|
|
|
101
114
|
end
|
|
102
115
|
|
|
103
116
|
def self.superclass_metadata
|
|
104
|
-
self.superclass.respond_to?(:metadata) ? self.superclass.metadata : nil
|
|
117
|
+
@superclass_metadata ||= self.superclass.respond_to?(:metadata) ? self.superclass.metadata : nil
|
|
105
118
|
end
|
|
106
119
|
|
|
107
120
|
def self.describe(*args, &example_group_block)
|
|
@@ -109,7 +122,6 @@ module RSpec
|
|
|
109
122
|
@_subclass_count += 1
|
|
110
123
|
args << {} unless args.last.is_a?(Hash)
|
|
111
124
|
args.last.update(:example_group_block => example_group_block)
|
|
112
|
-
args.last.update(:caller => caller)
|
|
113
125
|
|
|
114
126
|
# TODO 2010-05-05: Because we don't know if const_set is thread-safe
|
|
115
127
|
child = const_set(
|
|
@@ -136,7 +148,7 @@ module RSpec
|
|
|
136
148
|
end
|
|
137
149
|
|
|
138
150
|
def self.descendants
|
|
139
|
-
[self] + children.
|
|
151
|
+
@_descendants ||= [self] + children.inject([]) {|list, c| list + c.descendants}
|
|
140
152
|
end
|
|
141
153
|
|
|
142
154
|
def self.ancestors
|
|
@@ -144,10 +156,30 @@ module RSpec
|
|
|
144
156
|
end
|
|
145
157
|
|
|
146
158
|
def self.top_level?
|
|
147
|
-
|
|
159
|
+
@top_level ||= superclass == ExampleGroup
|
|
160
|
+
end
|
|
161
|
+
|
|
162
|
+
def self.ensure_example_groups_are_configured
|
|
163
|
+
unless defined?(@@example_groups_configured)
|
|
164
|
+
RSpec.configuration.configure_mock_framework
|
|
165
|
+
RSpec.configuration.configure_expectation_framework
|
|
166
|
+
@@example_groups_configured = true
|
|
167
|
+
end
|
|
148
168
|
end
|
|
149
169
|
|
|
150
170
|
def self.set_it_up(*args)
|
|
171
|
+
# Ruby 1.9 has a bug that can lead to infinite recursion and a
|
|
172
|
+
# SystemStackError if you include a module in a superclass after
|
|
173
|
+
# including it in a subclass: https://gist.github.com/845896
|
|
174
|
+
# To prevent this, we must include any modules in RSpec::Core::ExampleGroup
|
|
175
|
+
# before users create example groups and have a chance to include
|
|
176
|
+
# the same module in a subclass of RSpec::Core::ExampleGroup.
|
|
177
|
+
# So we need to configure example groups here.
|
|
178
|
+
ensure_example_groups_are_configured
|
|
179
|
+
|
|
180
|
+
symbol_description = args.shift if args.first.is_a?(Symbol)
|
|
181
|
+
args << build_metadata_hash_from(args)
|
|
182
|
+
args.unshift(symbol_description) if symbol_description
|
|
151
183
|
@metadata = RSpec::Core::Metadata.new(superclass_metadata).process(*args)
|
|
152
184
|
world.configure_group(self)
|
|
153
185
|
end
|
|
@@ -157,49 +189,65 @@ module RSpec
|
|
|
157
189
|
end
|
|
158
190
|
|
|
159
191
|
def self.store_before_all_ivars(example_group_instance)
|
|
192
|
+
return if example_group_instance.instance_variables.empty?
|
|
160
193
|
example_group_instance.instance_variables.each { |ivar|
|
|
161
194
|
before_all_ivars[ivar] = example_group_instance.instance_variable_get(ivar)
|
|
162
195
|
}
|
|
163
196
|
end
|
|
164
197
|
|
|
165
198
|
def self.assign_before_all_ivars(ivars, example_group_instance)
|
|
199
|
+
return if ivars.empty?
|
|
166
200
|
ivars.each { |ivar, val| example_group_instance.instance_variable_set(ivar, val) }
|
|
167
201
|
end
|
|
168
202
|
|
|
169
203
|
def self.eval_before_alls(example_group_instance)
|
|
170
204
|
return if descendant_filtered_examples.empty?
|
|
171
205
|
assign_before_all_ivars(superclass.before_all_ivars, example_group_instance)
|
|
172
|
-
world.run_hook_filtered(:before, :all, self, example_group_instance)
|
|
206
|
+
world.run_hook_filtered(:before, :all, self, example_group_instance)
|
|
173
207
|
run_hook!(:before, :all, example_group_instance)
|
|
174
208
|
store_before_all_ivars(example_group_instance)
|
|
175
209
|
end
|
|
176
210
|
|
|
177
|
-
def self.eval_around_eachs(
|
|
178
|
-
around_hooks.reverse.inject(
|
|
179
|
-
|
|
180
|
-
|
|
211
|
+
def self.eval_around_eachs(example, initial_procsy)
|
|
212
|
+
example.around_hooks.reverse.inject(initial_procsy) do |procsy, around_hook|
|
|
213
|
+
Example.procsy(procsy.metadata) do
|
|
214
|
+
example.example_group_instance.instance_eval_with_args(procsy, &around_hook)
|
|
215
|
+
end
|
|
181
216
|
end
|
|
182
217
|
end
|
|
183
218
|
|
|
184
|
-
def self.eval_before_eachs(
|
|
185
|
-
world.run_hook_filtered(:before, :each, self, example_group_instance)
|
|
186
|
-
ancestors.reverse.each { |ancestor| ancestor.run_hook(:before, :each, example_group_instance) }
|
|
219
|
+
def self.eval_before_eachs(example)
|
|
220
|
+
world.run_hook_filtered(:before, :each, self, example.example_group_instance, example)
|
|
221
|
+
ancestors.reverse.each { |ancestor| ancestor.run_hook(:before, :each, example.example_group_instance) }
|
|
187
222
|
end
|
|
188
223
|
|
|
189
|
-
def self.eval_after_eachs(
|
|
190
|
-
ancestors.each { |ancestor| ancestor.run_hook(:after, :each, example_group_instance) }
|
|
191
|
-
world.run_hook_filtered(:after, :each, self, example_group_instance)
|
|
224
|
+
def self.eval_after_eachs(example)
|
|
225
|
+
ancestors.each { |ancestor| ancestor.run_hook(:after, :each, example.example_group_instance) }
|
|
226
|
+
world.run_hook_filtered(:after, :each, self, example.example_group_instance, example)
|
|
192
227
|
end
|
|
193
228
|
|
|
194
229
|
def self.eval_after_alls(example_group_instance)
|
|
195
230
|
return if descendant_filtered_examples.empty?
|
|
196
231
|
assign_before_all_ivars(before_all_ivars, example_group_instance)
|
|
197
|
-
|
|
198
|
-
|
|
232
|
+
|
|
233
|
+
begin
|
|
234
|
+
run_hook!(:after, :all, example_group_instance)
|
|
235
|
+
rescue => e
|
|
236
|
+
# TODO: come up with a better solution for this.
|
|
237
|
+
RSpec.configuration.reporter.message <<-EOS
|
|
238
|
+
|
|
239
|
+
An error occurred in an after(:all) hook.
|
|
240
|
+
#{e.class}: #{e.message}
|
|
241
|
+
occurred at #{e.backtrace.first}
|
|
242
|
+
|
|
243
|
+
EOS
|
|
244
|
+
end
|
|
245
|
+
|
|
246
|
+
world.run_hook_filtered(:after, :all, self, example_group_instance)
|
|
199
247
|
end
|
|
200
248
|
|
|
201
|
-
def self.
|
|
202
|
-
|
|
249
|
+
def self.around_hooks_for(example)
|
|
250
|
+
world.find_hook(:around, :each, self, example) + ancestors.reverse.inject([]){|l,a| l + a.find_hook(:around, :each, self, example)}
|
|
203
251
|
end
|
|
204
252
|
|
|
205
253
|
def self.run(reporter)
|
|
@@ -207,47 +255,56 @@ module RSpec
|
|
|
207
255
|
RSpec.clear_remaining_example_groups if top_level?
|
|
208
256
|
return
|
|
209
257
|
end
|
|
210
|
-
@reporter = reporter
|
|
211
|
-
example_group_instance = new
|
|
212
258
|
reporter.example_group_started(self)
|
|
213
259
|
|
|
214
260
|
begin
|
|
215
|
-
eval_before_alls(
|
|
216
|
-
result_for_this_group = run_examples(
|
|
261
|
+
eval_before_alls(new)
|
|
262
|
+
result_for_this_group = run_examples(reporter)
|
|
217
263
|
results_for_descendants = children.map {|child| child.run(reporter)}.all?
|
|
218
264
|
result_for_this_group && results_for_descendants
|
|
219
265
|
rescue Exception => ex
|
|
220
266
|
fail_filtered_examples(ex, reporter)
|
|
221
267
|
ensure
|
|
222
|
-
eval_after_alls(
|
|
268
|
+
eval_after_alls(new)
|
|
269
|
+
before_all_ivars.clear
|
|
223
270
|
reporter.example_group_finished(self)
|
|
224
271
|
end
|
|
225
272
|
end
|
|
226
273
|
|
|
227
274
|
def self.fail_filtered_examples(exception, reporter)
|
|
228
275
|
filtered_examples.each { |example| example.fail_fast(reporter, exception) }
|
|
276
|
+
|
|
277
|
+
children.each do |child|
|
|
278
|
+
reporter.example_group_started(child)
|
|
279
|
+
child.fail_filtered_examples(exception, reporter)
|
|
280
|
+
reporter.example_group_finished(child)
|
|
281
|
+
end
|
|
282
|
+
false
|
|
229
283
|
end
|
|
230
284
|
|
|
231
|
-
def self.
|
|
285
|
+
def self.fail_fast?
|
|
286
|
+
RSpec.configuration.fail_fast?
|
|
287
|
+
end
|
|
288
|
+
|
|
289
|
+
def self.run_examples(reporter)
|
|
232
290
|
filtered_examples.map do |example|
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
end
|
|
291
|
+
next if RSpec.wants_to_quit
|
|
292
|
+
instance = new
|
|
293
|
+
set_ivars(instance, before_all_ivars)
|
|
294
|
+
succeeded = example.run(instance, reporter)
|
|
295
|
+
RSpec.wants_to_quit = true if fail_fast? && !succeeded
|
|
296
|
+
succeeded
|
|
240
297
|
end.all?
|
|
241
298
|
end
|
|
242
299
|
|
|
243
|
-
def self.
|
|
244
|
-
metadata.
|
|
300
|
+
def self.apply?(predicate, filters)
|
|
301
|
+
metadata.apply?(predicate, filters)
|
|
245
302
|
end
|
|
246
303
|
|
|
247
304
|
def self.declaration_line_numbers
|
|
248
|
-
[metadata[:example_group][:line_number]] +
|
|
305
|
+
@declaration_line_numbers ||= [metadata[:example_group][:line_number]] +
|
|
249
306
|
examples.collect {|e| e.metadata[:line_number]} +
|
|
250
|
-
children.
|
|
307
|
+
children.inject([]) {|l,c| l + c.declaration_line_numbers}
|
|
251
308
|
end
|
|
252
309
|
|
|
253
310
|
def self.top_level_description
|
|
@@ -258,14 +315,6 @@ module RSpec
|
|
|
258
315
|
ivars.each {|name, value| instance.instance_variable_set(name, value)}
|
|
259
316
|
end
|
|
260
317
|
|
|
261
|
-
def self.clear_ivars(instance)
|
|
262
|
-
instance.instance_variables.each { |ivar| instance.send(:remove_instance_variable, ivar) }
|
|
263
|
-
end
|
|
264
|
-
|
|
265
|
-
def self.clear_memoized(instance)
|
|
266
|
-
instance.__memoized.clear
|
|
267
|
-
end
|
|
268
|
-
|
|
269
318
|
def described_class
|
|
270
319
|
self.class.described_class
|
|
271
320
|
end
|
|
@@ -274,6 +323,7 @@ module RSpec
|
|
|
274
323
|
begin
|
|
275
324
|
instance_eval(&hook)
|
|
276
325
|
rescue Exception => e
|
|
326
|
+
raise unless example
|
|
277
327
|
example.set_exception(e)
|
|
278
328
|
end
|
|
279
329
|
end
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
module Kernel
|
|
2
2
|
def debugger(*args)
|
|
3
|
-
RSpec.configuration.error_stream.puts "debugger statement ignored, use -d or --debug option to enable debugging\n#{caller(0)[1]}"
|
|
3
|
+
(RSpec.configuration.error_stream || $stderr).puts "\n***** debugger statement ignored, use -d or --debug option to enable debugging\n#{caller(0)[1]}"
|
|
4
4
|
end unless respond_to?(:debugger)
|
|
5
5
|
end
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
require 'rspec/core/formatters/helpers'
|
|
2
|
+
require 'stringio'
|
|
3
|
+
|
|
1
4
|
module RSpec
|
|
2
5
|
module Core
|
|
3
6
|
module Formatters
|
|
@@ -9,8 +12,15 @@ module RSpec
|
|
|
9
12
|
attr_reader :example_count, :pending_count, :failure_count
|
|
10
13
|
attr_reader :failed_examples, :pending_examples
|
|
11
14
|
|
|
15
|
+
def self.relative_path(line)
|
|
16
|
+
line = line.sub(File.expand_path("."), ".")
|
|
17
|
+
line = line.sub(/\A([^:]+:\d+)$/, '\\1')
|
|
18
|
+
return nil if line == '-e:1'
|
|
19
|
+
line
|
|
20
|
+
end
|
|
21
|
+
|
|
12
22
|
def initialize(output)
|
|
13
|
-
@output = output
|
|
23
|
+
@output = output || StringIO.new
|
|
14
24
|
@example_count = @pending_count = @failure_count = 0
|
|
15
25
|
@examples = []
|
|
16
26
|
@failed_examples = []
|
|
@@ -43,11 +53,6 @@ module RSpec
|
|
|
43
53
|
def example_group_finished(example_group)
|
|
44
54
|
end
|
|
45
55
|
|
|
46
|
-
def add_example_group(example_group)
|
|
47
|
-
RSpec.deprecate("add_example_group", "example_group_started")
|
|
48
|
-
example_group_started(example_group)
|
|
49
|
-
end
|
|
50
|
-
|
|
51
56
|
def example_started(example)
|
|
52
57
|
examples << example
|
|
53
58
|
end
|
|
@@ -98,6 +103,11 @@ module RSpec
|
|
|
98
103
|
def format_backtrace(backtrace, example)
|
|
99
104
|
return "" unless backtrace
|
|
100
105
|
return backtrace if example.metadata[:full_backtrace] == true
|
|
106
|
+
|
|
107
|
+
if at_exit_index = backtrace.index(RSpec::Core::Runner::AT_EXIT_HOOK_BACKTRACE_LINE)
|
|
108
|
+
backtrace = backtrace[0, at_exit_index]
|
|
109
|
+
end
|
|
110
|
+
|
|
101
111
|
cleansed = backtrace.map { |line| backtrace_line(line) }.compact
|
|
102
112
|
cleansed.empty? ? backtrace : cleansed
|
|
103
113
|
end
|
|
@@ -110,26 +120,31 @@ module RSpec
|
|
|
110
120
|
|
|
111
121
|
def backtrace_line(line)
|
|
112
122
|
return nil if configuration.cleaned_from_backtrace?(line)
|
|
113
|
-
|
|
114
|
-
line = line.sub(/\A([^:]+:\d+)$/, '\\1')
|
|
115
|
-
return nil if line == '-e:1'
|
|
116
|
-
line
|
|
123
|
+
self.class.relative_path(line)
|
|
117
124
|
end
|
|
118
125
|
|
|
119
126
|
def read_failed_line(exception, example)
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
return "Unable to find matching line from backtrace" if matching_line.nil?
|
|
127
|
+
unless matching_line = find_failed_line(exception.backtrace, example.file_path)
|
|
128
|
+
return "Unable to find matching line from backtrace"
|
|
129
|
+
end
|
|
124
130
|
|
|
125
131
|
file_path, line_number = matching_line.match(/(.+?):(\d+)(|:\d+)/)[1..2]
|
|
132
|
+
|
|
126
133
|
if File.exist?(file_path)
|
|
127
|
-
|
|
134
|
+
File.readlines(file_path)[line_number.to_i - 1]
|
|
128
135
|
else
|
|
129
136
|
"Unable to find #{file_path} to read failed line"
|
|
130
137
|
end
|
|
131
138
|
end
|
|
132
139
|
|
|
140
|
+
def find_failed_line(backtrace, path)
|
|
141
|
+
backtrace.detect { |line|
|
|
142
|
+
match = line.match(/(.+?):(\d+)(|:\d+)/)
|
|
143
|
+
match && match[1].downcase == path.downcase
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
end
|
|
147
|
+
|
|
133
148
|
def start_sync_output
|
|
134
149
|
@old_sync, output.sync = output.sync, true if output_supports_sync
|
|
135
150
|
end
|