rspec-core 3.7.0 → 3.9.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.
Files changed (45) hide show
  1. checksums.yaml +5 -5
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +0 -0
  4. data/Changelog.md +80 -2
  5. data/README.md +16 -16
  6. data/lib/rspec/core.rb +1 -0
  7. data/lib/rspec/core/bisect/coordinator.rb +26 -30
  8. data/lib/rspec/core/bisect/example_minimizer.rb +12 -8
  9. data/lib/rspec/core/bisect/fork_runner.rb +134 -0
  10. data/lib/rspec/core/bisect/server.rb +5 -14
  11. data/lib/rspec/core/bisect/{runner.rb → shell_command.rb} +27 -70
  12. data/lib/rspec/core/bisect/shell_runner.rb +73 -0
  13. data/lib/rspec/core/bisect/utilities.rb +58 -0
  14. data/lib/rspec/core/configuration.rb +219 -62
  15. data/lib/rspec/core/configuration_options.rb +41 -4
  16. data/lib/rspec/core/did_you_mean.rb +46 -0
  17. data/lib/rspec/core/example.rb +8 -5
  18. data/lib/rspec/core/example_group.rb +8 -3
  19. data/lib/rspec/core/formatters.rb +13 -6
  20. data/lib/rspec/core/formatters/base_bisect_formatter.rb +45 -0
  21. data/lib/rspec/core/formatters/bisect_drb_formatter.rb +29 -0
  22. data/lib/rspec/core/formatters/bisect_progress_formatter.rb +29 -16
  23. data/lib/rspec/core/formatters/deprecation_formatter.rb +3 -1
  24. data/lib/rspec/core/formatters/documentation_formatter.rb +35 -3
  25. data/lib/rspec/core/formatters/exception_presenter.rb +13 -1
  26. data/lib/rspec/core/formatters/failure_list_formatter.rb +23 -0
  27. data/lib/rspec/core/formatters/html_printer.rb +0 -2
  28. data/lib/rspec/core/formatters/protocol.rb +17 -17
  29. data/lib/rspec/core/formatters/syntax_highlighter.rb +19 -19
  30. data/lib/rspec/core/hooks.rb +15 -9
  31. data/lib/rspec/core/invocations.rb +8 -6
  32. data/lib/rspec/core/memoized_helpers.rb +33 -14
  33. data/lib/rspec/core/metadata.rb +2 -3
  34. data/lib/rspec/core/option_parser.rb +8 -0
  35. data/lib/rspec/core/profiler.rb +3 -1
  36. data/lib/rspec/core/rake_task.rb +21 -1
  37. data/lib/rspec/core/reporter.rb +11 -6
  38. data/lib/rspec/core/runner.rb +25 -14
  39. data/lib/rspec/core/shared_example_group.rb +2 -4
  40. data/lib/rspec/core/shell_escape.rb +2 -2
  41. data/lib/rspec/core/version.rb +1 -1
  42. data/lib/rspec/core/world.rb +11 -0
  43. metadata +22 -13
  44. metadata.gz.sig +0 -0
  45. data/lib/rspec/core/formatters/bisect_formatter.rb +0 -69
@@ -7,7 +7,7 @@ module RSpec
7
7
  # In addition to metadata that is used internally, this also stores
8
8
  # user-supplied metadata, e.g.
9
9
  #
10
- # describe Something, :type => :ui do
10
+ # RSpec.describe Something, :type => :ui do
11
11
  # it "does something", :slow => true do
12
12
  # # ...
13
13
  # end
@@ -136,7 +136,6 @@ module RSpec
136
136
 
137
137
  populate_location_attributes
138
138
  metadata.update(user_metadata)
139
- RSpec.configuration.apply_derived_metadata_to(metadata)
140
139
  end
141
140
 
142
141
  private
@@ -169,7 +168,7 @@ module RSpec
169
168
  end
170
169
 
171
170
  def description_separator(parent_part, child_part)
