[Pkg-puppet-devel] [SCM] Puppet packaging for Debian branch, upstream, updated. 0.25.5-639-g8f94f35

test branch puppet-dev at googlegroups.com
Wed Jul 14 10:33:01 UTC 2010


The following commit has been merged in the upstream branch:
commit 8b99367ccedefe0e341a79487ccea2a95f2720a3
Author: Luke Kanies <luke at puppetlabs.com>
Date:   Sat Apr 17 19:46:23 2010 -0700

    Adding indirector support to Resource Types
    
    Also adding JSON support.
    
    This is so that we can remotely retrieve information
    about resource types and classes, such as what arguments
    are required.
    
    Signed-off-by: Luke Kanies <luke at puppetlabs.com>

diff --git a/ext/puppet-test b/ext/puppet-test
index 5333307..61397e7 100755
--- a/ext/puppet-test
+++ b/ext/puppet-test
@@ -229,6 +229,30 @@ Suite.new :local_catalog, "Local catalog handling" do
     end
 end
 
+Suite.new :resource_type, "Managing resource types" do
+    newtest :find, "Find a type" do
+        Puppet::Resource::Type.terminus_class = :parser
+        ARGV.each do |name|
+            json = Puppet::Resource::Type.find(name).to_pson
+            data = PSON.parse(json)
+            p Puppet::Resource::Type.from_pson(data)
+        end
+    end
+
+    newtest :search_types, "Find all types" do
+        Puppet::Resource::Type.terminus_class = :rest
+        result = Puppet::Resource::Type.search("*")
+        result.each { |r| p r }
+    end
+
+    newtest :restful_type, "Find a type and return it via REST" do
+        Puppet::Resource::Type.terminus_class = :rest
+        ARGV.each do |name|
+            p Puppet::Resource::Type.find(name)
+        end
+    end
+end
+
 Suite.new :remote_catalog, "Remote catalog handling" do
     def prepare
         $args[:cache] = false
diff --git a/lib/puppet/indirector/resource_type.rb b/lib/puppet/indirector/resource_type.rb
new file mode 100644
index 0000000..0564dc2
--- /dev/null
+++ b/lib/puppet/indirector/resource_type.rb
@@ -0,0 +1,5 @@
+require 'puppet/resource/type'
+
+# A stub class, so our constants work.
+class Puppet::Indirector::ResourceType # :nodoc:
+end
diff --git a/lib/puppet/indirector/resource_type/parser.rb b/lib/puppet/indirector/resource_type/parser.rb
new file mode 100644
index 0000000..81ec1bf
--- /dev/null
+++ b/lib/puppet/indirector/resource_type/parser.rb
@@ -0,0 +1,27 @@
+require 'puppet/resource/type'
+require 'puppet/indirector/code'
+require 'puppet/indirector/resource_type'
+
+class Puppet::Indirector::ResourceType::Parser < Puppet::Indirector::Code
+    desc "Return the data-form of a resource type."
+
+    def find(request)
+        krt = request.environment.known_resource_types
+
+        # This is a bit ugly.
+        [:hostclass, :definition, :node].each do |type|
+            if r = krt.send(type, request.key)
+                return r
+            end
+        end
+        nil
+    end
+
+    def search(request)
+        raise ArgumentError, "Only '*' is acceptable as a search request" unless request.key == "*"
+        krt = request.environment.known_resource_types
+        result = [krt.hostclasses.values, krt.definitions.values, krt.nodes.values].flatten
+        return nil if result.empty?
+        result
+    end
+end
diff --git a/lib/puppet/indirector/resource_type/rest.rb b/lib/puppet/indirector/resource_type/rest.rb
new file mode 100644
index 0000000..66d3320
--- /dev/null
+++ b/lib/puppet/indirector/resource_type/rest.rb
@@ -0,0 +1,7 @@
+require 'puppet/resource/type'
+require 'puppet/indirector/rest'
+require 'puppet/indirector/resource_type'
+
+class Puppet::Indirector::ResourceType::Rest < Puppet::Indirector::REST
+    desc "Retrieve resource types via a REST HTTP interface."
+end
diff --git a/lib/puppet/resource/type.rb b/lib/puppet/resource/type.rb
index 402df06..3657f89 100644
--- a/lib/puppet/resource/type.rb
+++ b/lib/puppet/resource/type.rb
@@ -6,6 +6,7 @@ require 'puppet/parser/ast/leaf'
 require 'puppet/dsl'
 
 class Puppet::Resource::Type
+    Puppet::ResourceType = self
     include Puppet::Util::InlineDocs
     include Puppet::Util::Warnings
     include Puppet::Util::Errors
@@ -19,6 +20,38 @@ class Puppet::Resource::Type
         define_method("#{t}?") { self.type == t }
     end
 
+    require 'puppet/indirector'
+    extend Puppet::Indirector
+    indirects :resource_type, :terminus_class => :parser
+
+    def self.from_pson(data)
+        name = data.delete('name') or raise ArgumentError, "Resource Type names must be specified"
+        type = data.delete('type') || "definition"
+
+        data = data.inject({}) { |result, ary| result[ary[0].intern] = ary[1]; result }
+
+        new(type, name, data)
+    end
+
+    def to_pson_data_hash
+        data = [:code, :doc, :line, :file, :parent].inject({}) do |hash, param|
+            next hash unless value = self.send(param)
+            hash[param.to_s] = value
+            hash
+        end
+
+        data['arguments'] = arguments.dup
+
+        data['name'] = name
+        data['type'] = type
+
+        data
+    end
+
+    def to_pson(*args)
+        to_pson_data_hash.to_pson(*args)
+    end
+
     # Are we a child of the passed class?  Do a recursive search up our
     # parentage tree to figure it out.
     def child_of?(klass)
