rubocop-rspec 1.20.1 → 1.21.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +6 -0
- data/config/default.yml +1 -0
- data/lib/rubocop/cop/rspec/capybara/feature_methods.rb +2 -2
- data/lib/rubocop/cop/rspec/cop.rb +22 -2
- data/lib/rubocop/cop/rspec/described_class.rb +4 -3
- data/lib/rubocop/cop/rspec/example_length.rb +2 -2
- data/lib/rubocop/cop/rspec/file_path.rb +6 -2
- data/lib/rubocop/cop/rspec/hook_argument.rb +6 -5
- data/lib/rubocop/cop/rspec/it_behaves_like.rb +3 -3
- data/lib/rubocop/cop/rspec/leading_subject.rb +6 -2
- data/lib/rubocop/cop/rspec/message_expectation.rb +3 -2
- data/lib/rubocop/cop/rspec/message_spies.rb +3 -3
- data/lib/rubocop/cop/rspec/multiple_expectations.rb +6 -1
- data/lib/rubocop/cop/rspec/nested_groups.rb +3 -2
- data/lib/rubocop/cop/rspec/not_to_not.rb +2 -2
- data/lib/rubocop/cop/rspec/predicate_matcher.rb +2 -2
- data/lib/rubocop/rspec/version.rb +1 -1
- data/rubocop-rspec.gemspec +1 -1
- data/spec/rubocop/cop/rspec/cop_spec.rb +1 -0
- data/spec/rubocop/cop/rspec/factory_bot/dynamic_attribute_defined_statically_spec.rb +2 -0
- data/spec/rubocop/cop/rspec/focus_spec.rb +1 -0
- data/spec/rubocop/cop/rspec/multiple_expectations_spec.rb +52 -1
- data/spec/rubocop/rspec/example_spec.rb +2 -2
- metadata +4 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: db6a354c4b2a3ba18944c5a6fc3ce076eaec380b3f84b67d3a825ab81a2f18a2
|
4
|
+
data.tar.gz: c15d5bb4a019e0ff6d419058e136959aa54af22a409e302c4cbd012f06960ba6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: cd09459ea1199299104e462a6592ffe6ecba612f6560e4f5003c13c302cf47a9b21b5da186cb7237378c2187f83c63894fb0a89780ce9c22d328b4cfb9795c81
|
7
|
+
data.tar.gz: 2f24de47526a5719c96772d5c4e557fc37d2cc39472c372e0c3c6d4913a47cee1568bb06547de1d67684d1afd60b8875c7073e162b8e637e5718b4b4f8972839
|
data/CHANGELOG.md
CHANGED
@@ -2,6 +2,12 @@
|
|
2
2
|
|
3
3
|
## Master (Unreleased)
|
4
4
|
|
5
|
+
## 1.21.0 (2017-12-13)
|
6
|
+
|
7
|
+
* Compatibility with RuboCop v0.52.0. ([@bquorning][])
|
8
|
+
* Improve performance when user does not override default RSpec Pattern config. ([@walf443][])
|
9
|
+
* Add `AggregateFailuresByDefault` configuration for `RSpec/MultipleExpectations` cop. ([@onk][])
|
10
|
+
|
5
11
|
## 1.20.1 (2017-11-15)
|
6
12
|
|
7
13
|
* Add "without" to list of default allowed prefixes for `RSpec/ContextWording`. ([@bquorning][])
|
data/config/default.yml
CHANGED
@@ -237,6 +237,7 @@ RSpec/MultipleExpectations:
|
|
237
237
|
Description: Checks if examples contain too many `expect` calls.
|
238
238
|
Enabled: true
|
239
239
|
Max: 1
|
240
|
+
AggregateFailuresByDefault: false
|
240
241
|
StyleGuide: http://www.rubydoc.info/gems/rubocop-rspec/RuboCop/Cop/RSpec/MultipleExpectations
|
241
242
|
|
242
243
|
RSpec/MultipleSubjects:
|
@@ -33,7 +33,7 @@ module RuboCop
|
|
33
33
|
# end
|
34
34
|
# end
|
35
35
|
class FeatureMethods < Cop
|
36
|
-
MSG = 'Use
|
36
|
+
MSG = 'Use `%<replacement>s` instead of `%<method>s`.'.freeze
|
37
37
|
|
38
38
|
# https://git.io/v7Kwr
|
39
39
|
MAP = {
|
@@ -56,7 +56,7 @@ module RuboCop
|
|
56
56
|
add_offense(
|
57
57
|
send_node,
|
58
58
|
location: :selector,
|
59
|
-
message: format(MSG, MAP[match]
|
59
|
+
message: format(MSG, method: match, replacement: MAP[match])
|
60
60
|
)
|
61
61
|
end
|
62
62
|
end
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module RuboCop
|
2
4
|
module Cop # rubocop:disable Style/Documentation
|
3
5
|
WorkaroundCop = Cop.dup
|
@@ -42,6 +44,11 @@ module RuboCop
|
|
42
44
|
DEFAULT_CONFIGURATION =
|
43
45
|
RuboCop::RSpec::CONFIG.fetch('AllCops').fetch('RSpec')
|
44
46
|
|
47
|
+
DEFAULT_PATTERN_RE = Regexp.union(
|
48
|
+
DEFAULT_CONFIGURATION.fetch('Patterns')
|
49
|
+
.map(&Regexp.public_method(:new))
|
50
|
+
)
|
51
|
+
|
45
52
|
# Invoke the original inherited hook so our cops are recognized
|
46
53
|
def self.inherited(subclass)
|
47
54
|
RuboCop::Cop::Cop.inherited(subclass)
|
@@ -58,12 +65,25 @@ module RuboCop
|
|
58
65
|
end
|
59
66
|
|
60
67
|
def rspec_pattern
|
61
|
-
|
68
|
+
if rspec_pattern_config?
|
69
|
+
Regexp.union(rspec_pattern_config.map(&Regexp.public_method(:new)))
|
70
|
+
else
|
71
|
+
DEFAULT_PATTERN_RE
|
72
|
+
end
|
62
73
|
end
|
63
74
|
|
64
|
-
def
|
75
|
+
def all_cops_config
|
65
76
|
config
|
66
77
|
.for_all_cops
|
78
|
+
end
|
79
|
+
|
80
|
+
def rspec_pattern_config?
|
81
|
+
return unless all_cops_config.key?('RSpec')
|
82
|
+
all_cops_config.fetch('RSpec').key?('Patterns')
|
83
|
+
end
|
84
|
+
|
85
|
+
def rspec_pattern_config
|
86
|
+
all_cops_config
|
67
87
|
.fetch('RSpec', DEFAULT_CONFIGURATION)
|
68
88
|
.fetch('Patterns')
|
69
89
|
end
|
@@ -37,7 +37,7 @@ module RuboCop
|
|
37
37
|
include ConfigurableEnforcedStyle
|
38
38
|
|
39
39
|
DESCRIBED_CLASS = 'described_class'.freeze
|
40
|
-
MSG = 'Use
|
40
|
+
MSG = 'Use `%<replacement>s` instead of `%<src>s`.'.freeze
|
41
41
|
|
42
42
|
def_node_matcher :common_instance_exec_closure?, <<-PATTERN
|
43
43
|
(block (send (const nil? {:Class :Module}) :new ...) ...)
|
@@ -91,9 +91,10 @@ module RuboCop
|
|
91
91
|
|
92
92
|
def message(offense)
|
93
93
|
if style == :described_class
|
94
|
-
format(MSG, DESCRIBED_CLASS, offense)
|
94
|
+
format(MSG, replacement: DESCRIBED_CLASS, src: offense)
|
95
95
|
else
|
96
|
-
format(MSG, @described_class.const_name,
|
96
|
+
format(MSG, replacement: @described_class.const_name,
|
97
|
+
src: DESCRIBED_CLASS)
|
97
98
|
end
|
98
99
|
end
|
99
100
|
|
@@ -28,7 +28,7 @@ module RuboCop
|
|
28
28
|
class ExampleLength < Cop
|
29
29
|
include CodeLength
|
30
30
|
|
31
|
-
MSG = 'Example has too many lines [
|
31
|
+
MSG = 'Example has too many lines [%<total>d/%<max>d].'.freeze
|
32
32
|
|
33
33
|
def on_block(node)
|
34
34
|
return unless example?(node)
|
@@ -47,7 +47,7 @@ module RuboCop
|
|
47
47
|
end
|
48
48
|
|
49
49
|
def message(length)
|
50
|
-
format(MSG, length, max_length)
|
50
|
+
format(MSG, total: length, max: max_length)
|
51
51
|
end
|
52
52
|
end
|
53
53
|
end
|
@@ -44,7 +44,7 @@ module RuboCop
|
|
44
44
|
class FilePath < Cop
|
45
45
|
include RuboCop::RSpec::TopLevelDescribe
|
46
46
|
|
47
|
-
MSG = 'Spec path should end with
|
47
|
+
MSG = 'Spec path should end with `%<suffix>s`.'.freeze
|
48
48
|
|
49
49
|
def_node_search :const_described?, '(send _ :describe (const ...) ...)'
|
50
50
|
def_node_search :routing_metadata?, '(pair (sym :type) (sym :routing))'
|
@@ -57,7 +57,11 @@ module RuboCop
|
|
57
57
|
|
58
58
|
return if filename_ends_with?(glob)
|
59
59
|
|
60
|
-
add_offense(
|
60
|
+
add_offense(
|
61
|
+
node,
|
62
|
+
location: :expression,
|
63
|
+
message: format(MSG, suffix: glob)
|
64
|
+
)
|
61
65
|
end
|
62
66
|
|
63
67
|
private
|
@@ -60,8 +60,9 @@ module RuboCop
|
|
60
60
|
class HookArgument < Cop
|
61
61
|
include ConfigurableEnforcedStyle
|
62
62
|
|
63
|
-
IMPLICIT_MSG = 'Omit the default
|
64
|
-
|
63
|
+
IMPLICIT_MSG = 'Omit the default `%<scope>p` ' \
|
64
|
+
'argument for RSpec hooks.'.freeze
|
65
|
+
EXPLICIT_MSG = 'Use `%<scope>p` for RSpec hooks.'.freeze
|
65
66
|
|
66
67
|
HOOKS = Hooks::ALL.node_pattern_union.freeze
|
67
68
|
|
@@ -102,15 +103,15 @@ module RuboCop
|
|
102
103
|
add_offense(
|
103
104
|
method_send,
|
104
105
|
location: :selector,
|
105
|
-
message: format(EXPLICIT_MSG, style)
|
106
|
+
message: format(EXPLICIT_MSG, scope: style)
|
106
107
|
)
|
107
108
|
end
|
108
109
|
|
109
110
|
def explicit_message(scope)
|
110
111
|
if implicit_style?
|
111
|
-
format(IMPLICIT_MSG, scope)
|
112
|
+
format(IMPLICIT_MSG, scope: scope)
|
112
113
|
else
|
113
|
-
format(EXPLICIT_MSG, style)
|
114
|
+
format(EXPLICIT_MSG, scope: style)
|
114
115
|
end
|
115
116
|
end
|
116
117
|
|
@@ -21,8 +21,8 @@ module RuboCop
|
|
21
21
|
class ItBehavesLike < Cop
|
22
22
|
include ConfigurableEnforcedStyle
|
23
23
|
|
24
|
-
MSG = 'Prefer
|
25
|
-
'a nested context.'.freeze
|
24
|
+
MSG = 'Prefer `%<replacement>s` over `%<original>s` when including '\
|
25
|
+
'examples in a nested context.'.freeze
|
26
26
|
|
27
27
|
def_node_matcher :example_inclusion_offense, '(send _ % ...)'
|
28
28
|
|
@@ -39,7 +39,7 @@ module RuboCop
|
|
39
39
|
private
|
40
40
|
|
41
41
|
def message(_node)
|
42
|
-
format(MSG, style, alternative_style)
|
42
|
+
format(MSG, replacement: style, original: alternative_style)
|
43
43
|
end
|
44
44
|
end
|
45
45
|
end
|
@@ -63,8 +63,12 @@ module RuboCop
|
|
63
63
|
|
64
64
|
def node_range(node)
|
65
65
|
range = node.source_range
|
66
|
-
range = range_with_surrounding_space(
|
67
|
-
|
66
|
+
range = range_with_surrounding_space(
|
67
|
+
range: range, side: :left, newlines: false
|
68
|
+
)
|
69
|
+
range = range_with_surrounding_space(
|
70
|
+
range: range, side: :right, newlines: true
|
71
|
+
)
|
68
72
|
range
|
69
73
|
end
|
70
74
|
|
@@ -27,7 +27,7 @@ module RuboCop
|
|
27
27
|
class MessageExpectation < Cop
|
28
28
|
include ConfigurableEnforcedStyle
|
29
29
|
|
30
|
-
MSG = 'Prefer
|
30
|
+
MSG = 'Prefer `%<style>s` for setting message expectations.'.freeze
|
31
31
|
|
32
32
|
SUPPORTED_STYLES = %w[allow expect].freeze
|
33
33
|
|
@@ -41,7 +41,8 @@ module RuboCop
|
|
41
41
|
message_expectation(node) do |match|
|
42
42
|
return correct_style_detected if preferred_style?(match)
|
43
43
|
|
44
|
-
|
44
|
+
message = format(MSG, style: style)
|
45
|
+
add_offense(match, location: :selector, message: message) do
|
45
46
|
opposite_style_detected
|
46
47
|
end
|
47
48
|
end
|
@@ -31,8 +31,8 @@ module RuboCop
|
|
31
31
|
'expectations.'.freeze
|
32
32
|
|
33
33
|
MSG_HAVE_RECEIVED = 'Prefer `have_received` for setting message '\
|
34
|
-
'expectations. Setup
|
35
|
-
' or `instance_spy`.'.freeze
|
34
|
+
'expectations. Setup `%<source>s` as a spy using '\
|
35
|
+
'`allow` or `instance_spy`.'.freeze
|
36
36
|
|
37
37
|
SUPPORTED_STYLES = %w[have_received receive].freeze
|
38
38
|
|
@@ -73,7 +73,7 @@ module RuboCop
|
|
73
73
|
when :receive
|
74
74
|
MSG_RECEIVE
|
75
75
|
when :have_received
|
76
|
-
MSG_HAVE_RECEIVED
|
76
|
+
format(MSG_HAVE_RECEIVED, source: receiver.source)
|
77
77
|
end
|
78
78
|
end
|
79
79
|
end
|
@@ -79,7 +79,8 @@ module RuboCop
|
|
79
79
|
def example_with_aggregated_failures?(node)
|
80
80
|
example = node.children.first
|
81
81
|
|
82
|
-
|
82
|
+
(aggregated_failures_by_default? ||
|
83
|
+
with_aggregated_failures?(example)) &&
|
83
84
|
!disabled_aggregated_failures?(example)
|
84
85
|
end
|
85
86
|
|
@@ -111,6 +112,10 @@ module RuboCop
|
|
111
112
|
def max_expectations
|
112
113
|
Integer(cop_config.fetch('Max', 1))
|
113
114
|
end
|
115
|
+
|
116
|
+
def aggregated_failures_by_default?
|
117
|
+
cop_config.fetch('AggregateFailuresByDefault', false)
|
118
|
+
end
|
114
119
|
end
|
115
120
|
end
|
116
121
|
end
|
@@ -87,7 +87,8 @@ module RuboCop
|
|
87
87
|
class NestedGroups < Cop
|
88
88
|
include RuboCop::RSpec::TopLevelDescribe
|
89
89
|
|
90
|
-
MSG = 'Maximum example group nesting exceeded
|
90
|
+
MSG = 'Maximum example group nesting exceeded ' \
|
91
|
+
'[%<total>d/%<max>d].'.freeze
|
91
92
|
|
92
93
|
DEPRECATED_MAX_KEY = 'MaxNesting'.freeze
|
93
94
|
|
@@ -120,7 +121,7 @@ module RuboCop
|
|
120
121
|
end
|
121
122
|
|
122
123
|
def message(nesting)
|
123
|
-
format(MSG, nesting, max_nesting)
|
124
|
+
format(MSG, total: nesting, max: max_nesting)
|
124
125
|
end
|
125
126
|
|
126
127
|
def max_nesting
|
@@ -16,7 +16,7 @@ module RuboCop
|
|
16
16
|
class NotToNot < Cop
|
17
17
|
include ConfigurableEnforcedStyle
|
18
18
|
|
19
|
-
MSG = 'Prefer
|
19
|
+
MSG = 'Prefer `%<replacement>s` over `%<original>s`.'.freeze
|
20
20
|
|
21
21
|
def_node_matcher :not_to_not_offense, '(send _ % ...)'
|
22
22
|
|
@@ -33,7 +33,7 @@ module RuboCop
|
|
33
33
|
private
|
34
34
|
|
35
35
|
def message(_node)
|
36
|
-
format(MSG, style, alternative_style)
|
36
|
+
format(MSG, replacement: style, original: alternative_style)
|
37
37
|
end
|
38
38
|
end
|
39
39
|
end
|
@@ -311,8 +311,6 @@ module RuboCop
|
|
311
311
|
check_explicit(node) if style == :explicit
|
312
312
|
end
|
313
313
|
|
314
|
-
private
|
315
|
-
|
316
314
|
def autocorrect(node)
|
317
315
|
case style
|
318
316
|
when :inflected
|
@@ -322,6 +320,8 @@ module RuboCop
|
|
322
320
|
end
|
323
321
|
end
|
324
322
|
|
323
|
+
private
|
324
|
+
|
325
325
|
# returns args location with whitespace
|
326
326
|
# @example
|
327
327
|
# foo 1, 2
|
data/rubocop-rspec.gemspec
CHANGED
@@ -32,7 +32,7 @@ Gem::Specification.new do |spec|
|
|
32
32
|
spec.test_files = spec.files.grep(%r{^spec/})
|
33
33
|
spec.extra_rdoc_files = ['MIT-LICENSE.md', 'README.md']
|
34
34
|
|
35
|
-
spec.add_runtime_dependency 'rubocop', '>= 0.
|
35
|
+
spec.add_runtime_dependency 'rubocop', '>= 0.52.0'
|
36
36
|
|
37
37
|
spec.add_development_dependency 'rake'
|
38
38
|
spec.add_development_dependency 'rspec', '>= 3.4'
|
@@ -132,7 +132,7 @@ RSpec.describe RuboCop::Cop::RSpec::MultipleExpectations, :config do
|
|
132
132
|
end
|
133
133
|
end
|
134
134
|
|
135
|
-
context 'with configuration' do
|
135
|
+
context 'with Max configuration' do
|
136
136
|
let(:cop_config) do
|
137
137
|
{ 'Max' => '2' }
|
138
138
|
end
|
@@ -162,6 +162,57 @@ RSpec.describe RuboCop::Cop::RSpec::MultipleExpectations, :config do
|
|
162
162
|
end
|
163
163
|
end
|
164
164
|
|
165
|
+
context 'with AggregateFailuresByDefault configuration' do
|
166
|
+
let(:cop_config) do
|
167
|
+
{ 'AggregateFailuresByDefault' => true }
|
168
|
+
end
|
169
|
+
|
170
|
+
it 'ignores examples without metadata' do
|
171
|
+
expect_no_offenses(<<-RUBY)
|
172
|
+
describe Foo do
|
173
|
+
it 'uses expect twice' do
|
174
|
+
expect(foo).to eq(bar)
|
175
|
+
expect(baz).to eq(bar)
|
176
|
+
end
|
177
|
+
end
|
178
|
+
RUBY
|
179
|
+
end
|
180
|
+
|
181
|
+
it 'ignores examples with `:aggregate_failures`' do
|
182
|
+
expect_no_offenses(<<-RUBY)
|
183
|
+
describe Foo do
|
184
|
+
it 'uses expect twice', :aggregate_failures do
|
185
|
+
expect(foo).to eq(bar)
|
186
|
+
expect(baz).to eq(bar)
|
187
|
+
end
|
188
|
+
end
|
189
|
+
RUBY
|
190
|
+
end
|
191
|
+
|
192
|
+
it 'ignores examples with `aggregate_failures: true`' do
|
193
|
+
expect_no_offenses(<<-RUBY)
|
194
|
+
describe Foo do
|
195
|
+
it 'uses expect twice', aggregate_failures: true do
|
196
|
+
expect(foo).to eq(bar)
|
197
|
+
expect(baz).to eq(bar)
|
198
|
+
end
|
199
|
+
end
|
200
|
+
RUBY
|
201
|
+
end
|
202
|
+
|
203
|
+
it 'checks examples with `aggregate_failures: false`' do
|
204
|
+
expect_offense(<<-RUBY)
|
205
|
+
describe Foo do
|
206
|
+
it 'uses expect twice', aggregate_failures: false do
|
207
|
+
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Example has too many expectations [2/1].
|
208
|
+
expect(foo).to eq(bar)
|
209
|
+
expect(baz).to eq(bar)
|
210
|
+
end
|
211
|
+
end
|
212
|
+
RUBY
|
213
|
+
end
|
214
|
+
end
|
215
|
+
|
165
216
|
it 'generates a todo based on the worst violation' do
|
166
217
|
inspect_source(<<-RUBY, 'spec/foo_spec.rb')
|
167
218
|
describe Foo do
|
@@ -9,12 +9,12 @@ RSpec.describe RuboCop::RSpec::Example do
|
|
9
9
|
|
10
10
|
it 'extracts doc string' do
|
11
11
|
expect(example("it('does x') { foo }").doc_string)
|
12
|
-
.to
|
12
|
+
.to eq(s(:str, 'does x'))
|
13
13
|
end
|
14
14
|
|
15
15
|
it 'extracts doc string for unimplemented examples' do
|
16
16
|
expect(example("it('does x')").doc_string)
|
17
|
-
.to
|
17
|
+
.to eq(s(:str, 'does x'))
|
18
18
|
end
|
19
19
|
|
20
20
|
it 'returns nil for examples without doc strings' do
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rubocop-rspec
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.21.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- John Backus
|
@@ -10,7 +10,7 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date: 2017-
|
13
|
+
date: 2017-12-13 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: rubocop
|
@@ -18,14 +18,14 @@ dependencies:
|
|
18
18
|
requirements:
|
19
19
|
- - ">="
|
20
20
|
- !ruby/object:Gem::Version
|
21
|
-
version: 0.
|
21
|
+
version: 0.52.0
|
22
22
|
type: :runtime
|
23
23
|
prerelease: false
|
24
24
|
version_requirements: !ruby/object:Gem::Requirement
|
25
25
|
requirements:
|
26
26
|
- - ">="
|
27
27
|
- !ruby/object:Gem::Version
|
28
|
-
version: 0.
|
28
|
+
version: 0.52.0
|
29
29
|
- !ruby/object:Gem::Dependency
|
30
30
|
name: rake
|
31
31
|
requirement: !ruby/object:Gem::Requirement
|