rubocop 0.93.0 → 0.93.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 4d381604ba6395ffc42db74e3f57245307935ec7a56d365e10b8d07207d432a1
4
- data.tar.gz: 2b290525226f487d860b5a1201266d1b20e403a05ed8a704c1270b7edaca5e2f
3
+ metadata.gz: b8ce11205d6a6bb518654cbe498544aa799fbb8d9c9057afd2f551edfc35bbb8
4
+ data.tar.gz: a1f79001991b28508ca7c9a79d75ed58f39ae0dcf2bad419d6a75919b3a3d539
5
5
  SHA512:
6
- metadata.gz: 8639a2098ab1fb1e50fe6993e0a2d9f305998b7cc0215ab6bdd615506a4f8271de1fe78dbe1592b1ade597b40b79acfe4c5bc0503d8ee72940ff1732fd25a19d
7
- data.tar.gz: 11278958d9183ba56561ffc1f6b3cc69ac0b2f7d883cf5192cb31ab3ace1eacce21a23a13f998f4f2917d14574a6c27309be8f48085fc7abf940eab2ba0d1cce
6
+ metadata.gz: a32001a91575c41b5ca71b6a148af79f45b2a7b8cbc3909a0dcbb7a652f5e62b6a79a84c14189eda64fd3d2a9e8c40d207c37c0f5a78a156e1f636c5191b995e
7
+ data.tar.gz: 9ac5df57938099031807a96bd87a7fb9c5f7f40c314528b4c3254edb45b1386ce199fa9c394c9e7531655d117df9d3d5215bd66e4a927b9b2b0878e0eac2a1f6
data/README.md CHANGED
@@ -49,7 +49,7 @@ haven't reached version 1.0 yet). To prevent an unwanted RuboCop update you
49
49
  might want to use a conservative version lock in your `Gemfile`:
50
50
 
51
51
  ```rb
52
- gem 'rubocop', '~> 0.93.0', require: false
52
+ gem 'rubocop', '~> 0.93.1', require: false
53
53
  ```
54
54
 
55
55
  ## Quickstart
@@ -1757,16 +1757,14 @@ Lint/RedundantSafeNavigation:
1757
1757
  Description: 'Checks for redundant safe navigation calls.'
1758
1758
  Enabled: pending
1759
1759
  VersionAdded: '0.93'
1760
+ AllowedMethods:
1761
+ - instance_of?
1762
+ - kind_of?
1763
+ - is_a?
1764
+ - eql?
1765
+ - respond_to?
1766
+ - equal?
1760
1767
  Safe: false
1761
- IgnoredMethods:
1762
- - to_c
1763
- - to_f
1764
- - to_i
1765
- - to_r
1766
- - rationalize
1767
- - public_send
1768
- - send
1769
- - __send__
1770
1768
 
1771
1769
  Lint/RedundantSplatExpansion:
1772
1770
  Description: 'Checks for splat unnecessarily being called on literals.'
@@ -53,15 +53,18 @@ module RuboCop
53
53
  def find_offense_node(node, regexp_receiver)
54
54
  return node unless node.parent
55
55
 
56
- if node.parent.send_type? || method_chain_to_regexp_receiver?(node)
56
+ if node.parent.send_type? || method_chain_to_regexp_receiver?(node, regexp_receiver)
57
57
  node = find_offense_node(node.parent, regexp_receiver)
58
58
  end
59
59
 
60
60
  node
61
61
  end
62
62
 
63
- def method_chain_to_regexp_receiver?(node)
64
- node.parent.parent && node.parent.receiver.receiver == regexp_receiver
63
+ def method_chain_to_regexp_receiver?(node, regexp_receiver)
64
+ return false unless (parent = node.parent)
65
+ return false unless (parent_receiver = parent.receiver)
66
+
67
+ parent.parent && parent_receiver.receiver == regexp_receiver
65
68
  end
66
69
  end
67
70
  end
@@ -4,29 +4,52 @@ module RuboCop
4
4
  module Cop
5
5
  module Lint
6
6
  # This cop checks for redundant safe navigation calls.
