rubocop-rails 2.7.1 → 2.10.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 (102) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE.txt +1 -1
  3. data/README.md +18 -2
  4. data/config/default.yml +144 -6
  5. data/config/obsoletion.yml +7 -0
  6. data/lib/rubocop/cop/mixin/active_record_helper.rb +16 -3
  7. data/lib/rubocop/cop/mixin/enforce_superclass.rb +40 -0
  8. data/lib/rubocop/cop/mixin/index_method.rb +25 -11
  9. data/lib/rubocop/cop/rails/action_filter.rb +10 -14
  10. data/lib/rubocop/cop/rails/active_record_aliases.rb +13 -17
  11. data/lib/rubocop/cop/rails/active_record_callbacks_order.rb +19 -16
  12. data/lib/rubocop/cop/rails/active_record_override.rb +1 -1
  13. data/lib/rubocop/cop/rails/active_support_aliases.rb +12 -21
  14. data/lib/rubocop/cop/rails/after_commit_override.rb +91 -0
  15. data/lib/rubocop/cop/rails/application_controller.rb +3 -7
  16. data/lib/rubocop/cop/rails/application_job.rb +2 -1
  17. data/lib/rubocop/cop/rails/application_mailer.rb +2 -7
  18. data/lib/rubocop/cop/rails/application_record.rb +2 -7
  19. data/lib/rubocop/cop/rails/arel_star.rb +41 -0
  20. data/lib/rubocop/cop/rails/assert_not.rb +8 -10
  21. data/lib/rubocop/cop/rails/attribute_default_block_value.rb +90 -0
  22. data/lib/rubocop/cop/rails/belongs_to.rb +10 -19
  23. data/lib/rubocop/cop/rails/blank.rb +31 -27
  24. data/lib/rubocop/cop/rails/bulk_change_table.rb +1 -1
  25. data/lib/rubocop/cop/rails/content_tag.rb +34 -19
  26. data/lib/rubocop/cop/rails/create_table_with_timestamps.rb +2 -1
  27. data/lib/rubocop/cop/rails/date.rb +10 -11
  28. data/lib/rubocop/cop/rails/default_scope.rb +11 -4
  29. data/lib/rubocop/cop/rails/delegate.rb +9 -9
  30. data/lib/rubocop/cop/rails/delegate_allow_blank.rb +7 -8
  31. data/lib/rubocop/cop/rails/dynamic_find_by.rb +15 -12
  32. data/lib/rubocop/cop/rails/enum_hash.rb +11 -10
  33. data/lib/rubocop/cop/rails/enum_uniqueness.rb +2 -1
  34. data/lib/rubocop/cop/rails/environment_comparison.rb +18 -14
  35. data/lib/rubocop/cop/rails/environment_variable_access.rb +67 -0
  36. data/lib/rubocop/cop/rails/exit.rb +4 -10
  37. data/lib/rubocop/cop/rails/file_path.rb +7 -8
  38. data/lib/rubocop/cop/rails/find_by.rb +13 -13
  39. data/lib/rubocop/cop/rails/find_by_id.rb +12 -21
  40. data/lib/rubocop/cop/rails/find_each.rb +19 -18
  41. data/lib/rubocop/cop/rails/has_and_belongs_to_many.rb +3 -2
  42. data/lib/rubocop/cop/rails/has_many_or_has_one_dependent.rb +37 -10
  43. data/lib/rubocop/cop/rails/helper_instance_variable.rb +30 -2
  44. data/lib/rubocop/cop/rails/http_positional_arguments.rb +32 -21
  45. data/lib/rubocop/cop/rails/http_status.rb +7 -9
  46. data/lib/rubocop/cop/rails/ignored_skip_action_filter_option.rb +8 -6
  47. data/lib/rubocop/cop/rails/index_by.rb +11 -2
  48. data/lib/rubocop/cop/rails/index_with.rb +11 -2
  49. data/lib/rubocop/cop/rails/inquiry.rb +7 -2
  50. data/lib/rubocop/cop/rails/inverse_of.rb +3 -2
  51. data/lib/rubocop/cop/rails/lexically_scoped_action_filter.rb +17 -15
  52. data/lib/rubocop/cop/rails/link_to_blank.rb +25 -23
  53. data/lib/rubocop/cop/rails/mailer_name.rb +19 -13
  54. data/lib/rubocop/cop/rails/match_route.rb +14 -13
  55. data/lib/rubocop/cop/rails/negate_include.rb +10 -8
  56. data/lib/rubocop/cop/rails/not_null_column.rb +2 -1
  57. data/lib/rubocop/cop/rails/order_by_id.rb +52 -0
  58. data/lib/rubocop/cop/rails/output.rb +5 -2
  59. data/lib/rubocop/cop/rails/output_safety.rb +3 -2
  60. data/lib/rubocop/cop/rails/pick.rb +14 -12
  61. data/lib/rubocop/cop/rails/pluck.rb +6 -9
  62. data/lib/rubocop/cop/rails/pluck_id.rb +4 -6
  63. data/lib/rubocop/cop/rails/pluck_in_where.rb +39 -5
  64. data/lib/rubocop/cop/rails/pluralization_grammar.rb +10 -14
  65. data/lib/rubocop/cop/rails/presence.rb +12 -13
  66. data/lib/rubocop/cop/rails/present.rb +30 -24
  67. data/lib/rubocop/cop/rails/rake_environment.rb +8 -10
  68. data/lib/rubocop/cop/rails/read_write_attribute.rb +12 -11
  69. data/lib/rubocop/cop/rails/redundant_allow_nil.rb +29 -31
  70. data/lib/rubocop/cop/rails/redundant_foreign_key.rb +9 -12
  71. data/lib/rubocop/cop/rails/redundant_receiver_in_with_options.rb +11 -10
  72. data/lib/rubocop/cop/rails/reflection_class_name.rb +18 -4
  73. data/lib/rubocop/cop/rails/refute_methods.rb +9 -10
  74. data/lib/rubocop/cop/rails/relative_date_constant.rb +34 -22
  75. data/lib/rubocop/cop/rails/render_inline.rb +2 -1
  76. data/lib/rubocop/cop/rails/render_plain_text.rb +9 -14
  77. data/lib/rubocop/cop/rails/request_referer.rb +7 -7
  78. data/lib/rubocop/cop/rails/require_dependency.rb +38 -0
  79. data/lib/rubocop/cop/rails/reversible_migration.rb +83 -8
  80. data/lib/rubocop/cop/rails/reversible_migration_method_definition.rb +75 -0
  81. data/lib/rubocop/cop/rails/safe_navigation.rb +30 -11
  82. data/lib/rubocop/cop/rails/safe_navigation_with_blank.rb +5 -10
  83. data/lib/rubocop/cop/rails/save_bang.rb +19 -22
  84. data/lib/rubocop/cop/rails/scope_args.rb +2 -1
  85. data/lib/rubocop/cop/rails/short_i18n.rb +7 -9
  86. data/lib/rubocop/cop/rails/skips_model_validations.rb +4 -4
  87. data/lib/rubocop/cop/rails/squished_sql_heredocs.rb +82 -0
  88. data/lib/rubocop/cop/rails/time_zone.rb +35 -25
  89. data/lib/rubocop/cop/rails/time_zone_assignment.rb +37 -0
  90. data/lib/rubocop/cop/rails/uniq_before_pluck.rb +6 -6
  91. data/lib/rubocop/cop/rails/unique_validation_without_index.rb +18 -8
  92. data/lib/rubocop/cop/rails/unknown_env.rb +3 -3
  93. data/lib/rubocop/cop/rails/validation.rb +15 -14
  94. data/lib/rubocop/cop/rails/where_equals.rb +98 -0
  95. data/lib/rubocop/cop/rails/where_exists.rb +85 -16
  96. data/lib/rubocop/cop/rails/where_not.rb +101 -0
  97. data/lib/rubocop/cop/rails_cops.rb +12 -0
  98. data/lib/rubocop/rails.rb +2 -0
  99. data/lib/rubocop/rails/schema_loader.rb +4 -4
  100. data/lib/rubocop/rails/schema_loader/schema.rb +4 -8
  101. data/lib/rubocop/rails/version.rb +5 -1
  102. metadata +33 -14
