From 4f95a440035224bfa7a7f91867ff14d1f118cc9a Mon Sep 17 00:00:00 2001 From: Juan Vasquez Date: Wed, 18 Oct 2023 16:57:07 -0600 Subject: [PATCH] Fix Module Initialize when nesting classes Fixes https://github.com/troessner/reek/issues/1505 --- lib/reek/smell_detectors/module_initialize.rb | 18 +++++---- .../smell_detectors/module_initialize_spec.rb | 40 +++++++++++++++++++ 2 files changed, 50 insertions(+), 8 deletions(-) diff --git a/lib/reek/smell_detectors/module_initialize.rb b/lib/reek/smell_detectors/module_initialize.rb index a9f0dea38..fc0bb94de 100644 --- a/lib/reek/smell_detectors/module_initialize.rb +++ b/lib/reek/smell_detectors/module_initialize.rb @@ -21,14 +21,16 @@ def self.contexts # :nodoc: # @return [Array] # def sniff - context.defined_instance_methods.each do |node| - if node.name == :initialize - return smell_warning( - lines: [source_line], - message: 'has initialize method') - end - end - [] + return [] if does_not_have_initializer_method? + + smell_warning(lines: [source_line], message: 'has initialize method') + end + + private + + # :reek:FeatureEnvy + def does_not_have_initializer_method? + context.exp.direct_children.none? { |child| child.type == :def && child.name == :initialize } end end end diff --git a/spec/reek/smell_detectors/module_initialize_spec.rb b/spec/reek/smell_detectors/module_initialize_spec.rb index c53bbc745..bbb47d8a9 100644 --- a/spec/reek/smell_detectors/module_initialize_spec.rb +++ b/spec/reek/smell_detectors/module_initialize_spec.rb @@ -86,4 +86,44 @@ def initialize; end expect(src).not_to reek_of(:ModuleInitialize) end + + it 'reports nothing for a method named initialize in a class assigned to a let variable' do + src = <<-RUBY + module Alfa + RSpec.describe Bravo do + let(:klass) do + Class.new do + def initialize; end + end + end + end + end + RUBY + + expect(src).not_to reek_of(:ModuleInitialize) + end + + it 'reports nothing for a DSL-based method instantiating a class' do + src = <<-RUBY + module Alfa + bravo Class.new do + def initialize; end + end + end + RUBY + + expect(src).not_to reek_of(:ModuleInitialize) + end + + it 'reports nothing for a method named initialize in a variable assignment' do + src = <<-RUBY + module Alfa + bravo = Class.new do + def initialize; end + end + end + RUBY + + expect(src).not_to reek_of(:ModuleInitialize) + end end