chef-provisioning-docker 0.11.0 → 1.0.0.beta.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +5 -5
- data/Gemfile +3 -0
- data/README.md +51 -62
- data/chef-provisioning-docker.gemspec +4 -4
- data/lib/chef/provisioning/docker_driver/docker_container_machine.rb +13 -199
- data/lib/chef/provisioning/docker_driver/docker_transport.rb +21 -43
- data/lib/chef/provisioning/docker_driver/driver.rb +167 -76
- data/lib/chef/provisioning/docker_driver/version.rb +1 -1
- data/lib/chef/provisioning/driver_init/docker.rb +1 -1
- metadata +14 -27
- data/lib/chef/provisioning/docker_driver/chef_zero_http_proxy.rb +0 -95
- data/lib/chef/provisioning/docker_driver/docker_run_options.rb +0 -593
@@ -28,10 +28,6 @@ module DockerDriver
|
|
28
28
|
Driver.new(driver_url, config)
|
29
29
|
end
|
30
30
|
|
31
|
-
def driver_url
|
32
|
-
"docker:#{Docker.url}"
|
33
|
-
end
|
34
|
-
|
35
31
|
def initialize(driver_url, config)
|
36
32
|
super
|
37
33
|
url = Driver.connection_url(driver_url)
|
@@ -41,14 +37,10 @@ module DockerDriver
|
|
41
37
|
# to be set for command-line utilities
|
42
38
|
ENV['DOCKER_HOST'] = url
|
43
39
|
Chef::Log.debug("Setting Docker URL to #{url}")
|
40
|
+
Docker.url = url
|
44
41
|
end
|
45
42
|
|
46
|
-
|
47
|
-
Docker.logger = Chef::Log
|
48
|
-
options = Docker.options.dup || {}
|
49
|
-
options.merge!(read_timeout: 600)
|
50
|
-
options.merge!(config[:docker_connection].hash_dup) if config && config[:docker_connection]
|
51
|
-
@connection = Docker::Connection.new(url || Docker.url, options)
|
43
|
+
@connection = Docker.connection
|
52
44
|
end
|
53
45
|
|
54
46
|
def self.canonicalize_url(driver_url, config)
|
@@ -83,8 +75,6 @@ module DockerDriver
|
|
83
75
|
action_handler,
|
84
76
|
machine_spec
|
85
77
|
)
|
86
|
-
|
87
|
-
# Grab options from existing machine (TODO seems wrong) and set the machine_spec to that
|
88
78
|
docker_options = machine_options[:docker_options]
|
89
79
|
container_id = nil
|
90
80
|
image_id = machine_options[:image_id]
|
@@ -94,6 +84,7 @@ module DockerDriver
|
|
94
84
|
image_id ||= machine_spec.reference['image_id']
|
95
85
|
docker_options ||= machine_spec.reference['docker_options']
|
96
86
|
end
|
87
|
+
|
97
88
|
container_name ||= machine_spec.name
|
98
89
|
machine_spec.reference = {
|
99
90
|
'driver_url' => driver_url,
|
@@ -105,66 +96,125 @@ module DockerDriver
|
|
105
96
|
'docker_options' => stringize_keys(docker_options),
|
106
97
|
'container_id' => container_id
|
107
98
|
}
|
99
|
+
build_container(machine_spec, docker_options)
|
108
100
|
end
|
109
101
|
|
110
102
|
def ready_machine(action_handler, machine_spec, machine_options)
|
103
|
+
start_machine(action_handler, machine_spec, machine_options)
|
111
104
|
machine_for(machine_spec, machine_options)
|
112
105
|
end
|
113
106
|
|
114
|
-
def
|
107
|
+
def build_container(machine_spec, docker_options)
|
115
108
|
container = container_for(machine_spec)
|
116
|
-
|
117
|
-
|
118
|
-
|
109
|
+
return container unless container.nil?
|
110
|
+
|
111
|
+
image = find_image(machine_spec) ||
|
112
|
+
build_image(machine_spec, docker_options)
|
113
|
+
|
114
|
+
args = [
|
115
|
+
'docker',
|
116
|
+
'run',
|
117
|
+
'--name',
|
118
|
+
machine_spec.reference['container_name'],
|
119
|
+
'--detach'
|
120
|
+
]
|
121
|
+
|
122
|
+
if docker_options[:keep_stdin_open]
|
123
|
+
args << '-i'
|
124
|
+
end
|
125
|
+
|
126
|
+
# We create the initial container with --net host so it can access things
|
127
|
+
# while it converges. When the final container starts, it will have its
|
128
|
+
# normal network.
|
129
|
+
args << '--net'
|
130
|
+
args << 'host'
|
131
|
+
|
132
|
+
if docker_options[:env]
|
133
|
+
docker_options[:env].each do |key, value|
|
134
|
+
args << '-e'
|
135
|
+
args << "#{key}=#{value}"
|
119
136
|
end
|
120
137
|
end
|
121
|
-
end
|
122
138
|
|
123
|
-
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
139
|
+
if docker_options[:ports]
|
140
|
+
docker_options[:ports].each do |portnum|
|
141
|
+
args << '-p'
|
142
|
+
args << "#{portnum}"
|
143
|
+
end
|
144
|
+
end
|
128
145
|
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
action_handler.perform_action "stop and destroy container #{machine_spec.name}" do
|
134
|
-
container.stop
|
135
|
-
container.delete
|
146
|
+
if docker_options[:volumes]
|
147
|
+
docker_options[:volumes].each do |volume|
|
148
|
+
args << '-v'
|
149
|
+
args << "#{volume}"
|
136
150
|
end
|
137
151
|
end
|
138
|
-
end
|
139
152
|
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
container.stop!
|
153
|
+
if docker_options[:dns]
|
154
|
+
docker_options[:dns].each do |entry|
|
155
|
+
args << '--dns'
|
156
|
+
args << "#{entry}"
|
145
157
|
end
|
146
158
|
end
|
159
|
+
|
160
|
+
if docker_options[:dns_search]
|
161
|
+
args << '--dns-search'
|
162
|
+
args << "#{docker_options[:dns_search]}"
|
163
|
+
end
|
164
|
+
|
165
|
+
args << image.id
|
166
|
+
args += Shellwords.split("/bin/sh -c 'while true;do sleep 1000; done'")
|
167
|
+
|
168
|
+
cmdstr = Shellwords.join(args)
|
169
|
+
Chef::Log.debug("Executing #{cmdstr}")
|
170
|
+
|
171
|
+
cmd = Mixlib::ShellOut.new(cmdstr)
|
172
|
+
cmd.run_command
|
173
|
+
|
174
|
+
container = Docker::Container.get(machine_spec.reference['container_name'])
|
175
|
+
|
176
|
+
Chef::Log.debug("Container id: #{container.id}")
|
177
|
+
machine_spec.reference['container_id'] = container.id
|
178
|
+
container
|
147
179
|
end
|
148
180
|
|
149
|
-
|
150
|
-
|
151
|
-
|
181
|
+
def build_image(machine_spec, docker_options)
|
182
|
+
base_image = docker_options[:base_image] || base_image_for(machine_spec)
|
183
|
+
source_name = base_image[:name]
|
184
|
+
source_repository = base_image[:repository]
|
185
|
+
source_tag = base_image[:tag]
|
152
186
|
|
153
|
-
|
154
|
-
|
187
|
+
target_tag = machine_spec.reference['container_name']
|
188
|
+
|
189
|
+
image = Docker::Image.create(
|
190
|
+
'fromImage' => source_name,
|
191
|
+
'repo' => source_repository,
|
192
|
+
'tag' => source_tag
|
193
|
+
)
|
194
|
+
|
195
|
+
Chef::Log.debug("Allocated #{image}")
|
196
|
+
image.tag('repo' => 'chef', 'tag' => target_tag)
|
197
|
+
Chef::Log.debug("Tagged image #{image}")
|
198
|
+
|
199
|
+
machine_spec.reference['image_id'] = image.id
|
200
|
+
image
|
201
|
+
end
|
155
202
|
|
203
|
+
def allocate_image(action_handler, image_spec, image_options, machine_spec, machine_options)
|
156
204
|
# Set machine options on the image to match our newly created image
|
157
205
|
image_spec.reference = {
|
158
206
|
'driver_url' => driver_url,
|
159
207
|
'driver_version' => Chef::Provisioning::DockerDriver::VERSION,
|
160
208
|
'allocated_at' => Time.now.to_i,
|
161
|
-
|
162
|
-
|
163
|
-
|
164
|
-
|
209
|
+
:docker_options => {
|
210
|
+
:base_image => {
|
211
|
+
:name => "chef_#{image_spec.name}",
|
212
|
+
:repository => 'chef',
|
213
|
+
:tag => image_spec.name
|
214
|
+
},
|
215
|
+
:from_image => true
|
165
216
|
}
|
166
217
|
}
|
167
|
-
|
168
218
|
# Workaround for chef/chef-provisioning-docker#37
|
169
219
|
machine_spec.attrs[:keep_image] = true
|
170
220
|
end
|
@@ -175,33 +225,66 @@ module DockerDriver
|
|
175
225
|
|
176
226
|
# workaround for https://github.com/chef/chef-provisioning/issues/358.
|
177
227
|
def destroy_image(action_handler, image_spec, image_options, machine_options={})
|
178
|
-
image =
|
228
|
+
image = Docker::Image.get("chef:#{image_spec.name}")
|
179
229
|
image.delete unless image.nil?
|
180
230
|
end
|
181
231
|
|
182
|
-
|
232
|
+
# Connect to machine without acquiring it
|
233
|
+
def connect_to_machine(machine_spec, machine_options)
|
234
|
+
Chef::Log.debug('Connect to machine')
|
235
|
+
machine_for(machine_spec, machine_options)
|
236
|
+
end
|
183
237
|
|
184
|
-
def
|
238
|
+
def destroy_machine(action_handler, machine_spec, machine_options)
|
185
239
|
container = container_for(machine_spec)
|
186
|
-
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
191
|
-
|
240
|
+
if container
|
241
|
+
Chef::Log.debug("Destroying container: #{container.id}")
|
242
|
+
container.delete(:force => true)
|
243
|
+
end
|
244
|
+
|
245
|
+
if !machine_spec.attrs[:keep_image] && !machine_options[:keep_image]
|
246
|
+
image = find_image(machine_spec)
|
247
|
+
Chef::Log.debug("Destroying image: chef:#{image.id}")
|
248
|
+
image.delete
|
192
249
|
end
|
193
250
|
end
|
194
251
|
|
195
|
-
def
|
196
|
-
|
252
|
+
def stop_machine(action_handler, machine_spec, machine_options)
|
253
|
+
container = container_for(machine_spec)
|
254
|
+
return if container.nil?
|
255
|
+
|
256
|
+
container.stop if container.info['State']['Running']
|
197
257
|
end
|
198
258
|
|
199
|
-
def
|
200
|
-
|
201
|
-
|
202
|
-
|
203
|
-
|
204
|
-
|
259
|
+
def find_image(machine_spec)
|
260
|
+
image = nil
|
261
|
+
|
262
|
+
if machine_spec.reference['image_id']
|
263
|
+
begin
|
264
|
+
image = Docker::Image.get(machine_spec.reference['image_id'])
|
265
|
+
rescue Docker::Error::NotFoundError
|
266
|
+
end
|
267
|
+
end
|
268
|
+
|
269
|
+
if image.nil?
|
270
|
+
image_name = "chef:#{machine_spec.reference['container_name']}"
|
271
|
+
if machine_spec.from_image
|
272
|
+
base_image = base_image_for(machine_spec)
|
273
|
+
image_name = "#{base_image[:repository]}:#{base_image[:tag]}"
|
274
|
+
end
|
275
|
+
|
276
|
+
image = Docker::Image.all.select {
|
277
|
+
|i| i.info['RepoTags'].include? image_name
|
278
|
+
}.first
|
279
|
+
|
280
|
+
if machine_spec.from_image && image.nil?
|
281
|
+
raise "Unable to locate machine_image for #{image_name}"
|
282
|
+
end
|
283
|
+
end
|
284
|
+
|
285
|
+
machine_spec.reference['image_id'] = image.id if image
|
286
|
+
|
287
|
+
image
|
205
288
|
end
|
206
289
|
|
207
290
|
def from_image_from_action_handler(action_handler, machine_spec)
|
@@ -215,11 +298,22 @@ module DockerDriver
|
|
215
298
|
end
|
216
299
|
end
|
217
300
|
|
301
|
+
def driver_url
|
302
|
+
"docker:#{Docker.url}"
|
303
|
+
end
|
304
|
+
|
305
|
+
def start_machine(action_handler, machine_spec, machine_options)
|
306
|
+
container = container_for(machine_spec)
|
307
|
+
if container && !container.info['State']['Running']
|
308
|
+
container.start
|
309
|
+
end
|
310
|
+
end
|
311
|
+
|
218
312
|
def machine_for(machine_spec, machine_options)
|
219
313
|
Chef::Log.debug('machine_for...')
|
220
|
-
docker_options = machine_options[:docker_options] || Mash.from_hash(machine_spec.reference['docker_options']
|
314
|
+
docker_options = machine_options[:docker_options] || Mash.from_hash(machine_spec.reference['docker_options'])
|
221
315
|
|
222
|
-
container =
|
316
|
+
container = Docker::Container.get(machine_spec.reference['container_id'], @connection)
|
223
317
|
|
224
318
|
if machine_spec.from_image
|
225
319
|
convergence_strategy = Chef::Provisioning::ConvergenceStrategy::NoConverge.new({}, config)
|
@@ -234,31 +328,28 @@ module DockerDriver
|
|
234
328
|
machine_spec,
|
235
329
|
transport,
|
236
330
|
convergence_strategy,
|
237
|
-
@connection,
|
238
331
|
docker_options[:command]
|
239
332
|
)
|
240
333
|
end
|
241
334
|
|
242
335
|
def container_for(machine_spec)
|
336
|
+
container_id = machine_spec.reference['container_id']
|
243
337
|
begin
|
244
|
-
Docker::Container.get(
|
338
|
+
container = Docker::Container.get(container_id, @connection) if container_id
|
245
339
|
rescue Docker::Error::NotFoundError
|
246
340
|
end
|
247
341
|
end
|
248
342
|
|
249
|
-
def
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
end
|
343
|
+
def base_image_for(machine_spec)
|
344
|
+
Chef::Log.debug("Looking for image #{machine_spec.from_image}")
|
345
|
+
image_spec = machine_spec.managed_entry_store.get!(:machine_image, machine_spec.from_image)
|
346
|
+
Mash.new(image_spec.reference)[:docker_options][:base_image]
|
254
347
|
end
|
255
348
|
|
256
349
|
def stringize_keys(hash)
|
257
|
-
|
258
|
-
|
259
|
-
|
260
|
-
hash[k.to_s] = v
|
261
|
-
end
|
350
|
+
hash.each_with_object({}) do |(k,v),hash|
|
351
|
+
v = stringize_keys(v) if v.is_a?(Hash)
|
352
|
+
hash[k.to_s] = v
|
262
353
|
end
|
263
354
|
end
|
264
355
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: chef-provisioning-docker
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 1.0.0.beta.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Tom Duffield
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2016-03-11 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: chef
|
@@ -28,42 +28,30 @@ dependencies:
|
|
28
28
|
name: chef-provisioning
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
|
-
- - "
|
32
|
-
- !ruby/object:Gem::Version
|
33
|
-
version: '2.0'
|
34
|
-
- - "<"
|
31
|
+
- - "~>"
|
35
32
|
- !ruby/object:Gem::Version
|
36
|
-
version: '
|
33
|
+
version: '1.0'
|
37
34
|
type: :runtime
|
38
35
|
prerelease: false
|
39
36
|
version_requirements: !ruby/object:Gem::Requirement
|
40
37
|
requirements:
|
41
|
-
- - "
|
42
|
-
- !ruby/object:Gem::Version
|
43
|
-
version: '2.0'
|
44
|
-
- - "<"
|
38
|
+
- - "~>"
|
45
39
|
- !ruby/object:Gem::Version
|
46
|
-
version: '
|
40
|
+
version: '1.0'
|
47
41
|
- !ruby/object:Gem::Dependency
|
48
42
|
name: docker-api
|
49
43
|
requirement: !ruby/object:Gem::Requirement
|
50
44
|
requirements:
|
51
45
|
- - "~>"
|
52
46
|
- !ruby/object:Gem::Version
|
53
|
-
version: '1.
|
54
|
-
- - ">="
|
55
|
-
- !ruby/object:Gem::Version
|
56
|
-
version: 1.26.2
|
47
|
+
version: '1.25'
|
57
48
|
type: :runtime
|
58
49
|
prerelease: false
|
59
50
|
version_requirements: !ruby/object:Gem::Requirement
|
60
51
|
requirements:
|
61
52
|
- - "~>"
|
62
53
|
- !ruby/object:Gem::Version
|
63
|
-
version: '1.
|
64
|
-
- - ">="
|
65
|
-
- !ruby/object:Gem::Version
|
66
|
-
version: 1.26.2
|
54
|
+
version: '1.25'
|
67
55
|
- !ruby/object:Gem::Dependency
|
68
56
|
name: minitar
|
69
57
|
requirement: !ruby/object:Gem::Requirement
|
@@ -135,7 +123,7 @@ dependencies:
|
|
135
123
|
- !ruby/object:Gem::Version
|
136
124
|
version: '0'
|
137
125
|
description: Provisioner for creating Docker containers in Chef Provisioning.
|
138
|
-
email: tom@
|
126
|
+
email: tom@getchef.com
|
139
127
|
executables: []
|
140
128
|
extensions: []
|
141
129
|
extra_rdoc_files:
|
@@ -148,9 +136,7 @@ files:
|
|
148
136
|
- Rakefile
|
149
137
|
- chef-provisioning-docker.gemspec
|
150
138
|
- lib/chef/provisioning/docker_driver.rb
|
151
|
-
- lib/chef/provisioning/docker_driver/chef_zero_http_proxy.rb
|
152
139
|
- lib/chef/provisioning/docker_driver/docker_container_machine.rb
|
153
|
-
- lib/chef/provisioning/docker_driver/docker_run_options.rb
|
154
140
|
- lib/chef/provisioning/docker_driver/docker_transport.rb
|
155
141
|
- lib/chef/provisioning/docker_driver/driver.rb
|
156
142
|
- lib/chef/provisioning/docker_driver/version.rb
|
@@ -158,7 +144,7 @@ files:
|
|
158
144
|
- spec/docker_support.rb
|
159
145
|
- spec/integration/primitives_spec.rb
|
160
146
|
- spec/spec_helper.rb
|
161
|
-
homepage: https://github.com/
|
147
|
+
homepage: https://github.com/opscode/chef-provisioning-docker
|
162
148
|
licenses: []
|
163
149
|
metadata: {}
|
164
150
|
post_install_message:
|
@@ -172,13 +158,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
172
158
|
version: '0'
|
173
159
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
174
160
|
requirements:
|
175
|
-
- - "
|
161
|
+
- - ">"
|
176
162
|
- !ruby/object:Gem::Version
|
177
|
-
version:
|
163
|
+
version: 1.3.1
|
178
164
|
requirements: []
|
179
165
|
rubyforge_project:
|
180
|
-
rubygems_version: 2.
|
166
|
+
rubygems_version: 2.6.1
|
181
167
|
signing_key:
|
182
168
|
specification_version: 4
|
183
169
|
summary: Provisioner for creating Docker containers in Chef Provisioning.
|
184
170
|
test_files: []
|
171
|
+
has_rdoc:
|