Skip to content

Commit

Permalink
Merge remote-tracking branch 'zaphod42/bug/2.7.x/8174-incorrect-warni…
Browse files Browse the repository at this point in the history
…ng-about-deprecated-scoping' into 2.7.x

* zaphod42/bug/2.7.x/8174-incorrect-warning-about-deprecated-scoping:
  Fixed old log test to match new autoflush behavior
  Make sure the log file writable
  Default autoflushing of log files to true
  Created test that shows enc warning problem
  Increased test coverage of scoping rules
  Use more descriptive terms for the differing scopes
  Make new scoping look through inherited scopes
  Add tests for mixed inheritence/inclusion
  Remove dynamic option for lookupvar
  Implement newlookupvar() to replace dynamic scope
  Tests for deprecation warnings for dynamic scoping
  • Loading branch information
Jeff Weiss committed Apr 12, 2012
2 parents a30b45f + fb96747 commit 849a882
Show file tree
Hide file tree
Showing 8 changed files with 414 additions and 36 deletions.
@@ -0,0 +1,80 @@
test_name "#8174: incorrect warning about deprecated scoping"

testdir = master.tmpdir('scoping_deprecation')

create_remote_file(master, "#{testdir}/puppet.conf", <<END)
[main]
node_terminus = exec
external_nodes = "#{testdir}/enc"
manifest = "#{testdir}/site.pp"
modulepath = "#{testdir}/modules"
END

on master, "mkdir -p #{testdir}/modules/a/manifests"

create_remote_file(master, "#{testdir}/enc", <<-PP)
#!/usr/bin/env sh
cat <<END
---
classes:
a
parameters:
enc_var: "Set from ENC."
END
exit 0
PP

create_remote_file(master, "#{testdir}/site.pp", <<-PP)
$top_scope = "set from site.pp"
node default {
$node_var = "in node"
}
PP
create_remote_file(master, "#{testdir}/modules/a/manifests/init.pp", <<-PP)
class a {
$locally = "locally declared"
$dynamic_for_b = "dynamic and declared in a"
notify { "fqdn from facts": message => $fqdn }
notify { "locally declared var": message => $locally }
notify { "var via enc": message => $enc_var }
notify { "declared top scope": message => $top_scope }
notify { "declared node": message => $node_var }
include a::b
}
PP
create_remote_file(master, "#{testdir}/modules/a/manifests/b.pp", <<-PP)
class a::b {
notify { "dynamic from elsewhere": message => $dynamic_for_b }
}
PP

on master, "chown -R root:puppet #{testdir}"
on master, "chmod -R g+rwX #{testdir}"
on master, "chmod -R a+x #{testdir}/enc"
on master, "touch #{testdir}/log"
on master, "chown puppet #{testdir}/log"

assert_log_on_master_contains = lambda do |string|
on master, "grep '#{string}' #{testdir}/log"
end

assert_log_on_master_does_not_contain = lambda do |string|
on master, "grep -v '#{string}' #{testdir}/log"
end

with_master_running_on(master, "--config #{testdir}/puppet.conf --debug --verbose --daemonize --dns_alt_names=\"puppet,$(hostname -s),$(hostname -f)\" --autosign true --logdest #{testdir}/log") do
agents.each do |agent|
run_agent_on(agent, "--no-daemonize --onetime --server #{master}")
end

assert_log_on_master_contains['Dynamic lookup of $dynamic_for_b']
assert_log_on_master_does_not_contain['Dynamic lookup of $fqdn']
assert_log_on_master_does_not_contain['Dynamic lookup of $locally']
assert_log_on_master_does_not_contain['Dynamic lookup of $enc_var']
assert_log_on_master_does_not_contain['Dynamic lookup of $top_scope']
assert_log_on_master_does_not_contain['Dynamic lookup of $node_var']
end

