diff options
Diffstat (limited to 'lib/chef/resource.rb')
-rw-r--r-- | lib/chef/resource.rb | 107 |
1 files changed, 38 insertions, 69 deletions
diff --git a/lib/chef/resource.rb b/lib/chef/resource.rb index 5099446335..c38f36aa72 100644 --- a/lib/chef/resource.rb +++ b/lib/chef/resource.rb @@ -27,11 +27,12 @@ require 'chef/guard_interpreter/resource_guard_interpreter' require 'chef/resource/conditional' require 'chef/resource/conditional_action_not_nothing' require 'chef/resource_collection' -require 'chef/resource_platform_map' +require 'chef/node_map' require 'chef/node' require 'chef/platform' require 'chef/mixin/deprecation' +require 'chef/mixin/descendants_tracker' class Chef class Resource @@ -133,6 +134,7 @@ F include Chef::Mixin::Deprecation extend Chef::Mixin::ConvertToClassName + extend Chef::Mixin::DescendantsTracker if Module.method(:const_defined?).arity == 1 def self.strict_const_defined?(const) @@ -144,24 +146,13 @@ F end end - # Track all subclasses of Resource. This is used so names can be looked up - # when attempting to deserialize from JSON. (See: json_compat) - def self.resource_classes - # Using a class variable here ensures we have one variable to track - # subclasses shared by the entire class hierarchy; without this, each - # subclass would have its own list of subclasses. - @@resource_classes ||= [] - end - - # Callback when subclass is defined. Adds subclass to list of subclasses. - def self.inherited(subclass) - resource_classes << subclass - end - - # Look up a subclass by +class_name+ which should be a string that matches - # `Subclass.name` - def self.find_subclass_by_name(class_name) - resource_classes.first {|c| c.name == class_name } + class << self + # back-compat + # NOTE: that we do not support unregistering classes as descendents like + # we used to for LWRP unloading because that was horrible and removed in + # Chef-12. + alias :resource_classes :descendants + alias :find_subclass_by_name :find_descendants_by_name end # Set or return the list of "state attributes" implemented by the Resource @@ -687,21 +678,10 @@ F raise ArgumentError, "nil is not a valid action for resource #{self}" if action.nil? end - def evaluate_providers(providers) - provider = providers.first - end - def provider_for_action(action) - # leverage new platform => short_name => resource - # which requires explicitly setting provider in - # resource class - if self.provider - provider = self.provider.new(self, self.run_context) - provider.action = action - provider - else # fall back to old provider resolution - Chef::Platform.provider_for_resource(self, action) - end + provider = run_context.provider_resolver.resolve(self, action).new(self, run_context) + provider.action = action + provider end def custom_exception_message(e) @@ -776,8 +756,8 @@ F @provider_base ||= Chef::Provider end - def self.platform_map - @@platform_map ||= PlatformMap.new + def self.node_map + @@node_map ||= NodeMap.new end # Maps a short_name (and optionally a platform and version) to a @@ -786,66 +766,55 @@ F # (I'm looking at you Chef::Resource::Package) # Ex: # class WindowsFile < Chef::Resource - # provides :file, :on_platforms => ["windows"] + # provides :file, os: "linux", platform_family: "rhel", platform: "redhat" + # provides :file, os: "!windows + # provides :file, os: [ "linux", "aix" ] + # provides :file, os: "solaris2" do |node| + # node['platform_version'].to_f <= 5.11 + # end # # ...other stuff # end # - # TODO: 2011-11-02 schisamo - platform_version support - def self.provides(short_name, opts={}) + def self.provides(short_name, opts={}, &block) short_name_sym = short_name if short_name.kind_of?(String) + # YAGNI: this is probably completely unnecessary and can be removed? + Chef::Log.warn "[DEPRECATION] Passing a String to Chef::Resource#provides will be removed" short_name.downcase! short_name.gsub!(/\s/, "_") short_name_sym = short_name.to_sym end - if opts.has_key?(:on_platforms) - platforms = [opts[:on_platforms]].flatten - platforms.each do |p| - p = :default if :all == p.to_sym - platform_map.set( - :platform => p.to_sym, - :short_name => short_name_sym, - :resource => self - ) - end - else - platform_map.set( - :short_name => short_name_sym, - :resource => self - ) - end + node_map.set(short_name_sym, constantize(self.name), opts, &block) end - # Returns a resource based on a short_name anda platform and version. - # + # Returns a resource based on a short_name and node # # ==== Parameters # short_name<Symbol>:: short_name of the resource (ie :directory) - # platform<Symbol,String>:: platform name - # version<String>:: platform version + # node<Chef::Node>:: Node object to look up platform and version in # # === Returns # <Chef::Resource>:: returns the proper Chef::Resource class - def self.resource_for_platform(short_name, platform=nil, version=nil) - platform_map.get(short_name, platform, version) + def self.resource_for_node(short_name, node) + klass = node_map.get(node, short_name) || + resource_matching_short_name(short_name) + raise Chef::Exceptions::NoSuchResourceType.new(short_name, node) if klass.nil? + klass end - # Returns a resource based on a short_name and a node's - # platform and version. - # + # Returns the class of a Chef::Resource based on the short name # ==== Parameters # short_name<Symbol>:: short_name of the resource (ie :directory) - # node<Chef::Node>:: Node object to look up platform and version in # # === Returns # <Chef::Resource>:: returns the proper Chef::Resource class - def self.resource_for_node(short_name, node) + def self.resource_matching_short_name(short_name) begin - platform, version = Chef::Platform.find_platform_and_version(node) - rescue ArgumentError + rname = convert_to_class_name(short_name.to_s) + Chef::Resource.const_get(rname) + rescue NameError + nil end - resource = resource_for_platform(short_name, platform, version) - resource end private |