@@ -16,7 +16,8 @@ module RuboCop
16
16
  # class MyMailer < ActionMailer::Base
17
17
  # # ...
18
18
  # end
19
- class ApplicationMailer < Cop
19
+ class ApplicationMailer < Base
20
+ extend AutoCorrector
20
21
  extend TargetRailsVersion
21
22
 
22
23
  minimum_target_rails_version 5.0
@@ -28,12 +29,6 @@ module RuboCop
28
29
  # rubocop:disable Layout/ClassStructure
29
30
  include RuboCop::Cop::EnforceSuperclass
30
31
  # rubocop:enable Layout/ClassStructure
31
-
32
- def autocorrect(node)
33
- lambda do |corrector|
34
- corrector.replace(node.source_range, self.class::SUPERCLASS)
35
- end
36
- end
37
32
  end
38
33
  end
39
34
  end
@@ -16,7 +16,8 @@ module RuboCop
16
16
  # class Rails4Model < ActiveRecord::Base
17
17
  # # ...
18
18
  # end
19
- class ApplicationRecord < Cop
19
+ class ApplicationRecord < Base
20
+ extend AutoCorrector
20
21
  extend TargetRailsVersion
21
22
 
22
23
  minimum_target_rails_version 5.0
@@ -28,12 +29,6 @@ module RuboCop
28
29
  # rubocop:disable Layout/ClassStructure
