1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
|
class Puppet::Parser::AST
# The specific code associated with a host. Nodes are annoyingly unlike
# other objects. That's just the way it is, at least for now.
class Node < AST::HostClass
@name = :node
attr_accessor :type, :args, :code, :parentclass
#def evaluate(scope, facts = {})
def evaluate(hash)
origscope = hash[:scope]
facts = hash[:facts] || {}
# nodes are never instantiated like a normal object,
# but we need the type to be the name users would use for
# instantiation, otherwise tags don't work out
pscope = origscope
#pscope = if ! Puppet[:lexical] or hash[:asparent]
# @scope
#else
# origscope
#end
scope = pscope.newscope(
:type => self.type,
:keyword => @keyword
)
scope.context = self.object_id
# Now set all of the facts inside this scope
facts.each { |var, value|
scope.setvar(var, value)
}
if tmp = self.evalparent(scope)
# Again, override our scope with the parent scope, if
# there is one.
scope = tmp
end
#scope.tag(@name)
# We never pass the facts to the parent class, because they've
# already been defined at this top-level scope.
#super(scope, facts, @name, @name)
# Mark our node name as a class, too, but strip it of the domain
# name. Make the mark before we evaluate the code, so that it is
# marked within the code itself.
scope.setclass(self.object_id, @type.sub(/\..+/, ''))
# And then evaluate our code.
@code.safeevaluate(:scope => scope)
return scope
end
# Evaluate our parent class.
def evalparent(scope)
if @parentclass
# This is pretty messed up. I don't know if this will
# work in the long term, but we need to evaluate the node
# in our own scope, even though our parent node has
# a scope associated with it, because otherwise we 1) won't
# get our facts defined, and 2) we won't actually get the
# objects returned, based on how nodes work.
# We also can't just evaluate the node itself, because
# it would create a node scope within this scope,
# and that would cause mass havoc.
node = nil
# The 'node' method just returns a hash of the node
# code and name. It's used here, and in 'evalnode'.
unless hash = scope.node(@parentclass)
raise Puppet::ParseError,
"Could not find parent node %s" %
@parentclass
end
node = hash[:node]
type = nil
if type = node.type
scope.tag(node.type)
end
begin
code = node.code
code.safeevaluate(:scope => scope, :asparent => true)
rescue Puppet::ParseError => except
except.line = self.line
except.file = self.file
raise except
rescue => detail
error = Puppet::ParseError.new(detail)
error.line = self.line
error.file = self.file
raise error
end
if node.parentclass
node.evalparent(scope)
end
end
end
def initialize(hash)
@parentclass = nil
super
end
end
end
|