on master, "rm -rf #{testdir}"
2 changes: 1 addition & 1 deletion lib/puppet/defaults.rb
Expand Up @@ -15,7 +15,7 @@ module Puppet
setdefaults(:main, setdefaults(:main,
:trace => [false, "Whether to print stack traces on some errors"], :trace => [false, "Whether to print stack traces on some errors"],
:autoflush => { :autoflush => {
:default => false, :default => true,
:desc => "Whether log files should always flush to disk.", :desc => "Whether log files should always flush to disk.",
:hook => proc { |value| Log.autoflush = value } :hook => proc { |value| Log.autoflush = value }
}, },
Expand Down
51 changes: 42 additions & 9 deletions lib/puppet/parser/scope.rb
Expand Up @@ -21,7 +21,7 @@ class Puppet::Parser::Scope
attr_accessor :source, :resource attr_accessor :source, :resource
attr_accessor :base, :keyword attr_accessor :base, :keyword
attr_accessor :top, :translated, :compiler attr_accessor :top, :translated, :compiler
attr_accessor :parent, :dynamic attr_accessor :parent
attr_reader :namespaces attr_reader :namespaces


# thin wrapper around an ephemeral # thin wrapper around an ephemeral
Expand Down Expand Up @@ -222,27 +222,60 @@ def qualified_scope(classname)


private :qualified_scope private :qualified_scope


# Look up a variable. The simplest value search we do. # Look up a variable with traditional scoping and then with new scoping. If
# the answers differ then print a deprecation warning.
def lookupvar(name, options = {}) def lookupvar(name, options = {})
dynamic_value = dynamic_lookupvar(name,options)
twoscope_value = twoscope_lookupvar(name,options)
if dynamic_value != twoscope_value
location = (options[:file] && options[:line]) ? " at #{options[:file]}:#{options[:line]}" : ''
Puppet.deprecation_warning "Dynamic lookup of $#{name}#{location} is deprecated. Support will be removed in a later version of Puppet. Use a fully-qualified variable name (e.g., $classname::variable) or parameterized classes."
end
dynamic_value
end

# Look up a variable. The simplest value search we do.
def twoscope_lookupvar(name, options = {})
# Save the originating scope for the request
options[:origin] = self unless options[:origin]
table = ephemeral?(name) ? @ephemeral.last : @symtable
if name =~ /^(.*)::(.+)$/
begin
qualified_scope($1).twoscope_lookupvar($2,options.merge({:origin => nil}))
rescue RuntimeError => e
location = (options[:file] && options[:line]) ? " at #{options[:file]}:#{options[:line]}" : ''
warning "Could not look up qualified variable '#{name}'; #{e.message}#{location}"
:undefined
end
# If the value is present and either we are top/node scope or originating scope...
elsif (ephemeral_include?(name) or table.include?(name)) and (compiler and self == compiler.topscope or (self.resource and self.resource.type == "Node") or self == options[:origin])
table[name]
elsif resource and resource.resource_type and resource.resource_type.respond_to?("parent") and parent_type = resource.resource_type.parent
class_scope(parent_type).twoscope_lookupvar(name,options.merge({:origin => nil}))
elsif parent
parent.twoscope_lookupvar(name,options)
else
:undefined
end
end

# Look up a variable. The simplest value search we do.
def dynamic_lookupvar(name, options = {})
table = ephemeral?(name) ? @ephemeral.last : @symtable table = ephemeral?(name) ? @ephemeral.last : @symtable
# If the variable is qualified, then find the specified scope and look the variable up there instead. # If the variable is qualified, then find the specified scope and look the variable up there instead.
if name =~ /^(.*)::(.+)$/ if name =~ /^(.*)::(.+)$/
begin begin
qualified_scope($1).lookupvar($2,options) qualified_scope($1).dynamic_lookupvar($2,options)
rescue RuntimeError => e rescue RuntimeError => e
location = (options[:file] && options[:line]) ? " at #{options[:file]}:#{options[:line]}" : '' location = (options[:file] && options[:line]) ? " at #{options[:file]}:#{options[:line]}" : ''
warning "Could not look up qualified variable '#{name}'; #{e.message}#{location}" warning "Could not look up qualified variable '#{name}'; #{e.message}#{location}"
:undefined :undefined
end end
elsif ephemeral_include?(name) or table.include?(name) elsif ephemeral_include?(name) or table.include?(name)
# We can't use "if table[name]" here because the value might be false # We can't use "if table[name]" here because the value might be false
if options[:dynamic] and self != compiler.topscope
location = (options[:file] && options[:line]) ? " at #{options[:file]}:#{options[:line]}" : ''
Puppet.deprecation_warning "Dynamic lookup of $#{name}#{location} is deprecated. Support will be removed in Puppet 2.8. Use a fully-qualified variable name (e.g., $classname::variable) or parameterized classes."
end
table[name] table[name]
elsif parent elsif parent
parent.lookupvar(name,options.merge(:dynamic => (dynamic || options[:dynamic]))) parent.dynamic_lookupvar(name,options)
else else
:undefined :undefined
end end
Expand Down Expand Up @@ -374,7 +407,7 @@ def unset_ephemeral_var(level=:all)


# check if name exists in one of the ephemeral scope. # check if name exists in one of the ephemeral scope.
def ephemeral_include?(name) def ephemeral_include?(name)
@ephemeral.reverse.each do |eph| @ephemeral.reverse_each do |eph|
return true if eph.include?(name) return true if eph.include?(name)
end end
false false
Expand Down
2 changes: 1 addition & 1 deletion lib/puppet/resource/type.rb
Expand Up @@ -66,7 +66,7 @@ def evaluate_code(resource)
static_parent = evaluate_parent_type(resource) static_parent = evaluate_parent_type(resource)
scope = static_parent || resource.scope scope = static_parent || resource.scope


scope = scope.newscope(:namespace => namespace, :source => self, :resource => resource, :dynamic => !static_parent) unless resource.title == :main scope = scope.newscope(:namespace => namespace, :source => self, :resource => resource) unless resource.title == :main
scope.compiler.add_class(name) unless definition? scope.compiler.add_class(name) unless definition?


set_resource_parameters(resource, scope) set_resource_parameters(resource, scope)
Expand Down

0 comments on commit 849a882

Please sign in to comment.