7
- # It is marked as unsafe, because it can produce code that returns
8
- # non `nil` while `nil` result is expected on `nil` receiver.
7
+ # `instance_of?`, `kind_of?`, `is_a?`, `eql?`, `respond_to?`, and `equal?` methods
8
+ # are checked by default. These are customizable with `AllowedMethods` option.
9
+ #
10
+ # This cop is marked as unsafe, because auto-correction can change the
11
+ # return type of the expression. An offending expression that previously
12
+ # could return `nil` will be auto-corrected to never return `nil`.
13
+ #
14
+ # In the example below, the safe navigation operator (`&.`) is unnecessary
15
+ # because `NilClass` has methods like `respond_to?` and `is_a?`.
9
16
  #
10
17
  # @example
11
18
  # # bad
12
- # attrs&.respond_to?(:[])
13
- # foo&.dup&.inspect
19
+ # do_something if attrs&.respond_to?(:[])
20
+ #
21
+ # # good
22
+ # do_something if attrs.respond_to?(:[])
23
+ #
24
+ # # bad
25
+ # while node&.is_a?(BeginNode)
26
+ # node = node.parent
27
+ # end
14
28
  #
15
29
  # # good
16
- # attrs.respond_to?(:[])
17
- # foo.dup.inspect
30
+ # while node.is_a?(BeginNode)
31
+ # node = node.parent
32
+ # end
33
+ #
34
+ # # good - without `&.` this will always return `true`
35
+ # foo&.respond_to?(:to_a)
18
36
  #
19
37
  class RedundantSafeNavigation < Base
20
- include IgnoredMethods
38
+ include AllowedMethods
21
39
  include RangeHelp
22
40
  extend AutoCorrector
23
41
 
24
42
  MSG = 'Redundant safe navigation detected.'
25
43
 
26
- NIL_METHODS = nil.methods.to_set.freeze
44
+ NIL_SPECIFIC_METHODS = (nil.methods - Object.new.methods).to_set.freeze
45
+
46
+ def_node_matcher :respond_to_nil_specific_method?, <<~PATTERN
47
+ (csend _ :respond_to? (sym %NIL_SPECIFIC_METHODS))
48
+ PATTERN
27
49
 
28
50
  def on_csend(node)
29
- return unless check_method?(node.method_name)
51
+ return unless check?(node) && allowed_method?(node.method_name)
52
+ return if respond_to_nil_specific_method?(node)
30
53
 
31
54
  range = range_between(node.loc.dot.begin_pos, node.source_range.end_pos)
32
55
  add_offense(range) do |corrector|
@@ -36,8 +59,18 @@ module RuboCop
36
59
 
37
60
  private
38
61
 
39
- def check_method?(method_name)
40
- NIL_METHODS.include?(method_name) && !ignored_method?(method_name)
62
+ def check?(node)
63
+ parent = node.parent
64
+ return false unless parent
65
+
66
+ condition?(parent, node) ||
67
+ parent.and_type? ||
68
+ parent.or_type? ||
69
+ (parent.send_type? && parent.negation_method?)
70
+ end
71
+
72
+ def condition?(parent, node)
73
+ (parent.conditional? || parent.post_condition_loop?) && parent.condition == node
41
74
  end
42
75
  end
43
76
  end
@@ -39,13 +39,19 @@ module RuboCop
39
39
  end
40
40
 
41
41
  def on_casgn(node)
42
- if node.parent&.assignment?
43
- block_node = node.parent.children[1]
42
+ parent = node.parent
43
+
44
+ if parent&.assignment?
45
+ block_node = parent.children[1]
46
+ elsif parent&.parent&.masgn_type?
47
+ block_node = parent.parent.children[1]
44
48
  else
45
49
  _scope, _name, block_node = *node
46
50
  end
47
51
 
48
- check_code_length(block_node) if block_node.class_definition?
52
+ return unless block_node.respond_to?(:class_definition?) && block_node.class_definition?
53
+
54
+ check_code_length(block_node)
49
55
  end
50
56
 
51
57
  private
