chef-metal-docker 0.2 → 0.4.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +62 -1
- data/lib/chef/provider/docker_container.rb +3 -109
- data/lib/chef/resource/docker_container.rb +1 -7
- data/lib/chef_metal/driver_init/docker.rb +3 -0
- data/lib/chef_metal_docker.rb +2 -2
- data/lib/chef_metal_docker/chef_zero_http_proxy.rb +92 -0
- data/lib/chef_metal_docker/docker_container_machine.rb +26 -0
- data/lib/chef_metal_docker/docker_driver.rb +238 -0
- data/lib/chef_metal_docker/docker_transport.rb +41 -65
- data/lib/chef_metal_docker/version.rb +1 -1
- metadata +23 -13
- data/lib/chef_metal/provisioner_init/docker_init.rb +0 -4
- data/lib/chef_metal_docker/docker_provisioner.rb +0 -272
- data/lib/chef_metal_docker/docker_unix_machine.rb +0 -9
- data/lib/chef_metal_docker/helpers.rb +0 -146
- data/lib/chef_metal_docker/helpers/container.rb +0 -15
- data/lib/chef_metal_docker/helpers/container/actions.rb +0 -313
- data/lib/chef_metal_docker/helpers/container/helpers.rb +0 -156
@@ -1,146 +0,0 @@
|
|
1
|
-
require 'chef/mixin/shell_out'
|
2
|
-
include Chef::Mixin::ShellOut
|
3
|
-
|
4
|
-
# Helpers module
|
5
|
-
module ChefMetalDocker
|
6
|
-
# Helpers::Docker module
|
7
|
-
module Helpers
|
8
|
-
# Exception to signify that the Docker daemon is not yet ready to handle
|
9
|
-
# docker commands.
|
10
|
-
class DockerNotReady < StandardError
|
11
|
-
def initialize(timeout)
|
12
|
-
super <<-EOH
|
13
|
-
The Docker daemon did not become ready within #{timeout} seconds.
|
14
|
-
This most likely means that Docker failed to start.
|
15
|
-
Docker can fail to start if:
|
16
|
-
|
17
|
-
- a configuration file is invalid
|
18
|
-
- permissions are incorrect for the root directory of the docker runtime.
|
19
|
-
|
20
|
-
If this problem persists, check your service log files.
|
21
|
-
EOH
|
22
|
-
end
|
23
|
-
end
|
24
|
-
|
25
|
-
# Exception to signify that the docker command timed out.
|
26
|
-
class CommandTimeout < RuntimeError; end
|
27
|
-
|
28
|
-
def cli_args(spec)
|
29
|
-
cli_line = ''
|
30
|
-
spec.each_pair do |arg, value|
|
31
|
-
case value
|
32
|
-
when Array
|
33
|
-
next if value.empty?
|
34
|
-
args = value.map do |v|
|
35
|
-
v = "\"#{v}\"" if v.is_a?(String)
|
36
|
-
" --#{arg}=#{v}"
|
37
|
-
end
|
38
|
-
cli_line += args.join
|
39
|
-
when FalseClass, Fixnum, Integer, String, TrueClass
|
40
|
-
value = "\"#{value}\"" if value.is_a?(String)
|
41
|
-
cli_line += " --#{arg}=#{value}"
|
42
|
-
end
|
43
|
-
end
|
44
|
-
cli_line
|
45
|
-
end
|
46
|
-
|
47
|
-
def docker_inspect(id)
|
48
|
-
require 'json'
|
49
|
-
JSON.parse(docker_cmd("inspect #{id}").stdout)[0]
|
50
|
-
end
|
51
|
-
|
52
|
-
def docker_inspect_id(id)
|
53
|
-
inspect = docker_inspect(id)
|
54
|
-
inspect['id'] if inspect
|
55
|
-
end
|
56
|
-
|
57
|
-
def dockercfg_parse
|
58
|
-
require 'json'
|
59
|
-
dockercfg = JSON.parse(::File.read(::File.join(::Dir.home, '.dockercfg')))
|
60
|
-
dockercfg.each_pair do |k, v|
|
61
|
-
dockercfg[k].merge!(dockercfg_parse_auth(v['auth']))
|
62
|
-
end
|
63
|
-
dockercfg
|
64
|
-
end
|
65
|
-
|
66
|
-
def dockercfg_parse_auth(str)
|
67
|
-
require 'base64'
|
68
|
-
decoded_str = Base64.decode64(str)
|
69
|
-
if decoded_str
|
70
|
-
auth = {}
|
71
|
-
auth['username'], auth['password'] = decoded_str.split(':')
|
72
|
-
auth
|
73
|
-
end
|
74
|
-
end
|
75
|
-
|
76
|
-
def timeout
|
77
|
-
10
|
78
|
-
end
|
79
|
-
|
80
|
-
# This is based upon wait_until_ready! from the opscode jenkins cookbook.
|
81
|
-
#
|
82
|
-
# Since the docker service returns immediately and the actual docker
|
83
|
-
# process is started as a daemon, we block the Chef Client run until the
|
84
|
-
# daemon is actually ready.
|
85
|
-
#
|
86
|
-
# This method will effectively "block" the current thread until the docker
|
87
|
-
# daemon is ready
|
88
|
-
#
|
89
|
-
# @raise [DockerNotReady]
|
90
|
-
# if the Docker master does not respond within (+timeout+) seconds
|
91
|
-
#
|
92
|
-
def wait_until_ready!
|
93
|
-
Timeout.timeout(timeout) do
|
94
|
-
loop do
|
95
|
-
result = shell_out('docker info')
|
96
|
-
break if Array(result.valid_exit_codes).include?(result.exitstatus)
|
97
|
-
Chef::Log.debug("Docker daemon is not running - #{result.stdout}\n#{result.stderr}")
|
98
|
-
sleep(0.5)
|
99
|
-
end
|
100
|
-
end
|
101
|
-
rescue Timeout::Error
|
102
|
-
raise DockerNotReady.new(timeout), 'docker timeout exceeded'
|
103
|
-
end
|
104
|
-
|
105
|
-
# the Error message to display if a command times out. Subclasses
|
106
|
-
# may want to override this to provide more details on the timeout.
|
107
|
-
def command_timeout_error_message
|
108
|
-
<<-EOM
|
109
|
-
|
110
|
-
Command timed out:
|
111
|
-
#{cmd}
|
112
|
-
|
113
|
-
EOM
|
114
|
-
end
|
115
|
-
|
116
|
-
# Runs a docker command. Does not raise exception on non-zero exit code.
|
117
|
-
def docker_cmd(cmd, timeout = new_resource.cmd_timeout)
|
118
|
-
execute_cmd('docker ' + cmd, timeout)
|
119
|
-
end
|
120
|
-
|
121
|
-
# Executes the given command with the specified timeout. Does not raise an
|
122
|
-
# exception on a non-zero exit code.
|
123
|
-
def execute_cmd(cmd, timeout = new_resource.cmd_timeout)
|
124
|
-
Chef::Log.debug('Executing: ' + cmd)
|
125
|
-
begin
|
126
|
-
shell_out(cmd, :timeout => timeout)
|
127
|
-
rescue Mixlib::ShellOut::CommandTimeout
|
128
|
-
raise CommandTimeout, command_timeout_error_message(cmd)
|
129
|
-
end
|
130
|
-
end
|
131
|
-
|
132
|
-
# Executes the given docker command with the specified timeout. Raises an
|
133
|
-
# exception if the command returns a non-zero exit code.
|
134
|
-
def docker_cmd!(cmd, timeout = new_resource.cmd_timeout)
|
135
|
-
execute_cmd!('docker ' + cmd, timeout)
|
136
|
-
end
|
137
|
-
|
138
|
-
# Executes the given command with the specified timeout. Raises an
|
139
|
-
# exception if the command returns a non-zero exit code.
|
140
|
-
def execute_cmd!(cmd, timeout = new_resource.cmd_timeout)
|
141
|
-
cmd = execute_cmd(cmd, timeout)
|
142
|
-
cmd.error!
|
143
|
-
cmd
|
144
|
-
end
|
145
|
-
end
|
146
|
-
end
|
@@ -1,15 +0,0 @@
|
|
1
|
-
require 'chef_metal_docker/helpers'
|
2
|
-
require 'chef_metal_docker/helpers/container/actions'
|
3
|
-
require 'chef_metal_docker/helpers/container/helpers'
|
4
|
-
|
5
|
-
module ChefMetalDocker
|
6
|
-
module Helpers
|
7
|
-
module Container
|
8
|
-
|
9
|
-
include ChefMetalDocker::Helpers
|
10
|
-
include ChefMetalDocker::Helpers::Container::Helpers
|
11
|
-
include ChefMetalDocker::Helpers::Container::Actions
|
12
|
-
|
13
|
-
end
|
14
|
-
end
|
15
|
-
end
|
@@ -1,313 +0,0 @@
|
|
1
|
-
module ChefMetalDocker
|
2
|
-
module Helpers
|
3
|
-
module Container
|
4
|
-
# This is a collection of helper methods that are used to trigger actions in
|
5
|
-
# the LWRPs. By putting them in a separate file we can a) keep the LWRPs cleaner
|
6
|
-
# and b) unit test them!
|
7
|
-
module Actions
|
8
|
-
|
9
|
-
def commit
|
10
|
-
commit_args = cli_args(
|
11
|
-
'author' => new_resource.author,
|
12
|
-
'message' => new_resource.message,
|
13
|
-
'run' => new_resource.run
|
14
|
-
)
|
15
|
-
commit_end_args = ''
|
16
|
-
|
17
|
-
if new_resource.repository
|
18
|
-
commit_end_args = new_resource.repository
|
19
|
-
commit_end_args += ":#{new_resource.tag}" if new_resource.tag
|
20
|
-
end
|
21
|
-
|
22
|
-
docker_cmd!("commit #{commit_args} #{current_resource.id} #{commit_end_args}")
|
23
|
-
end
|
24
|
-
|
25
|
-
def cp
|
26
|
-
docker_cmd!("cp #{current_resource.id}:#{new_resource.source} #{new_resource.destination}")
|
27
|
-
end
|
28
|
-
|
29
|
-
def export
|
30
|
-
docker_cmd!("export #{current_resource.id} > #{new_resource.destination}")
|
31
|
-
end
|
32
|
-
|
33
|
-
def kill
|
34
|
-
if service?
|
35
|
-
service_stop
|
36
|
-
else
|
37
|
-
docker_cmd!("kill #{current_resource.id}")
|
38
|
-
end
|
39
|
-
end
|
40
|
-
|
41
|
-
def remove
|
42
|
-
rm_args = cli_args(
|
43
|
-
'force' => new_resource.force,
|
44
|
-
'link' => new_resource.link
|
45
|
-
)
|
46
|
-
docker_cmd!("rm #{rm_args} #{current_resource.id}")
|
47
|
-
service_remove if service?
|
48
|
-
end
|
49
|
-
|
50
|
-
def redeploy
|
51
|
-
stop if running?
|
52
|
-
remove if exists?
|
53
|
-
run
|
54
|
-
end
|
55
|
-
|
56
|
-
def restart
|
57
|
-
if service?
|
58
|
-
service_restart
|
59
|
-
else
|
60
|
-
docker_cmd!("restart #{current_resource.id}")
|
61
|
-
end
|
62
|
-
end
|
63
|
-
|
64
|
-
# rubocop:disable MethodLength
|
65
|
-
def run
|
66
|
-
run_args = cli_args(
|
67
|
-
'cpu-shares' => new_resource.cpu_shares,
|
68
|
-
'cidfile' => cidfile,
|
69
|
-
'detach' => new_resource.detach,
|
70
|
-
'dns' => Array(new_resource.dns),
|
71
|
-
'dns-search' => Array(new_resource.dns_search),
|
72
|
-
'env' => Array(new_resource.env),
|
73
|
-
'entrypoint' => new_resource.entrypoint,
|
74
|
-
'expose' => Array(new_resource.expose),
|
75
|
-
'hostname' => new_resource.hostname,
|
76
|
-
'interactive' => new_resource.stdin,
|
77
|
-
'label' => new_resource.label,
|
78
|
-
'link' => Array(new_resource.link),
|
79
|
-
'lxc-conf' => Array(new_resource.lxc_conf),
|
80
|
-
'memory' => new_resource.memory,
|
81
|
-
'networking' => new_resource.networking,
|
82
|
-
'name' => container_name,
|
83
|
-
'opt' => Array(new_resource.opt),
|
84
|
-
'publish' => Array(port),
|
85
|
-
'publish-all' => new_resource.publish_exposed_ports,
|
86
|
-
'privileged' => new_resource.privileged,
|
87
|
-
'rm' => new_resource.remove_automatically,
|
88
|
-
'tty' => new_resource.tty,
|
89
|
-
'user' => new_resource.user,
|
90
|
-
'volume' => Array(new_resource.volume),
|
91
|
-
'volumes-from' => new_resource.volumes_from,
|
92
|
-
'workdir' => new_resource.working_directory
|
93
|
-
)
|
94
|
-
dr = docker_cmd!("run #{run_args} #{new_resource.image} #{new_resource.command}")
|
95
|
-
dr.error!
|
96
|
-
new_resource.id(dr.stdout.chomp)
|
97
|
-
service_create if service?
|
98
|
-
end
|
99
|
-
# rubocop:enable MethodLength
|
100
|
-
|
101
|
-
def service_action(actions)
|
102
|
-
if new_resource.init_type == 'runit'
|
103
|
-
runit_service service_name do
|
104
|
-
run_template_name 'docker-container'
|
105
|
-
action actions
|
106
|
-
end
|
107
|
-
else
|
108
|
-
service service_name do
|
109
|
-
case new_resource.init_type
|
110
|
-
when 'systemd'
|
111
|
-
provider Chef::Provider::Service::Systemd
|
112
|
-
when 'upstart'
|
113
|
-
provider Chef::Provider::Service::Upstart
|
114
|
-
end
|
115
|
-
supports :status => true, :restart => true, :reload => true
|
116
|
-
action actions
|
117
|
-
end
|
118
|
-
end
|
119
|
-
end
|
120
|
-
|
121
|
-
def service_create
|
122
|
-
case new_resource.init_type
|
123
|
-
when 'runit'
|
124
|
-
service_create_runit
|
125
|
-
when 'systemd'
|
126
|
-
service_create_systemd
|
127
|
-
when 'sysv'
|
128
|
-
service_create_sysv
|
129
|
-
when 'upstart'
|
130
|
-
service_create_upstart
|
131
|
-
end
|
132
|
-
end
|
133
|
-
|
134
|
-
def service_create_runit
|
135
|
-
runit_service service_name do
|
136
|
-
cookbook new_resource.cookbook
|
137
|
-
default_logger true
|
138
|
-
options(
|
139
|
-
'service_name' => service_name
|
140
|
-
)
|
141
|
-
run_template_name service_template
|
142
|
-
end
|
143
|
-
end
|
144
|
-
|
145
|
-
def service_create_systemd
|
146
|
-
template "/usr/lib/systemd/system/#{service_name}.socket" do
|
147
|
-
if new_resource.socket_template.nil?
|
148
|
-
source 'docker-container.socket.erb'
|
149
|
-
else
|
150
|
-
source new_resource.socket_template
|
151
|
-
end
|
152
|
-
cookbook new_resource.cookbook
|
153
|
-
mode '0644'
|
154
|
-
owner 'root'
|
155
|
-
group 'root'
|
156
|
-
variables(
|
157
|
-
:service_name => service_name,
|
158
|
-
:sockets => sockets
|
159
|
-
)
|
160
|
-
not_if port.empty?
|
161
|
-
end
|
162
|
-
|
163
|
-
template "/usr/lib/systemd/system/#{service_name}.service" do
|
164
|
-
source service_template
|
165
|
-
cookbook new_resource.cookbook
|
166
|
-
mode '0644'
|
167
|
-
owner 'root'
|
168
|
-
group 'root'
|
169
|
-
variables(
|
170
|
-
:cmd_timeout => new_resource.cmd_timeout,
|
171
|
-
:service_name => service_name
|
172
|
-
)
|
173
|
-
end
|
174
|
-
|
175
|
-
service_action([:start, :enable])
|
176
|
-
end
|
177
|
-
|
178
|
-
def service_create_sysv
|
179
|
-
template "/etc/init.d/#{service_name}" do
|
180
|
-
source service_template
|
181
|
-
cookbook new_resource.cookbook
|
182
|
-
mode '0755'
|
183
|
-
owner 'root'
|
184
|
-
group 'root'
|
185
|
-
variables(
|
186
|
-
:cmd_timeout => new_resource.cmd_timeout,
|
187
|
-
:service_name => service_name
|
188
|
-
)
|
189
|
-
end
|
190
|
-
|
191
|
-
service_action([:start, :enable])
|
192
|
-
end
|
193
|
-
|
194
|
-
def service_create_upstart
|
195
|
-
# The upstart init script requires inotifywait, which is in inotify-tools
|
196
|
-
package 'inotify-tools'
|
197
|
-
|
198
|
-
template "/etc/init/#{service_name}.conf" do
|
199
|
-
source service_template
|
200
|
-
cookbook new_resource.cookbook
|
201
|
-
mode '0600'
|
202
|
-
owner 'root'
|
203
|
-
group 'root'
|
204
|
-
variables(
|
205
|
-
:cmd_timeout => new_resource.cmd_timeout,
|
206
|
-
:service_name => service_name
|
207
|
-
)
|
208
|
-
end
|
209
|
-
|
210
|
-
service_action([:start, :enable])
|
211
|
-
end
|
212
|
-
|
213
|
-
def service_remove
|
214
|
-
case new_resource.init_type
|
215
|
-
when 'runit'
|
216
|
-
service_remove_runit
|
217
|
-
when 'systemd'
|
218
|
-
service_remove_systemd
|
219
|
-
when 'sysv'
|
220
|
-
service_remove_sysv
|
221
|
-
when 'upstart'
|
222
|
-
service_remove_upstart
|
223
|
-
end
|
224
|
-
end
|
225
|
-
|
226
|
-
def service_remove_runit
|
227
|
-
runit_service service_name do
|
228
|
-
action :disable
|
229
|
-
end
|
230
|
-
end
|
231
|
-
|
232
|
-
def service_remove_systemd
|
233
|
-
service_action([:stop, :disable])
|
234
|
-
|
235
|
-
%w(service socket).each do |f|
|
236
|
-
file "/usr/lib/systemd/system/#{service_name}.#{f}" do
|
237
|
-
action :delete
|
238
|
-
end
|
239
|
-
end
|
240
|
-
end
|
241
|
-
|
242
|
-
def service_remove_sysv
|
243
|
-
service_action([:stop, :disable])
|
244
|
-
|
245
|
-
file "/etc/init.d/#{service_name}" do
|
246
|
-
action :delete
|
247
|
-
end
|
248
|
-
end
|
249
|
-
|
250
|
-
def service_remove_upstart
|
251
|
-
service_action([:stop, :disable])
|
252
|
-
|
253
|
-
file "/etc/init/#{service_name}" do
|
254
|
-
action :delete
|
255
|
-
end
|
256
|
-
end
|
257
|
-
|
258
|
-
def service_restart
|
259
|
-
service_action([:restart])
|
260
|
-
end
|
261
|
-
|
262
|
-
def service_start
|
263
|
-
service_action([:start])
|
264
|
-
end
|
265
|
-
|
266
|
-
def service_stop
|
267
|
-
service_action([:stop])
|
268
|
-
end
|
269
|
-
|
270
|
-
def service_template
|
271
|
-
return new_resource.init_template unless new_resource.init_template.nil?
|
272
|
-
case new_resource.init_type
|
273
|
-
when 'runit'
|
274
|
-
'docker-container'
|
275
|
-
when 'systemd'
|
276
|
-
'docker-container.service.erb'
|
277
|
-
when 'upstart'
|
278
|
-
'docker-container.conf.erb'
|
279
|
-
when 'sysv'
|
280
|
-
'docker-container.sysv.erb'
|
281
|
-
end
|
282
|
-
end
|
283
|
-
|
284
|
-
def start
|
285
|
-
start_args = cli_args(
|
286
|
-
'attach' => new_resource.attach,
|
287
|
-
'interactive' => new_resource.stdin
|
288
|
-
)
|
289
|
-
if service?
|
290
|
-
service_create
|
291
|
-
else
|
292
|
-
docker_cmd!("start #{start_args} #{current_resource.id}")
|
293
|
-
end
|
294
|
-
end
|
295
|
-
|
296
|
-
def stop
|
297
|
-
stop_args = cli_args(
|
298
|
-
'time' => new_resource.cmd_timeout
|
299
|
-
)
|
300
|
-
if service?
|
301
|
-
service_stop
|
302
|
-
else
|
303
|
-
docker_cmd!("stop #{stop_args} #{current_resource.id}", (new_resource.cmd_timeout + 15))
|
304
|
-
end
|
305
|
-
end
|
306
|
-
|
307
|
-
def wait
|
308
|
-
docker_cmd!("wait #{current_resource.id}")
|
309
|
-
end
|
310
|
-
end
|
311
|
-
end
|
312
|
-
end
|
313
|
-
end
|