summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--lib/puppet/indirector/rest.rb35
-rw-r--r--spec/integration/indirector/rest.rb76
-rwxr-xr-xspec/unit/indirector/rest.rb59
3 files changed, 157 insertions, 13 deletions
diff --git a/lib/puppet/indirector/rest.rb b/lib/puppet/indirector/rest.rb
index 0c86b2706..076e96356 100644
--- a/lib/puppet/indirector/rest.rb
+++ b/lib/puppet/indirector/rest.rb
@@ -4,19 +4,38 @@ require 'uri'
# Access objects via REST
class Puppet::Indirector::REST < Puppet::Indirector::Terminus
def network_fetch(path)
- # TODO: url_encode path, set proper server + port
Net::HTTP.get(URI.parse("http://127.0.0.1:34343/#{path}"))
end
+ def network_delete(path)
+ Net::HTTP.start("127.0.0.1", 34343) {|x| x.delete("/#{path}").body } # weird-ass net/http library
+ end
+
def find(name, options = {})
- network_result = network_fetch("#{indirection.name}/#{name}")
- raise YAML.load(network_result) if network_result =~ %r{--- !ruby/exception}
- decoded_result = indirection.model.from_yaml(network_result)
+ network_result = network_fetch("#{indirection.name}/#{name}")
+ raise YAML.load(network_result) if exception?(network_result)
+ decoded_result = indirection.model.from_yaml(network_result)
+ end
+
+ def search(name, options = {})
+ network_results = network_fetch("#{indirection.name}s/#{name}")
+ raise YAML.load(network_results) if exception?(network_results)
+ decoded_results = YAML.load(network_results.to_s).collect {|result| indirection.model.from_yaml(result) }
+ end
+
+ def destroy(name, options = {})
+ network_result = network_delete("#{indirection.name}/#{name}")
+ raise YAML.load(network_result) if exception?(network_result)
+ decoded_result = YAML.load(network_result.to_s)
+ end
+
+ def save
+
end
- def search(key, options = {})
- network_results = network_fetch("#{indirection.name}s/#{key}")
- raise YAML.load(network_results) if network_results =~ %r{--- !ruby/exception}
- decoded_results = YAML.load(network_results.to_s).collect {|result| indirection.model.from_yaml(result) }
+ private
+
+ def exception?(yaml_string)
+ yaml_string =~ %r{--- !ruby/exception}
end
end
diff --git a/spec/integration/indirector/rest.rb b/spec/integration/indirector/rest.rb
index 418575fb6..46a26ee91 100644
--- a/spec/integration/indirector/rest.rb
+++ b/spec/integration/indirector/rest.rb
@@ -146,7 +146,43 @@ describe Puppet::Indirector::REST do
end
describe "when destroying a model instance over REST" do
- it "needs more specs"
+ describe "when a matching model instance can be found" do
+ before :each do
+ @mock_model = stub('faked model', :destroy => true)
+ Puppet::Network::HTTP::WEBrickREST.any_instance.stubs(:model).returns(@mock_model)
+ end
+
+ it "should not fail" do
+ lambda { Puppet::TestIndirectedFoo.destroy('bar') }.should_not raise_error
+ end
+
+ it 'should return success' do
+ Puppet::TestIndirectedFoo.destroy('bar').should == true
+ end
+ end
+
+ describe "when no matching model instance can be found" do
+ before :each do
+ @mock_model = stub('faked model', :destroy => false)
+ Puppet::Network::HTTP::WEBrickREST.any_instance.stubs(:model).returns(@mock_model)
+ end
+
+ it "should return failure" do
+ Puppet::TestIndirectedFoo.destroy('bar').should == false
+ end
+ end
+
+ describe "when an exception is encountered in destroying a model instance" do
+ before :each do
+ @mock_model = stub('faked model')
+ @mock_model.stubs(:destroy).raises(RuntimeError)
+ Puppet::Network::HTTP::WEBrickREST.any_instance.stubs(:model).returns(@mock_model)
+ end
+
+ it "should raise an exception" do
+ lambda { Puppet::TestIndirectedFoo.destroy('bar') }.should raise_error(RuntimeError)
+ end
+ end
end
describe "when saving a model instance over REST" do
@@ -281,7 +317,43 @@ describe Puppet::Indirector::REST do
end
describe "when destroying a model instance over REST" do
- it "needs more specs"
+ describe "when a matching model instance can be found" do
+ before :each do
+ @mock_model = stub('faked model', :destroy => true)
+ Puppet::Network::HTTP::MongrelREST.any_instance.stubs(:model).returns(@mock_model)
+ end
+
+ it "should not fail" do
+ lambda { Puppet::TestIndirectedFoo.destroy('bar') }.should_not raise_error
+ end
+
+ it 'should return success' do
+ Puppet::TestIndirectedFoo.destroy('bar').should == true
+ end
+ end
+
+ describe "when no matching model instance can be found" do
+ before :each do
+ @mock_model = stub('faked model', :destroy => false)
+ Puppet::Network::HTTP::MongrelREST.any_instance.stubs(:model).returns(@mock_model)
+ end
+
+ it "should return failure" do
+ Puppet::TestIndirectedFoo.destroy('bar').should == false
+ end
+ end
+
+ describe "when an exception is encountered in destroying a model instance" do
+ before :each do
+ @mock_model = stub('faked model')
+ @mock_model.stubs(:destroy).raises(RuntimeError)
+ Puppet::Network::HTTP::MongrelREST.any_instance.stubs(:model).returns(@mock_model)
+ end
+
+ it "should raise an exception" do
+ lambda { Puppet::TestIndirectedFoo.destroy('bar') }.should raise_error(RuntimeError)
+ end
+ end
end
describe "when saving a model instance over REST" do
diff --git a/spec/unit/indirector/rest.rb b/spec/unit/indirector/rest.rb
index 37c0480ed..fb3790e0c 100755
--- a/spec/unit/indirector/rest.rb
+++ b/spec/unit/indirector/rest.rb
@@ -19,6 +19,28 @@ describe Puppet::Indirector::REST do
@searcher = @rest_class.new
end
+
+ describe "when doing a network fetch" do
+ it "should escape the provided path"
+ it "should look up the appropriate remote server"
+ it "should look up the appropriate remote port"
+ it "should use the GET http method"
+ it "should use the appropriate remote server"
+ it "should use the appropriate remote port"
+ it "should use the escaped provided path"
+ it "should return the results of the GET request"
+ end
+
+ describe "when doing a network delete" do
+ it "should escape the provided path"
+ it "should look up the appropriate remote server"
+ it "should look up the appropriate remote port"
+ it "should use the delete http method"
+ it "should use the appropriate remote server"
+ it "should use the appropriate remote port"
+ it "should use the escaped provided path"
+ it "should return the results of the DELETE request"
+ end
describe "when doing a find" do
before :each do
@@ -106,9 +128,40 @@ describe Puppet::Indirector::REST do
end
describe "when doing a destroy" do
- it "should deserialize result data into a boolean"
- it "should generate an error when result data deserializes improperly"
- it "should generate an error when result data specifies an error"
+ before :each do
+ @result = true.to_yaml
+ @searcher.stubs(:network_delete).returns(@result) # neuter the network connection
+ @model.stubs(:from_yaml).returns(@instance)
+ end
+
+ it "should look up the model instance over the network" do
+ @searcher.expects(:network_delete).returns(@result)
+ @searcher.destroy('foo')
+ end
+
+ it "should look up the model instance using the named indirection" do
+ @searcher.expects(:network_delete).with {|path| path =~ %r{^#{@indirection.name.to_s}/} }.returns(@result)
+ @searcher.destroy('foo')
+ end
+
+ it "should look up the model instance using the provided key" do
+ @searcher.expects(:network_delete).with {|path| path =~ %r{/foo$} }.returns(@result)
+ @searcher.destroy('foo')
+ end
+
+ it "should deserialize result data" do
+ YAML.expects(:load).with(@result)
+ @searcher.destroy('foo')
+ end
+
+ it "should return deserialized result data" do
+ @searcher.destroy('foo').should == true
+ end
+
+ it "should generate an error when result data specifies an error" do
+ @searcher.stubs(:network_delete).returns(RuntimeError.new("bogus").to_yaml)
+ lambda { @searcher.destroy('foo') }.should raise_error(RuntimeError)
+ end
end
describe "when doing a save" do