From 5de911893a469a7c867a7787dcab479e8c6a00f8 Mon Sep 17 00:00:00 2001 From: Owen Stephens Date: Wed, 10 Jun 2020 19:26:10 +0100 Subject: [PATCH] [Fix #8098]: Fix false-positive in Style/RedundantRegexpCharacterClass Also correct the handling of interpolations and comments - we need to preserve their width in the checked pattern source without their contents triggering the cop in question, so that we can correctly highlight following offenses based on the offset in the pattern_source. --- CHANGELOG.md | 1 + lib/rubocop/cop/mixin/regexp_literal_help.rb | 27 +++++++++ .../style/redundant_regexp_character_class.rb | 4 +- .../cop/style/redundant_regexp_escape.rb | 15 ----- .../redundant_regexp_character_class_spec.rb | 60 ++++++++++++++++--- .../cop/style/redundant_regexp_escape_spec.rb | 38 ++++++++++++ 6 files changed, 121 insertions(+), 24 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 166f0e55c92..a294b44599c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -13,6 +13,7 @@ * [#8115](https://github.com/rubocop-hq/rubocop/issues/8115): Fix false negative for `Lint::FormatParameterMismatch` when argument contains formatting. ([@andrykonchin][]) * [#8131](https://github.com/rubocop-hq/rubocop/pull/8131): Fix false positive for `Style/RedundantRegexpEscape` with escaped delimiters. ([@owst][]) * [#8124](https://github.com/rubocop-hq/rubocop/issues/8124): Fix a false positive for `Lint/FormatParameterMismatch` when using named parameters with escaped `%`. ([@koic][]) +* [#8098](https://github.com/rubocop-hq/rubocop/issues/8098): Fix a false positive for `Style/RedundantRegexpCharacterClass` when using interpolations. ([@owst][]) ## 0.85.1 (2020-06-07) diff --git a/lib/rubocop/cop/mixin/regexp_literal_help.rb b/lib/rubocop/cop/mixin/regexp_literal_help.rb index e28f8671c56..bba68606e9a 100644 --- a/lib/rubocop/cop/mixin/regexp_literal_help.rb +++ b/lib/rubocop/cop/mixin/regexp_literal_help.rb @@ -11,6 +11,33 @@ def freespace_mode_regexp?(node) regopt.children.include?(:x) end + + def pattern_source(node) + freespace_mode = freespace_mode_regexp?(node) + + node.children.reject(&:regopt_type?).map do |child| + source_with_comments_and_interpolations_blanked(child, freespace_mode) + end.join + end + + def source_with_comments_and_interpolations_blanked(child, freespace_mode) + source = child.source + + # We don't want to consider the contents of interpolations or free-space mode comments as + # part of the pattern source, but need to preserve their width, to allow offsets to + # correctly line up with the original source: spaces have no effect, and preserve width. + if child.begin_type? + replace_match_with_spaces(source, /.*/) # replace all content + elsif freespace_mode + replace_match_with_spaces(source, /(?