summaryrefslogtreecommitdiffstats
path: root/lib/puppet/parser
diff options
context:
space:
mode:
authorMax Martin <max@puppetlabs.com>2011-04-13 17:30:44 -0700
committerMax Martin <max@puppetlabs.com>2011-04-13 17:30:44 -0700
commit3dde838ac992571e13262ea29ba3a0eb8152e753 (patch)
tree90520cf62bfa2f1bb9c992bbfe1bc47ae10471f2 /lib/puppet/parser
parentfe45c2417af580597cd39adec96a30a05a7cd66a (diff)
parent3ab44c7ce01ab86a995deb66228f5be95239c92a (diff)
downloadpuppet-3dde838ac992571e13262ea29ba3a0eb8152e753.tar.gz
puppet-3dde838ac992571e13262ea29ba3a0eb8152e753.tar.xz
puppet-3dde838ac992571e13262ea29ba3a0eb8152e753.zip
Merge branch 'next'
* next: (204 commits) Revert "(#6928) Removed --ignoreimport" Updated CHANGELOG for 2.6.8rc1 (#6928) Removed --ignoreimport (#6928) Remove --parseonly (#6928) Add a Parser face with Validate action (#6830) Fix sha1 to digest/sha1 require issue for Ruby 1.9 (#6830) Fix UTF-8 encoding issue for Ruby 1.9 (#6830) Fix string method sub call on a symbol for Ruby 1.9 (#2331) Remove darwinports pkg provider, replace with rewritten macports provider (#7059) handle inherited action binding scope maint: ensure we handle '-foo=' options correctly in faces. (#2150) Fix File const lookup when configuring routes Fixed #7082 - Added system support for groups maint: install erb templates under lib/ maint: clean up the spec test headers in bulk. (#7056) Use 'face' rather than 'faces' in the production code. maint: eliminate deprecated since 2008 code from Puppet. (#6117) Add POST support to indirector requests (#6962) Move option handling into #parse_options, not #preinit. maint: whitespace cleanup for puppet/util/command_line. ...
Diffstat (limited to 'lib/puppet/parser')
-rw-r--r--lib/puppet/parser/ast/leaf.rb4
-rw-r--r--lib/puppet/parser/ast/vardef.rb2
-rw-r--r--lib/puppet/parser/functions/extlookup.rb9
-rw-r--r--lib/puppet/parser/functions/fqdn_rand.rb2
-rw-r--r--lib/puppet/parser/functions/sha1.rb2
-rw-r--r--lib/puppet/parser/grammar.ra6
-rw-r--r--lib/puppet/parser/parser.rb6
-rw-r--r--lib/puppet/parser/resource.rb2
-rw-r--r--lib/puppet/parser/scope.rb132
-rw-r--r--lib/puppet/parser/templatewrapper.rb18
10 files changed, 54 insertions, 129 deletions
diff --git a/lib/puppet/parser/ast/leaf.rb b/lib/puppet/parser/ast/leaf.rb
index 77617e992..c8ebc9483 100644
--- a/lib/puppet/parser/ast/leaf.rb
+++ b/lib/puppet/parser/ast/leaf.rb
@@ -124,7 +124,7 @@ class Puppet::Parser::AST
# not include syntactical constructs, like '$' and '{}').
def evaluate(scope)
parsewrap do
- if (var = scope.lookupvar(@value, false)) == :undefined
+ if (var = scope.lookupvar(@value, :file => file, :line => line)) == :undefined
var = :undef
end
var
@@ -141,7 +141,7 @@ class Puppet::Parser::AST
def evaluate_container(scope)
container = variable.respond_to?(:evaluate) ? variable.safeevaluate(scope) : variable
- (container.is_a?(Hash) or container.is_a?(Array)) ? container : scope.lookupvar(container)
+ (container.is_a?(Hash) or container.is_a?(Array)) ? container : scope.lookupvar(container, :file => file, :line => line)
end
def evaluate_key(scope)
diff --git a/lib/puppet/parser/ast/vardef.rb b/lib/puppet/parser/ast/vardef.rb
index 6de1860c8..b766311dd 100644
--- a/lib/puppet/parser/ast/vardef.rb
+++ b/lib/puppet/parser/ast/vardef.rb
@@ -20,7 +20,7 @@ class Puppet::Parser::AST
name = @name.safeevaluate(scope)
parsewrap do
- scope.setvar(name,value, :file => @file, :line => @line, :append => @append)
+ scope.setvar(name,value, :file => file, :line => line, :append => @append)
end
end
end
diff --git a/lib/puppet/parser/functions/extlookup.rb b/lib/puppet/parser/functions/extlookup.rb
index bc55410b9..5fbf26cec 100644
--- a/lib/puppet/parser/functions/extlookup.rb
+++ b/lib/puppet/parser/functions/extlookup.rb
@@ -91,14 +91,9 @@ This is for back compatibility to interpolate variables with %. % interpolation
raise Puppet::ParseError, ("extlookup(): wrong number of arguments (#{args.length}; must be <= 3)") if args.length > 3
- extlookup_datadir = lookupvar('extlookup_datadir')
- extlookup_precedence = Array.new
+ extlookup_datadir = undef_as('',lookupvar('::extlookup_datadir'))
- extlookup_precedence = lookupvar('extlookup_precedence').collect do |var|
- var.gsub(/%\{(.+?)\}/) do |capture|
- lookupvar($1)
- end
- end
+ extlookup_precedence = undef_as([],lookupvar('::extlookup_precedence')).collect { |var| var.gsub(/%\{(.+?)\}/) { lookupvar("::#{$1}") } }
datafiles = Array.new
diff --git a/lib/puppet/parser/functions/fqdn_rand.rb b/lib/puppet/parser/functions/fqdn_rand.rb
index 91157a148..93ab98bcd 100644
--- a/lib/puppet/parser/functions/fqdn_rand.rb
+++ b/lib/puppet/parser/functions/fqdn_rand.rb
@@ -7,6 +7,6 @@ Puppet::Parser::Functions::newfunction(:fqdn_rand, :type => :rvalue, :doc =>
$random_number_seed = fqdn_rand(30,30)") do |args|
require 'digest/md5'
max = args.shift
- srand(Digest::MD5.hexdigest([lookupvar('fqdn'),args].join(':')).hex)
+ srand(Digest::MD5.hexdigest([lookupvar('::fqdn'),args].join(':')).hex)
rand(max).to_s
end
diff --git a/lib/puppet/parser/functions/sha1.rb b/lib/puppet/parser/functions/sha1.rb
index 10cc55cfe..1e7d5abe4 100644
--- a/lib/puppet/parser/functions/sha1.rb
+++ b/lib/puppet/parser/functions/sha1.rb
@@ -1,5 +1,5 @@
Puppet::Parser::Functions::newfunction(:sha1, :type => :rvalue, :doc => "Returns a SHA1 hash value from a provided string.") do |args|
- require 'sha1'
+ require 'digest/sha1'
Digest::SHA1.hexdigest(args[0])
end
diff --git a/lib/puppet/parser/grammar.ra b/lib/puppet/parser/grammar.ra
index 8339c51b7..d2bd06e94 100644
--- a/lib/puppet/parser/grammar.ra
+++ b/lib/puppet/parser/grammar.ra
@@ -156,7 +156,7 @@ resourceoverride: resourceref LBRACE anyparams endcomma RBRACE {
virtualresource: at resource {
type = val[0]
- if (type == :exported and ! Puppet[:storeconfigs]) and ! Puppet[:parseonly]
+ if (type == :exported and ! Puppet[:storeconfigs])
Puppet.warning addcontext("You cannot collect without storeconfigs being set")
end
@@ -188,7 +188,7 @@ collection: classref collectrhand LBRACE anyparams endcomma RBRACE {
else
args[:form] = val[1]
end
- if args[:form] == :exported and ! Puppet[:storeconfigs] and ! Puppet[:parseonly]
+ if args[:form] == :exported and ! Puppet[:storeconfigs]
Puppet.warning addcontext("You cannot collect exported resources without storeconfigs being set; the collection will be ignored")
end
args[:override] = val[3]
@@ -208,7 +208,7 @@ collection: classref collectrhand LBRACE anyparams endcomma RBRACE {
else
args[:form] = val[1]
end
- if args[:form] == :exported and ! Puppet[:storeconfigs] and ! Puppet[:parseonly]
+ if args[:form] == :exported and ! Puppet[:storeconfigs]
Puppet.warning addcontext("You cannot collect exported resources without storeconfigs being set; the collection will be ignored")
end
result = ast AST::Collection, args
diff --git a/lib/puppet/parser/parser.rb b/lib/puppet/parser/parser.rb
index 300ddddd6..611398d14 100644
--- a/lib/puppet/parser/parser.rb
+++ b/lib/puppet/parser/parser.rb
@@ -1366,7 +1366,7 @@ module_eval(<<'.,.,', 'grammar.ra', 156)
def _reduce_50(val, _values, result)
type = val[0]
- if (type == :exported and ! Puppet[:storeconfigs]) and ! Puppet[:parseonly]
+ if (type == :exported and ! Puppet[:storeconfigs])
Puppet.warning addcontext("You cannot collect without storeconfigs being set")
end
@@ -1411,7 +1411,7 @@ module_eval(<<'.,.,', 'grammar.ra', 178)
else
args[:form] = val[1]
end
- if args[:form] == :exported and ! Puppet[:storeconfigs] and ! Puppet[:parseonly]
+ if args[:form] == :exported and ! Puppet[:storeconfigs]
Puppet.warning addcontext("You cannot collect exported resources without storeconfigs being set; the collection will be ignored")
end
args[:override] = val[3]
@@ -1436,7 +1436,7 @@ module_eval(<<'.,.,', 'grammar.ra', 197)
else
args[:form] = val[1]
end
- if args[:form] == :exported and ! Puppet[:storeconfigs] and ! Puppet[:parseonly]
+ if args[:form] == :exported and ! Puppet[:storeconfigs]
Puppet.warning addcontext("You cannot collect exported resources without storeconfigs being set; the collection will be ignored")
end
result = ast AST::Collection, args
diff --git a/lib/puppet/parser/resource.rb b/lib/puppet/parser/resource.rb
index c007d4dbe..ace01bb4b 100644
--- a/lib/puppet/parser/resource.rb
+++ b/lib/puppet/parser/resource.rb
@@ -241,7 +241,7 @@ class Puppet::Parser::Resource < Puppet::Resource
def add_backward_compatible_relationship_param(name)
# Skip metaparams for which we get no value.
- return unless val = scope.lookupvar(name.to_s, false) and val != :undefined
+ return unless val = scope.lookupvar(name.to_s) and val != :undefined
# The default case: just set the value
set_parameter(name, val) and return unless @parameters[name]
diff --git a/lib/puppet/parser/scope.rb b/lib/puppet/parser/scope.rb
index 24f1d01f7..8de9d60b1 100644
--- a/lib/puppet/parser/scope.rb
+++ b/lib/puppet/parser/scope.rb
@@ -18,10 +18,10 @@ class Puppet::Parser::Scope
include Enumerable
include Puppet::Util::Errors
- attr_accessor :level, :source, :resource
+ attr_accessor :source, :resource
attr_accessor :base, :keyword
attr_accessor :top, :translated, :compiler
- attr_accessor :parent
+ attr_accessor :parent, :dynamic
attr_reader :namespaces
# thin wrapper around an ephemeral
@@ -104,11 +104,6 @@ class Puppet::Parser::Scope
compiler.environment
end
- # Are we the top scope?
- def topscope?
- @level == 1
- end
-
def find_hostclass(name)
known_resource_types.find_hostclass(namespaces, name)
end
@@ -215,45 +210,41 @@ class Puppet::Parser::Scope
find_definition(name) || find_hostclass(name)
end
- def lookup_qualified_var(name, usestring)
- parts = name.split(/::/)
- shortname = parts.pop
- klassname = parts.join("::")
- klass = find_hostclass(klassname)
- unless klass
- warning "Could not look up qualified variable '#{name}'; class #{klassname} could not be found"
- return usestring ? "" : :undefined
- end
- unless kscope = class_scope(klass)
- warning "Could not look up qualified variable '#{name}'; class #{klassname} has not been evaluated"
- return usestring ? "" : :undefined
- end
- kscope.lookupvar(shortname, usestring)
+ def undef_as(x,v)
+ (v == :undefined) ? x : (v == :undef) ? x : v
end
- private :lookup_qualified_var
+ def qualified_scope(classname)
+ raise "class #{classname} could not be found" unless klass = find_hostclass(classname)
+ raise "class #{classname} has not been evaluated" unless kscope = class_scope(klass)
+ kscope
+ end
+
+ private :qualified_scope
- # Look up a variable. The simplest value search we do. Default to returning
- # an empty string for missing values, but support returning a constant.
- def lookupvar(name, usestring = true)
+ # Look up a variable. The simplest value search we do.
+ def lookupvar(name, options = {})
table = ephemeral?(name) ? @ephemeral.last : @symtable
# If the variable is qualified, then find the specified scope and look the variable up there instead.
- if name =~ /::/
- return lookup_qualified_var(name, usestring)
- end
- # We can't use "if table[name]" here because the value might be false
- if ephemeral_include?(name) or table.include?(name)
- if usestring and table[name] == :undef
- return ""
- else
- return table[name]
+ if name =~ /^(.*)::(.+)$/
+ begin
+ qualified_scope($1).lookupvar($2,options)
+ 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
- elsif self.parent
- return parent.lookupvar(name, usestring)
- elsif usestring
- return ""
+ elsif ephemeral_include?(name) or table.include?(name)
+ # 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} will not be supported in future versions. Use a fully-qualified variable name or parameterized classes."
+ end
+ table[name]
+ elsif parent
+ parent.lookupvar(name,options.merge(:dynamic => (dynamic || options[:dynamic])))
else
- return :undefined
+ :undefined
end
end
@@ -323,8 +314,6 @@ class Puppet::Parser::Scope
# to be reassigned.
def setvar(name,value, options = {})
table = options[:ephemeral] ? @ephemeral.last : @symtable
- #Puppet.debug "Setting %s to '%s' at level %s mode append %s" %
- # [name.inspect,value,self.level, append]
if table.include?(name)
unless options[:append]
error = Puppet::ParseError.new("Cannot reassign variable #{name}")
@@ -340,7 +329,7 @@ class Puppet::Parser::Scope
table[name] = value
else # append case
# lookup the value in the scope if it exists and insert the var
- table[name] = lookupvar(name)
+ table[name] = undef_as('',lookupvar(name))
# concatenate if string, append if array, nothing for other types
case value
when Array
@@ -354,65 +343,6 @@ class Puppet::Parser::Scope
end
end
- # Return an interpolated string.
- def strinterp(string, file = nil, line = nil)
- # Most strings won't have variables in them.
- ss = StringScanner.new(string)
- out = ""
- while not ss.eos?
- if ss.scan(/^\$\{((\w*::)*\w+|[0-9]+)\}|^\$([0-9])|^\$((\w*::)*\w+)/)
- # If it matches the backslash, then just retun the dollar sign.
- if ss.matched == '\\$'
- out << '$'
- else # look the variable up
- # make sure $0-$9 are lookupable only if ephemeral
- var = ss[1] || ss[3] || ss[4]
- if var and var =~ /^[0-9]+$/ and not ephemeral_include?(var)
- next
- end
- out << lookupvar(var).to_s || ""
- end
- elsif ss.scan(/^\\(.)/)
- # Puppet.debug("Got escape: pos:%d; m:%s" % [ss.pos, ss.matched])
- case ss[1]
- when 'n'
- out << "\n"
- when 't'
- out << "\t"
- when 's'
- out << " "
- when '\\'
- out << '\\'
- when '$'
- out << '$'
- else
- str = "Unrecognised escape sequence '#{ss.matched}'"
- str += " in file #{file}" if file
- str += " at line #{line}" if line
- Puppet.warning str
- out << ss.matched
- end
- elsif ss.scan(/^\$/)
- out << '$'
- elsif ss.scan(/^\\\n/) # an escaped carriage return
- next
- else
- tmp = ss.scan(/[^\\$]+/)
- # Puppet.debug("Got other: pos:%d; m:%s" % [ss.pos, tmp])
- unless tmp
- error = Puppet::ParseError.new("Could not parse string #{string.inspect}")
- {:file= => file, :line= => line}.each do |m,v|
- error.send(m, v) if v
- end
- raise error
- end
- out << tmp
- end
- end
-
- out
- end
-
# Return the tags associated with this scope. It's basically
# just our parents' tags, plus our type. We don't cache this value
# because our parent tags might change between calls.
diff --git a/lib/puppet/parser/templatewrapper.rb b/lib/puppet/parser/templatewrapper.rb
index 6864aa1a9..180a03dc9 100644
--- a/lib/puppet/parser/templatewrapper.rb
+++ b/lib/puppet/parser/templatewrapper.rb
@@ -18,13 +18,14 @@ class Puppet::Parser::TemplateWrapper
@__scope__
end
+ def script_line
+ # find which line in the template (if any) we were called from
+ caller.find { |l| l =~ /#{file}:/ }.first[/:(\d+):/,1]
+ end
+
# Should return true if a variable is defined, false if it is not
def has_variable?(name)
- if scope.lookupvar(name.to_s, false) != :undefined
- true
- else
- false
- end
+ scope.lookupvar(name.to_s, :file => file, :line => script_line) != :undefined
end
# Allow templates to access the defined classes
@@ -55,15 +56,13 @@ class Puppet::Parser::TemplateWrapper
# the missing_method definition here until we declare the syntax finally
# dead.
def method_missing(name, *args)
- # We have to tell lookupvar to return :undefined to us when
- # appropriate; otherwise it converts to "".
- value = scope.lookupvar(name.to_s, false)
+ value = scope.lookupvar(name.to_s,:file => file,:line => script_line)
if value != :undefined
return value
else
# Just throw an error immediately, instead of searching for
# other missingmethod things or whatever.
- raise Puppet::ParseError, "Could not find value for '#{name}'"
+ raise Puppet::ParseError.new("Could not find value for '#{name}'",@file,script_line)
end
end
@@ -103,6 +102,7 @@ class Puppet::Parser::TemplateWrapper
result = nil
benchmark(:debug, "Interpolated template #{template_source}") do
template = ERB.new(self.string, 0, "-")
+ template.filename = file
result = template.result(binding)
end