29
30
  include RuboCop::Cop::EnforceSuperclass
30
31
  # rubocop:enable Layout/ClassStructure
31
-
32
- def autocorrect(node)
33
- lambda do |corrector|
34
- corrector.replace(node.source_range, self.class::SUPERCLASS)
35
- end
36
- end
37
32
  end
38
33
  end
39
34
  end
@@ -0,0 +1,41 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Rails
6
+ # This cop prevents usage of `"*"` on an Arel::Table column reference.
7
+ #
8
+ # Using `arel_table["*"]` causes the outputted string to be a literal
9
+ # quoted asterisk (e.g. <tt>`my_model`.`*`</tt>). This causes the
10
+ # database to look for a column named <tt>`*`</tt> (or `"*"`) as opposed
11
+ # to expanding the column list as one would likely expect.
12
+ #
13
+ # @example
14
+ # # bad
15
+ # MyTable.arel_table["*"]
16
+ #
17
+ # # good
18
+ # MyTable.arel_table[Arel.star]
19
+ #
20
+ class ArelStar < Base
21
+ extend AutoCorrector
22
+
23
+ MSG = 'Use `Arel.star` instead of `"*"` for expanded column lists.'
24
+
25
+ RESTRICT_ON_SEND = %i[[]].freeze
26
+
27
+ def_node_matcher :star_bracket?, <<~PATTERN
28
+ (send {const (send _ :arel_table)} :[] $(str "*"))
29
+ PATTERN
30
+
31
+ def on_send(node)
32
+ return unless (star = star_bracket?(node))
33
+
34
+ add_offense(star) do |corrector|
35
+ corrector.replace(star.loc.expression, 'Arel.star')
36
+ end
37
+ end
38
+ end
39
+ end
40
+ end
41
+ end
@@ -13,23 +13,21 @@ module RuboCop
13
13
  # # good
14
14
  # assert_not x
15
15
  #
16
- class AssertNot < RuboCop::Cop::Cop
16
+ class AssertNot < Base
17
+ extend AutoCorrector
18
+
17
19
  MSG = 'Prefer `assert_not` over `assert !`.'
20
+ RESTRICT_ON_SEND = %i[assert].freeze
18
21
 
19
22
  def_node_matcher :offensive?, '(send nil? :assert (send ... :!) ...)'
20
23
 
21
24
  def on_send(node)
22
- add_offense(node) if offensive?(node)
23
- end
25
+ return unless offensive?(node)
24
26
 
25
- def autocorrect(node)
26
- expression = node.loc.expression
27
+ add_offense(node) do |corrector|
28
+ expression = node.loc.expression
27
29
 
28
- lambda do |corrector|
29
- corrector.replace(
30
- expression,
31
- corrected_source(expression.source)
32
- )
30
+ corrector.replace(expression, corrected_source(expression.source))
33
31
  end
34
32
  end
35
33
 
