summaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorMarkus Roberts <Markus@reality.com>2010-10-24 23:29:38 -0700
committerNick Lewis <nick@puppetlabs.com>2011-04-12 12:47:32 -0700
commit739260b28d7c09bacbb34cd4f4d4a32cfee01385 (patch)
tree9dc514930f0f433786211a9c8c07742aec99ae01 /lib
parentd7201ed38929f867d31bc9b916e90679606dc9f8 (diff)
downloadpuppet-739260b28d7c09bacbb34cd4f4d4a32cfee01385.tar.gz
puppet-739260b28d7c09bacbb34cd4f4d4a32cfee01385.tar.xz
puppet-739260b28d7c09bacbb34cd4f4d4a32cfee01385.zip
Towards 5027 -- add options hash to lookupvar as with setvar
This patch adds an options hash to lookupvar analogous to the one taken by setvar and uses it to pass in source location for error reporting. It also fixes the mechanism used by setvar (file was not being passed correctly), adds line and file information to errors in templates, and extends/corrects tests. As presently written it does not gather userful line numbers from inline templates and there are no tests for the template line number generation.
Diffstat (limited to 'lib')
-rw-r--r--lib/puppet/parser/ast/leaf.rb4
-rw-r--r--lib/puppet/parser/ast/vardef.rb2
-rw-r--r--lib/puppet/parser/scope.rb9
-rw-r--r--lib/puppet/parser/templatewrapper.rb12
4 files changed, 17 insertions, 10 deletions
diff --git a/lib/puppet/parser/ast/leaf.rb b/lib/puppet/parser/ast/leaf.rb
index b61634d6c..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)) == :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/scope.rb b/lib/puppet/parser/scope.rb
index 95b765b52..a61a8578f 100644
--- a/lib/puppet/parser/scope.rb
+++ b/lib/puppet/parser/scope.rb
@@ -223,21 +223,22 @@ class Puppet::Parser::Scope
private :qualified_scope
# Look up a variable. The simplest value search we do.
- def lookupvar(name)
+ 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 =~ /^(.*)::(.+)$/
begin
- qualified_scope($1).lookupvar($2)
+ qualified_scope($1).lookupvar($2,options)
rescue RuntimeError => e
- warning "Could not look up qualified variable '#{name}'; #{e.message}"
+ location = (options[:file] && options[:line]) ? " at #{options[:file]}:#{options[:line]}" : ''
+ warning "Could not look up qualified variable '#{name}'; #{e.message}#{location}"
:undefined
end
elsif ephemeral_include?(name) or table.include?(name)
# We can't use "if table[name]" here because the value might be false
table[name]
elsif parent
- parent.lookupvar(name)
+ parent.lookupvar(name,options)
else
:undefined
end
diff --git a/lib/puppet/parser/templatewrapper.rb b/lib/puppet/parser/templatewrapper.rb
index 73fcb8aac..180a03dc9 100644
--- a/lib/puppet/parser/templatewrapper.rb
+++ b/lib/puppet/parser/templatewrapper.rb
@@ -18,9 +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)
- scope.lookupvar(name.to_s) != :undefined
+ scope.lookupvar(name.to_s, :file => file, :line => script_line) != :undefined
end
# Allow templates to access the defined classes
@@ -51,13 +56,13 @@ class Puppet::Parser::TemplateWrapper
# the missing_method definition here until we declare the syntax finally
# dead.
def method_missing(name, *args)
- value = scope.lookupvar(name.to_s)
+ 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
@@ -97,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