@@ -21,7 +21,7 @@ module RuboCop
21
21
  include IgnoredMethods
22
22
  extend AutoCorrector
23
23
 
24
- MSG = 'Use `Object.instance_of?` instead of comparing classes.'
24
+ MSG = 'Use `instance_of?(%<class_name>s)` instead of comparing classes.'
25
25
 
26
26
  RESTRICT_ON_SEND = %i[== equal? eql?].freeze
27
27
 
@@ -36,13 +36,28 @@ module RuboCop
36
36
  return if def_node && ignored_method?(def_node.method_name)
37
37
 
38
38
  class_comparison_candidate?(node) do |receiver_node, class_node|
39
- range = range_between(receiver_node.loc.selector.begin_pos, node.source_range.end_pos)
39
+ range = offense_range(receiver_node, node)
40
+ class_name = class_name(class_node, node)
40
41
 
41
- add_offense(range) do |corrector|
42
- corrector.replace(range, "instance_of?(#{class_node.source})")
42
+ add_offense(range, message: format(MSG, class_name: class_name)) do |corrector|
43
+ corrector.replace(range, "instance_of?(#{class_name})")
43
44
  end
44
45
  end
45
46
  end
47
+
48
+ private
49
+
50
+ def class_name(class_node, node)
51
+ if node.children.first.method?(:name)
52
+ class_node.source.delete('"').delete("'")
53
+ else
54
+ class_node.source
55
+ end
56
+ end
57
+
58
+ def offense_range(receiver_node, node)
59
+ range_between(receiver_node.loc.selector.begin_pos, node.source_range.end_pos)
60
+ end
46
61
  end
47
62
  end
48
63
  end
@@ -85,10 +85,7 @@ module RuboCop
85
85
  end
86
86
 
87
87
  def on_kwbegin(node)
88
- return if node.parent&.assignment?
89
-
90
- first_child = node.children.first
91
- return if first_child.rescue_type? || first_child.ensure_type?
88
+ return if contain_rescue_or_ensure?(node) || valid_context_using_only_begin?(node)
92
89
 
93
90
  register_offense(node)
94
91
  end
@@ -101,6 +98,19 @@ module RuboCop
101
98
  corrector.remove(node.loc.end)
102
99
  end
103
100
  end
101
+
102
+ def contain_rescue_or_ensure?(node)
103
+ first_child = node.children.first
104
+
105
+ first_child.rescue_type? || first_child.ensure_type?
106
+ end
107
+
108
+ def valid_context_using_only_begin?(node)
109
+ parent = node.parent
110
+
111
+ node.each_ancestor.any?(&:assignment?) || parent&.post_condition_loop? ||
112
+ parent&.send_type? || parent&.operator_keyword?
113
+ end
104
114
  end
105
115
  end
106
116
  end
@@ -192,7 +192,7 @@ module RuboCop
192
192
  end
193
193
 
194
194
  def_node_matcher :method_name, <<~PATTERN
195
- {($:defined? (send nil? _) ...)
195
+ {($:defined? _ ...)
196
196
  (send {_ nil?} $_ _ ...)}
197
197
  PATTERN
198
198
 
@@ -3,7 +3,7 @@
3
3
  module RuboCop
4
4
  # This module holds the RuboCop version information.
5
5
  module Version
6
- STRING = '0.93.0'
6
+ STRING = '0.93.1'
7
7
 
8
8
  MSG = '%<version>s (using Parser %<parser_version>s, '\
9
9
  'rubocop-ast %<rubocop_ast_version>s, ' \
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rubocop
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.93.0
4
+ version: 0.93.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Bozhidar Batsov
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: exe
12
12
  cert_chain: []
13
- date: 2020-10-08 00:00:00.000000000 Z
13
+ date: 2020-10-12 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: parallel
@@ -822,7 +822,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
822
822
  - !ruby/object:Gem::Version
823
823
  version: '0'
824
824
  requirements: []
825
- rubygems_version: 3.1.2
825
+ rubygems_version: 3.1.4
826
826
  signing_key:
827
827
  specification_version: 4
828
828
  summary: Automatic Ruby code style checking tool.