A simple class that can function as the base class for indirected types.
Are we an abstract terminus type, rather than an instance with an associated indirection?
# File lib/puppet/indirector/terminus.rb, line 19 def abstract_terminus? abstract_terminus end
Convert a constant to a short name.
# File lib/puppet/indirector/terminus.rb, line 24 def const2name(const) const.sub(/^[A-Z]/) { |i| i.downcase }.gsub(/[A-Z]/) { |i| "_#{i.downcase}" }.intern end
Look up the indirection if we were only provided a name.
# File lib/puppet/indirector/terminus.rb, line 29 def indirection=(name) if name.is_a?(Puppet::Indirector::Indirection) @indirection = name elsif ind = Puppet::Indirector::Indirection.instance(name) @indirection = ind else raise ArgumentError, "Could not find indirection instance #{name} for #{self.name}" end end
# File lib/puppet/indirector/terminus.rb, line 39 def indirection_name @indirection.name end
Register our subclass with the appropriate indirection. This follows the convention that our terminus is named after the indirection.
# File lib/puppet/indirector/terminus.rb, line 46 def inherited(subclass) longname = subclass.to_s if longname =~ /#<Class/ raise Puppet::DevError, "Terminus subclasses must have associated constants" end names = longname.split("::") # Convert everything to a lower-case symbol, converting camelcase to underscore word separation. name = names.pop.sub(/^[A-Z]/) { |i| i.downcase }.gsub(/[A-Z]/) { |i| "_#{i.downcase}" }.intern subclass.name = name # Short-circuit the abstract types, which are those that directly subclass # the Terminus class. if self == Puppet::Indirector::Terminus subclass.mark_as_abstract_terminus return end # Set the terminus type to be the name of the abstract terminus type. # Yay, class/instance confusion. subclass.terminus_type = self.name # Our subclass is specifically associated with an indirection. raise("Invalid name #{longname}") unless names.length > 0 indirection_name = names.pop.sub(/^[A-Z]/) { |i| i.downcase }.gsub(/[A-Z]/) { |i| "_#{i.downcase}" }.intern if indirection_name == "" or indirection_name.nil? raise Puppet::DevError, "Could not discern indirection model from class constant" end # This will throw an exception if the indirection instance cannot be found. # Do this last, because it also registers the terminus type with the indirection, # which needs the above information. subclass.indirection = indirection_name # And add this instance to the instance hash. Puppet::Indirector::Terminus.register_terminus_class(subclass) end
Mark that this instance is abstract.
# File lib/puppet/indirector/terminus.rb, line 87 def mark_as_abstract_terminus @abstract_terminus = true end
# File lib/puppet/indirector/terminus.rb, line 91 def model indirection.model end
Convert a short name to a constant.
# File lib/puppet/indirector/terminus.rb, line 96 def name2const(name) name.to_s.capitalize.sub(/_(.)/) { |i| $1.upcase } end
# File lib/puppet/indirector/terminus.rb, line 131 def initialize raise Puppet::DevError, "Cannot create instances of abstract terminus types" if self.class.abstract_terminus? end
Register a class, probably autoloaded.
# File lib/puppet/indirector/terminus.rb, line 101 def register_terminus_class(klass) setup_instance_loading klass.indirection_name instance_hash(klass.indirection_name)[klass.name] = klass end
Return a terminus by name, using the autoloader.
# File lib/puppet/indirector/terminus.rb, line 107 def terminus_class(indirection_name, terminus_type) setup_instance_loading indirection_name loaded_instance(indirection_name, terminus_type) end
Return all terminus classes for a given indirection.
# File lib/puppet/indirector/terminus.rb, line 113 def terminus_classes(indirection_name) setup_instance_loading indirection_name instance_loader(indirection_name).files_to_load.map do |file| File.basename(file).chomp(".rb").intern end end
# File lib/puppet/indirector/terminus.rb, line 127 def indirection self.class.indirection end
# File lib/puppet/indirector/terminus.rb, line 135 def model self.class.model end
# File lib/puppet/indirector/terminus.rb, line 139 def name self.class.name end
# File lib/puppet/indirector/terminus.rb, line 143 def terminus_type self.class.terminus_type end
# File lib/puppet/indirector/terminus.rb, line 147 def validate(request) if request.instance validate_model(request) validate_key(request) end end
# File lib/puppet/indirector/terminus.rb, line 154 def validate_key(request) unless request.key == request.instance.name raise Puppet::Indirector::ValidationError, "Instance name #{request.instance.name.inspect} does not match requested key #{request.key.inspect}" end end
# File lib/puppet/indirector/terminus.rb, line 160 def validate_model(request) unless model === request.instance raise Puppet::Indirector::ValidationError, "Invalid instance type #{request.instance.class.inspect}, expected #{model.inspect}" end end