From b3dfc770c02f6b5bfb2ad711ba046826c17a8d8c Mon Sep 17 00:00:00 2001 From: Chris Andreae Date: Fri, 22 Mar 2024 13:02:50 +0900 Subject: [PATCH] Don't alias subspecs when merge!ing Otherwise they'll be subject to being clobbered in subsequent merges --- lib/deep_preloader/polymorphic_spec.rb | 6 +++++- lib/deep_preloader/spec.rb | 6 +++++- spec/unit/deep_preloader_spec.rb | 12 ++++++++++++ 3 files changed, 22 insertions(+), 2 deletions(-) diff --git a/lib/deep_preloader/polymorphic_spec.rb b/lib/deep_preloader/polymorphic_spec.rb index 1918d89..ab21cba 100644 --- a/lib/deep_preloader/polymorphic_spec.rb +++ b/lib/deep_preloader/polymorphic_spec.rb @@ -35,7 +35,7 @@ def merge!(other) if specs_by_type[k] specs_by_type[k].merge!(v) else - specs_by_type[k] = v + specs_by_type[k] = v.deep_dup end end else @@ -54,6 +54,10 @@ def ==(other) alias eql? == + def deep_dup + self.class.new(specs_by_type.deep_dup) + end + def inspect "PolySpec#{specs_by_type.inspect}" end diff --git a/lib/deep_preloader/spec.rb b/lib/deep_preloader/spec.rb index 3a1f738..bab503f 100644 --- a/lib/deep_preloader/spec.rb +++ b/lib/deep_preloader/spec.rb @@ -38,7 +38,7 @@ def merge!(other) if association_specs[k] association_specs[k].merge!(v) else - association_specs[k] = v + association_specs[k] = v.deep_dup end end else @@ -57,6 +57,10 @@ def ==(other) alias eql? == + def deep_dup + self.class.new(association_specs.deep_dup) + end + def inspect "Spec#{association_specs.inspect}" end diff --git a/spec/unit/deep_preloader_spec.rb b/spec/unit/deep_preloader_spec.rb index bc69c5d..251fce8 100644 --- a/spec/unit/deep_preloader_spec.rb +++ b/spec/unit/deep_preloader_spec.rb @@ -34,6 +34,18 @@ expect(DeepPreloader::Spec.parse(spec)).to eq(expected_spec) end + it 'can merge specs' do + a = DeepPreloader::Spec.parse(a: :b) + b = DeepPreloader::Spec.parse(a: :c) + result = DeepPreloader::Spec.new.merge!(a).merge!(b) + + # The result should contain each of the merged specs and the merged specs + # themselves should not be altered + expect(result).to eq(DeepPreloader::Spec.parse(a: [:b, :c])) + expect(a).to eq(DeepPreloader::Spec.parse(a: :b)) + expect(b).to eq(DeepPreloader::Spec.parse(a: :c)) + end + context 'with a test model' do with_temporary_table(:model)