Change to skip regexp bodies regexp_parser does not accept

[Fix #813]
This commit is contained in:
Markus Schirp 2018-12-24 15:41:15 +00:00
parent cffcd910c4
commit 8cf5e0f079
5 changed files with 34 additions and 16 deletions

View file

@ -8,10 +8,15 @@ module Mutant
#
# @param regexp [String]
#
# @return [Regexp::Expression]
# @return [Regexp::Expression, nil]
#
# rubocop:disable Lint/HandleExceptions
def self.parse(regexp)
::Regexp::Parser.parse(regexp)
# regexp_parser is more strict than MRI
rescue ::Regexp::Scanner::PrematureEndError
end
# rubocop:enable Lint/HandleExceptions
# Convert expression into ast node
#

View file

@ -42,7 +42,7 @@ module Mutant
#
# @return [undefined]
def mutate_body
return unless body.all?(&method(:n_str?))
return unless body.all?(&method(:n_str?)) && body_ast
Mutator.mutate(body_ast).each do |mutation|
source = AST::Regexp.to_expression(mutation).to_s
@ -52,14 +52,14 @@ module Mutant
# AST representation of regexp body
#
# @return [Parser::AST::Node]
# @return [Parser::AST::Node, nil]
def body_ast
AST::Regexp.to_ast(body_expression)
body_expression and AST::Regexp.to_ast(body_expression)
end
# Expression representation of regexp body
#
# @return [Regexp::Expression]
# @return [Regexp::Expression, nil]
def body_expression
AST::Regexp.parse(body.map(&:children).join)
end

View file

@ -76,6 +76,15 @@ Mutant::Meta::Example.add :regexp do
mutation '/(?(1)(foo)(?:bar))/'
end
# Case where MRI would accept an expression but regexp_parser not.
Mutant::Meta::Example.add :regexp do
source '/u{/'
singleton_mutations
mutation '//'
mutation '/nomatch\A/'
end
Pathname
.glob(Pathname.new(__dir__).join('regexp', '*.rb'))
.sort

View file

@ -7,15 +7,7 @@
ruby_glob_pattern: '**/*_spec.rb'
mutation_coverage: false
mutation_generation: true
expected_errors:
"#<Parser::SyntaxError: invalid multibyte escape: /\xAA/>":
- language/regexp/escapes_spec.rb
'#<RegexpError: invalid multibyte escape: /\xAA/>':
- language/regexp/escapes_spec.rb
"#<Regexp::Scanner::PrematureEndError: Premature end of pattern at #{str}>":
- language/regexp/interpolation_spec.rb
'#<Regexp::Scanner::PrematureEndError: Premature end of pattern at \xA>':
- language/regexp/escapes_spec.rb
expected_errors: {}
exclude:
- core/string/casecmp_spec.rb
- core/symbol/casecmp_spec.rb

View file

@ -1,7 +1,19 @@
# frozen_string_literal: true
RSpec.describe Mutant::AST::Regexp, '.parse' do
it 'parses using minor ruby version' do
expect(described_class.parse(/foo/).to_re).to eql(/foo/)
def apply(input)
described_class.parse(input)
end
context 'on regexp regexp_parser does accept' do
it 'parses using minor ruby version' do
expect(apply(/foo/).to_re).to eql(/foo/)
end
end
context 'on regexp regexp_parser does not accept' do
it 'returns nil' do
expect(apply(/u{/)).to be(nil)
end
end
end