From 074363eefbb5578612275126832205f6122858a6 Mon Sep 17 00:00:00 2001 From: Alexander Fisher Date: Wed, 15 Mar 2023 12:06:42 +0000 Subject: [PATCH] Support dot-notation when retrieving facts in facter_impl In Puppet 8, core providers are being confined using facts fetched using 'dot-notation'. We need to support this style of lookup in our stub implementation. For example in `lib/puppet/provider/service/init.rb` ```ruby confine :true => begin os = Puppet.runtime[:facter].value(:operatingsystem).downcase # ... ``` was updated to ```ruby confine :true => begin os = Puppet.runtime[:facter].value('os.name').downcase # ... ``` See https://github.com/puppetlabs/puppet/commit/82cef2371352b648cc60aa7b7cedaa973c38ad35 for Puppet 8 change. Relates to puppetlabs/rspec-puppet#38 --- lib/rspec-puppet/facter_impl.rb | 6 +++++- spec/unit/facter_impl_spec.rb | 24 ++++++++++++++++++++++++ 2 files changed, 29 insertions(+), 1 deletion(-) diff --git a/lib/rspec-puppet/facter_impl.rb b/lib/rspec-puppet/facter_impl.rb index d37a7518e..0e1e3dd20 100644 --- a/lib/rspec-puppet/facter_impl.rb +++ b/lib/rspec-puppet/facter_impl.rb @@ -8,7 +8,11 @@ def initialize end def value(fact_name) - @facts[fact_name.to_s] + begin + @facts.dig(*fact_name.to_s.split('.')) + rescue TypeError + nil + end end def clear diff --git a/spec/unit/facter_impl_spec.rb b/spec/unit/facter_impl_spec.rb index 3f6ef321c..71d234409 100644 --- a/spec/unit/facter_impl_spec.rb +++ b/spec/unit/facter_impl_spec.rb @@ -10,6 +10,7 @@ 'int_fact' => 3, 'true_fact' => true, 'false_fact' => false, + 'os' => { 'name' => 'my_os', 'release' => { 'major' => '42' } } } end @@ -19,6 +20,7 @@ facter_impl.add(:int_fact) { setcode { 3 } } facter_impl.add(:true_fact) { setcode { true } } facter_impl.add(:false_fact) { setcode { false } } + facter_impl.add(:os) { setcode { { 'name' => 'my_os', 'release' => { 'major' => '42' }} } } end describe 'noop methods' do @@ -49,6 +51,28 @@ it 'retrieves a fact of type FalseClass' do expect(facter_impl.value(:false_fact)).to eq(false) end + + context 'when using dot-notation' do + it 'retrieves a child fact using dot-notation' do + expect(facter_impl.value('os.name')).to eq('my_os') + end + + it 'retrieves a hash child fact using dot-notation' do + expect(facter_impl.value('os.release')).to eq({ 'major' => '42' }) + end + + it 'retrieves a deeply nested child fact using dot-notation' do + expect(facter_impl.value('os.release.major')).to eq('42') + end + + it 'returns nil if a child fact is missing' do + expect(facter_impl.value('os.release.unknown_subkey')).to eq(nil) + end + + it 'returns nil if trying to lookup into a string' do + expect(facter_impl.value('os.name.foo')).to eq(nil) + end + end end describe '#to_hash' do