@@ -260,3 +293,4 @@ class Puppet::Resource::Type
         end
     end
 end
+
diff --git a/spec/unit/indirector/resource_type/parser.rb b/spec/unit/indirector/resource_type/parser.rb
new file mode 100755
index 0000000..331ca1c
--- /dev/null
+++ b/spec/unit/indirector/resource_type/parser.rb
@@ -0,0 +1,75 @@
+#!/usr/bin/env ruby
+
+require File.dirname(__FILE__) + '/../../../spec_helper'
+
+require 'puppet/indirector/resource_type/parser'
+
+describe Puppet::Indirector::ResourceType::Parser do
+    before do
+        @terminus = Puppet::Indirector::ResourceType::Parser.new
+        @request = Puppet::Indirector::Request.new(:resource_type, :find, "foo")
+        @krt = Puppet::Resource::TypeCollection.new(@request.environment)
+        @request.environment.stubs(:known_resource_types).returns @krt
+    end
+
+    it "should be registered with the resource_type indirection" do
+        Puppet::Indirector::Terminus.terminus_class(:resource_type, :parser).should equal(Puppet::Indirector::ResourceType::Parser)
+    end
+
+    describe "when finding" do
+        it "should use the request's environment's list of known resource types" do
+            @request.environment.known_resource_types.expects(:hostclass).returns nil
+
+            @terminus.find(@request)
+        end
+
+        it "should return any found type" do
+            type = @krt.add(Puppet::Resource::Type.new(:hostclass, "foo"))
+
+            @terminus.find(@request).should == type
+        end
+
+        it "should return nil if no type can be found" do
+            @terminus.find(@request).should be_nil
+        end
+
+        it "should prefer definitions to nodes" do
+            type = @krt.add(Puppet::Resource::Type.new(:hostclass, "foo"))
+            node = @krt.add(Puppet::Resource::Type.new(:node, "foo"))
+
+            @terminus.find(@request).should == type
+        end
+    end
+
+    describe "when searching" do
+        before do
+            @request.key = "*"
+        end
+
+        it "should use the request's environment's list of known resource types" do
+            @request.environment.known_resource_types.expects(:hostclasses).returns({})
+
+            @terminus.search(@request)
+        end
+
+        it "should fail if anyther other than '*' was provided as the search key" do
+            @request.key = "foo*"
+            lambda { @terminus.search(@request) }.should raise_error(ArgumentError)
+        end
+
+        it "should return all known types" do
+            type = @krt.add(Puppet::Resource::Type.new(:hostclass, "foo"))
+            node = @krt.add(Puppet::Resource::Type.new(:node, "bar"))
+            define = @krt.add(Puppet::Resource::Type.new(:definition, "baz"))
+
+            result = @terminus.search(@request)
+            result.should be_include(type)
+            result.should be_include(node)
+            result.should be_include(define)
+        end
+
+        it "should return nil if no types can be found" do
+            @terminus.search(@request).should be_nil
+        end
+    end
+end
diff --git a/spec/unit/indirector/resource_type/rest.rb b/spec/unit/indirector/resource_type/rest.rb
new file mode 100755
index 0000000..28196d5
--- /dev/null
+++ b/spec/unit/indirector/resource_type/rest.rb
@@ -0,0 +1,15 @@
+#!/usr/bin/env ruby
+
+require File.dirname(__FILE__) + '/../../../spec_helper'
+
+require 'puppet/indirector/resource_type/rest'
+
+describe Puppet::Indirector::ResourceType::Rest do
+    it "should be registered with the resource_type indirection" do
+        Puppet::Indirector::Terminus.terminus_class(:resource_type, :rest).should equal(Puppet::Indirector::ResourceType::Rest)
+    end
+
+    it "should be a subclass of Puppet::Indirector::Rest" do
+        Puppet::Indirector::ResourceType::Rest.superclass.should == Puppet::Indirector::REST
+    end
+end
diff --git a/spec/unit/resource/type.rb b/spec/unit/resource/type.rb
index bbf2f73..8c024d7 100755
--- a/spec/unit/resource/type.rb
+++ b/spec/unit/resource/type.rb
@@ -23,6 +23,47 @@ describe Puppet::Resource::Type do
         end
     end
 
+    it "should indirect 'resource_type'" do
+        Puppet::Resource::Type.indirection.name.should == :resource_type
+    end
+
+    it "should default to 'parser' for its terminus class" do
+        Puppet::Resource::Type.indirection.terminus_class.should == :parser
+    end
+
+    describe "when converting to json" do
+        before do
+            @type = Puppet::Resource::Type.new(:hostclass, "foo")
+        end
+
+        def from_json(json)
+            Puppet::Resource::Type.from_pson(json)
+        end
+
+        def double_convert
+            Puppet::Resource::Type.from_pson(PSON.parse(@type.to_pson))
+        end
+
+        it "should include the name and type" do
+            double_convert.name.should == @type.name
+            double_convert.type.should == @type.type
+        end
+
+        it "should include any arguments" do
+            @type.set_arguments("one" => nil, "two" => "foo")
+
+            double_convert.arguments.should == {"one" => nil, "two" => "foo"}
+        end
+
+        it "should include any extra attributes" do
+            @type.file = "/my/file"
+            @type.line = 50
+
+            double_convert.file.should == "/my/file"
+            double_convert.line.should == 50
+        end
+    end
+
     describe "when a node"  do
         it "should allow a regex as its name" do
             lambda { Puppet::Resource::Type.new(:node, /foo/) }.should_not raise_error

-- 
Puppet packaging for Debian



More information about the Pkg-puppet-devel mailing list