summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordanielsdeleo <dan@opscode.com>2014-01-31 17:36:32 -0800
committerdanielsdeleo <dan@opscode.com>2014-02-03 17:08:54 -0800
commit913719507749e341602608bd6cea714872de021e (patch)
treebb9db4c98cf4c92ce8ff5459813b60fc18c75c2e
parentb4c8facbf495423950345937ab4a8d6d8792ad16 (diff)
downloadchef-913719507749e341602608bd6cea714872de021e.tar.gz
Better specify what happens for NoMethodErrors in the DSL
-rw-r--r--lib/chef/dsl/recipe.rb25
-rw-r--r--lib/chef/exceptions.rb4
-rw-r--r--lib/chef/resource_platform_map.rb2
-rw-r--r--spec/unit/recipe_spec.rb27
4 files changed, 55 insertions, 3 deletions
diff --git a/lib/chef/dsl/recipe.rb b/lib/chef/dsl/recipe.rb
index a1bdd9d665..d8d0b158b3 100644
--- a/lib/chef/dsl/recipe.rb
+++ b/lib/chef/dsl/recipe.rb
@@ -51,10 +51,16 @@ class Chef
# to.
if has_resource_definition?(method_symbol)
evaluate_resource_definition(method_symbol, *args, &block)
- else
+ elsif have_resource_class_for?(method_symbol)
# Otherwise, we're rocking the regular resource call route.
declare_resource(method_symbol, args[0], caller[0], &block)
+ else
+ super
end
+ rescue NoMethodError
+ raise NoMethodError, "No resource or method named `#{method_symbol}' for #{describe_self_for_error}"
+ rescue NameError
+ raise NameError, "No resource, method, or local variable named `#{method_symbol}' for #{describe_self_for_error}"
end
def has_resource_definition?(name)
@@ -107,7 +113,6 @@ class Chef
# backward compatibility
resource_class = resource_class_for(type)
- super unless resource_class
raise ArgumentError, "You must supply a name when declaring a #{type} resource" if name.nil?
resource = resource_class.new(name, run_context)
@@ -138,6 +143,22 @@ class Chef
Chef::Resource.resource_for_node(snake_case_name, run_context.node)
end
+ def have_resource_class_for?(snake_case_name)
+ not resource_class_for(snake_case_name).nil?
+ rescue NameError
+ false
+ end
+
+ def describe_self_for_error
+ if respond_to?(:name)
+ %Q[`#{self.class.name} "#{name}"']
+ elsif respond_to?(:recipe_name)
+ %Q[`#{self.class.name} "#{recipe_name}"']
+ else
+ to_s
+ end
+ end
+
end
end
end
diff --git a/lib/chef/exceptions.rb b/lib/chef/exceptions.rb
index 0b4cd28d03..afd42885f9 100644
--- a/lib/chef/exceptions.rb
+++ b/lib/chef/exceptions.rb
@@ -80,6 +80,10 @@ class Chef
class ConflictingMembersInGroup < ArgumentError; end
class InvalidResourceReference < RuntimeError; end
class ResourceNotFound < RuntimeError; end
+
+ # Can't find a Resource of this type that is valid on this platform.
+ class NoSuchResourceType < NameError; end
+
class InvalidResourceSpecification < ArgumentError; end
class SolrConnectionError < RuntimeError; end
class IllegalChecksumRevert < RuntimeError; end
diff --git a/lib/chef/resource_platform_map.rb b/lib/chef/resource_platform_map.rb
index ad27aa91c1..a678f5be4b 100644
--- a/lib/chef/resource_platform_map.rb
+++ b/lib/chef/resource_platform_map.rb
@@ -123,7 +123,7 @@ class Chef
resource_klass = platform_resource(short_name, platform, version) ||
resource_matching_short_name(short_name)
- raise NameError, "Cannot find a resource for #{short_name} on #{platform} version #{version}" if resource_klass.nil?
+ raise Exceptions::NoSuchResourceType, "Cannot find a resource for #{short_name} on #{platform} version #{version}" if resource_klass.nil?
resource_klass
end
diff --git a/spec/unit/recipe_spec.rb b/spec/unit/recipe_spec.rb
index bc3a62be3f..612eae2b8e 100644
--- a/spec/unit/recipe_spec.rb
+++ b/spec/unit/recipe_spec.rb
@@ -175,6 +175,33 @@ describe Chef::Recipe do
end
+ describe "when attempting to create a resource of an invalid type" do
+
+ it "gives a sane error message when using method_missing" do
+ lambda do
+ @recipe.no_such_resource("foo")
+ end.should raise_error(NoMethodError, %q[No resource or method named `no_such_resource' for `Chef::Recipe "test"'])
+ end
+
+ it "gives a sane error message when using method_missing 'bare'" do
+ lambda do
+ @recipe.instance_eval do
+ # Giving an argument will change this from NameError to NoMethodError
+ no_such_resource
+ end
+ end.should raise_error(NameError, %q[No resource, method, or local variable named `no_such_resource' for `Chef::Recipe "test"'])
+ end
+
+ it "gives a sane error message when using build_resource" do
+ expect { @recipe.build_resource(:no_such_resource, "foo") }.to raise_error(Chef::Exceptions::NoSuchResourceType)
+ end
+
+ it "gives a sane error message when using declare_resource" do
+ expect { @recipe.declare_resource(:no_such_resource, "bar") }.to raise_error(Chef::Exceptions::NoSuchResourceType)
+ end
+
+ end
+
describe "resource definitions" do
it "should execute defined resources" do
crow_define = Chef::ResourceDefinition.new