chef-resource 0.2.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/CHANGELOG.md +23 -0
- data/LICENSE +201 -0
- data/README.md +264 -0
- data/Rakefile +8 -0
- data/files/lib/chef_resource.rb +24 -0
- data/files/lib/chef_resource/camel_case.rb +23 -0
- data/files/lib/chef_resource/chef.rb +102 -0
- data/files/lib/chef_resource/chef_dsl/chef_cookbook_compiler.rb +44 -0
- data/files/lib/chef_resource/chef_dsl/chef_recipe.rb +10 -0
- data/files/lib/chef_resource/chef_dsl/chef_recipe_dsl_extensions.rb +84 -0
- data/files/lib/chef_resource/chef_dsl/chef_resource_base.rb +12 -0
- data/files/lib/chef_resource/chef_dsl/chef_resource_class_extensions.rb +30 -0
- data/files/lib/chef_resource/chef_dsl/chef_resource_extensions.rb +224 -0
- data/files/lib/chef_resource/chef_dsl/chef_resource_log.rb +54 -0
- data/files/lib/chef_resource/chef_dsl/resource_container_module.rb +80 -0
- data/files/lib/chef_resource/chef_dsl/resource_definition_dsl.rb +128 -0
- data/files/lib/chef_resource/constants.rb +8 -0
- data/files/lib/chef_resource/errors.rb +31 -0
- data/files/lib/chef_resource/lazy_proc.rb +82 -0
- data/files/lib/chef_resource/output/nested_converge.rb +91 -0
- data/files/lib/chef_resource/output/nested_converge/open_resource.rb +113 -0
- data/files/lib/chef_resource/output/region_stream.rb +145 -0
- data/files/lib/chef_resource/output/simple_output.rb +83 -0
- data/files/lib/chef_resource/resource.rb +428 -0
- data/files/lib/chef_resource/resource/resource_log.rb +197 -0
- data/files/lib/chef_resource/resource/resource_type.rb +74 -0
- data/files/lib/chef_resource/resource/struct_property.rb +39 -0
- data/files/lib/chef_resource/resource/struct_property_type.rb +185 -0
- data/files/lib/chef_resource/resource/struct_resource.rb +410 -0
- data/files/lib/chef_resource/resource/struct_resource_base.rb +11 -0
- data/files/lib/chef_resource/resource/struct_resource_type.rb +275 -0
- data/files/lib/chef_resource/simple_struct.rb +121 -0
- data/files/lib/chef_resource/type.rb +371 -0
- data/files/lib/chef_resource/types.rb +4 -0
- data/files/lib/chef_resource/types/boolean.rb +16 -0
- data/files/lib/chef_resource/types/byte_size.rb +10 -0
- data/files/lib/chef_resource/types/date_time_type.rb +18 -0
- data/files/lib/chef_resource/types/date_type.rb +18 -0
- data/files/lib/chef_resource/types/float_type.rb +28 -0
- data/files/lib/chef_resource/types/integer_type.rb +53 -0
- data/files/lib/chef_resource/types/interval.rb +21 -0
- data/files/lib/chef_resource/types/path.rb +39 -0
- data/files/lib/chef_resource/types/pathname_type.rb +34 -0
- data/files/lib/chef_resource/types/string_type.rb +16 -0
- data/files/lib/chef_resource/types/symbol_type.rb +18 -0
- data/files/lib/chef_resource/types/uri_type.rb +37 -0
- data/files/lib/chef_resource/version.rb +3 -0
- data/spec/integration/chef.rb +81 -0
- data/spec/integration/struct_spec.rb +611 -0
- data/spec/integration/struct_state_spec.rb +538 -0
- data/spec/integration/type_spec.rb +1123 -0
- data/spec/integration/validation_spec.rb +207 -0
- data/spec/support/spec_support.rb +7 -0
- metadata +167 -0
data/Rakefile
ADDED
@@ -0,0 +1,24 @@
|
|
1
|
+
require 'chef_resource/version'
|
2
|
+
require 'chef_resource/constants'
|
3
|
+
|
4
|
+
module ChefResource
|
5
|
+
#
|
6
|
+
# Print a list of values with a conjunction like 'and' or 'or'
|
7
|
+
#
|
8
|
+
# @param conjunction [String] A word like 'and' or 'or'
|
9
|
+
# @param separator [String] A separator like ', ' or '; '
|
10
|
+
# @param *values A list of values to join with `to_s`
|
11
|
+
# @return the list, joined with the separator
|
12
|
+
# @example
|
13
|
+
# english_list(1, 2, 3, 4) #=> "1, 2, 3 and 4"
|
14
|
+
def self.english_list(*values, conjunction: 'and', separator: ', ')
|
15
|
+
case values.size
|
16
|
+
when 0
|
17
|
+
nil
|
18
|
+
when 1
|
19
|
+
values[0].to_s
|
20
|
+
else
|
21
|
+
"#{values[0..-2].join(separator)} #{conjunction} #{values[-1]}"
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module ChefResource
|
2
|
+
module CamelCase
|
3
|
+
# foo_bar/baz_bonk -> FooBar::BazBonk
|
4
|
+
def self.from_snake_case(snake_case)
|
5
|
+
snake_case.to_s.split('/').map do |str|
|
6
|
+
str.split('_').map { |s| s.capitalize }.join('')
|
7
|
+
end.join('::')
|
8
|
+
end
|
9
|
+
|
10
|
+
# FooBar::BazBonk -> foo_bar/baz_bonk
|
11
|
+
if RUBY_VERSION.to_f >= 2
|
12
|
+
UPPERCASE_SPLIT = Regexp.new('(?=\p{Lu})')
|
13
|
+
else
|
14
|
+
UPPERCASE_SPLIT = Regexp.new('(?=[A-Z])')
|
15
|
+
end
|
16
|
+
|
17
|
+
def self.to_snake_case(camel_case)
|
18
|
+
camel_case.to_s.split('::').map do |str|
|
19
|
+
str.split(UPPERCASE_SPLIT).map { |s| s.downcase! }.join('_')
|
20
|
+
end.join('/')
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,102 @@
|
|
1
|
+
#
|
2
|
+
# This file includes all the monkeypatches to Chef. (They are fairly minimal,
|
3
|
+
# and generally designed to only affect ChefResource cookbooks, as well as to allow
|
4
|
+
# other cookbooks to use resources defined in ChefResource cookbooks.)
|
5
|
+
#
|
6
|
+
|
7
|
+
#
|
8
|
+
# Redefine Chef's DelayedEvaluator (same basic def, with added goodies
|
9
|
+
# for cache and instance_eval)
|
10
|
+
#
|
11
|
+
|
12
|
+
require 'chef_resource/lazy_proc'
|
13
|
+
require 'chef/mixin/params_validate' # for DelayedEvaluator
|
14
|
+
|
15
|
+
Chef.send(:remove_const, :DelayedEvaluator)
|
16
|
+
Chef.const_set(:DelayedEvaluator, ChefResource::LazyProc)
|
17
|
+
|
18
|
+
#
|
19
|
+
# Add "ChefResource.define", "Chef.resource" and "ChefResource.defaults"
|
20
|
+
#
|
21
|
+
|
22
|
+
require 'chef_resource/chef_dsl/resource_definition_dsl'
|
23
|
+
|
24
|
+
class Chef
|
25
|
+
extend ChefResource::ChefDSL::ResourceDefinitionDSL
|
26
|
+
end
|
27
|
+
|
28
|
+
#
|
29
|
+
# Add "define" "resource" and "defaults" directly to ChefResource recipes/ and resource DSLs
|
30
|
+
#
|
31
|
+
|
32
|
+
require 'chef_resource/chef_dsl/chef_recipe'
|
33
|
+
require 'chef/recipe'
|
34
|
+
|
35
|
+
class Chef
|
36
|
+
class Recipe
|
37
|
+
def self.new(cookbook_name, recipe_name, run_context)
|
38
|
+
if run_context
|
39
|
+
cookbook = run_context.cookbook_collection[cookbook_name]
|
40
|
+
if cookbook.metadata.dependencies.has_key?('resource') && !(self <= ChefResource::ChefDSL::ChefRecipe)
|
41
|
+
return ChefResource::ChefDSL::ChefRecipe.new(cookbook_name, recipe_name, run_context)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
super
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
#
|
50
|
+
# Turn "resources/" into ChefResource resources in ChefResource cookbooks
|
51
|
+
#
|
52
|
+
|
53
|
+
require 'chef/run_context/cookbook_compiler'
|
54
|
+
require 'chef_resource/chef_dsl/chef_cookbook_compiler'
|
55
|
+
|
56
|
+
class Chef
|
57
|
+
class RunContext
|
58
|
+
class CookbookCompiler
|
59
|
+
prepend ChefResource::ChefDSL::ChefCookbookCompiler
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
#
|
65
|
+
# Support new-style resources in Chef recipes by adding a method to update the
|
66
|
+
# list of definitions when resources are defined
|
67
|
+
#
|
68
|
+
|
69
|
+
require 'chef_resource/chef_dsl/resource_container_module'
|
70
|
+
require 'chef/dsl/recipe'
|
71
|
+
require 'chef/resource'
|
72
|
+
|
73
|
+
class Chef
|
74
|
+
class Resource
|
75
|
+
extend ChefResource::ChefDSL::ResourceContainerModule
|
76
|
+
def self.recipe_dsl_module
|
77
|
+
Chef::DSL::Recipe
|
78
|
+
end
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
|
83
|
+
#
|
84
|
+
# Build ChefResource resources all special-like
|
85
|
+
#
|
86
|
+
|
87
|
+
require 'chef_resource/chef_dsl/chef_recipe_dsl_extensions'
|
88
|
+
require 'chef/dsl/recipe'
|
89
|
+
require 'chef/recipe'
|
90
|
+
require 'chef/resource/lwrp_base'
|
91
|
+
|
92
|
+
class Chef
|
93
|
+
module DSL::Recipe
|
94
|
+
prepend ChefResource::ChefDSL::ChefRecipeDSLExtensions
|
95
|
+
end
|
96
|
+
class Recipe
|
97
|
+
prepend ChefResource::ChefDSL::ChefRecipeDSLExtensions
|
98
|
+
end
|
99
|
+
class Resource::LWRPBase
|
100
|
+
prepend ChefResource::ChefDSL::ChefRecipeDSLExtensions
|
101
|
+
end
|
102
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
require 'chef/resource'
|
2
|
+
require 'chef/log'
|
3
|
+
require 'chef/mixin/convert_to_class_name'
|
4
|
+
require 'chef_resource/chef'
|
5
|
+
|
6
|
+
module ChefResource
|
7
|
+
module ChefDSL
|
8
|
+
module ChefCookbookCompiler
|
9
|
+
def depends_on_resource_cookbook?(cookbook_name)
|
10
|
+
cookbook_collection[cookbook_name].metadata.dependencies.has_key?('resource')
|
11
|
+
end
|
12
|
+
|
13
|
+
# After compiling libraries, we update the resource collection
|
14
|
+
def compile_libraries
|
15
|
+
super
|
16
|
+
Chef::Resource.update_resource_definition_methods!
|
17
|
+
end
|
18
|
+
|
19
|
+
def compile_lwrps
|
20
|
+
super
|
21
|
+
Chef::Resource.update_resource_definition_methods!
|
22
|
+
end
|
23
|
+
|
24
|
+
def load_lwrp_resource(cookbook_name, filename)
|
25
|
+
if depends_on_resource_cookbook?(cookbook_name)
|
26
|
+
begin
|
27
|
+
Chef::Log.debug("Loading cookbook #{cookbook_name}'s resources from #{filename}")
|
28
|
+
resource_name = Chef::Mixin::ConvertToClassName.filename_to_qualified_string(cookbook_name, filename)
|
29
|
+
resource_class = Chef.resource resource_name do
|
30
|
+
class_eval IO.read(filename), filename
|
31
|
+
end
|
32
|
+
Chef::Log.debug("Loaded contents of #{filename} into a resource named #{resource_name} defined in #{resource_class.name}")
|
33
|
+
@events.lwrp_file_loaded(filename)
|
34
|
+
rescue Exception => e
|
35
|
+
@events.lwrp_file_load_failed(filename, e)
|
36
|
+
raise
|
37
|
+
end
|
38
|
+
else
|
39
|
+
super
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,84 @@
|
|
1
|
+
require 'chef_resource/resource'
|
2
|
+
|
3
|
+
module ChefResource
|
4
|
+
module ChefDSL
|
5
|
+
module ChefRecipeDSLExtensions
|
6
|
+
#
|
7
|
+
# Allow ChefResource resources to be declared with a different syntax:
|
8
|
+
#
|
9
|
+
# declare_resource(:resource, ..., created_at)
|
10
|
+
# declare_resource(ResourceClass, ..., created_at)
|
11
|
+
#
|
12
|
+
# Which translates to open() in the end.
|
13
|
+
#
|
14
|
+
def declare_resource(type, *identity, created_at, &update_block)
|
15
|
+
resource_class = resource_class_for(type)
|
16
|
+
|
17
|
+
# Handle normal resources
|
18
|
+
if !resource_class.is_a?(ChefResource::Resource)
|
19
|
+
case identity.size
|
20
|
+
when 0
|
21
|
+
name, created_at = created_at, caller[0]
|
22
|
+
when 1
|
23
|
+
name = identity[0]
|
24
|
+
else
|
25
|
+
raise ArgumentError, "wrong number of arguments (#{identity.size+1} for 1..2)"
|
26
|
+
end
|
27
|
+
return super(type, name, created_at, &update_block)
|
28
|
+
end
|
29
|
+
|
30
|
+
# ChefResource resources!
|
31
|
+
resource = buildbuild_resource_v2(resource_class, *identity, created_at, &update_block)
|
32
|
+
run_context.resource_collection.insert(resource,
|
33
|
+
resource_type: resource_class.dsl_name,
|
34
|
+
instance_name: resource.resource_identity_string)
|
35
|
+
end
|
36
|
+
|
37
|
+
def build_resource(type, *identity, created_at, &update_block)
|
38
|
+
resource_class = resource_class_for(type)
|
39
|
+
if !resource_class.is_a?(ChefResource::Resource)
|
40
|
+
# Handle normal resources
|
41
|
+
case identity.size
|
42
|
+
when 0
|
43
|
+
name, created_at = created_at, caller[0]
|
44
|
+
when 1
|
45
|
+
name = identity[0]
|
46
|
+
else
|
47
|
+
raise ArgumentError, "wrong number of arguments (#{identity.size+1} for 1..2)"
|
48
|
+
end
|
49
|
+
return super(type, name, created_at, &update_block)
|
50
|
+
end
|
51
|
+
|
52
|
+
# ChefResource!
|
53
|
+
buildbuild_resource_v2(resource_class, *identity, created_at, &update_block)
|
54
|
+
end
|
55
|
+
|
56
|
+
def buildbuild_resource_v2(resource_class, *identity, created_at, &update_block)
|
57
|
+
resource = resource_class.open(*identity)
|
58
|
+
resource.run_context = run_context
|
59
|
+
resource.cookbook_name = cookbook_name
|
60
|
+
resource.recipe_name = recipe_name
|
61
|
+
resource.source_line = created_at
|
62
|
+
resource.declared_type = resource_class.dsl_name
|
63
|
+
# Determine whether this resource is being created in the context of an enclosing Provider
|
64
|
+
resource.enclosing_provider = self.is_a?(Chef::Provider) ? self : nil
|
65
|
+
resource.params = @params
|
66
|
+
|
67
|
+
# Evaluate resource attribute DSL
|
68
|
+
resource.instance_eval(&update_block) if block_given?
|
69
|
+
|
70
|
+
# Freeze resource
|
71
|
+
resource.resource_fully_defined
|
72
|
+
|
73
|
+
# Run optional resource hook
|
74
|
+
resource.after_created
|
75
|
+
|
76
|
+
resource
|
77
|
+
end
|
78
|
+
|
79
|
+
def resource_class_for(type)
|
80
|
+
type.is_a?(Class) ? type : super
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
84
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
require 'chef/resource'
|
2
|
+
require 'chef_resource/chef_dsl/chef_resource_extensions'
|
3
|
+
require 'chef_resource/chef_dsl/chef_resource_class_extensions'
|
4
|
+
|
5
|
+
module ChefResource
|
6
|
+
module ChefDSL
|
7
|
+
class ChefResourceBase < Chef::Resource
|
8
|
+
include ChefResourceExtensions
|
9
|
+
extend ChefResourceClassExtensions
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
require 'chef_resource/resource/struct_resource'
|
2
|
+
require 'chef_resource/resource/struct_resource_type'
|
3
|
+
require 'chef_resource/camel_case'
|
4
|
+
require 'chef/dsl/recipe'
|
5
|
+
require 'chef/resource'
|
6
|
+
|
7
|
+
module ChefResource
|
8
|
+
module ChefDSL
|
9
|
+
#
|
10
|
+
# Define properties on the type itself
|
11
|
+
#
|
12
|
+
module ChefResourceClassExtensions
|
13
|
+
# We are a StructResource (so that we can use "property" for properties
|
14
|
+
# of the ChefResource class itself) and a StructResourceType (because
|
15
|
+
# Chef Resources are traditionally structs).
|
16
|
+
include ChefResource::Resource::StructResource
|
17
|
+
include ChefResource::Resource::StructResourceType
|
18
|
+
extend ChefResource::Resource::StructResourceType
|
19
|
+
|
20
|
+
#
|
21
|
+
# recipe do
|
22
|
+
# ...
|
23
|
+
# end
|
24
|
+
#
|
25
|
+
def recipe(&recipe_block)
|
26
|
+
define_method(:update_resource, &recipe_block)
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
@@ -0,0 +1,224 @@
|
|
1
|
+
require 'chef/resource_collection'
|
2
|
+
require 'chef/runner'
|
3
|
+
require 'chef/dsl/recipe'
|
4
|
+
require 'chef_resource/resource/struct_resource'
|
5
|
+
require 'chef_resource/chef_dsl/chef_resource_log'
|
6
|
+
require 'chef_resource/chef_dsl/chef_recipe_dsl_extensions'
|
7
|
+
require 'chef_resource/types'
|
8
|
+
|
9
|
+
module ChefResource
|
10
|
+
module ChefDSL
|
11
|
+
module ChefResourceExtensions
|
12
|
+
include Chef::DSL::Recipe
|
13
|
+
include ChefResource::ChefDSL::ChefRecipeDSLExtensions
|
14
|
+
include ChefResource::Resource::StructResource
|
15
|
+
|
16
|
+
#
|
17
|
+
# We don't set name, and we expect our run_context to be set elsewhere.
|
18
|
+
#
|
19
|
+
def initialize
|
20
|
+
super(nil, nil)
|
21
|
+
end
|
22
|
+
|
23
|
+
#
|
24
|
+
# Returns a super-friendly string showing this struct.
|
25
|
+
#
|
26
|
+
# @param only [Symbol] Which values to include. Default: `:only_known`. One of:
|
27
|
+
# - :only_known :: Values explicitly set by the user or current values.
|
28
|
+
# If the current value has not been loaded, this will NOT load it or
|
29
|
+
# show any of those values.
|
30
|
+
# - :only_changed :: Values which the user has set and which have
|
31
|
+
# actually changed from their current or default value.
|
32
|
+
# - :only_explicit :: Values explicitly set by the user.
|
33
|
+
# - :all :: All values, including default values.
|
34
|
+
#
|
35
|
+
def to_text(only=:only_known)
|
36
|
+
# return "suppressed sensitive resource output" if sensitive
|
37
|
+
text = self.class.dsl_name + "(\"#{name}\") do\n"
|
38
|
+
text << " # Declared in #{@source_line}\n"
|
39
|
+
results = to_h(only)
|
40
|
+
results_width = results.keys.map { |k| k.size }.max
|
41
|
+
results.each do |name, value|
|
42
|
+
text << " #{name.to_s.ljust(results_width)} "
|
43
|
+
if value.respond_to?(:to_text)
|
44
|
+
lines = value.to_text.lines
|
45
|
+
text << lines.map do |line|
|
46
|
+
"#{line}#{line.end_with?("\n") ? "" : "\n"}"
|
47
|
+
end.join(" ")
|
48
|
+
else
|
49
|
+
text << "#{value.inspect}\n"
|
50
|
+
end
|
51
|
+
end
|
52
|
+
[@not_if, @only_if].flatten.each do |conditional|
|
53
|
+
text << " #{conditional.to_text}\n"
|
54
|
+
end
|
55
|
+
text << "end\n"
|
56
|
+
end
|
57
|
+
|
58
|
+
#
|
59
|
+
# Returns this struct as a string with <resource_name name: value name: value name
|
60
|
+
#
|
61
|
+
# @param only [Symbol] Which values to include. Default: `:only_known`. One of:
|
62
|
+
# - :only_known :: Values explicitly set by the user or current values.
|
63
|
+
# If the current value has not been loaded, this will NOT load it or
|
64
|
+
# show any of those values.
|
65
|
+
# - :only_changed :: Values which the user has set and which have
|
66
|
+
# actually changed from their current or default value.
|
67
|
+
# - :only_explicit :: Values explicitly set by the user.
|
68
|
+
# - :all :: All values, including default values.
|
69
|
+
#
|
70
|
+
def inspect(only=:only_known)
|
71
|
+
to_h(only).inject("<#{to_s}") do |str, (name, value)|
|
72
|
+
str << " #{name}: #{value.inspect}"
|
73
|
+
end << ">"
|
74
|
+
end
|
75
|
+
|
76
|
+
#
|
77
|
+
# No such thing as a provider, yo. (Also not supporting
|
78
|
+
# multiple actions yet.)
|
79
|
+
#
|
80
|
+
def provider_for_action(action)
|
81
|
+
self
|
82
|
+
end
|
83
|
+
|
84
|
+
#
|
85
|
+
# Mimic Chef::Provider.run_action
|
86
|
+
#
|
87
|
+
# This is where we do the work to get rid of Providers!
|
88
|
+
#
|
89
|
+
# NOTE: both Chef::Resource and Chef::Provider have a
|
90
|
+
# run_action. In fact, they can both technically take a single-argument
|
91
|
+
# form. However, in practice in Chef, Chef::Provider.run_action() is the
|
92
|
+
# only method ever called. So we say that if we are passed multiple args,
|
93
|
+
# it is the Resource version ("super") and if we are passed only one arg,
|
94
|
+
# it is the Provider version.
|
95
|
+
#
|
96
|
+
def run_action(*args)
|
97
|
+
if args.size > 0
|
98
|
+
return super
|
99
|
+
end
|
100
|
+
|
101
|
+
# Call update.
|
102
|
+
log.update_started
|
103
|
+
begin
|
104
|
+
|
105
|
+
# Enable update to run its own resources, inline.
|
106
|
+
|
107
|
+
# Executes the given block in a temporary run_context with its own
|
108
|
+
# resource collection. After the block is executed, any resources
|
109
|
+
# declared inside are converged, and if any are updated, the
|
110
|
+
# new_resource will be marked updated.
|
111
|
+
saved_run_context = @run_context
|
112
|
+
temp_run_context = @run_context.dup
|
113
|
+
@run_context = temp_run_context
|
114
|
+
@run_context.resource_collection = Chef::ResourceCollection.new
|
115
|
+
|
116
|
+
update_resource
|
117
|
+
|
118
|
+
Chef::Runner.new(@run_context).converge
|
119
|
+
rescue
|
120
|
+
log.update_failed($!)
|
121
|
+
raise
|
122
|
+
ensure
|
123
|
+
@run_context = saved_run_context
|
124
|
+
if temp_run_context.resource_collection.any? {|r| r.updated? }
|
125
|
+
updated_by_last_action(true)
|
126
|
+
end
|
127
|
+
end
|
128
|
+
log.update_succeeded
|
129
|
+
end
|
130
|
+
|
131
|
+
#
|
132
|
+
# This is how we support inline resources that can access their parent
|
133
|
+
# resource's data: enclosing_provider is how Chef delegates to our scope.
|
134
|
+
#
|
135
|
+
def build_resource(*args, &block)
|
136
|
+
parent = self
|
137
|
+
super(*args) do
|
138
|
+
self.enclosing_provider = parent
|
139
|
+
instance_eval(&block) if block
|
140
|
+
end
|
141
|
+
end
|
142
|
+
|
143
|
+
#
|
144
|
+
# The name of this resource type. Just calls self.class.resource_name.
|
145
|
+
#
|
146
|
+
def resource_name
|
147
|
+
self.class.dsl_name
|
148
|
+
end
|
149
|
+
|
150
|
+
#
|
151
|
+
# We only support one action, presently. Hardcode it.
|
152
|
+
#
|
153
|
+
def action
|
154
|
+
[ :update ]
|
155
|
+
end
|
156
|
+
|
157
|
+
#
|
158
|
+
# Subtle difference from ChefResource::Resource::StructResource.reopen_resource:
|
159
|
+
# this method passes the name and run_context into the resource constructor
|
160
|
+
# (since Resource requires that).
|
161
|
+
#
|
162
|
+
def reopen_resource
|
163
|
+
resource = super
|
164
|
+
resource.run_context = run_context
|
165
|
+
resource.cookbook_name = cookbook_name
|
166
|
+
resource.recipe_name = recipe_name
|
167
|
+
resource.source_line = source_line
|
168
|
+
resource.declared_type = declared_type
|
169
|
+
resource.enclosing_provider = enclosing_provider
|
170
|
+
resource.params = params
|
171
|
+
resource
|
172
|
+
end
|
173
|
+
|
174
|
+
def to_s
|
175
|
+
"#{self.class.dsl_name}[#{resource_identity_string}]"
|
176
|
+
end
|
177
|
+
|
178
|
+
#
|
179
|
+
# For our short_name, we just grab #to_s, which outputs the right notification
|
180
|
+
# syntax.
|
181
|
+
#
|
182
|
+
def resource_short_name
|
183
|
+
to_s
|
184
|
+
end
|
185
|
+
|
186
|
+
#
|
187
|
+
# Log to Chef!
|
188
|
+
#
|
189
|
+
def log(*args)
|
190
|
+
@resource_log ||= ChefResourceLog.new(self)
|
191
|
+
super
|
192
|
+
end
|
193
|
+
|
194
|
+
#
|
195
|
+
# Make damn sure we're not doing the whole silly cloning thing
|
196
|
+
#
|
197
|
+
def load_from(*args)
|
198
|
+
raise NotImplementedError, "load_from is not implemented on ChefResource resources."
|
199
|
+
end
|
200
|
+
|
201
|
+
#
|
202
|
+
# Take an action that will update the resource.
|
203
|
+
#
|
204
|
+
# @param description [String] The action being taken.
|
205
|
+
# @yield A block that will perform the actual update.
|
206
|
+
# @raise Any error raised by the block is passed through.
|
207
|
+
#
|
208
|
+
def take_action(description, &action_block)
|
209
|
+
if Chef::Config[:why_run]
|
210
|
+
log.action_skipped(description)
|
211
|
+
else
|
212
|
+
log.action_started(description)
|
213
|
+
begin
|
214
|
+
instance_eval(&action_block)
|
215
|
+
rescue
|
216
|
+
log.action_failed($!)
|
217
|
+
raise
|
218
|
+
end
|
219
|
+
log.action_succeeded
|
220
|
+
end
|
221
|
+
end
|
222
|
+
end
|
223
|
+
end
|
224
|
+
end
|