chef-provisioning 0.15
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/CHANGELOG.md +207 -0
- data/LICENSE +201 -0
- data/README.md +260 -0
- data/Rakefile +6 -0
- data/lib/chef/provider/load_balancer.rb +77 -0
- data/lib/chef/provider/machine.rb +176 -0
- data/lib/chef/provider/machine_batch.rb +191 -0
- data/lib/chef/provider/machine_execute.rb +35 -0
- data/lib/chef/provider/machine_file.rb +54 -0
- data/lib/chef/provider/machine_image.rb +60 -0
- data/lib/chef/provisioning.rb +95 -0
- data/lib/chef/provisioning/action_handler.rb +68 -0
- data/lib/chef/provisioning/add_prefix_action_handler.rb +31 -0
- data/lib/chef/provisioning/chef_image_spec.rb +108 -0
- data/lib/chef/provisioning/chef_load_balancer_spec.rb +108 -0
- data/lib/chef/provisioning/chef_machine_spec.rb +84 -0
- data/lib/chef/provisioning/chef_provider_action_handler.rb +74 -0
- data/lib/chef/provisioning/chef_run_data.rb +139 -0
- data/lib/chef/provisioning/convergence_strategy.rb +28 -0
- data/lib/chef/provisioning/convergence_strategy/install_cached.rb +156 -0
- data/lib/chef/provisioning/convergence_strategy/install_msi.rb +58 -0
- data/lib/chef/provisioning/convergence_strategy/install_sh.rb +55 -0
- data/lib/chef/provisioning/convergence_strategy/no_converge.rb +39 -0
- data/lib/chef/provisioning/convergence_strategy/precreate_chef_objects.rb +183 -0
- data/lib/chef/provisioning/driver.rb +304 -0
- data/lib/chef/provisioning/image_spec.rb +72 -0
- data/lib/chef/provisioning/load_balancer_spec.rb +86 -0
- data/lib/chef/provisioning/machine.rb +112 -0
- data/lib/chef/provisioning/machine/basic_machine.rb +84 -0
- data/lib/chef/provisioning/machine/unix_machine.rb +278 -0
- data/lib/chef/provisioning/machine/windows_machine.rb +104 -0
- data/lib/chef/provisioning/machine_spec.rb +82 -0
- data/lib/chef/provisioning/recipe_dsl.rb +103 -0
- data/lib/chef/provisioning/transport.rb +95 -0
- data/lib/chef/provisioning/transport/ssh.rb +343 -0
- data/lib/chef/provisioning/transport/winrm.rb +151 -0
- data/lib/chef/provisioning/version.rb +5 -0
- data/lib/chef/resource/chef_data_bag_resource.rb +148 -0
- data/lib/chef/resource/load_balancer.rb +57 -0
- data/lib/chef/resource/machine.rb +124 -0
- data/lib/chef/resource/machine_batch.rb +78 -0
- data/lib/chef/resource/machine_execute.rb +28 -0
- data/lib/chef/resource/machine_file.rb +34 -0
- data/lib/chef/resource/machine_image.rb +35 -0
- data/lib/chef_metal.rb +1 -0
- metadata +217 -0
data/Rakefile
ADDED
@@ -0,0 +1,77 @@
|
|
1
|
+
require 'chef/provider/lwrp_base'
|
2
|
+
require 'chef/provider/chef_node'
|
3
|
+
require 'openssl'
|
4
|
+
require 'chef/provisioning/chef_provider_action_handler'
|
5
|
+
require 'chef/provisioning/chef_load_balancer_spec'
|
6
|
+
|
7
|
+
class Chef
|
8
|
+
class Provider
|
9
|
+
class LoadBalancer < Chef::Provider::LWRPBase
|
10
|
+
|
11
|
+
def action_handler
|
12
|
+
@action_handler ||= Chef::Provisioning::ChefProviderActionHandler.new(self)
|
13
|
+
end
|
14
|
+
|
15
|
+
def whyrun_supported?
|
16
|
+
true
|
17
|
+
end
|
18
|
+
|
19
|
+
def new_driver
|
20
|
+
@new_driver ||= run_context.chef_provisioning.driver_for(new_resource.driver)
|
21
|
+
end
|
22
|
+
|
23
|
+
action :create do
|
24
|
+
lb_spec = Chef::Provisioning::ChefLoadBalancerSpec.get(new_resource.name, new_resource.chef_server) ||
|
25
|
+
Chef::Provisioning::ChefLoadBalancerSpec.empty(new_resource.name, new_resource.chef_server)
|
26
|
+
|
27
|
+
if lb_spec.location
|
28
|
+
# Updating
|
29
|
+
update_loadbalancer(lb_spec)
|
30
|
+
else
|
31
|
+
lb_spec.load_balancer_options = new_resource.load_balancer_options
|
32
|
+
lb_spec.machines = new_resource.machines
|
33
|
+
create_loadbalancer(lb_spec)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
action :destroy do
|
38
|
+
lb_spec = Chef::Provisioning::ChefLoadBalancerSpec.get(new_resource.name, new_resource.chef_server)
|
39
|
+
new_driver.destroy_load_balancer(@action_handler, lb_spec, lb_options)
|
40
|
+
end
|
41
|
+
|
42
|
+
attr_reader :lb_spec
|
43
|
+
|
44
|
+
|
45
|
+
def update_loadbalancer(lb_spec)
|
46
|
+
machines = Hash[
|
47
|
+
*(new_resource.machines).collect {
|
48
|
+
|machine_name| [machine_name, get_machine_spec(machine_name)]
|
49
|
+
}.flatten
|
50
|
+
]
|
51
|
+
new_driver.update_load_balancer(action_handler, lb_spec, lb_options, {
|
52
|
+
:machines => machines
|
53
|
+
}
|
54
|
+
)
|
55
|
+
lb_spec.load_balancer_options = new_resource.load_balancer_options
|
56
|
+
lb_spec.machines = new_resource.machines
|
57
|
+
lb_spec.save(action_handler)
|
58
|
+
end
|
59
|
+
|
60
|
+
def create_loadbalancer(lb_spec)
|
61
|
+
new_driver.allocate_load_balancer(action_handler, lb_spec, lb_options)
|
62
|
+
lb_spec.save(action_handler)
|
63
|
+
new_driver.ready_load_balancer(action_handler, lb_spec, lb_options)
|
64
|
+
end
|
65
|
+
|
66
|
+
private
|
67
|
+
def get_machine_spec(machine_name)
|
68
|
+
Chef::Provisioning::ChefMachineSpec.get(machine_name, new_resource.chef_server)
|
69
|
+
end
|
70
|
+
|
71
|
+
def lb_options
|
72
|
+
new_resource.load_balancer_options
|
73
|
+
end
|
74
|
+
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
@@ -0,0 +1,176 @@
|
|
1
|
+
require 'chef/provider/lwrp_base'
|
2
|
+
require 'chef/provider/chef_node'
|
3
|
+
require 'openssl'
|
4
|
+
require 'chef/provisioning/chef_provider_action_handler'
|
5
|
+
require 'chef/provisioning/chef_machine_spec'
|
6
|
+
|
7
|
+
class Chef
|
8
|
+
class Provider
|
9
|
+
class Machine < Chef::Provider::LWRPBase
|
10
|
+
|
11
|
+
def action_handler
|
12
|
+
@action_handler ||= Chef::Provisioning::ChefProviderActionHandler.new(self)
|
13
|
+
end
|
14
|
+
|
15
|
+
use_inline_resources
|
16
|
+
|
17
|
+
def whyrun_supported?
|
18
|
+
true
|
19
|
+
end
|
20
|
+
|
21
|
+
action :allocate do
|
22
|
+
if current_driver && current_driver.driver_url != new_driver.driver_url
|
23
|
+
raise "Cannot move '#{machine_spec.name}' from #{current_driver.driver_url} to #{new_driver.driver_url}: machine moving is not supported. Destroy and recreate."
|
24
|
+
end
|
25
|
+
if !new_driver
|
26
|
+
raise "Driver not specified for machine #{machine_spec.name}"
|
27
|
+
end
|
28
|
+
new_driver.allocate_machine(action_handler, machine_spec, new_machine_options)
|
29
|
+
machine_spec.save(action_handler)
|
30
|
+
end
|
31
|
+
|
32
|
+
action :ready do
|
33
|
+
action_allocate
|
34
|
+
machine = current_driver.ready_machine(action_handler, machine_spec, current_machine_options)
|
35
|
+
machine_spec.save(action_handler)
|
36
|
+
machine
|
37
|
+
end
|
38
|
+
|
39
|
+
action :setup do
|
40
|
+
machine = action_ready
|
41
|
+
begin
|
42
|
+
machine.setup_convergence(action_handler)
|
43
|
+
machine_spec.save(action_handler)
|
44
|
+
upload_files(machine)
|
45
|
+
ensure
|
46
|
+
machine.disconnect
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
action :converge do
|
51
|
+
machine = action_ready
|
52
|
+
begin
|
53
|
+
machine.setup_convergence(action_handler)
|
54
|
+
machine_spec.save(action_handler)
|
55
|
+
upload_files(machine)
|
56
|
+
# If we were asked to converge, or anything changed, or if a converge has never succeeded, converge.
|
57
|
+
if new_resource.converge || (new_resource.converge.nil? && resource_updated?) ||
|
58
|
+
!machine_spec.node['automatic'] || machine_spec.node['automatic'].size == 0
|
59
|
+
machine.converge(action_handler)
|
60
|
+
end
|
61
|
+
ensure
|
62
|
+
machine.disconnect
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
action :converge_only do
|
67
|
+
machine = run_context.chef_provisioning.connect_to_machine(machine_spec, current_machine_options)
|
68
|
+
begin
|
69
|
+
machine.converge(action_handler)
|
70
|
+
ensure
|
71
|
+
machine.disconnect
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
action :stop do
|
76
|
+
if current_driver
|
77
|
+
current_driver.stop_machine(action_handler, machine_spec, current_machine_options)
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
action :destroy do
|
82
|
+
if current_driver
|
83
|
+
current_driver.destroy_machine(action_handler, machine_spec, current_machine_options)
|
84
|
+
end
|
85
|
+
end
|
86
|
+
|
87
|
+
attr_reader :machine_spec
|
88
|
+
|
89
|
+
def new_driver
|
90
|
+
run_context.chef_provisioning.driver_for(new_resource.driver)
|
91
|
+
end
|
92
|
+
|
93
|
+
def current_driver
|
94
|
+
if machine_spec.driver_url
|
95
|
+
run_context.chef_provisioning.driver_for(machine_spec.driver_url)
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
def from_image_spec
|
100
|
+
@from_image_spec ||= begin
|
101
|
+
if new_resource.from_image
|
102
|
+
Chef::Provisioning::ChefImageSpec.get(new_resource.from_image, new_resource.chef_server)
|
103
|
+
else
|
104
|
+
nil
|
105
|
+
end
|
106
|
+
end
|
107
|
+
end
|
108
|
+
|
109
|
+
def new_machine_options
|
110
|
+
machine_options(new_driver)
|
111
|
+
end
|
112
|
+
|
113
|
+
def current_machine_options
|
114
|
+
machine_options(current_driver)
|
115
|
+
end
|
116
|
+
|
117
|
+
def machine_options(driver)
|
118
|
+
configs = []
|
119
|
+
|
120
|
+
if from_image_spec && from_image_spec.machine_options
|
121
|
+
configs << from_image_spec.machine_options
|
122
|
+
end
|
123
|
+
|
124
|
+
configs << {
|
125
|
+
:convergence_options =>
|
126
|
+
[ :chef_server,
|
127
|
+
:allow_overwrite_keys,
|
128
|
+
:source_key, :source_key_path, :source_key_pass_phrase,
|
129
|
+
:private_key_options,
|
130
|
+
:ohai_hints,
|
131
|
+
:public_key_path, :public_key_format,
|
132
|
+
:admin, :validator
|
133
|
+
].inject({}) do |result, key|
|
134
|
+
result[key] = new_resource.send(key)
|
135
|
+
result
|
136
|
+
end
|
137
|
+
}
|
138
|
+
|
139
|
+
configs << new_resource.machine_options if new_resource.machine_options
|
140
|
+
configs << driver.config[:machine_options] if driver.config[:machine_options]
|
141
|
+
Cheffish::MergedConfig.new(*configs)
|
142
|
+
end
|
143
|
+
|
144
|
+
def load_current_resource
|
145
|
+
node_driver = Chef::Provider::ChefNode.new(new_resource, run_context)
|
146
|
+
node_driver.load_current_resource
|
147
|
+
json = node_driver.new_json
|
148
|
+
json['normal']['chef_provisioning'] = node_driver.current_json['normal']['chef_provisioning']
|
149
|
+
@machine_spec = Chef::Provisioning::ChefMachineSpec.new(json, new_resource.chef_server)
|
150
|
+
end
|
151
|
+
|
152
|
+
def self.upload_files(action_handler, machine, files)
|
153
|
+
if files
|
154
|
+
files.each_pair do |remote_file, local|
|
155
|
+
if local.is_a?(Hash)
|
156
|
+
if local[:local_path]
|
157
|
+
machine.upload_file(action_handler, local[:local_path], remote_file)
|
158
|
+
else
|
159
|
+
machine.write_file(action_handler, remote_file, local[:content])
|
160
|
+
end
|
161
|
+
else
|
162
|
+
machine.upload_file(action_handler, local, remote_file)
|
163
|
+
end
|
164
|
+
end
|
165
|
+
end
|
166
|
+
end
|
167
|
+
|
168
|
+
private
|
169
|
+
|
170
|
+
def upload_files(machine)
|
171
|
+
Machine.upload_files(action_handler, machine, new_resource.files)
|
172
|
+
end
|
173
|
+
|
174
|
+
end
|
175
|
+
end
|
176
|
+
end
|
@@ -0,0 +1,191 @@
|
|
1
|
+
require 'chef/chef_fs/parallelizer'
|
2
|
+
require 'chef/provider/lwrp_base'
|
3
|
+
require 'chef/provider/machine'
|
4
|
+
require 'chef/provisioning/chef_provider_action_handler'
|
5
|
+
require 'chef/provisioning/add_prefix_action_handler'
|
6
|
+
require 'chef/provisioning/machine_spec'
|
7
|
+
require 'chef/provisioning/chef_machine_spec'
|
8
|
+
|
9
|
+
class Chef
|
10
|
+
class Provider
|
11
|
+
class MachineBatch < Chef::Provider::LWRPBase
|
12
|
+
|
13
|
+
def action_handler
|
14
|
+
@action_handler ||= Chef::Provisioning::ChefProviderActionHandler.new(self)
|
15
|
+
end
|
16
|
+
|
17
|
+
use_inline_resources
|
18
|
+
|
19
|
+
def whyrun_supported?
|
20
|
+
true
|
21
|
+
end
|
22
|
+
|
23
|
+
def parallelizer
|
24
|
+
@parallelizer ||= Chef::ChefFS::Parallelizer.new(new_resource.max_simultaneous || 100)
|
25
|
+
end
|
26
|
+
|
27
|
+
action :allocate do
|
28
|
+
by_new_driver.each do |driver, specs_and_options|
|
29
|
+
driver.allocate_machines(action_handler, specs_and_options, parallelizer) do |machine_spec|
|
30
|
+
prefixed_handler = Chef::Provisioning::AddPrefixActionHandler.new(action_handler, "[#{machine_spec.name}] ")
|
31
|
+
machine_spec.save(prefixed_handler)
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
action :ready do
|
37
|
+
with_ready_machines
|
38
|
+
end
|
39
|
+
|
40
|
+
action :setup do
|
41
|
+
with_ready_machines do |m|
|
42
|
+
prefixed_handler = Chef::Provisioning::AddPrefixActionHandler.new(action_handler, "[#{m[:spec].name}] ")
|
43
|
+
m[:machine].setup_convergence(prefixed_handler)
|
44
|
+
m[:spec].save(prefixed_handler)
|
45
|
+
Chef::Provider::Machine.upload_files(prefixed_handler, m[:machine], m[:files])
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
action :converge do
|
50
|
+
with_ready_machines do |m|
|
51
|
+
prefixed_handler = Chef::Provisioning::AddPrefixActionHandler.new(action_handler, "[#{m[:spec].name}] ")
|
52
|
+
m[:machine].setup_convergence(prefixed_handler)
|
53
|
+
m[:spec].save(action_handler)
|
54
|
+
Chef::Provider::Machine.upload_files(prefixed_handler, m[:machine], m[:files])
|
55
|
+
# TODO only converge if machine was modified
|
56
|
+
m[:machine].converge(prefixed_handler)
|
57
|
+
m[:spec].save(prefixed_handler)
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
action :converge_only do
|
62
|
+
parallel_do(@machines) do |m|
|
63
|
+
prefixed_handler = Chef::Provisioning::AddPrefixActionHandler.new(action_handler, "[#{m[:spec].name}] ")
|
64
|
+
machine = run_context.chef_provisioning.connect_to_machine(m[:spec])
|
65
|
+
machine.converge(prefixed_handler)
|
66
|
+
end
|
67
|
+
end
|
68
|
+
|
69
|
+
action :destroy do
|
70
|
+
parallel_do(by_current_driver) do |driver, specs_and_options|
|
71
|
+
driver.destroy_machines(action_handler, specs_and_options, parallelizer)
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
action :stop do
|
76
|
+
parallel_do(by_current_driver) do |driver, specs_and_options|
|
77
|
+
driver.stop_machines(action_handler, specs_and_options, parallelizer)
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
def with_ready_machines
|
82
|
+
action_allocate
|
83
|
+
by_id = @machines.inject({}) { |hash,m| hash[m[:spec].id] = m; hash }
|
84
|
+
parallel_do(by_new_driver) do |driver, specs_and_options|
|
85
|
+
driver.ready_machines(action_handler, specs_and_options, parallelizer) do |machine|
|
86
|
+
machine.machine_spec.save(action_handler)
|
87
|
+
|
88
|
+
m = by_id[machine.machine_spec.id]
|
89
|
+
|
90
|
+
m[:machine] = machine
|
91
|
+
begin
|
92
|
+
yield m if block_given?
|
93
|
+
ensure
|
94
|
+
machine.disconnect
|
95
|
+
end
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
# TODO in many of these cases, the order of the results only matters because you
|
101
|
+
# want to match it up with the input. Make a parallelize method that doesn't
|
102
|
+
# care about order and spits back results as quickly as possible.
|
103
|
+
def parallel_do(enum, options = {}, &block)
|
104
|
+
parallelizer.parallelize(enum, options, &block).to_a
|
105
|
+
end
|
106
|
+
|
107
|
+
def by_new_driver
|
108
|
+
result = {}
|
109
|
+
drivers = {}
|
110
|
+
@machines.each do |m|
|
111
|
+
if m[:desired_driver]
|
112
|
+
drivers[m[:desired_driver]] ||= run_context.chef_provisioning.driver_for(m[:desired_driver])
|
113
|
+
driver = drivers[m[:desired_driver]]
|
114
|
+
# Check whether the current driver is same or different; we disallow
|
115
|
+
# moving a machine from one place to another.
|
116
|
+
if m[:spec].driver_url
|
117
|
+
drivers[m[:spec].driver_url] ||= run_context.chef_provisioning.driver_for(m[:spec].driver_url)
|
118
|
+
current_driver = drivers[m[:spec].driver_url]
|
119
|
+
if driver.driver_url != current_driver.driver_url
|
120
|
+
raise "Cannot move '#{m[:spec].name}' from #{current_driver.driver_url} to #{driver.driver_url}: machine moving is not supported. Destroy and recreate."
|
121
|
+
end
|
122
|
+
end
|
123
|
+
result[driver] ||= {}
|
124
|
+
result[driver][m[:spec]] = m[:machine_options].call(driver)
|
125
|
+
else
|
126
|
+
raise "No driver specified for #{m[:spec].name}"
|
127
|
+
end
|
128
|
+
end
|
129
|
+
result
|
130
|
+
end
|
131
|
+
|
132
|
+
def by_current_driver
|
133
|
+
result = {}
|
134
|
+
drivers = {}
|
135
|
+
@machines.each do |m|
|
136
|
+
if m[:spec].driver_url
|
137
|
+
drivers[m[:spec].driver_url] ||= run_context.chef_provisioning.driver_for(m[:spec].driver_url)
|
138
|
+
driver = drivers[m[:spec].driver_url]
|
139
|
+
result[driver] ||= {}
|
140
|
+
result[driver][m[:spec]] = m[:machine_options].call(driver)
|
141
|
+
end
|
142
|
+
end
|
143
|
+
result
|
144
|
+
end
|
145
|
+
|
146
|
+
def load_current_resource
|
147
|
+
# Load nodes in parallel
|
148
|
+
@machines = parallel_do(new_resource.machines) do |machine|
|
149
|
+
if machine.is_a?(Chef::Resource::Machine)
|
150
|
+
machine_resource = machine
|
151
|
+
provider = Chef::Provider::Machine.new(machine_resource, machine_resource.run_context)
|
152
|
+
provider.load_current_resource
|
153
|
+
{
|
154
|
+
:spec => provider.machine_spec,
|
155
|
+
:desired_driver => machine_resource.driver,
|
156
|
+
:files => machine_resource.files,
|
157
|
+
:machine_options => proc { |driver| provider.machine_options(driver) }
|
158
|
+
}
|
159
|
+
elsif machine.is_a?(Chef::Provisioning::MachineSpec)
|
160
|
+
machine_spec = machine
|
161
|
+
{
|
162
|
+
:spec => machine_spec,
|
163
|
+
:desired_driver => new_resource.driver,
|
164
|
+
:files => new_resource.files,
|
165
|
+
:machine_options => proc { |driver| machine_options(driver) }
|
166
|
+
}
|
167
|
+
else
|
168
|
+
name = machine
|
169
|
+
machine_spec = Chef::Provisioning::ChefMachineSpec.get(name, new_resource.chef_server) ||
|
170
|
+
Chef::Provisioning::ChefMachineSpec.empty(name, new_resource.chef_server)
|
171
|
+
{
|
172
|
+
:spec => machine_spec,
|
173
|
+
:desired_driver => new_resource.driver,
|
174
|
+
:files => new_resource.files,
|
175
|
+
:machine_options => proc { |driver| machine_options(driver) }
|
176
|
+
}
|
177
|
+
end
|
178
|
+
end.to_a
|
179
|
+
end
|
180
|
+
|
181
|
+
def machine_options(driver)
|
182
|
+
result = { :convergence_options => { :chef_server => new_resource.chef_server } }
|
183
|
+
result = Chef::Mixin::DeepMerge.hash_only_merge(result, run_context.chef_provisioning.config[:machine_options]) if run_context.chef_provisioning.config[:machine_options]
|
184
|
+
result = Chef::Mixin::DeepMerge.hash_only_merge(result, driver.config[:machine_options]) if driver.config && driver.config[:machine_options]
|
185
|
+
result = Chef::Mixin::DeepMerge.hash_only_merge(result, new_resource.machine_options)
|
186
|
+
result
|
187
|
+
end
|
188
|
+
|
189
|
+
end
|
190
|
+
end
|
191
|
+
end
|