Skip to content

Commit 6d7b9f7

Browse files
authored
Merge pull request #9043 from tvpartytonight/PUP-11751-resurrecting-nil-in-scope
(PUP-11751) Handle possible nil values in interpolation
2 parents fa55910 + 46d6d5f commit 6d7b9f7

File tree

2 files changed

+29
-5
lines changed

2 files changed

+29
-5
lines changed

lib/puppet/pops/lookup/interpolation.rb

Lines changed: 17 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -91,15 +91,18 @@ def interpolate_method(method_key)
9191
else
9292
scope = lookup_invocation.scope
9393
val = nil
94-
if (default_val = lookup_invocation.default_values[root_key])
94+
if (default_key_exists = lookup_invocation.default_values.include?(root_key) )
9595
catch(:undefined_variable) { val = scope[root_key] }
9696
else
9797
val = scope[root_key]
9898
end
99-
if val.nil? && default_val.nil?
100-
nil
101-
elsif val.nil?
102-
lookup_invocation.report_found_in_defaults(root_key, default_val)
99+
if val.nil? && !nil_in_scope?(scope, root_key)
100+
if default_key_exists
101+
lookup_invocation.report_found_in_defaults(root_key,
102+
lookup_invocation.default_values[root_key])
103+
else
104+
nil
105+
end
103106
else
104107
lookup_invocation.report_found(root_key, val)
105108
end
@@ -127,6 +130,15 @@ def interpolate_method(method_key)
127130
interpolate_method
128131
end
129132

133+
# Because the semantics of Puppet::Parser::Scope#include? differs from Hash#include?
134+
def nil_in_scope?(scope, key)
135+
if scope.is_a?(Hash)
136+
scope.include?(key)
137+
else
138+
scope.exist?(key)
139+
end
140+
end
141+
130142
def get_method_and_data(data, allow_methods)
131143
match = data.match(/^(\w+)\((?:["]([^"]+)["]|[']([^']+)['])\)$/)
132144
if match

spec/unit/pops/lookup/interpolation_spec.rb

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,18 @@ def expect_lookup(*keys)
4545
keys.each { |key| expect(adapter).to receive(:track).with(key) }
4646
end
4747

48+
context 'when the invocation has a default falsey values' do
49+
let(:lookup_invocation) { Lookup::Invocation.new(scope, {}, {'key' => false, 'key2' => nil}, nil) }
50+
51+
it 'converts boolean false to a "false" string in interpolation' do
52+
expect(interpolator.interpolate('%{key}', lookup_invocation, true)).to eq("false")
53+
end
54+
55+
it 'converts nil to an empty string in interpolation' do
56+
expect(interpolator.interpolate('%{key2}', lookup_invocation, true)).to eq("")
57+
end
58+
end
59+
4860
context 'when interpolating nested data' do
4961
let(:nested_hash) { {'a' => {'aa' => "%{alias('aaa')}"}} }
5062

0 commit comments

Comments
 (0)