summaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/puppet/metatype/container.rb20
-rw-r--r--lib/puppet/metatype/manager.rb8
-rw-r--r--lib/puppet/metatype/metaparams.rb87
-rw-r--r--lib/puppet/metatype/relationships.rb142
-rw-r--r--lib/puppet/pgraph.rb125
-rw-r--r--lib/puppet/relationship.rb18
-rw-r--r--lib/puppet/transaction.rb179
-rw-r--r--lib/puppet/type.rb2
-rw-r--r--lib/puppet/type/component.rb3
9 files changed, 257 insertions, 327 deletions
diff --git a/lib/puppet/metatype/container.rb b/lib/puppet/metatype/container.rb
index 3f970b7d9..9ed587a4c 100644
--- a/lib/puppet/metatype/container.rb
+++ b/lib/puppet/metatype/container.rb
@@ -78,26 +78,6 @@ class Puppet::Type
hash.clear
end
-
- if rmdeps
- Puppet::Event::Subscription.dependencies(self).each { |dep|
- #info "Deleting dependency %s" % dep
- #begin
- # self.unsubscribe(dep)
- #rescue
- # # ignore failed unsubscribes
- #end
- dep.delete
- }
- Puppet::Event::Subscription.subscribers(self).each { |dep|
- #info "Unsubscribing from %s" % dep
- begin
- dep.unsubscribe(self)
- rescue
- # ignore failed unsubscribes
- end
- }
- end
self.class.delete(self)
if defined? @parent and @parent
diff --git a/lib/puppet/metatype/manager.rb b/lib/puppet/metatype/manager.rb
index 996d9a3cc..d2749b87d 100644
--- a/lib/puppet/metatype/manager.rb
+++ b/lib/puppet/metatype/manager.rb
@@ -106,6 +106,14 @@ module Manager
klass
end
+
+ # Remove an existing defined type. Largely used for testing.
+ def rmtype(name)
+ # Then create the class.
+ klass = rmclass(name,
+ :hash => @types
+ )
+ end
# Return a Type instance by name.
def type(name)
diff --git a/lib/puppet/metatype/metaparams.rb b/lib/puppet/metatype/metaparams.rb
index e09bbc6d5..f28103a87 100644
--- a/lib/puppet/metatype/metaparams.rb
+++ b/lib/puppet/metatype/metaparams.rb
@@ -92,6 +92,47 @@ class Puppet::Type
}
end
end
+
+ # We've got four relationship metaparameters, so this method is used
+ # to reduce code duplication between them.
+ def store_relationship(param, values)
+ # We need to support values passed in as an array or as a
+ # resource reference.
+ result = []
+
+ # 'values' could be an array or a reference. If it's an array,
+ # it could be an array of references or an array of arrays.
+ if values.is_a?(Puppet::Type)
+ result << [values.class.name, values.title]
+ else
+ unless values.is_a?(Array)
+ devfail "Relationships must be resource references"
+ end
+ if values[0].is_a?(String) or values[0].is_a?(Symbol)
+ # we're a type/title array reference
+ values[0] = symbolize(values[0])
+ result << values
+ else
+ # we're an array of stuff
+ values.each do |value|
+ if value.is_a?(Puppet::Type)
+ result << [value.class.name, value.title]
+ elsif value.is_a?(Array)
+ value[0] = symbolize(value[0])
+ result << value
+ else
+ devfail "Invalid relationship %s" % value.inspect
+ end
+ end
+ end
+ end
+
+ if existing = self[param]
+ result = existing + result
+ end
+
+ result
+ end
# For each object we require, subscribe to all events that it generates. We
# might reduce the level of subscription eventually, but for now...
@@ -133,17 +174,7 @@ class Puppet::Type
# Take whatever dependencies currently exist and add these.
# Note that this probably doesn't behave correctly with unsubscribe.
munge do |requires|
- # We need to be two arrays deep...
- unless requires.is_a?(Array)
- requires = [requires]
- end
- unless requires[0].is_a?(Array)
- requires = [requires]
- end
- if values = @parent[:require]
- requires = values + requires
- end
- requires
+ @parent.store_relationship(:require, requires)
end
end
@@ -167,11 +198,7 @@ class Puppet::Type
"
munge do |requires|
- if values = @parent[:subscribe]
- requires = values + requires
- end
- requires
- # @parent.handledepends(requires, :ALL_EVENTS, :refresh)
+ @parent.store_relationship(:subscribe, requires)
end
end
@@ -295,21 +322,9 @@ class Puppet::Type
This will restart the sshd service if the sshd config file changes.}
- # Take whatever dependencies currently exist and add these.
munge do |notifies|
- # We need to be two arrays deep...
- unless notifies.is_a?(Array)
- notifies = [notifies]
- end
- unless notifies[0].is_a?(Array)
- notifies = [notifies]
- end
- if values = @parent[:notify]
- notifies = values + notifies
- end
- notifies
+ @parent.store_relationship(:notify, notifies)
end
-
end
newmetaparam(:before) do
@@ -331,21 +346,9 @@ class Puppet::Type
This will make sure all of the files are up to date before the
make command is run.}
- # Take whatever dependencies currently exist and add these.
munge do |notifies|
- # We need to be two arrays deep...
- unless notifies.is_a?(Array)
- notifies = [notifies]
- end
- unless notifies[0].is_a?(Array)
- notifies = [notifies]
- end
- if values = @parent[:notify]
- notifies = values + notifies
- end
- notifies
+ @parent.store_relationship(:before, notifies)
end
-
end
end # Puppet::Type
diff --git a/lib/puppet/metatype/relationships.rb b/lib/puppet/metatype/relationships.rb
index 714ed7690..5f2471460 100644
--- a/lib/puppet/metatype/relationships.rb
+++ b/lib/puppet/metatype/relationships.rb
@@ -18,6 +18,7 @@ class Puppet::Type
# Figure out of there are any objects we can automatically add as
# dependencies.
def autorequire
+ reqs = []
self.class.eachautorequire { |type, block|
# Ignore any types we can't find, although that would be a bit odd.
next unless typeobj = Puppet.type(type)
@@ -32,74 +33,48 @@ class Puppet::Type
list.each { |dep|
obj = nil
# Support them passing objects directly, to save some effort.
- if dep.is_a? Puppet::Type
- type = dep.class.name
- obj = dep
-
- # Now change our dependency to just the string, instead of
- # the object itself.
- dep = dep.title
- else
+ unless dep.is_a? Puppet::Type
# Skip autorequires that we aren't managing
- unless obj = typeobj[dep]
+ unless dep = typeobj[dep]
next
end
end
-
- # Skip autorequires that we already require
- next if self.requires?(obj)
-
- debug "Autorequiring %s %s" % [obj.class.name, obj.title]
- self[:require] = [type, dep]
+
+ debug "Autorequiring %s" % [dep.ref]
+ reqs << Puppet::Relationship[dep, self]
}
-
- #self.info reqs.inspect
- #self[:require] = reqs
}
+
+ return reqs
end
- # Build the dependencies associated with an individual object.
+ # Build the dependencies associated with an individual object. :in
+ # relationships are specified by the event-receivers, and :out
+ # relationships are specified by the event generator. This
+ # way 'source' and 'target' are consistent terms in both edges
+ # and events -- that is, an event targets edges whose source matches
+ # the event's source. Note that the direction of the relationship
+ # doesn't actually mean anything until you start using events --
+ # the same information is present regardless.
def builddepends
# Handle the requires
- if self[:require]
- self.handledepends(self[:require], :NONE, nil, true)
- end
-
- # And the subscriptions
- if self[:subscribe]
- self.handledepends(self[:subscribe], :ALL_EVENTS, :refresh, true)
- end
-
- if self[:notify]
- self.handledepends(self[:notify], :ALL_EVENTS, :refresh, false)
- end
-
- if self[:before]
- self.handledepends(self[:before], :NONE, nil, false)
- end
- end
-
- # return all objects that we depend on
- def eachdependency
- Puppet::Event::Subscription.dependencies(self).each { |dep|
- yield dep.source
- }
- end
-
- # return all objects subscribed to the current object
- def eachsubscriber
- Puppet::Event::Subscription.subscribers(self).each { |sub|
- yield sub.target
- }
+ {:require => [:NONE, nil, :in],
+ :subscribe => [:ALL_EVENTS, :refresh, :in],
+ :notify => [:ALL_EVENTS, :refresh, :out],
+ :before => [:NONE, nil, :out]}.collect do |type, args|
+ if self[type]
+ handledepends(self[type], *args)
+ end
+ end.flatten.reject { |r| r.nil? }
end
- def handledepends(requires, event, method, up)
+ def handledepends(requires, event, method, direction)
# Requires are specified in the form of [type, name], so they're always
# an array. But we want them to be an array of arrays.
unless requires[0].is_a?(Array)
requires = [requires]
end
- requires.each { |rname|
+ requires.collect { |rname|
# we just have a name and a type, and we need to convert it
# to an object...
type = nil
@@ -115,9 +90,9 @@ class Puppet::Type
end
self.debug("subscribes to %s" % [object])
- # Are we requiring them, or vice versa?
- source = target = nil
- if up
+ # Are we requiring them, or vice versa? See the builddepends
+ # method for further docs on this.
+ if direction == :in
source = object
target = self
else
@@ -129,61 +104,30 @@ class Puppet::Type
# we store the method to call when a given subscription is
# triggered, but the source object decides whether
subargs = {
- :event => event,
- :source => source,
- :target => target
+ :event => event
}
- if method and target.respond_to?(method)
+ if method
subargs[:callback] = method
end
- Puppet::Event::Subscription.new(subargs)
+ rel = Puppet::Relationship.new(source, target, subargs)
}
end
- def requires?(object)
- req = false
- self.eachdependency { |dep|
- if dep == object
- req = true
- break
- end
- }
-
- return req
- end
-
- def subscribe(hash)
- hash[:source] = self
- Puppet::Event::Subscription.new(hash)
-
- # add to the correct area
- #@subscriptions.push sub
- end
-
- def subscribesto?(object)
- sub = false
- self.eachsubscriber { |o|
- if o == object
- sub = true
- break
- end
- }
-
- return sub
- end
-
# Unsubscribe from a given object, possibly with a specific event.
def unsubscribe(object, event = nil)
- Puppet::Event::Subscription.dependencies(self).find_all { |sub|
- if event
- sub.match?(event)
- else
- sub.source == object
+ # First look through our own relationship params
+ [:require, :subscribe].each do |param|
+ if values = self[param]
+ newvals = values.reject { |d|
+ d == [object.class.name, object.title]
+ }
+ if newvals.length != values.length
+ self.delete(param)
+ self[param] = newvals
+ end
end
- }.each { |sub|
- sub.delete
- }
+ end
end
# we've received an event
diff --git a/lib/puppet/pgraph.rb b/lib/puppet/pgraph.rb
index fba93d20c..292e25073 100644
--- a/lib/puppet/pgraph.rb
+++ b/lib/puppet/pgraph.rb
@@ -11,27 +11,6 @@ require 'puppet/relationship'
# This class subclasses a graph class in order to handle relationships
# among resources.
class Puppet::PGraph < GRATR::Digraph
- # Collect all of the targets for the list of events. Basically just iterates
- # over the sources of the events and returns all of the targets of them.
- def collect_targets(events)
- events.collect do |event|
- source = event.source
- start = source
-
- # Get all of the edges that this vertex points at
- adjacent(source, :direction => :out, :type => :edges).find_all do |edge|
- edge.match?(event.event)
- end.collect { |event|
- target = event.target
- if target.respond_to?(:ref)
- source.info "Scheduling %s of %s" %
- [event.callback, target.ref]
- end
- target
- }
- end.flatten
- end
-
# The dependencies for a given resource.
def dependencies(resource)
tree_from_vertex(resource, :dfs).keys
@@ -49,6 +28,32 @@ class Puppet::PGraph < GRATR::Digraph
return leaves
end
+ # Collect all of the edges that the passed events match. Returns
+ # an array of edges.
+ def matching_edges(events)
+ events.collect do |event|
+ source = event.source
+
+ unless vertex?(source)
+ Puppet.warning "Got an event from invalid vertex %s" % source.ref
+ next
+ end
+
+ # Get all of the edges that this vertex should forward events
+ # to, which is the same thing as saying all edges directly below
+ # This vertex in the graph.
+ adjacent(source, :direction => :out, :type => :edges).find_all do |edge|
+ edge.match?(event.event)
+ end.each { |edge|
+ target = edge.target
+ if target.respond_to?(:ref)
+ source.info "Scheduling %s of %s" %
+ [edge.callback, target.ref]
+ end
+ }
+ end.flatten
+ end
+
# Take container information from another graph and use it
# to replace any container vertices with their respective leaves.
# This creates direct relationships where there were previously
@@ -63,9 +68,9 @@ class Puppet::PGraph < GRATR::Digraph
next if leaves.empty?
# First create new edges for each of the :in edges
- adjacent(vertex, :direction => :in).each do |up|
+ adjacent(vertex, :direction => :in, :type => :edges).each do |edge|
leaves.each do |leaf|
- add_edge!(up, leaf)
+ add_edge!(edge.source, leaf, edge.label)
if cyclic?
raise ArgumentError,
"%s => %s results in a loop" %
@@ -75,9 +80,9 @@ class Puppet::PGraph < GRATR::Digraph
end
# Then for each of the out edges
- adjacent(vertex, :direction => :out).each do |down|
+ adjacent(vertex, :direction => :out, :type => :edges).each do |edge|
leaves.each do |leaf|
- add_edge!(leaf, down)
+ add_edge!(leaf, edge.target, edge.label)
if cyclic?
raise ArgumentError,
"%s => %s results in a loop" %
@@ -89,76 +94,10 @@ class Puppet::PGraph < GRATR::Digraph
# And finally, remove the vertex entirely.
remove_vertex!(vertex)
end
- end
-
- # Trigger any subscriptions to a child. This does an upwardly recursive
- # search -- it triggers the passed object, but also the object's parent
- # and so on up the tree.
- def trigger(child)
- obj = child
- callbacks = Hash.new { |hash, key| hash[key] = [] }
- sources = Hash.new { |hash, key| hash[key] = [] }
-
- trigged = []
- while obj
- if @targets.include?(obj)
- callbacks.clear
- sources.clear
- @targets[obj].each do |event, sub|
- # Collect all of the subs for each callback
- callbacks[sub.callback] << sub
-
- # And collect the sources for logging
- sources[event.source] << sub.callback
- end
-
- sources.each do |source, callbacklist|
- obj.debug "%s[%s] results in triggering %s" %
- [source.class.name, source.name, callbacklist.join(", ")]
- end
-
- callbacks.each do |callback, subs|
- message = "Triggering '%s' from %s dependencies" %
- [callback, subs.length]
- obj.notice message
- # At this point, just log failures, don't try to react
- # to them in any way.
- begin
- obj.send(callback)
- @resourcemetrics[:restarted] += 1
- rescue => detail
- obj.err "Failed to call %s on %s: %s" %
- [callback, obj, detail]
-
- @resourcemetrics[:failed_restarts] += 1
-
- if Puppet[:debug]
- puts detail.backtrace
- end
- end
-
- # And then add an event for it.
- trigged << Puppet::Event.new(
- :event => :triggered,
- :transaction => self,
- :source => obj,
- :message => message
- )
-
- triggered(obj, callback)
- end
- end
-
- obj = obj.parent
- end
-
- if trigged.empty?
- return nil
- else
- return trigged
- end
end
+ # For some reason, unconnected vertices do not show up in
+ # this graph.
def to_jpg(name)
gv = vertices()
Dir.chdir("/Users/luke/Desktop/pics") do
diff --git a/lib/puppet/relationship.rb b/lib/puppet/relationship.rb
index cbd15b2af..879beeab7 100644
--- a/lib/puppet/relationship.rb
+++ b/lib/puppet/relationship.rb
@@ -11,15 +11,23 @@ require 'puppet/gratr'
class Puppet::Relationship < GRATR::Edge
# Return the callback
def callback
- label[:callback]
+ if label
+ label[:callback]
+ else
+ nil
+ end
end
# Return our event.
def event
- label[:event]
+ if label
+ label[:event]
+ else
+ nil
+ end
end
- def initialize(source, target, label = nil)
+ def initialize(source, target, label = {})
if label
unless label.is_a?(Hash)
raise Puppet::DevError, "The label must be a hash"
@@ -46,6 +54,10 @@ class Puppet::Relationship < GRATR::Edge
return false
end
end
+
+ def ref
+ "%s => %s" % [source.ref, target.ref]
+ end
end
# $Id$
diff --git a/lib/puppet/transaction.rb b/lib/puppet/transaction.rb
index 1551acbb6..6835b1b19 100644
--- a/lib/puppet/transaction.rb
+++ b/lib/puppet/transaction.rb
@@ -1,4 +1,4 @@
-# the class that actually walks our object/state tree, collects the changes,
+# the class that actually walks our resource/state tree, collects the changes,
# and performs them
require 'puppet'
@@ -6,13 +6,14 @@ require 'puppet/statechange'
module Puppet
class Transaction
- attr_accessor :component, :objects, :tags, :ignoreschedules, :ignoretags
+ attr_accessor :component, :resources, :tags, :ignoreschedules, :ignoretags
+ attr_accessor :relgraph
include Puppet::Util
Puppet.config.setdefaults(:transaction,
- :tags => ["", "Tags to use to find objects. If this is set, then
- only objects tagged with the specified tags will be applied.
+ :tags => ["", "Tags to use to find resources. If this is set, then
+ only resources tagged with the specified tags will be applied.
Values must be comma-separated."]
)
@@ -26,8 +27,13 @@ class Transaction
# Apply all changes for a child, returning a list of the events
# generated.
def apply(child)
- # First make sure there are no failed dependencies
- child.eachdependency do |dep|
+ child.info "applying"
+ # First make sure there are no failed dependencies. To do this,
+ # we check for failures in any of the vertexes above us. It's not
+ # enough to check the immediate dependencies, which is why we use
+ # a tree from the reversed graph.
+ p @relgraph.vertices.collect { |v| v.ref }
+ @relgraph.reversal.tree_from_vertex(child, :dfs).keys.each do |dep|
skip = false
if fails = failed?(dep)
child.notice "Dependency %s[%s] has %s failures" %
@@ -76,7 +82,7 @@ class Transaction
# event if they want
events = [change.forward].flatten.reject { |e| e.nil? }
rescue => detail
- if Puppet[:debug]
+ if Puppet[:trace]
puts detail.backtrace
end
change.state.err "change from %s to %s failed: %s" %
@@ -111,37 +117,13 @@ class Transaction
childevents
end
- # Find all of the changed objects.
+ # Find all of the changed resources.
def changed?
@changes.find_all { |change| change.changed }.collect { |change|
change.state.parent
}.uniq
end
- # Collect all of the targets for the list of events. This is an unintuitive
- # method because it recurses up through the source the event.
- def collecttargets(events)
- events.each do |event|
- source = event.source
- start = source
-
- while source
- Puppet::Event::Subscription.targets_of(event, source) do |sub|
- if target = sub.target
- start.info "Scheduling %s of %s[%s]" %
- [sub.callback, sub.target.class.name, sub.target.title]
- @targets[sub.target][event] = sub
- else
- raise Puppet::DevError,
- "Failed to find a target for %s" % sub.inspect
- end
- end
-
- source = source.parent
- end
- end
- end
-
# This method does all the actual work of running a transaction. It
# collects all of the changes, executes them, and responds to any
# necessary events.
@@ -163,9 +145,17 @@ class Transaction
Puppet::Log.newdestination(@report)
prefetch()
+
+ # Now add any dynamically generated resources
+ generate()
+
+ # Create a relationship graph from our resource graph
+ @relgraph = relationship_graph
+
+ @relgraph.to_jpg("relations")
begin
- allevents = @objects.collect { |child|
+ allevents = @relgraph.topsort.collect { |child|
events = []
if (self.ignoretags or tags.nil? or child.tagged?(tags))
if self.ignoreschedules or child.scheduled?
@@ -176,7 +166,7 @@ class Transaction
events = apply(child)
end
- # Keep track of how long we spend in each type of object
+ # Keep track of how long we spend in each type of resource
@timemetrics[child.class.name] += seconds
else
child.debug "Not scheduled"
@@ -191,7 +181,9 @@ class Transaction
end
# Collect the targets of any subscriptions to those events
- collecttargets(events)
+ @relgraph.matching_edges(events).each do |edge|
+ @targets[edge.target] << edge
+ end
# And return the events for collection
events
@@ -207,7 +199,7 @@ class Transaction
allevents
end
- # Determine whether a given object has failed.
+ # Determine whether a given resource has failed.
def failed?(obj)
if @failures[obj] > 0
return @failures[obj]
@@ -215,40 +207,63 @@ class Transaction
return false
end
end
+
+ # Collect any dynamically generated resources.
+ def generate
+ list = @resources.vertices
+ newlist = []
+ while ! list.empty?
+ list.each do |resource|
+ if resource.respond_to?(:generate)
+ made = resource.generate
+ unless made.is_a?(Array)
+ made = [made]
+ end
+ made.each do |res|
+ @resources.add_vertex!(res)
+ newlist << res
+ end
+ end
+ end
+ list.clear
+ list = newlist
+ newlist = []
+ end
+ end
- # this should only be called by a Puppet::Container object now
+ # this should only be called by a Puppet::Type::Component resource now
# and it should only receive an array
- def initialize(objects)
- @objects = objects
+ def initialize(resources)
+ @resources = resources.to_graph
@resourcemetrics = {
- :total => @objects.length,
- :out_of_sync => 0, # The number of objects that had changes
- :applied => 0, # The number of objects fixed
- :skipped => 0, # The number of objects skipped
- :restarted => 0, # The number of objects triggered
- :failed_restarts => 0, # The number of objects that fail a trigger
- :scheduled => 0 # The number of objects scheduled
+ :total => @resources.vertices.length,
+ :out_of_sync => 0, # The number of resources that had changes
+ :applied => 0, # The number of resources fixed
+ :skipped => 0, # The number of resources skipped
+ :restarted => 0, # The number of resources triggered
+ :failed_restarts => 0, # The number of resources that fail a trigger
+ :scheduled => 0 # The number of resources scheduled
}
# Metrics for distributing times across the different types.
@timemetrics = Hash.new(0)
- # The number of objects that were triggered in this run
+ # The number of resources that were triggered in this run
@triggered = Hash.new { |hash, key|
hash[key] = Hash.new(0)
}
# Targets of being triggered.
@targets = Hash.new do |hash, key|
- hash[key] = {}
+ hash[key] = []
end
# The changes we're performing
@changes = []
- # The objects that have failed and the number of failures each. This
- # is used for skipping objects because of failed dependencies.
+ # The resources that have failed and the number of failures each. This
+ # is used for skipping resources because of failed dependencies.
@failures = Hash.new do |h, key|
h[key] = 0
end
@@ -259,7 +274,7 @@ class Transaction
# Prefetch any providers that support it. We don't support prefetching
# types, just providers.
def prefetch
- @objects.collect { |obj|
+ @resources.collect { |obj|
if pro = obj.provider
pro.class
else
@@ -272,6 +287,33 @@ class Transaction
end
end
end
+
+ # Create a graph of all of the relationships in our resource graph.
+ def relationship_graph
+ graph = Puppet::PGraph.new
+
+ # First create the dependency graph
+ @resources.vertices.each do |vertex|
+ graph.add_vertex!(vertex)
+ vertex.builddepends.each do |edge|
+ graph.add_edge!(edge)
+ end
+ end
+
+ # Then splice in the container information
+ graph.splice!(@resources, Puppet::Type::Component)
+
+ # Lastly, add in any autorequires
+ graph.vertices.each do |vertex|
+ vertex.autorequire.each do |edge|
+ unless graph.edge?(edge)
+ graph.add_edge!(edge)
+ end
+ end
+ end
+
+ return graph
+ end
# Generate a transaction report.
def report
@@ -295,10 +337,10 @@ class Transaction
end
end
- # Add all of the metrics related to object count and status
+ # Add all of the metrics related to resource count and status
@report.newmetric(:resources, @resourcemetrics)
- # Record the relative time spent in each object.
+ # Record the relative time spent in each resource.
@report.newmetric(:time, @timemetrics)
# Then all of the change-related metrics
@@ -325,19 +367,21 @@ class Transaction
events = change.backward
rescue => detail
Puppet.err("%s rollback failed: %s" % [change,detail])
- if Puppet[:debug]
+ if Puppet[:trace]
puts detail.backtrace
end
next
# at this point, we would normally do error handling
# but i haven't decided what to do for that yet
- # so just record that a sync failed for a given object
+ # so just record that a sync failed for a given resource
#@@failures[change.state.parent] += 1
# this still could get hairy; what if file contents changed,
# but a chmod failed? how would i handle that error? dern
end
-
- collecttargets(events) if events
+
+ @relgraph.matching_edges(events).each do |edge|
+ @targets[edge.target] << edge
+ end
# Now check to see if there are any events for this child.
# Kind of hackish, since going backwards goes a change at a
@@ -350,7 +394,7 @@ class Transaction
end
# Trigger any subscriptions to a child. This does an upwardly recursive
- # search -- it triggers the passed object, but also the object's parent
+ # search -- it triggers the passed resource, but also the resource's parent
# and so on up the tree.
def trigger(child)
obj = child
@@ -362,12 +406,15 @@ class Transaction
if @targets.include?(obj)
callbacks.clear
sources.clear
- @targets[obj].each do |event, sub|
+ @targets[obj].each do |edge|
+ # Some edges don't have callbacks
+ next unless edge.callback
+
# Collect all of the subs for each callback
- callbacks[sub.callback] << sub
+ callbacks[edge.callback] << edge
# And collect the sources for logging
- sources[event.source] << sub.callback
+ sources[edge.source] << edge.callback
end
sources.each do |source, callbacklist|
@@ -390,7 +437,7 @@ class Transaction
@resourcemetrics[:failed_restarts] += 1
- if Puppet[:debug]
+ if Puppet[:trace]
puts detail.backtrace
end
end
@@ -417,12 +464,12 @@ class Transaction
end
end
- def triggered(object, method)
- @triggered[object][method] += 1
+ def triggered(resource, method)
+ @triggered[resource][method] += 1
end
- def triggered?(object, method)
- @triggered[object][method]
+ def triggered?(resource, method)
+ @triggered[resource][method]
end
end
end
diff --git a/lib/puppet/type.rb b/lib/puppet/type.rb
index 1adeb1366..19de99b7c 100644
--- a/lib/puppet/type.rb
+++ b/lib/puppet/type.rb
@@ -301,8 +301,6 @@ class Type < Puppet::Element
# Set up all of our autorequires.
def finish
- self.autorequire
-
# Scheduling has to be done when the whole config is instantiated, so
# that file order doesn't matter in finding them.
self.schedule
diff --git a/lib/puppet/type/component.rb b/lib/puppet/type/component.rb
index 3165d9e11..cadd586c8 100644
--- a/lib/puppet/type/component.rb
+++ b/lib/puppet/type/component.rb
@@ -79,7 +79,7 @@ module Puppet
# this also won't work with scheduling, but eh
def evaluate
self.finalize unless self.finalized?
- transaction = Puppet::Transaction.new(self.flatten)
+ transaction = Puppet::Transaction.new(self)
transaction.component = self
return transaction
end
@@ -102,7 +102,6 @@ module Puppet
end
unless finished.has_key?(object)
object.finish
- object.builddepends
finished[object] = true
end
end