172
- if parent_part.is_a?(Module) && child_part =~ /^(#|::|\.)/
171
+ if parent_part.is_a?(Module) && /^(?:#|::|\.)/.match(child_part.to_s)
173
172
  ''.freeze
174
173
  else
175
174
  ' '.freeze
@@ -37,6 +37,7 @@ module RSpec::Core
37
37
  # rubocop:disable Metrics/AbcSize
38
38
  # rubocop:disable CyclomaticComplexity
39
39
  # rubocop:disable PerceivedComplexity
40
+ # rubocop:disable Metrics/BlockLength
40
41
  def parser(options)
41
42
  OptionParser.new do |parser|
42
43
  parser.summary_width = 34
@@ -111,6 +112,7 @@ module RSpec::Core
111
112
  ' [d]ocumentation (group and example names)',
112
113
  ' [h]tml',
113
114
  ' [j]son',
115
+ ' [f]ailures ("file:line:reason", suitable for editors integration)',
114
116
  ' custom formatter class name') do |o|
115
117
  options[:formatters] ||= []
116
118
  options[:formatters] << [o]
@@ -226,6 +228,11 @@ FILTERING
226
228
  (options[:full_description] ||= []) << Regexp.compile(Regexp.escape(o))
227
229
  end
228
230
 
231
+ parser.on('-E', '--example-matches REGEX', "Run examples whose full nested names match REGEX (may be",
232
+ " used more than once)") do |o|
233
+ (options[:full_description] ||= []) << Regexp.compile(o)
234
+ end
235
+
229
236
  parser.on('-t', '--tag TAG[:VALUE]',
230
237
  'Run examples with the specified tag, or exclude examples',
231
238
  'by adding ~ before the tag.',
@@ -288,6 +295,7 @@ FILTERING
288
295
  end
289
296
  end
290
297
  end
298
+ # rubocop:enable Metrics/BlockLength
291
299
  # rubocop:enable Metrics/AbcSize
292
300
  # rubocop:enable MethodLength
293
301
  # rubocop:enable CyclomaticComplexity
@@ -20,7 +20,9 @@ module RSpec
20
20
  def example_group_finished(notification)
21
21
  return unless notification.group.top_level?
22
22
 
23
- @example_groups[notification.group][:total_time] = Time.now - @example_groups[notification.group][:start]
23
+ group = @example_groups[notification.group]
24
+ return unless group.key?(:start)
25
+ group[:total_time] = Time.now - group[:start]
24
26
  end
25
27
 
26
28
  def example_started(notification)
@@ -45,6 +45,21 @@ module RSpec
45
45
  # A message to print to stderr when there are failures.
46
46
  attr_accessor :failure_message
47
47
 
48
+ if RUBY_VERSION < "1.9.0" || Support::Ruby.jruby?
49
+ # Run RSpec with a clean (empty) environment is not supported
50
+ def with_clean_environment=(_value)
51
+ raise ArgumentError, "Running in a clean environment is not supported on Ruby versions before 1.9.0"
52
+ end
53
+
54
+ # Run RSpec with a clean (empty) environment is not supported
55
+ def with_clean_environment
56
+ false
57
+ end
58
+ else
59
+ # Run RSpec with a clean (empty) environment.
60
+ attr_accessor :with_clean_environment
61
+ end
62
+
48
63
  # Use verbose output. If this is set to true, the task will print the
49
64
  # executed spec command to stdout. Defaults to `true`.
50
65
  attr_accessor :verbose
@@ -76,7 +91,12 @@ module RSpec
76
91
  command = spec_command
77
92
  puts command if verbose
78
93
 
79
- return if system(command)
94
+ if with_clean_environment
95
+ return if system({}, command, :unsetenv_others => true)
96
+ else
97
+ return if system(command)
98
+ end
99
+
80
100
  puts failure_message if failure_message
81
101
 
82
102
  return unless fail_on_error
@@ -21,17 +21,12 @@ module RSpec::Core
21
21
  @non_example_exception_count = 0
22
22
  @setup_default = lambda {}
23
23
  @setup = false
24
+ @profiler = nil
24
25
  end
25
26
 
26
27
  # @private
27
28
  attr_reader :examples, :failed_examples, :pending_examples
28
29
 
29
- # @private
30
- def setup_profiler
31
- @profiler = Profiler.new
32
- register_listener @profiler, *Profiler::NOTIFICATIONS
33
- end
34
-
35
30
  # Registers a listener to a list of notifications. The reporter will send
36
31
  # notification of events to all registered listeners.
37
32
  #
@@ -82,6 +77,14 @@ module RSpec::Core
82
77
  end
83
78
  end
84
79
 
80
+ # @param exit_code [Integer] the exit_code to be return by the reporter
81
+ #
82
+ # Reports a run that exited early without having run any examples.
83
+ #
84
+ def exit_early(exit_code)
85
+ report(0) { exit_code }
86
+ end
87
+
85
88
  # @private
86
89
  def start(expected_example_count, time=RSpec::Core::Time.now)
87
90
  @start = time
@@ -231,6 +234,8 @@ module RSpec::Core
231
234
  return if @setup
232
235
 
233
236
  @setup_default.call
237
+ @profiler = Profiler.new
238
+ register_listener @profiler, *Profiler::NOTIFICATIONS
234
239
  @setup = true
235
240
  end
236
241
 
@@ -84,6 +84,8 @@ module RSpec
84
84
  # @param out [IO] output stream
85
85
  def run(err, out)
86
86
  setup(err, out)
87
+ return @configuration.reporter.exit_early(@configuration.failure_exit_code) if RSpec.world.wants_to_quit
88
+
87
89
  run_specs(@world.ordered_example_groups).tap do
88
90
  persist_example_statuses
89
91
  end
@@ -94,10 +96,11 @@ module RSpec
94
96
  # @param err [IO] error stream
95
97
  # @param out [IO] output stream
96
98
  def setup(err, out)
97
- @configuration.error_stream = err
98
- @configuration.output_stream = out if @configuration.output_stream == $stdout
99
- @options.configure(@configuration)
99
+ configure(err, out)
100
+ return if RSpec.world.wants_to_quit
101
+
100
102
  @configuration.load_spec_files
103
+ ensure
101
104
  @world.announce_filters
102
105
  end
103
106
 
@@ -122,17 +125,11 @@ module RSpec
122
125
  success ? 0 : @configuration.failure_exit_code
123
126
  end
124
127
 
125
- private
126
-
127
- def persist_example_statuses
128
- return unless (path = @configuration.example_status_persistence_file_path)
129
-
130
- ExampleStatusPersister.persist(@world.all_examples, path)
131
- rescue SystemCallError => e
132
- RSpec.warning "Could not write example statuses to #{path} (configured as " \
133
- "`config.example_status_persistence_file_path`) due to a " \
134
- "system error: #{e.inspect}. Please check that the config " \
135
- "option is set to an accessible, valid file path", :call_site => nil
128
+ # @private
129
+ def configure(err, out)
130
+ @configuration.error_stream = err
131
+ @configuration.output_stream = out if @configuration.output_stream == $stdout
132
+ @options.configure(@configuration)
136
133
  end
137
134
 
138
135
  # @private
@@ -188,6 +185,20 @@ module RSpec
188
185
  $stderr.puts "\nRSpec is shutting down and will print the summary report... Interrupt again to force quit."
189
186
  end
190
187
  end
188
+
189
+ private
190
+
191
+ def persist_example_statuses
192
+ return if @configuration.dry_run
193
+ return unless (path = @configuration.example_status_persistence_file_path)
194
+
195
+ ExampleStatusPersister.persist(@world.all_examples, path)
196
+ rescue SystemCallError => e
197
+ RSpec.warning "Could not write example statuses to #{path} (configured as " \
198
+ "`config.example_status_persistence_file_path`) due to a " \
199
+ "system error: #{e.inspect}. Please check that the config " \
200
+ "option is set to an accessible, valid file path", :call_site => nil
201
+ end
191
202
  end
192
203
  end
193
204
  end
@@ -76,7 +76,7 @@ module RSpec
76
76
  # end
77
77
  # end
78
78
  #
79
- # describe Account do
79
+ # RSpec.describe Account do
80
80
  # it_behaves_like "auditable" do
81
81
  # let(:auditable) { Account.new }
82
82
  # end
@@ -103,7 +103,6 @@ module RSpec
103
103
  # Shared examples top level DSL.
104
104
  module TopLevelDSL
105
105
  # @private
106
- # rubocop:disable Lint/NestedMethodDefinition
107
106
  def self.definitions
108
107
  proc do
109
108
  def shared_examples(name, *args, &block)
@@ -113,7 +112,6 @@ module RSpec
113
112
  alias shared_examples_for shared_examples
114
113
  end
115
114
  end
116
- # rubocop:enable Lint/NestedMethodDefinition
117
115
 
118
116
  # @private
119
117
  def self.exposed_globally?
@@ -259,7 +257,7 @@ module RSpec
259
257
  # :nocov:
260
258
  def ensure_block_has_source_location(block)
261
259
  source_location = yield.split(':')
262
- block.extend Module.new { define_method(:source_location) { source_location } }
260
+ block.extend(Module.new { define_method(:source_location) { source_location } })
263
261
  end
264
262
  # :nocov:
265
263
  end
@@ -6,7 +6,7 @@ module RSpec
6
6
  module_function
7
7
 
8
8
  def quote(argument)
9
- "'#{argument.gsub("'", "\\\\'")}'"
9
+ "'#{argument.to_s.gsub("'", "\\\\'")}'"
10
10
  end
11
11
 
12
12
  if RSpec::Support::OS.windows?
@@ -17,7 +17,7 @@ module RSpec
17
17
  require 'shellwords'
18
18
 
19
19
  def escape(shell_command)
20
- shell_command.shellescape
20
+ Shellwords.escape(shell_command.to_s)
21
21
  end
22
22
  end
23
23
 
@@ -3,7 +3,7 @@ module RSpec
3
3
  # Version information for RSpec Core.
4
4
  module Version
5
5
  # Current version of RSpec Core, in semantic versioning format.
6
- STRING = '3.7.0'
6
+ STRING = '3.9.0'
7
7
  end
8
8
  end
9
9
  end
@@ -21,6 +21,17 @@ module RSpec
21
21
  configuration.world = self
22
22
  @example_groups = []
23
23
  @example_group_counts_by_spec_file = Hash.new(0)
24
+ prepare_example_filtering
25
+ end
26
+
27
+ # @api public
28
+ #
29
+ # Prepares filters so that they apply to example groups when they run.
30
+ #
31
+ # This is a separate method so that filters can be modified/replaced and
32
+ # examples refiltered during a process's lifetime, which can be useful for
33
+ # a custom runner.
34
+ def prepare_example_filtering
24
35
  @filtered_examples = Hash.new do |hash, group|
25
36
  hash[group] = filter_manager.prune(group.examples)
26
37
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rspec-core
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.7.0
4
+ version: 3.9.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Steven Baker
@@ -46,7 +46,7 @@ cert_chain:
46
46
  ZsVDj6a7lH3cNqtWXZxrb2wO38qV5AkYj8SQK7Hj3/Yui9myUX3crr+PdetazSqQ
47
47
  F3MdtaDehhjC
48
48
  -----END CERTIFICATE-----
49
- date: 2017-10-17 00:00:00.000000000 Z
49
+ date: 2019-10-07 00:00:00.000000000 Z
50
50
  dependencies:
51
51
  - !ruby/object:Gem::Dependency
52
52
  name: rspec-support
@@ -54,14 +54,14 @@ dependencies:
54
54
  requirements:
55
55
  - - "~>"
56
56
  - !ruby/object:Gem::Version
57
- version: 3.7.0
57
+ version: 3.9.0
58
58
  type: :runtime
59
59
  prerelease: false
60
60
  version_requirements: !ruby/object:Gem::Requirement
61
61
  requirements:
62
62
  - - "~>"
63
63
  - !ruby/object:Gem::Version
64
- version: 3.7.0
64
+ version: 3.9.0
65
65
  - !ruby/object:Gem::Dependency
66
66
  name: cucumber
67
67
  requirement: !ruby/object:Gem::Requirement
@@ -96,14 +96,14 @@ dependencies:
96
96
  requirements:
97
97
  - - "~>"
98
98
  - !ruby/object:Gem::Version
99
- version: 0.6.2
99
+ version: 0.14.9
100
100
  type: :development
101
101
  prerelease: false
102
102
  version_requirements: !ruby/object:Gem::Requirement
103
103
  requirements:
104
104
  - - "~>"
105
105
  - !ruby/object:Gem::Version
106
- version: 0.6.2
106
+ version: 0.14.9
107
107
  - !ruby/object:Gem::Dependency
108
108
  name: coderay
109
109
  requirement: !ruby/object:Gem::Requirement
@@ -192,10 +192,14 @@ files:
192
192
  - lib/rspec/core/backtrace_formatter.rb
193
193
  - lib/rspec/core/bisect/coordinator.rb
194
194
  - lib/rspec/core/bisect/example_minimizer.rb
195
- - lib/rspec/core/bisect/runner.rb
195
+ - lib/rspec/core/bisect/fork_runner.rb
196
196
  - lib/rspec/core/bisect/server.rb
197
+ - lib/rspec/core/bisect/shell_command.rb
198
+ - lib/rspec/core/bisect/shell_runner.rb
199
+ - lib/rspec/core/bisect/utilities.rb
197
200
  - lib/rspec/core/configuration.rb
198
201
  - lib/rspec/core/configuration_options.rb
202
+ - lib/rspec/core/did_you_mean.rb
199
203
  - lib/rspec/core/drb.rb
200
204
  - lib/rspec/core/dsl.rb
201
205
  - lib/rspec/core/example.rb
@@ -204,14 +208,16 @@ files:
204
208
  - lib/rspec/core/filter_manager.rb
205
209
  - lib/rspec/core/flat_map.rb
206
210
  - lib/rspec/core/formatters.rb
211
+ - lib/rspec/core/formatters/base_bisect_formatter.rb
207
212
  - lib/rspec/core/formatters/base_formatter.rb
208
213
  - lib/rspec/core/formatters/base_text_formatter.rb
209
- - lib/rspec/core/formatters/bisect_formatter.rb
214
+ - lib/rspec/core/formatters/bisect_drb_formatter.rb
210
215
  - lib/rspec/core/formatters/bisect_progress_formatter.rb
211
216
  - lib/rspec/core/formatters/console_codes.rb
212
217
  - lib/rspec/core/formatters/deprecation_formatter.rb
213
218
  - lib/rspec/core/formatters/documentation_formatter.rb
214
219
  - lib/rspec/core/formatters/exception_presenter.rb
220
+ - lib/rspec/core/formatters/failure_list_formatter.rb
215
221
  - lib/rspec/core/formatters/fallback_message_formatter.rb
216
222
  - lib/rspec/core/formatters/helpers.rb
217
223
  - lib/rspec/core/formatters/html_formatter.rb
@@ -259,7 +265,12 @@ files:
259
265
  homepage: https://github.com/rspec/rspec-core
260
266
  licenses:
261
267
  - MIT
262
- metadata: {}
268
+ metadata:
269
+ bug_tracker_uri: https://github.com/rspec/rspec-core/issues
270
+ changelog_uri: https://github.com/rspec/rspec-core/blob/v3.9.0/Changelog.md
271
+ documentation_uri: https://rspec.info/documentation/
272
+ mailing_list_uri: https://groups.google.com/forum/#!forum/rspec
273
+ source_code_uri: https://github.com/rspec/rspec-core
263
274
  post_install_message:
264
275
  rdoc_options:
265
276
  - "--charset=UTF-8"
@@ -276,10 +287,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
276
287
  - !ruby/object:Gem::Version
277
288
  version: '0'
278
289
  requirements: []
279
- rubyforge_project:
280
- rubygems_version: 2.6.14
290
+ rubygems_version: 3.0.6
281
291
  signing_key:
282
292
  specification_version: 4
283
- summary: rspec-core-3.7.0
293
+ summary: rspec-core-3.9.0
284
294
  test_files: []
285
- has_rdoc:
metadata.gz.sig CHANGED
Binary file
@@ -1,69 +0,0 @@
1
- require 'drb/drb'
2
-
3
- module RSpec
4
- module Core
5
- module Formatters
6
- # Used by `--bisect`. When it shells out and runs a portion of the suite, it uses
7
- # this formatter as a means to have the status reported back to it, via DRb.
8
- #
9
- # Note that since DRb calls carry considerable overhead compared to normal
10
- # method calls, we try to minimize the number of DRb calls for perf reasons,
11
- # opting to communicate only at the start and the end of the run, rather than
12
- # after each example.
13
- # @private
14
- class BisectFormatter
15
- Formatters.register self, :start, :start_dump, :example_started,
16
- :example_failed, :example_passed, :example_pending
17
-
18
- def initialize(_output)
19
- port = RSpec.configuration.drb_port
20
- drb_uri = "druby://localhost:#{port}"
21
- @all_example_ids = []
22
- @failed_example_ids = []
23
- @bisect_server = DRbObject.new_with_uri(drb_uri)
24
- @remaining_failures = []
25
- RSpec.configuration.files_or_directories_to_run = @bisect_server.files_or_directories_to_run
26
- end
27
-
28
- def start(_notification)
29
- @remaining_failures = Set.new(@bisect_server.expected_failures)
30
- end
31
-
32
- def example_started(notification)
33
- @all_example_ids << notification.example.id
34
- end
35
-
36
- def example_failed(notification)
37
- @failed_example_ids << notification.example.id
38
- example_finished(notification, :failed)
39
- end
40
-
41
- def example_passed(notification)
42
- example_finished(notification, :passed)
43
- end
44
-
45
- def example_pending(notification)
46
- example_finished(notification, :pending)
47
- end
48
-
49
- def start_dump(_notification)
50
- @bisect_server.latest_run_results = RunResults.new(
51
- @all_example_ids, @failed_example_ids
52
- )
53
- end
54
-
55
- RunResults = Struct.new(:all_example_ids, :failed_example_ids)
56
-
57
- private
58
-
59
- def example_finished(notification, status)
60
- return unless @remaining_failures.include?(notification.example.id)
61
- @remaining_failures.delete(notification.example.id)
62
-
63
- return if status == :failed && !@remaining_failures.empty?
64
- RSpec.world.wants_to_quit = true
65
- end
66
- end
67
- end
68
- end
69
- end