@@ -0,0 +1,90 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Rails
6
+ # This cop looks for `attribute` class methods that specify a `:default` option
7
+ # which value is an array, string literal or method call without a block.
8
+ # It will accept all other values, such as string, symbol, integer and float literals
9
+ # as well as constants.
10
+ #
11
+ # @example
12
+ # # bad
13
+ # class User < ApplicationRecord
14
+ # attribute :confirmed_at, :datetime, default: Time.zone.now
15
+ # end
16
+ #
17
+ # # good
18
+ # class User < ApplicationRecord
19
+ # attribute :confirmed_at, :datetime, default: -> { Time.zone.now }
20
+ # end
21
+ #
22
+ # # bad
23
+ # class User < ApplicationRecord
24
+ # attribute :roles, :string, array: true, default: []
25
+ # end
26
+ #
27
+ # # good
28
+ # class User < ApplicationRecord
29
+ # attribute :roles, :string, array: true, default: -> { [] }
30
+ # end
31
+ #
32
+ # # bad
33
+ # class User < ApplicationRecord
34
+ # attribute :configuration, default: {}
35
+ # end
36
+ #
37
+ # # good
38
+ # class User < ApplicationRecord
39
+ # attribute :configuration, default: -> { {} }
40
+ # end
41
+ #
42
+ # # good
43
+ # class User < ApplicationRecord
44
+ # attribute :role, :string, default: :customer
45
+ # end
46
+ #
47
+ # # good
48
+ # class User < ApplicationRecord
49
+ # attribute :activated, :boolean, default: false
50
+ # end
51
+ #
52
+ # # good
53
+ # class User < ApplicationRecord
54
+ # attribute :login_count, :integer, default: 0
55
+ # end
56
+ #
57
+ # # good
58
+ # class User < ApplicationRecord
59
+ # FOO = 123
60
+ # attribute :custom_attribute, :integer, default: FOO
61
+ # end
62
+ class AttributeDefaultBlockValue < Base
63
+ extend AutoCorrector
64
+
65
+ MSG = 'Pass method in a block to `:default` option.'
66
+ RESTRICT_ON_SEND = %i[attribute].freeze
67
+ TYPE_OFFENDERS = %i[send array hash].freeze
68
+
69
+ def_node_matcher :default_attribute, <<~PATTERN
70
+ (send nil? :attribute _ ?_ (hash <$#attribute ...>))
71
+ PATTERN
72
+
73
+ def_node_matcher :attribute, '(pair (sym :default) $_)'
74
+
75
+ def on_send(node)
76
+ default_attribute(node) do |attribute|
77
+ value = attribute.children.last
78
+ return unless TYPE_OFFENDERS.any?(value.type)
79
+
80
+ add_offense(value) do |corrector|
81
+ expression = default_attribute(node).children.last
82
+
83
+ corrector.replace(value, "-> { #{expression.source} }")
84
+ end
85
+ end
86
+ end
87
+ end
88
+ end
89
+ end
90
+ end
@@ -50,7 +50,8 @@ module RuboCop
50
50
  #
51
51
  # @see https://guides.rubyonrails.org/5_0_release_notes.html
52
52
  # @see https://github.com/rails/rails/pull/18937
53
- class BelongsTo < Cop
53
+ class BelongsTo < Base
54
+ extend AutoCorrector
54
55
  extend TargetRailsVersion
55
56
 
56
57
  minimum_target_rails_version 5.0
@@ -64,35 +65,25 @@ module RuboCop
64
65
  'option is deprecated and you want to use `optional: false`. ' \
65
66
  'In most configurations, this is the default and you can omit ' \
66
67
  'this option altogether'
68
+ RESTRICT_ON_SEND = %i[belongs_to].freeze
67
69
 
68
70
  def_node_matcher :match_belongs_to_with_options, <<~PATTERN
69
- (send _ :belongs_to _
71
+ (send _ :belongs_to ...
70
72
  (hash <$(pair (sym :required) ${true false}) ...>)
71
73
  )
72
74
  PATTERN
73
75
 
74
76
  def on_send(node)
75
- match_belongs_to_with_options(node) do |_option_node, option_value|
76
- message =
77
+ match_belongs_to_with_options(node) do |option_node, option_value|
78
+ message, replacement =
77
79
  if option_value.true_type?
78
- SUPERFLOUS_REQUIRE_TRUE_MSG
80
+ [SUPERFLOUS_REQUIRE_TRUE_MSG, 'optional: false']
79
81
  elsif option_value.false_type?
80
- SUPERFLOUS_REQUIRE_FALSE_MSG
82
+ [SUPERFLOUS_REQUIRE_FALSE_MSG, 'optional: true']
81
83
  end
82
84
 
83
- add_offense(node, message: message, location: :selector)
84
- end
85
- end
86
-
87
- def autocorrect(node)
88
- option_node, option_value = match_belongs_to_with_options(node)
89
- return unless option_node
90
-
91
- lambda do |corrector|
92
- if option_value.true_type?
93
- corrector.replace(option_node.loc.expression, 'optional: false')
94
- elsif option_value.false_type?
95
- corrector.replace(option_node.loc.expression, 'optional: true')
85
+ add_offense(node.loc.selector, message: message) do |corrector|
86
+ corrector.replace(option_node.loc.expression, replacement)
96
87
  end
97
88
  end
98
89
  end
@@ -6,6 +6,10 @@ module RuboCop
6
6
  # This cop checks for code that can be written with simpler conditionals
7
7
  # using `Object#blank?` defined by Active Support.
8
8
  #
9
+ # This cop is marked as unsafe auto-correction, because `' '.empty?` returns false,
10
+ # but `' '.blank?` returns true. Therefore, auto-correction is not compatible
11
+ # if the receiver is a non-empty blank string, tab, or newline meta characters.
12
+ #
9
13
  # Interaction with `Style/UnlessElse`:
10
14
  # The configuration of `NotPresent` will not produce an offense in the
11
15
  # context of `unless else` if `Style/UnlessElse` is inabled. This is
@@ -53,11 +57,14 @@ module RuboCop
53
57
  # def blank?
54
58
  # !present?
55
59
  # end
56
- class Blank < Cop
60
+ class Blank < Base
61
+ extend AutoCorrector
62
+
57
63
  MSG_NIL_OR_EMPTY = 'Use `%<prefer>s` instead of `%<current>s`.'
58
64
  MSG_NOT_PRESENT = 'Use `%<prefer>s` instead of `%<current>s`.'
59
65
  MSG_UNLESS_PRESENT = 'Use `if %<prefer>s` instead of ' \
60
66
  '`%<current>s`.'
67
+ RESTRICT_ON_SEND = %i[!].freeze
61
68
 
62
69
  # `(send nil $_)` is not actually a valid match for an offense. Nodes
63
70
  # that have a single method call on the left hand side
@@ -93,10 +100,10 @@ module RuboCop
93
100
  # accepts !present? if its in the body of a `blank?` method
94
101
  next if defining_blank?(node.parent)
95
102
 
96
- add_offense(node,
97
- message: format(MSG_NOT_PRESENT,
98
- prefer: replacement(receiver),
99
- current: node.source))
103
+ message = format(MSG_NOT_PRESENT, prefer: replacement(receiver), current: node.source)
104
+ add_offense(node, message: message) do |corrector|
105
+ autocorrect(corrector, node)
106
+ end
100
107
  end
101
108
  end
102
109
 
@@ -106,10 +113,10 @@ module RuboCop
106
113
  nil_or_empty?(node) do |var1, var2|
107
114
  return unless var1 == var2
108
115
 
109
- add_offense(node,
110
- message: format(MSG_NIL_OR_EMPTY,
111
- prefer: replacement(var1),
112
- current: node.source))
116
+ message = format(MSG_NIL_OR_EMPTY, prefer: replacement(var1), current: node.source)
117
+ add_offense(node, message: message) do |corrector|
118
+ autocorrect(corrector, node)
119
+ end
113
120
  end
114
121
  end
115
122
 
@@ -121,31 +128,28 @@ module RuboCop
121
128
  unless_present?(node) do |method_call, receiver|
122
129
  range = unless_condition(node, method_call)
123
130
 
124
- add_offense(node,
125
- location: range,
126
- message: format(MSG_UNLESS_PRESENT,
127
- prefer: replacement(receiver),
128
- current: range.source))
131
+ message = format(MSG_UNLESS_PRESENT, prefer: replacement(receiver), current: range.source)
132
+ add_offense(range, message: message) do |corrector|
133
+ autocorrect(corrector, node)
134
+ end
129
135
  end
130
136
  end
131
137
 
132
- def autocorrect(node)
133
- lambda do |corrector|
134
- method_call, variable1 = unless_present?(node)
138
+ private
135
139
 
136
- if method_call
137
- corrector.replace(node.loc.keyword, 'if')
138
- range = method_call.loc.expression
139
- else
140
- variable1, _variable2 = nil_or_empty?(node) || not_present?(node)
141
- range = node.loc.expression
142
- end
140
+ def autocorrect(corrector, node)
141
+ method_call, variable1 = unless_present?(node)
143
142
 
144
- corrector.replace(range, replacement(variable1))
143
+ if method_call
144
+ corrector.replace(node.loc.keyword, 'if')
145
+ range = method_call.loc.expression
146
+ else
147
+ variable1, _variable2 = nil_or_empty?(node) || not_present?(node)
148
+ range = node.loc.expression
145
149
  end
146
- end
147
150
 
148
- private
151
+ corrector.replace(range, replacement(variable1))
152
+ end
149
153
 
150
154
  def unless_condition(node, method_call)
151
155
  if node.modifier_form?
@@ -65,7 +65,7 @@ module RuboCop
65
65
  #
66
66
  # @see https://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/SchemaStatements.html#method-i-change_table
67
67
  # @see https://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/Table.html
68
- class BulkChangeTable < Cop
68
+ class BulkChangeTable < Base
69
69
  MSG_FOR_CHANGE_TABLE = <<~MSG.chomp
70
70
  You can combine alter queries using `bulk: true` options.
71
71
  MSG
@@ -18,46 +18,61 @@ module RuboCop
18
18
  # tag.p('Hello world!')
19
19
  # tag.br
20
20
  # content_tag(name, 'Hello world!')
21
- class ContentTag < Cop
21
+ class ContentTag < Base
22
22
  include RangeHelp
23
+ extend AutoCorrector
23
24
  extend TargetRailsVersion
24
25
 
25
26
  minimum_target_rails_version 5.1
26
27
 
27
28
  MSG = 'Use `tag` instead of `content_tag`.'
29
+ RESTRICT_ON_SEND = %i[content_tag].freeze
28
30
 
29
- def on_send(node)
30
- return unless node.method?(:content_tag)
31
+ def on_new_investigation
32
+ @corrected_nodes = nil
33
+ end
31
34
 
35
+ def on_send(node)
32
36
  first_argument = node.first_argument
33
- return unless first_argument
37
+ return if !first_argument ||
38
+ allowed_argument?(first_argument) ||
39
+ corrected_ancestor?(node)
40
+
41
+ add_offense(node) do |corrector|
42
+ autocorrect(corrector, node)
43
+
44
+ @corrected_nodes ||= Set.new.compare_by_identity
45
+ @corrected_nodes.add(node)
46
+ end
47
+ end
48
+
49
+ private
34
50
 
35
- return if first_argument.variable? || first_argument.send_type? || first_argument.const_type?
51
+ def corrected_ancestor?(node)
52
+ node.each_ancestor(:send).any? { |ancestor| @corrected_nodes&.include?(ancestor) }
53
+ end
36
54
 
37
- add_offense(node)
55
+ def allowed_argument?(argument)
56
+ argument.variable? || argument.send_type? || argument.const_type? || argument.splat_type?
38
57
  end
39
58
 
40
- def autocorrect(node)
41
- lambda do |corrector|
42
- if method_name?(node.first_argument)
43
- range = correction_range(node)
59
+ def autocorrect(corrector, node)
60
+ if method_name?(node.first_argument)
61
+ range = correction_range(node)
44
62
 
45
- rest_args = node.arguments.drop(1)
46
- replacement = "tag.#{node.first_argument.value}(#{rest_args.map(&:source).join(', ')})"
63
+ rest_args = node.arguments.drop(1)
64
+ replacement = "tag.#{node.first_argument.value.to_s.underscore}(#{rest_args.map(&:source).join(', ')})"
47
65
 
48
- corrector.replace(range, replacement)
49
- else
50
- corrector.replace(node.loc.selector, 'tag')
51
- end
66
+ corrector.replace(range, replacement)
67
+ else
68
+ corrector.replace(node.loc.selector, 'tag')
52
69
  end
53
70
  end
54
71
 
55
- private
56
-
57
72
  def method_name?(node)
58
73
  return false unless node.str_type? || node.sym_type?
59
74
 
60
- /^[a-zA-Z_][a-zA-Z_0-9]*$/.match?(node.value)
75
+ /^[a-zA-Z_][a-zA-Z_\-0-9]*$/.match?(node.value)
61
76
  end
62
77
 
63
78
  def correction_range(node)