chef-metal-docker 0.2 → 0.4.1

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.
@@ -1,9 +0,0 @@
1
- require 'chef_metal/machine/unix_machine'
2
-
3
- module ChefMetalDocker
4
- class DockerUnixMachine < ChefMetal::Machine::UnixMachine
5
- def execute_always(command, options = {})
6
- transport.execute(command, { :read_only => true }.merge(options))
7
- end
8
- end
9
- end
@@ -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