rubocop-rspec 2.0.0.pre → 2.3.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +39 -2
- data/README.md +7 -3
- data/config/default.yml +159 -73
- data/lib/rubocop-rspec.rb +8 -8
- data/lib/rubocop/cop/rspec/align_left_let_brace.rb +7 -3
- data/lib/rubocop/cop/rspec/align_right_let_brace.rb +7 -3
- data/lib/rubocop/cop/rspec/any_instance.rb +6 -10
- data/lib/rubocop/cop/rspec/around_block.rb +3 -1
- data/lib/rubocop/cop/rspec/base.rb +6 -55
- data/lib/rubocop/cop/rspec/be.rb +3 -2
- data/lib/rubocop/cop/rspec/be_eql.rb +2 -0
- data/lib/rubocop/cop/rspec/before_after_all.rb +6 -3
- data/lib/rubocop/cop/rspec/capybara/current_path_expectation.rb +7 -2
- data/lib/rubocop/cop/rspec/capybara/feature_methods.rb +6 -2
- data/lib/rubocop/cop/rspec/capybara/visibility_matcher.rb +4 -0
- data/lib/rubocop/cop/rspec/context_method.rb +1 -0
- data/lib/rubocop/cop/rspec/context_wording.rb +7 -1
- data/lib/rubocop/cop/rspec/describe_class.rb +5 -2
- data/lib/rubocop/cop/rspec/describe_method.rb +3 -2
- data/lib/rubocop/cop/rspec/describe_symbol.rb +2 -0
- data/lib/rubocop/cop/rspec/described_class.rb +6 -2
- data/lib/rubocop/cop/rspec/described_class_module_wrapping.rb +3 -3
- data/lib/rubocop/cop/rspec/dialect.rb +2 -1
- data/lib/rubocop/cop/rspec/empty_example_group.rb +6 -45
- data/lib/rubocop/cop/rspec/empty_hook.rb +2 -1
- data/lib/rubocop/cop/rspec/empty_line_after_example.rb +1 -1
- data/lib/rubocop/cop/rspec/empty_line_after_example_group.rb +1 -1
- data/lib/rubocop/cop/rspec/empty_line_after_final_let.rb +1 -1
- data/lib/rubocop/cop/rspec/empty_line_after_hook.rb +1 -1
- data/lib/rubocop/cop/rspec/empty_line_after_subject.rb +2 -2
- data/lib/rubocop/cop/rspec/example_length.rb +26 -12
- data/lib/rubocop/cop/rspec/example_without_description.rb +1 -0
- data/lib/rubocop/cop/rspec/example_wording.rb +1 -0
- data/lib/rubocop/cop/rspec/expect_actual.rb +3 -1
- data/lib/rubocop/cop/rspec/expect_change.rb +3 -0
- data/lib/rubocop/cop/rspec/expect_in_hook.rb +2 -1
- data/lib/rubocop/cop/rspec/expect_output.rb +1 -1
- data/lib/rubocop/cop/rspec/factory_bot/attribute_defined_statically.rb +3 -0
- data/lib/rubocop/cop/rspec/factory_bot/create_list.rb +4 -0
- data/lib/rubocop/cop/rspec/factory_bot/factory_class_name.rb +2 -0
- data/lib/rubocop/cop/rspec/file_path.rb +26 -17
- data/lib/rubocop/cop/rspec/focus.rb +46 -8
- data/lib/rubocop/cop/rspec/hook_argument.rb +4 -4
- data/lib/rubocop/cop/rspec/hooks_before_examples.rb +3 -2
- data/lib/rubocop/cop/rspec/implicit_block_expectation.rb +4 -0
- data/lib/rubocop/cop/rspec/implicit_expect.rb +2 -1
- data/lib/rubocop/cop/rspec/implicit_subject.rb +2 -0
- data/lib/rubocop/cop/rspec/instance_spy.rb +3 -1
- data/lib/rubocop/cop/rspec/instance_variable.rb +5 -1
- data/lib/rubocop/cop/rspec/it_behaves_like.rb +3 -1
- data/lib/rubocop/cop/rspec/iterated_expectation.rb +3 -1
- data/lib/rubocop/cop/rspec/let_before_examples.rb +3 -2
- data/lib/rubocop/cop/rspec/let_setup.rb +10 -4
- data/lib/rubocop/cop/rspec/message_chain.rb +4 -10
- data/lib/rubocop/cop/rspec/message_expectation.rb +3 -0
- data/lib/rubocop/cop/rspec/message_spies.rb +5 -3
- data/lib/rubocop/cop/rspec/mixin/comments_help.rb +38 -0
- data/lib/rubocop/cop/rspec/mixin/empty_line_separation.rb +51 -0
- data/lib/rubocop/cop/rspec/mixin/final_end_location.rb +19 -0
- data/lib/rubocop/cop/rspec/mixin/top_level_group.rb +54 -0
- data/lib/rubocop/cop/rspec/mixin/variable.rb +21 -0
- data/lib/rubocop/cop/rspec/multiple_describes.rb +2 -3
- data/lib/rubocop/cop/rspec/multiple_expectations.rb +4 -1
- data/lib/rubocop/cop/rspec/multiple_memoized_helpers.rb +3 -1
- data/lib/rubocop/cop/rspec/named_subject.rb +11 -12
- data/lib/rubocop/cop/rspec/nested_groups.rb +1 -1
- data/lib/rubocop/cop/rspec/not_to_not.rb +2 -0
- data/lib/rubocop/cop/rspec/overwriting_setup.rb +4 -1
- data/lib/rubocop/cop/rspec/pending.rb +17 -5
- data/lib/rubocop/cop/rspec/predicate_matcher.rb +8 -3
- data/lib/rubocop/cop/rspec/rails/http_status.rb +2 -0
- data/lib/rubocop/cop/rspec/receive_counts.rb +4 -0
- data/lib/rubocop/cop/rspec/receive_never.rb +2 -0
- data/lib/rubocop/cop/rspec/repeated_example_group_body.rb +8 -1
- data/lib/rubocop/cop/rspec/repeated_example_group_description.rb +4 -0
- data/lib/rubocop/cop/rspec/repeated_include_example.rb +6 -2
- data/lib/rubocop/cop/rspec/return_from_stub.rb +6 -0
- data/lib/rubocop/cop/rspec/scattered_setup.rb +1 -1
- data/lib/rubocop/cop/rspec/shared_context.rb +22 -11
- data/lib/rubocop/cop/rspec/shared_examples.rb +4 -1
- data/lib/rubocop/cop/rspec/single_argument_message_chain.rb +4 -1
- data/lib/rubocop/cop/rspec/stubbed_mock.rb +2 -1
- data/lib/rubocop/cop/rspec/subject_stub.rb +17 -6
- data/lib/rubocop/cop/rspec/unspecified_exception.rb +2 -0
- data/lib/rubocop/cop/rspec/variable_definition.rb +1 -1
- data/lib/rubocop/cop/rspec/variable_name.rb +1 -1
- data/lib/rubocop/cop/rspec/verified_doubles.rb +2 -0
- data/lib/rubocop/cop/rspec/void_expect.rb +3 -0
- data/lib/rubocop/cop/rspec/yield.rb +3 -0
- data/lib/rubocop/cop/rspec_cops.rb +0 -1
- data/lib/rubocop/rspec/align_let_brace.rb +1 -1
- data/lib/rubocop/rspec/concept.rb +2 -2
- data/lib/rubocop/rspec/config_formatter.rb +5 -3
- data/lib/rubocop/rspec/corrector/move_node.rb +7 -10
- data/lib/rubocop/rspec/example.rb +5 -0
- data/lib/rubocop/rspec/example_group.rb +15 -5
- data/lib/rubocop/rspec/hook.rb +2 -1
- data/lib/rubocop/rspec/inject.rb +4 -2
- data/lib/rubocop/rspec/language.rb +159 -115
- data/lib/rubocop/rspec/language/node_pattern.rb +7 -24
- data/lib/rubocop/rspec/node.rb +1 -1
- data/lib/rubocop/rspec/version.rb +1 -1
- metadata +27 -16
- data/lib/rubocop/cop/rspec/cop.rb +0 -10
- data/lib/rubocop/cop/rspec/invalid_predicate_matcher.rb +0 -41
- data/lib/rubocop/rspec.rb +0 -12
- data/lib/rubocop/rspec/empty_line_separation.rb +0 -48
- data/lib/rubocop/rspec/final_end_location.rb +0 -17
- data/lib/rubocop/rspec/top_level_describe.rb +0 -52
- data/lib/rubocop/rspec/top_level_group.rb +0 -57
- data/lib/rubocop/rspec/variable.rb +0 -16
@@ -23,8 +23,11 @@ module RuboCop
|
|
23
23
|
class SharedExamples < Base
|
24
24
|
extend AutoCorrector
|
25
25
|
|
26
|
+
# @!method shared_examples(node)
|
26
27
|
def_node_matcher :shared_examples,
|
27
|
-
(
|
28
|
+
send_pattern(
|
29
|
+
'{#SharedGroups.all #Includes.all}'
|
30
|
+
)
|
28
31
|
|
29
32
|
def on_send(node)
|
30
33
|
shared_examples(node) do
|
@@ -19,13 +19,16 @@ module RuboCop
|
|
19
19
|
class SingleArgumentMessageChain < Base
|
20
20
|
extend AutoCorrector
|
21
21
|
|
22
|
-
MSG = 'Use `%<recommended>s` instead of calling '\
|
22
|
+
MSG = 'Use `%<recommended>s` instead of calling ' \
|
23
23
|
'`%<called>s` with a single argument.'
|
24
|
+
RESTRICT_ON_SEND = %i[receive_message_chain stub_chain].freeze
|
24
25
|
|
26
|
+
# @!method message_chain(node)
|
25
27
|
def_node_matcher :message_chain, <<-PATTERN
|
26
28
|
(send _ {:receive_message_chain :stub_chain} $_)
|
27
29
|
PATTERN
|
28
30
|
|
31
|
+
# @!method single_key_hash?(node)
|
29
32
|
def_node_matcher :single_key_hash?, '(hash pair)'
|
30
33
|
|
31
34
|
def on_send(node)
|
@@ -39,6 +39,7 @@ module RuboCop
|
|
39
39
|
}
|
40
40
|
PATTERN
|
41
41
|
|
42
|
+
# @!method configured_response?(node)
|
42
43
|
def_node_matcher :configured_response?, <<~PATTERN
|
43
44
|
{ :and_return :and_raise :and_throw :and_yield
|
44
45
|
:and_call_original :and_wrap_original }
|
@@ -60,7 +61,7 @@ module RuboCop
|
|
60
61
|
# @yield [RuboCop::AST::Node] expectation, method name, matcher
|
61
62
|
def_node_matcher :expectation, <<~PATTERN
|
62
63
|
(send
|
63
|
-
$(send nil? $#
|
64
|
+
$(send nil? $#Expectations.all ...)
|
64
65
|
:to $_)
|
65
66
|
PATTERN
|
66
67
|
|
@@ -13,16 +13,26 @@ module RuboCop
|
|
13
13
|
#
|
14
14
|
# @example
|
15
15
|
# # bad
|
16
|
-
# describe
|
17
|
-
# subject(:
|
16
|
+
# describe Article do
|
17
|
+
# subject(:article) { Article.new }
|
18
18
|
#
|
19
|
-
#
|
20
|
-
# allow(
|
19
|
+
# it 'indicates that the author is unknown' do
|
20
|
+
# allow(article).to receive(:author).and_return(nil)
|
21
|
+
# expect(article.description).to include('by an unknown author')
|
22
|
+
# end
|
23
|
+
# end
|
24
|
+
#
|
25
|
+
# # good
|
26
|
+
# describe Article do
|
27
|
+
# subject(:article) { Article.new(author: nil) }
|
28
|
+
#
|
29
|
+
# it 'indicates that the author is unknown' do
|
30
|
+
# expect(article.description).to include('by an unknown author')
|
21
31
|
# end
|
22
32
|
# end
|
23
33
|
#
|
24
34
|
class SubjectStub < Base
|
25
|
-
include
|
35
|
+
include TopLevelGroup
|
26
36
|
|
27
37
|
MSG = 'Do not stub methods of the object under test.'
|
28
38
|
|
@@ -66,11 +76,12 @@ module RuboCop
|
|
66
76
|
(send nil? { :expect :allow } (send nil? {% :subject}))
|
67
77
|
(send nil? :is_expected)
|
68
78
|
}
|
69
|
-
#
|
79
|
+
#Runners.all
|
70
80
|
#message_expectation_matcher?
|
71
81
|
)
|
72
82
|
PATTERN
|
73
83
|
|
84
|
+
# @!method message_expectation_matcher?(node)
|
74
85
|
def_node_search :message_expectation_matcher?, <<-PATTERN
|
75
86
|
(send nil? {
|
76
87
|
:receive :receive_messages :receive_message_chain :have_received
|
@@ -32,7 +32,9 @@ module RuboCop
|
|
32
32
|
# expect { do_something }.not_to raise_error
|
33
33
|
class UnspecifiedException < Base
|
34
34
|
MSG = 'Specify the exception being captured'
|
35
|
+
RESTRICT_ON_SEND = %i[to].freeze
|
35
36
|
|
37
|
+
# @!method empty_raise_error_or_exception(node)
|
36
38
|
def_node_matcher :empty_raise_error_or_exception, <<-PATTERN
|
37
39
|
(send
|
38
40
|
(block
|
@@ -24,7 +24,9 @@ module RuboCop
|
|
24
24
|
# end
|
25
25
|
class VerifiedDoubles < Base
|
26
26
|
MSG = 'Prefer using verifying doubles over normal doubles.'
|
27
|
+
RESTRICT_ON_SEND = %i[double spy].freeze
|
27
28
|
|
29
|
+
# @!method unverified_double(node)
|
28
30
|
def_node_matcher :unverified_double, <<-PATTERN
|
29
31
|
{(send nil? {:double :spy} $...)}
|
30
32
|
PATTERN
|
@@ -14,11 +14,14 @@ module RuboCop
|
|
14
14
|
class VoidExpect < Base
|
15
15
|
MSG = 'Do not use `expect()` without `.to` or `.not_to`. ' \
|
16
16
|
'Chain the methods or remove it.'
|
17
|
+
RESTRICT_ON_SEND = %i[expect].freeze
|
17
18
|
|
19
|
+
# @!method expect?(node)
|
18
20
|
def_node_matcher :expect?, <<-PATTERN
|
19
21
|
(send nil? :expect ...)
|
20
22
|
PATTERN
|
21
23
|
|
24
|
+
# @!method expect_block?(node)
|
22
25
|
def_node_matcher :expect_block?, <<-PATTERN
|
23
26
|
(block #expect? (args) _body)
|
24
27
|
PATTERN
|
@@ -17,10 +17,13 @@ module RuboCop
|
|
17
17
|
|
18
18
|
MSG = 'Use `.and_yield`.'
|
19
19
|
|
20
|
+
# @!method method_on_stub?(node)
|
20
21
|
def_node_search :method_on_stub?, '(send nil? :receive ...)'
|
21
22
|
|
23
|
+
# @!method block_arg(node)
|
22
24
|
def_node_matcher :block_arg, '(args (blockarg $_))'
|
23
25
|
|
26
|
+
# @!method block_call?(node)
|
24
27
|
def_node_matcher :block_call?, '(send (lvar %) :call ...)'
|
25
28
|
|
26
29
|
def on_block(node)
|
@@ -52,7 +52,6 @@ require_relative 'rspec/implicit_expect'
|
|
52
52
|
require_relative 'rspec/implicit_subject'
|
53
53
|
require_relative 'rspec/instance_spy'
|
54
54
|
require_relative 'rspec/instance_variable'
|
55
|
-
require_relative 'rspec/invalid_predicate_matcher'
|
56
55
|
require_relative 'rspec/it_behaves_like'
|
57
56
|
require_relative 'rspec/iterated_expectation'
|
58
57
|
require_relative 'rspec/leading_subject'
|
@@ -4,9 +4,9 @@ module RuboCop
|
|
4
4
|
module RSpec
|
5
5
|
# Wrapper for RSpec DSL methods
|
6
6
|
class Concept
|
7
|
+
extend RuboCop::NodePattern::Macros
|
8
|
+
extend Language::NodePattern
|
7
9
|
include Language
|
8
|
-
include Language::NodePattern
|
9
|
-
extend NodePattern::Macros
|
10
10
|
|
11
11
|
def initialize(node)
|
12
12
|
@node = node
|
@@ -6,7 +6,7 @@ module RuboCop
|
|
6
6
|
module RSpec
|
7
7
|
# Builds a YAML config file from two config hashes
|
8
8
|
class ConfigFormatter
|
9
|
-
|
9
|
+
EXTENSION_ROOT_DEPARTMENT = %r{^(RSpec/)}.freeze
|
10
10
|
STYLE_GUIDE_BASE_URL = 'https://www.rubydoc.info/gems/rubocop-rspec/RuboCop/Cop/RSpec/'
|
11
11
|
|
12
12
|
def initialize(config, descriptions)
|
@@ -15,7 +15,9 @@ module RuboCop
|
|
15
15
|
end
|
16
16
|
|
17
17
|
def dump
|
18
|
-
YAML.dump(unified_config)
|
18
|
+
YAML.dump(unified_config)
|
19
|
+
.gsub(EXTENSION_ROOT_DEPARTMENT, "\n\\1")
|
20
|
+
.gsub(/^(\s+)- /, '\1 - ')
|
19
21
|
end
|
20
22
|
|
21
23
|
private
|
@@ -29,7 +31,7 @@ module RuboCop
|
|
29
31
|
end
|
30
32
|
|
31
33
|
def cops
|
32
|
-
(descriptions.keys | config.keys).grep(
|
34
|
+
(descriptions.keys | config.keys).grep(EXTENSION_ROOT_DEPARTMENT)
|
33
35
|
end
|
34
36
|
|
35
37
|
attr_reader :config, :descriptions
|
@@ -6,7 +6,8 @@ module RuboCop
|
|
6
6
|
# Helper methods to move a node
|
7
7
|
class MoveNode
|
8
8
|
include RuboCop::Cop::RangeHelp
|
9
|
-
include RuboCop::RSpec::
|
9
|
+
include RuboCop::Cop::RSpec::CommentsHelp
|
10
|
+
include RuboCop::Cop::RSpec::FinalEndLocation
|
10
11
|
|
11
12
|
attr_reader :original, :corrector, :processed_source
|
12
13
|
|
@@ -17,20 +18,16 @@ module RuboCop
|
|
17
18
|
end
|
18
19
|
|
19
20
|
def move_before(other)
|
20
|
-
position = other
|
21
|
-
indent = ' ' * other.loc.column
|
22
|
-
newline_indent = "\n#{indent}"
|
21
|
+
position = start_line_position(other)
|
23
22
|
|
24
|
-
corrector.insert_before(position, source(original)
|
23
|
+
corrector.insert_before(position, "#{source(original)}\n")
|
25
24
|
corrector.remove(node_range_with_surrounding_space(original))
|
26
25
|
end
|
27
26
|
|
28
27
|
def move_after(other)
|
29
|
-
position =
|
30
|
-
indent = ' ' * other.loc.column
|
31
|
-
newline_indent = "\n#{indent}"
|
28
|
+
position = end_line_position(other)
|
32
29
|
|
33
|
-
corrector.insert_after(position,
|
30
|
+
corrector.insert_after(position, "\n#{source(original)}")
|
34
31
|
corrector.remove(node_range_with_surrounding_space(original))
|
35
32
|
end
|
36
33
|
|
@@ -41,7 +38,7 @@ module RuboCop
|
|
41
38
|
end
|
42
39
|
|
43
40
|
def node_range(node)
|
44
|
-
|
41
|
+
source_range_with_comment(node)
|
45
42
|
end
|
46
43
|
|
47
44
|
def node_range_with_surrounding_space(node)
|
@@ -4,8 +4,13 @@ module RuboCop
|
|
4
4
|
module RSpec
|
5
5
|
# Wrapper for RSpec examples
|
6
6
|
class Example < Concept
|
7
|
+
# @!method extract_doc_string(node)
|
7
8
|
def_node_matcher :extract_doc_string, '(send _ _ $_ ...)'
|
9
|
+
|
10
|
+
# @!method extract_metadata(node)
|
8
11
|
def_node_matcher :extract_metadata, '(send _ _ _ $...)'
|
12
|
+
|
13
|
+
# @!method extract_implementation(node)
|
9
14
|
def_node_matcher :extract_implementation, '(block send args $_)'
|
10
15
|
|
11
16
|
def doc_string
|
@@ -10,9 +10,14 @@ module RuboCop
|
|
10
10
|
#
|
11
11
|
# Selectors which indicate that we should stop searching
|
12
12
|
#
|
13
|
-
def_node_matcher :scope_change?,
|
14
|
-
|
15
|
-
|
13
|
+
def_node_matcher :scope_change?,
|
14
|
+
block_pattern(<<~PATTERN)
|
15
|
+
{
|
16
|
+
#SharedGroups.all
|
17
|
+
#ExampleGroups.all
|
18
|
+
#Includes.all
|
19
|
+
}
|
20
|
+
PATTERN
|
16
21
|
|
17
22
|
def lets
|
18
23
|
find_all_in_scope(node, :let?)
|
@@ -23,11 +28,15 @@ module RuboCop
|
|
23
28
|
end
|
24
29
|
|
25
30
|
def examples
|
26
|
-
find_all_in_scope(node, :example?).map
|
31
|
+
find_all_in_scope(node, :example?).map do |node|
|
32
|
+
Example.new(node)
|
33
|
+
end
|
27
34
|
end
|
28
35
|
|
29
36
|
def hooks
|
30
|
-
find_all_in_scope(node, :hook?).map
|
37
|
+
find_all_in_scope(node, :hook?).map do |node|
|
38
|
+
Hook.new(node)
|
39
|
+
end
|
31
40
|
end
|
32
41
|
|
33
42
|
private
|
@@ -37,6 +46,7 @@ module RuboCop
|
|
37
46
|
# Searches node and halts when a scope change is detected
|
38
47
|
#
|
39
48
|
# @param node [RuboCop::AST::Node] node to recursively search
|
49
|
+
# @param predicate [Symbol] method to call with node as argument
|
40
50
|
#
|
41
51
|
# @return [Array<RuboCop::AST::Node>] discovered nodes
|
42
52
|
def find_all_in_scope(node, predicate)
|
data/lib/rubocop/rspec/hook.rb
CHANGED
@@ -4,6 +4,7 @@ module RuboCop
|
|
4
4
|
module RSpec
|
5
5
|
# Wrapper for RSpec hook
|
6
6
|
class Hook < Concept
|
7
|
+
# @!method extract_metadata(node)
|
7
8
|
def_node_matcher :extract_metadata, <<~PATTERN
|
8
9
|
(block
|
9
10
|
(send _ _ #valid_scope? ? $...) ...
|
@@ -44,7 +45,7 @@ module RuboCop
|
|
44
45
|
private
|
45
46
|
|
46
47
|
def valid_scope?(node)
|
47
|
-
node&.sym_type? &&
|
48
|
+
node&.sym_type? && Language::HookScopes.all(node.value)
|
48
49
|
end
|
49
50
|
|
50
51
|
def transform_metadata(meta)
|
data/lib/rubocop/rspec/inject.rb
CHANGED
@@ -6,9 +6,11 @@ module RuboCop
|
|
6
6
|
# bit of our configuration.
|
7
7
|
module Inject
|
8
8
|
def self.defaults!
|
9
|
-
|
9
|
+
project_root = Pathname.new(__dir__).parent.parent.parent.expand_path
|
10
|
+
config_default = project_root.join('config', 'default.yml')
|
11
|
+
path = config_default.to_s
|
10
12
|
hash = ConfigLoader.send(:load_yaml_configuration, path)
|
11
|
-
config = Config.new(hash, path)
|
13
|
+
config = RuboCop::Config.new(hash, path)
|
12
14
|
puts "configuration from #{path}" if ConfigLoader.debug?
|
13
15
|
config = ConfigLoader.merge_with_default(config, path)
|
14
16
|
ConfigLoader.instance_variable_set(:@default_configuration, config)
|
@@ -2,152 +2,196 @@
|
|
2
2
|
|
3
3
|
module RuboCop
|
4
4
|
module RSpec
|
5
|
-
#
|
5
|
+
# Contains node matchers for common RSpec DSL.
|
6
|
+
#
|
7
|
+
# RSpec allows for configuring aliases for commonly used DSL elements, e.g.
|
8
|
+
# example groups and hooks. It is possible to configure RuboCop RSpec to
|
9
|
+
# be able to properly detect these elements in the `RSpec/Language` section
|
10
|
+
# of the RuboCop YAML configuration file.
|
11
|
+
#
|
12
|
+
# In addition to providing useful matchers, this class is responsible for
|
13
|
+
# using the configured aliases.
|
6
14
|
module Language
|
7
|
-
|
8
|
-
|
9
|
-
def initialize(selectors)
|
10
|
-
@selectors = selectors.freeze
|
11
|
-
freeze
|
12
|
-
end
|
13
|
-
|
14
|
-
def ==(other)
|
15
|
-
selectors.eql?(other.selectors)
|
16
|
-
end
|
17
|
-
|
18
|
-
def +(other)
|
19
|
-
self.class.new(selectors + other.selectors)
|
20
|
-
end
|
21
|
-
|
22
|
-
def include?(selector)
|
23
|
-
selectors.include?(selector)
|
24
|
-
end
|
15
|
+
extend RuboCop::NodePattern::Macros
|
16
|
+
extend NodePattern
|
25
17
|
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
def block_pass_pattern
|
31
|
-
"(send #rspec? #{node_pattern_union} _ block_pass)"
|
32
|
-
end
|
18
|
+
class << self
|
19
|
+
attr_accessor :config
|
20
|
+
end
|
33
21
|
|
34
|
-
|
35
|
-
|
22
|
+
# @!method rspec?(node)
|
23
|
+
def_node_matcher :rspec?, '{(const {nil? cbase} :RSpec) nil?}'
|
24
|
+
|
25
|
+
# @!method example_group?(node)
|
26
|
+
def_node_matcher :example_group?, block_pattern('#ExampleGroups.all')
|
27
|
+
|
28
|
+
# @!method shared_group?(node)
|
29
|
+
def_node_matcher :shared_group?, block_pattern('#SharedGroups.all')
|
30
|
+
|
31
|
+
# @!method spec_group?(node)
|
32
|
+
def_node_matcher :spec_group?,
|
33
|
+
block_pattern('{#SharedGroups.all #ExampleGroups.all}')
|
34
|
+
|
35
|
+
# @!method example_group_with_body?(node)
|
36
|
+
def_node_matcher :example_group_with_body?, <<-PATTERN
|
37
|
+
(block #{send_pattern('#ExampleGroups.all')} args !nil?)
|
38
|
+
PATTERN
|
39
|
+
|
40
|
+
# @!method example?(node)
|
41
|
+
def_node_matcher :example?, block_pattern('#Examples.all')
|
42
|
+
|
43
|
+
# @!method hook?(node)
|
44
|
+
def_node_matcher :hook?, block_pattern('#Hooks.all')
|
45
|
+
|
46
|
+
# @!method let?(node)
|
47
|
+
def_node_matcher :let?, <<-PATTERN
|
48
|
+
{
|
49
|
+
#{block_pattern('#Helpers.all')}
|
50
|
+
(send #rspec? #Helpers.all _ block_pass)
|
51
|
+
}
|
52
|
+
PATTERN
|
53
|
+
|
54
|
+
# @!method include?(node)
|
55
|
+
def_node_matcher :include?, <<-PATTERN
|
56
|
+
{
|
57
|
+
#{send_pattern('#Includes.all')}
|
58
|
+
#{block_pattern('#Includes.all')}
|
59
|
+
}
|
60
|
+
PATTERN
|
61
|
+
|
62
|
+
# @!method subject?(node)
|
63
|
+
def_node_matcher :subject?, block_pattern('#Subjects.all')
|
64
|
+
|
65
|
+
module ExampleGroups # :nodoc:
|
66
|
+
class << self
|
67
|
+
def all(element)
|
68
|
+
regular(element) ||
|
69
|
+
skipped(element) ||
|
70
|
+
focused(element)
|
71
|
+
end
|
72
|
+
|
73
|
+
def regular(element)
|
74
|
+
Language.config['ExampleGroups']['Regular'].include?(element.to_s)
|
75
|
+
end
|
76
|
+
|
77
|
+
def focused(element)
|
78
|
+
Language.config['ExampleGroups']['Focused'].include?(element.to_s)
|
79
|
+
end
|
80
|
+
|
81
|
+
def skipped(element)
|
82
|
+
Language.config['ExampleGroups']['Skipped'].include?(element.to_s)
|
83
|
+
end
|
36
84
|
end
|
85
|
+
end
|
37
86
|
|
38
|
-
|
39
|
-
|
87
|
+
module Examples # :nodoc:
|
88
|
+
class << self
|
89
|
+
def all(element)
|
90
|
+
regular(element) ||
|
91
|
+
focused(element) ||
|
92
|
+
skipped(element) ||
|
93
|
+
pending(element)
|
94
|
+
end
|
95
|
+
|
96
|
+
def regular(element)
|
97
|
+
Language.config['Examples']['Regular'].include?(element.to_s)
|
98
|
+
end
|
99
|
+
|
100
|
+
def focused(element)
|
101
|
+
Language.config['Examples']['Focused'].include?(element.to_s)
|
102
|
+
end
|
103
|
+
|
104
|
+
def skipped(element)
|
105
|
+
Language.config['Examples']['Skipped'].include?(element.to_s)
|
106
|
+
end
|
107
|
+
|
108
|
+
def pending(element)
|
109
|
+
Language.config['Examples']['Pending'].include?(element.to_s)
|
110
|
+
end
|
40
111
|
end
|
112
|
+
end
|
41
113
|
|
42
|
-
|
43
|
-
|
114
|
+
module Expectations # :nodoc:
|
115
|
+
def self.all(element)
|
116
|
+
Language.config['Expectations'].include?(element.to_s)
|
44
117
|
end
|
118
|
+
end
|
45
119
|
|
46
|
-
|
47
|
-
|
120
|
+
module Helpers # :nodoc:
|
121
|
+
def self.all(element)
|
122
|
+
Language.config['Helpers'].include?(element.to_s)
|
48
123
|
end
|
124
|
+
end
|
49
125
|
|
50
|
-
|
51
|
-
|
126
|
+
module Hooks # :nodoc:
|
127
|
+
def self.all(element)
|
128
|
+
Language.config['Hooks'].include?(element.to_s)
|
52
129
|
end
|
130
|
+
end
|
53
131
|
|
54
|
-
|
55
|
-
|
132
|
+
module HookScopes # :nodoc:
|
133
|
+
def self.all(element)
|
134
|
+
Language.config['HookScopes'].include?(element.to_s)
|
56
135
|
end
|
57
|
-
|
58
|
-
protected
|
59
|
-
|
60
|
-
attr_reader :selectors
|
61
136
|
end
|
62
137
|
|
63
|
-
module
|
64
|
-
|
65
|
-
|
66
|
-
|
138
|
+
module Includes # :nodoc:
|
139
|
+
class << self
|
140
|
+
def all(element)
|
141
|
+
examples(element) ||
|
142
|
+
context(element)
|
143
|
+
end
|
67
144
|
|
68
|
-
|
69
|
-
|
145
|
+
def examples(element)
|
146
|
+
Language.config['Includes']['Examples'].include?(element.to_s)
|
147
|
+
end
|
70
148
|
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
ALL = EXAMPLES + CONTEXT
|
149
|
+
def context(element)
|
150
|
+
Language.config['Includes']['Context'].include?(element.to_s)
|
151
|
+
end
|
152
|
+
end
|
76
153
|
end
|
77
154
|
|
78
|
-
module
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
it_should_behave_like
|
83
|
-
include_examples
|
84
|
-
]
|
85
|
-
)
|
86
|
-
CONTEXT = SelectorSet.new(%i[include_context])
|
87
|
-
|
88
|
-
ALL = EXAMPLES + CONTEXT
|
155
|
+
module Runners # :nodoc:
|
156
|
+
def self.all(element)
|
157
|
+
Language.config['Runners'].include?(element.to_s)
|
158
|
+
end
|
89
159
|
end
|
90
160
|
|
91
|
-
module
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
161
|
+
module SharedGroups # :nodoc:
|
162
|
+
class << self
|
163
|
+
def all(element)
|
164
|
+
examples(element) ||
|
165
|
+
context(element)
|
166
|
+
end
|
96
167
|
|
97
|
-
|
98
|
-
|
168
|
+
def examples(element)
|
169
|
+
Language.config['SharedGroups']['Examples'].include?(element.to_s)
|
170
|
+
end
|
99
171
|
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
prepend_before
|
104
|
-
before
|
105
|
-
append_before
|
106
|
-
around
|
107
|
-
prepend_after
|
108
|
-
after
|
109
|
-
append_after
|
110
|
-
]
|
111
|
-
)
|
112
|
-
|
113
|
-
module Scopes
|
114
|
-
ALL = SelectorSet.new(
|
115
|
-
%i[
|
116
|
-
each
|
117
|
-
example
|
118
|
-
context
|
119
|
-
all
|
120
|
-
suite
|
121
|
-
]
|
122
|
-
)
|
172
|
+
def context(element)
|
173
|
+
Language.config['SharedGroups']['Context'].include?(element.to_s)
|
174
|
+
end
|
123
175
|
end
|
124
176
|
end
|
125
177
|
|
126
|
-
module
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
module Subject
|
131
|
-
ALL = SelectorSet.new(%i[subject subject!])
|
132
|
-
end
|
133
|
-
|
134
|
-
module Expectations
|
135
|
-
ALL = SelectorSet.new(%i[expect is_expected expect_any_instance_of])
|
178
|
+
module Subjects # :nodoc:
|
179
|
+
def self.all(element)
|
180
|
+
Language.config['Subjects'].include?(element.to_s)
|
181
|
+
end
|
136
182
|
end
|
137
183
|
|
138
|
-
|
139
|
-
|
184
|
+
# This is used in Dialect and DescribeClass cops to detect RSpec blocks.
|
185
|
+
module ALL # :nodoc:
|
186
|
+
def self.all(element)
|
187
|
+
[ExampleGroups, Examples, Expectations, Helpers, Hooks, Includes,
|
188
|
+
Runners, SharedGroups, Subjects]
|
189
|
+
.find { |concept| concept.all(element) }
|
190
|
+
end
|
140
191
|
end
|
141
192
|
|
142
|
-
|
143
|
-
|
144
|
-
SharedGroups::ALL +
|
145
|
-
Examples::ALL +
|
146
|
-
Hooks::ALL +
|
147
|
-
Helpers::ALL +
|
148
|
-
Subject::ALL +
|
149
|
-
Expectations::ALL +
|
150
|
-
Runners::ALL
|
193
|
+
private_constant :ExampleGroups, :Examples, :Expectations, :Hooks,
|
194
|
+
:Includes, :Runners, :SharedGroups, :ALL
|
151
195
|
end
|
152
196
|
end
|
153
197
|
end
|