dockistrano 0.0.5 → 0.0.6

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 158d3061ea38673eaf98d564749fc35d959d304b
4
- data.tar.gz: 6c106bbf2921d25169e3c1b0c2ed8e783755fdbd
3
+ metadata.gz: 91762ce1db149fa71eab678c80fbc5c7e60c5cbd
4
+ data.tar.gz: 28d8236dcd51b0d5235fb3ef62252514064d07c2
5
5
  SHA512:
6
- metadata.gz: 9d77e9bfa8f228b922b55d0e874cbd13fecd18a6a9c8ca7c80f25653981615984cd0d3c212afa4fe0ddb93b0181ecba6b2314986103dc990f23186957dbb8063
7
- data.tar.gz: 6664a8a469961282bcccf1dacf140cc7e68de7b699011e324cad4d89e1fc2d825c0319ee81f66dace7f1bc1783f915c9a7f918f631006e9a28e16b51c859bcae
6
+ metadata.gz: eec347010dcdec6e2db6ba72799be478aa41dff197cb2360849d20ad66a1ca205af2f817ade16b7369d5fbb3f193f89005a3ff1900455e23a18c879845f66196
7
+ data.tar.gz: a52f46d46ef9510b6a6a8dd7c23db0a67531958dc9f9e0731c14a73d7b795a53e4a358cf016892692c28de1d642430e7847fad54ff6bf252f2cc0c1e0ec3dbd6
data/Guardfile CHANGED
@@ -7,3 +7,8 @@ guard :rspec do
7
7
  watch('spec/spec_helper.rb') { "spec" }
8
8
  end
9
9
 
10
+ guard :shell do
11
+ watch %r{^lib\/(.+)\.rb$} do |m|
12
+ `rake install`
13
+ end
14
+ end
data/dockistrano.gemspec CHANGED
@@ -27,6 +27,7 @@ Gem::Specification.new do |spec|
27
27
  spec.add_development_dependency "rake"
28
28
  spec.add_development_dependency "guard"
29
29
  spec.add_development_dependency "guard-rspec"
30
+ spec.add_development_dependency "guard-shell"
30
31
  spec.add_development_dependency "terminal-notifier-guard"
31
32
  spec.add_development_dependency "webmock"
32
33
  end
@@ -3,14 +3,7 @@ require "dotenv"
3
3
  Dotenv.load(".dockistrano")
4
4
  ENV["DOCKISTRANO_ENVIRONMENT"] ||= "default"
5
5
  ENV["DOCKER_HOST_IP"] ||= "127.0.0.1"
6
- ENV["DOCKER_BINARY"] ||= begin
7
- if RUBY_PLATFORM =~ /darwin|mac os/
8
- bin_dir = File.expand_path(File.dirname(__FILE__) + "/../../bin")
9
- "#{bin_dir}/docker"
10
- else
11
- "docker"
12
- end
13
- end
6
+ ENV["DOCKER_BINARY"] ||= "docker"
14
7
 
15
8
  module Dockistrano
16
9
 
@@ -145,6 +138,7 @@ module Dockistrano
145
138
  def stop(id=nil)
146
139
  if id
147
140
  Docker.stop(id)
141
+ Docker.remove_container(id)
148
142
  say_status("Stopped", id, :green)
149
143
  else
150
144
  current_service.stop
@@ -186,16 +180,28 @@ module Dockistrano
186
180
 
187
181
  desc "logs [NAME]", "Prints the logs for the service"
188
182
  def logs(name=nil)
189
- service = name ? current_service.backing_services[name] : current_service
183
+ if name and current_service.backing_services[name]
184
+ service = current_service.backing_services[name]
185
+ command_name = nil
186
+ else
187
+ service = current_service
188
+ command_name = name
189
+ end
190
+
190
191
  if service.running?
191
192
  say "Container #{service.image_name} running, attaching to output", :blue
192
- service.attach
193
+ service.attach(command_name)
193
194
  else
194
195
  say "Container #{service.image_name} stopped, printing logs of last run", :blue
195
- service.logs
196
+ service.logs(command_name)
196
197
  end
197
198
  end
198
199
 
200
+ desc "version", "Prints version information"
201
+ def version
202
+ say "Dockistrano version: #{Dockistrano::VERSION}"
203
+ end
204
+
199
205
  def method_missing(*args)
200
206
  command = args[0]
201
207
  if command and current_service.config["aliases"] and current_service.config["aliases"][command.to_s]
@@ -95,6 +95,10 @@ module Dockistrano
95
95
  execute(["attach", id], :stream)
96
96
  end
97
97
 
98
+ def self.remove_container(name)
99
+ execute(["rm", name])
100
+ end
101
+
98
102
  def self.clean
99
103
  Dockistrano::CommandLine.command_with_stream("#{docker_command} rmi $(#{docker_command} images -a | grep \"^<none>\" | awk '{print $3}')")
100
104
  Dockistrano::CommandLine.command_with_stream("#{docker_command} rm $(#{docker_command} ps -a -q)")
@@ -115,18 +115,13 @@ module Dockistrano
115
115
 
116
116
  # Stops the container of the current service
117
117
  def stop
118
- if !host.nil?
119
- hipache = Hipache.new(ENV['DOCKER_HOST_IP'])
120
- if host.kind_of?(String)
121
- hipache.unregister(image_name, host, ip_address, port)
122
- else
123
- host.each do |hostname, port|
124
- hipache.unregister(image_name, hostname, ip_address, port)
125
- end
126
- end
118
+ update_hipache(false)
119
+ Docker.stop(image_name)
120
+ Docker.remove_container(image_name)
121
+ additional_commands.each do |name, _|
122
+ Docker.stop("#{image_name}_#{name}")
123
+ Docker.remove_container("#{image_name}_#{name}")
127
124
  end
128
-
129
- Docker.stop_all_containers_from_image(full_image_name)
130
125
  end
131
126
 
132
127
  # Returns if this service is running
@@ -151,6 +146,19 @@ module Dockistrano
151
146
  Dockistrano::Docker.push("#{registry}/#{image_name}", tag)
152
147
  end
153
148
 
149
+ def update_hipache(server_up=true)
150
+ if !host.nil?
151
+ hipache = Hipache.new(ENV['DOCKER_HOST_IP'])
152
+ host.each do |hostname, port|
153
+ if server_up
154
+ hipache.register(image_name, hostname, ip_address_for_port(port), port)
155
+ else
156
+ hipache.unregister(image_name, hostname, ip_address_for_port(port), port)
157
+ end
158
+ end
159
+ end
160
+ end
161
+
154
162
  # Starts this service
155
163
  def start(options={})
156
164
  ensure_backing_services
@@ -159,39 +167,29 @@ module Dockistrano
159
167
 
160
168
  if additional_commands.any?
161
169
  additional_commands.each do |name, command|
162
- Docker.run(full_image_name, e: environment, v: volumes, p: ports, d: true, command: command)
170
+ Docker.run(full_image_name, name: "#{image_name}_#{name}", link: link_backing_services, e: environment, v: volumes, d: true, command: command)
163
171
  end
164
172
  end
165
173
 
166
- Docker.run(full_image_name, e: environment, v: volumes, p: ports, d: true)
167
-
168
- if !host.nil?
169
- hipache = Hipache.new(ENV['DOCKER_HOST_IP'])
170
- if host.kind_of?(String)
171
- hipache.register(image_name, host, ip_address, port)
172
- else
173
- host.each do |hostname, port|
174
- hipache.register(image_name, hostname, ip_address, port)
175
- end
176
- end
177
- end
174
+ Docker.run(full_image_name, name: image_name, link: link_backing_services, e: environment, v: volumes, p: ports, d: true)
175
+ update_hipache(true)
178
176
  end
179
177
 
180
178
  # Runs a command in this container
181
179
  def run(command, options={})
182
- Docker.run(full_image_name_with_fallback, command: command, e: environment_variables, v: volumes, p: ports)
180
+ Docker.run(full_image_name_with_fallback, link: link_backing_services, command: command, e: environment_variables, v: volumes)
183
181
  end
184
182
 
185
183
  # Executes a command in this container
186
184
  def exec(command, options={})
187
185
  create_data_directories
188
- Docker.exec(full_image_name_with_fallback, command: command, e: environment_variables, v: volumes, p: ports)
186
+ Docker.exec(full_image_name_with_fallback, link: link_backing_services, command: command, e: environment_variables, v: volumes)
189
187
  end
190
188
 
191
189
  # Starts a console in the docker container
192
190
  def console(command, options={})
193
191
  create_data_directories
194
- Docker.console(full_image_name_with_fallback, command: command, e: environment_variables, v: volumes, p: ports)
192
+ Docker.console(full_image_name_with_fallback, link: link_backing_services, command: command, e: environment_variables, v: volumes)
195
193
  end
196
194
 
197
195
  # Lists all backing services for this service
@@ -205,6 +203,13 @@ module Dockistrano
205
203
  end
206
204
  end
207
205
 
206
+ # Returns an array of backing services to link
207
+ def link_backing_services
208
+ backing_services.collect { |name, service|
209
+ "#{service.image_name}:#{service.image_name}"
210
+ }
211
+ end
212
+
208
213
  # Returns an array of environment variables
209
214
  def environment_variables
210
215
  vars = {}
@@ -214,9 +219,6 @@ module Dockistrano
214
219
  end
215
220
 
216
221
  backing_services.each do |name, backing_service|
217
- vars["#{name.upcase}_IP"] = backing_service.ip_address
218
- vars["#{name.upcase}_PORT"] = backing_service.port
219
-
220
222
  backing_service.backing_service_env.each do |k,v|
221
223
  vars["#{name.upcase}_#{k.upcase}"] = v
222
224
  end
@@ -226,8 +228,10 @@ module Dockistrano
226
228
 
227
229
  vars.each do |key, value|
228
230
  vars.each do |replacement_key, replacement_value|
229
- unless vars[key].nil? or replacement_value.nil?
230
- vars[key] = vars[key].gsub('$'+replacement_key, replacement_value)
231
+ vars[key] = if vars[key].nil? or replacement_value.nil? or replacement_value.empty?
232
+ vars[key].gsub('$'+replacement_key, '$'+replacement_key)
233
+ else
234
+ vars[key].gsub('$'+replacement_key, replacement_value)
231
235
  end
232
236
  end
233
237
  end
@@ -244,7 +248,9 @@ module Dockistrano
244
248
  [].tap do |volumes|
245
249
  volumes << "/dockistrano/#{image_name.gsub("-", "_")}/data:/dockistrano/data"
246
250
  if mount_src and !mount_src.empty?
247
- volumes << "/dockistrano/#{image_name.gsub("-", "_")}/src:#{mount_src}"
251
+ mount_src.each do |host_src, container_src|
252
+ volumes << "#{host_src}:#{container_src}"
253
+ end
248
254
  end
249
255
  end
250
256
  end
@@ -281,24 +287,34 @@ module Dockistrano
281
287
  end
282
288
  end
283
289
 
284
- def ip_address
285
- container_settings["NetworkSettings"]["IPAddress"] if running?
286
- end
287
-
288
- def port
289
- container_settings["NetworkSettings"]["PortMapping"]["Tcp"].keys.first if running?
290
+ def ip_address_for_port(port)
291
+ container_settings["NetworkSettings"]["Ports"]["#{port}/tcp"].first["HostIp"] if running?
290
292
  end
291
293
 
292
294
  def ports
293
- (config["ports"] || {}).collect { |k,v| "#{k}:#{v}" }
295
+ (config["ports"] || {}).collect { |k,v|
296
+ if k.to_s.include?(":")
297
+ "#{k}:#{v}"
298
+ else
299
+ "172.17.42.1:#{k}:#{v}"
300
+ end
301
+ }
294
302
  end
295
303
 
296
- def attach
297
- Docker.attach(Docker.running_container_id(full_image_name))
304
+ def attach(name=nil)
305
+ if name
306
+ Docker.attach("#{image_name}_#{name}")
307
+ else
308
+ Docker.attach(image_name)
309
+ end
298
310
  end
299
311
 
300
- def logs
301
- Docker.logs(Docker.last_run_container_id(full_image_name))
312
+ def logs(name=nil)
313
+ if name
314
+ Docker.logs("#{image_name}_#{name}")
315
+ else
316
+ Docker.logs(image_name)
317
+ end
302
318
  end
303
319
 
304
320
  def create_data_directories
@@ -309,7 +325,7 @@ module Dockistrano
309
325
  command = "mkdir -p #{data_directories.collect { |dir| "/dockistrano/data/#{dir}"}.join(" ") }; "
310
326
  command += "chown #{image_user}:#{image_user} #{data_directories.collect { |dir| "/dockistrano/data/#{dir}"}.join(" ") }"
311
327
  bash_command = "/bin/bash -c '#{command}'"
312
- Docker.run(full_image_name_with_fallback, command: bash_command, v: volumes, e: environment_variables, u: "root")
328
+ Docker.run(full_image_name_with_fallback, command: bash_command, v: volumes, e: environment_variables, u: "root", rm: true)
313
329
  end
314
330
  end
315
331
 
@@ -76,7 +76,7 @@ module Dockistrano
76
76
  end
77
77
 
78
78
  def load_from_image
79
- raw_config = Docker.run(backing_service.full_image_name, command: "cat /dockistrano.yml")
79
+ raw_config = Docker.run(backing_service.full_image_name, command: "cat /dockistrano.yml", rm: true)
80
80
  if raw_config.empty? or raw_config.include?("No such file or directory")
81
81
  if raw_config.include?("failed to mount")
82
82
  raise HostDirectoriesMissing
@@ -1,3 +1,3 @@
1
1
  module Dockistrano
2
- VERSION = "0.0.5"
2
+ VERSION = "0.0.6"
3
3
  end
@@ -3,7 +3,7 @@ require 'spec_helper'
3
3
  describe Dockistrano::Cli do
4
4
 
5
5
  let(:service) { double(registry: "registry.provider.tld", image_name: "application", tag: "develop", volumes: [], backing_services: { "postgresql" => backing_service }, environment_variables: {}, newer_version_available?: false, stop: nil) }
6
- let(:backing_service) { double(full_image_name: "registry.provider.tld/postgresql:develop", image_name: "postgresql", running?: false, newer_version_available?: false, start: nil, stop: nil) }
6
+ let(:backing_service) { double(:backing_service, full_image_name: "registry.provider.tld/postgresql:develop", image_name: "postgresql", running?: false, newer_version_available?: false, start: nil, stop: nil) }
7
7
  let(:hipache) { double }
8
8
  let(:output) { capture(:stdout) { described_class.start(command) } }
9
9
 
@@ -187,6 +187,7 @@ describe Dockistrano::Cli do
187
187
 
188
188
  it "stops the container with the id" do
189
189
  expect(Dockistrano::Docker).to receive(:stop).with("123456789")
190
+ expect(Dockistrano::Docker).to receive(:remove_container).with("123456789")
190
191
  expect(output).to include("Stopped")
191
192
  end
192
193
  end
@@ -259,33 +260,49 @@ describe Dockistrano::Cli do
259
260
 
260
261
  it "attaches to the containers output when the container is running" do
261
262
  expect(service).to receive(:running?).and_return(true)
262
- expect(service).to receive(:attach)
263
+ expect(service).to receive(:attach).with(nil)
263
264
  expect(output).to include("Container application running, attaching to output")
264
265
  end
265
266
 
266
267
  it "prints the logs of the last run" do
267
268
  expect(service).to receive(:running?).and_return(false)
268
- expect(service).to receive(:logs)
269
+ expect(service).to receive(:logs).with(nil)
269
270
  expect(output).to include("Container application stopped, printing logs of last run")
270
271
  end
271
272
  end
272
273
 
273
- context "doc logs NAME" do
274
+ context "doc logs BACKING_SERVICE" do
274
275
  let(:command) { ["logs", "postgresql"] }
275
276
 
276
277
  it "attaches to the containers output when the container is running" do
277
278
  expect(backing_service).to receive(:running?).and_return(true)
278
- expect(backing_service).to receive(:attach)
279
+ expect(backing_service).to receive(:attach).with(nil)
279
280
  expect(output).to include("Container postgresql running, attaching to output")
280
281
  end
281
282
 
282
283
  it "prints the logs of the last run" do
283
284
  expect(backing_service).to receive(:running?).and_return(false)
284
- expect(backing_service).to receive(:logs)
285
+ expect(backing_service).to receive(:logs).with(nil)
285
286
  expect(output).to include("Container postgresql stopped, printing logs of last run")
286
287
  end
287
288
  end
288
289
 
290
+ context "doc logs ADDITIONAL_COMMAND" do
291
+ let(:command) { ["logs", "worker"] }
292
+
293
+ it "attaches to the containers output when the container is running" do
294
+ expect(service).to receive(:running?).and_return(true)
295
+ expect(service).to receive(:attach).with("worker")
296
+ expect(output).to include("Container application running, attaching to output")
297
+ end
298
+
299
+ it "prints the logs of the last run" do
300
+ expect(service).to receive(:running?).and_return(false)
301
+ expect(service).to receive(:logs).with("worker")
302
+ expect(output).to include("Container application stopped, printing logs of last run")
303
+ end
304
+ end
305
+
289
306
  context "doc ALIAS ARGUMENTS" do
290
307
  let(:command) { ["rspec", "spec/models/my_model_spec.rb"] }
291
308
 
@@ -187,6 +187,13 @@ describe Dockistrano::Docker do
187
187
  end
188
188
  end
189
189
 
190
+ context ".remove_container" do
191
+ it "removes the container" do
192
+ expect(subject).to receive(:execute).with(["rm", "application"])
193
+ subject.remove_container("application")
194
+ end
195
+ end
196
+
190
197
  context ".inspect_container" do
191
198
  it "returns information about the container" do
192
199
  stub_request(:get, 'http://127.0.0.1:4243/containers/123456789/json').to_return({
@@ -98,7 +98,7 @@ describe Dockistrano::ServiceDependency do
98
98
  end
99
99
 
100
100
  it "reads the configuration from the image and caches the configuration" do
101
- expect(Dockistrano::Docker).to receive(:run).with(backing_service.full_image_name, command: "cat /dockistrano.yml").and_return(raw_config = "---\ndefault:\n\tconfiguration: value")
101
+ expect(Dockistrano::Docker).to receive(:run).with(backing_service.full_image_name, command: "cat /dockistrano.yml", rm: true).and_return(raw_config = "---\ndefault:\n\tconfiguration: value")
102
102
 
103
103
  expect(FileUtils).to receive(:mkdir_p).with("tmp/configuration_cache")
104
104
  expect(File).to receive(:open).with("tmp/configuration_cache/#{backing_service.image_id}", "w+").and_return(file = double)
@@ -111,17 +111,17 @@ describe Dockistrano::ServiceDependency do
111
111
  end
112
112
 
113
113
  it "raises an error when host directories are missing" do
114
- expect(Dockistrano::Docker).to receive(:run).with(backing_service.full_image_name, command: "cat /dockistrano.yml").and_return("No such file or directory: failed to mount")
114
+ expect(Dockistrano::Docker).to receive(:run).with(backing_service.full_image_name, command: "cat /dockistrano.yml", rm: true).and_return("No such file or directory: failed to mount")
115
115
  expect { subject.load_from_image }.to raise_error(Dockistrano::ServiceDependency::HostDirectoriesMissing)
116
116
  end
117
117
 
118
118
  it "raises an error when the configuration is not found" do
119
- expect(Dockistrano::Docker).to receive(:run).with(backing_service.full_image_name, command: "cat /dockistrano.yml").and_return("No such file or directory: dockistrano.yml")
119
+ expect(Dockistrano::Docker).to receive(:run).with(backing_service.full_image_name, command: "cat /dockistrano.yml", rm: true).and_return("No such file or directory: dockistrano.yml")
120
120
  expect { subject.load_from_image }.to raise_error(Dockistrano::ServiceDependency::ContainerConfigurationMissing)
121
121
  end
122
122
 
123
123
  it "raises an error when the configuration is empty" do
124
- expect(Dockistrano::Docker).to receive(:run).with(backing_service.full_image_name, command: "cat /dockistrano.yml").and_return("")
124
+ expect(Dockistrano::Docker).to receive(:run).with(backing_service.full_image_name, command: "cat /dockistrano.yml", rm: true).and_return("")
125
125
  expect { subject.load_from_image }.to raise_error(Dockistrano::ServiceDependency::ContainerConfigurationMissing)
126
126
  end
127
127
  end
@@ -158,30 +158,31 @@ describe Dockistrano::Service do
158
158
  end
159
159
 
160
160
  context "#stop" do
161
- let(:hipache) { double }
162
-
163
161
  before do
164
- allow(Dockistrano::Docker).to receive(:stop_all_containers_from_image)
165
- allow(Dockistrano::Hipache).to receive(:new).and_return(hipache)
162
+ allow(Dockistrano::Docker).to receive(:stop)
163
+ allow(Dockistrano::Docker).to receive(:remove_container)
164
+ allow(subject).to receive(:additional_commands).and_return({ "worker" => "sidekiq" })
165
+ allow(subject).to receive(:update_hipache)
166
166
  end
167
167
 
168
168
  it "stops the container" do
169
- expect(Dockistrano::Docker).to receive(:stop_all_containers_from_image).with(subject.full_image_name)
169
+ expect(Dockistrano::Docker).to receive(:stop).with(subject.image_name)
170
170
  subject.stop
171
171
  end
172
172
 
173
- it "unregisters a host from Hipache" do
174
- allow(subject).to receive(:host).and_return("hostname.dev")
175
- expect(subject).to receive(:ip_address).and_return("33.33.33.33")
176
- expect(subject).to receive(:port).and_return("3000")
177
- expect(hipache).to receive(:unregister).with(subject.image_name, "hostname.dev", "33.33.33.33", "3000")
173
+ it "removes the container from Docker" do
174
+ expect(Dockistrano::Docker).to receive(:remove_container).with(subject.image_name)
178
175
  subject.stop
179
176
  end
180
177
 
181
- it "unregisters multiple hosts from Hipache" do
182
- allow(subject).to receive(:host).and_return({ "hostname.dev" => "8000" })
183
- expect(subject).to receive(:ip_address).and_return("33.33.33.33")
184
- expect(hipache).to receive(:unregister).with(subject.image_name, "hostname.dev", "33.33.33.33", "8000")
178
+ it "stops containers running additional commands" do
179
+ expect(Dockistrano::Docker).to receive(:stop).with("#{subject.image_name}_worker")
180
+ expect(Dockistrano::Docker).to receive(:remove_container).with("#{subject.image_name}_worker")
181
+ subject.stop
182
+ end
183
+
184
+ it "updates Hipache" do
185
+ expect(subject).to receive(:update_hipache).with(false)
185
186
  subject.stop
186
187
  end
187
188
  end
@@ -239,19 +240,42 @@ describe Dockistrano::Service do
239
240
  end
240
241
  end
241
242
 
243
+ context "#update_hipache" do
244
+ let(:hipache) { double }
245
+
246
+ before do
247
+ allow(Dockistrano::Hipache).to receive(:new).and_return(hipache)
248
+ end
249
+
250
+ it "registers the host in Hipache when the server is up" do
251
+ allow(subject).to receive(:host).and_return({ "hostname.dev" => "8000" })
252
+ expect(subject).to receive(:ip_address_for_port).with("8000").and_return("33.33.33.33")
253
+ expect(hipache).to receive(:register).with(subject.image_name, "hostname.dev", "33.33.33.33", "8000")
254
+ subject.update_hipache(true)
255
+ end
256
+
257
+ it "unregisters the host in Hipache when the server is down" do
258
+ allow(subject).to receive(:host).and_return({ "hostname.dev" => "8000" })
259
+ expect(subject).to receive(:ip_address_for_port).with("8000").and_return("33.33.33.33")
260
+ expect(hipache).to receive(:unregister).with(subject.image_name, "hostname.dev", "33.33.33.33", "8000")
261
+ subject.update_hipache(false)
262
+ end
263
+ end
264
+
242
265
  context "#start" do
243
266
  let(:environment) { double }
244
267
  let(:volumes) { double }
245
268
  let(:ports) { double }
246
- let(:hipache) { double }
269
+ let(:links) { double }
247
270
 
248
271
  before do
249
- allow(Dockistrano::Hipache).to receive(:new).and_return(hipache)
272
+ allow(subject).to receive(:update_hipache)
250
273
  allow(subject).to receive(:ensure_backing_services)
251
274
  allow(subject).to receive(:create_data_directories)
252
275
  allow(subject).to receive(:checked_environment_variables).and_return(environment)
253
276
  allow(subject).to receive(:volumes).and_return(volumes)
254
277
  allow(subject).to receive(:ports).and_return(ports)
278
+ allow(subject).to receive(:link_backing_services).and_return(links)
255
279
  allow(Dockistrano::Docker).to receive(:run)
256
280
  end
257
281
 
@@ -267,27 +291,17 @@ describe Dockistrano::Service do
267
291
 
268
292
  it "starts additional container when additional commands are configured" do
269
293
  allow(subject).to receive(:additional_commands).and_return({ "worker" => "sidekiq start" })
270
- expect(Dockistrano::Docker).to receive(:run).with(subject.full_image_name, e: environment, v: volumes, p: ports, d: true, command: "sidekiq start")
294
+ expect(Dockistrano::Docker).to receive(:run).with(subject.full_image_name, name: "#{subject.image_name}_worker", link: links, e: environment, v: volumes, d: true, command: "sidekiq start")
271
295
  subject.start
272
296
  end
273
297
 
274
298
  it "starts the container with the default command, providing env variables and volumes" do
275
- expect(Dockistrano::Docker).to receive(:run).with(subject.full_image_name, e: environment, v: volumes, p: ports, d: true)
276
- subject.start
277
- end
278
-
279
- it "registers a host with Hipache" do
280
- allow(subject).to receive(:host).and_return("hostname.dev")
281
- expect(subject).to receive(:ip_address).and_return("33.33.33.33")
282
- expect(subject).to receive(:port).and_return("3000")
283
- expect(hipache).to receive(:register).with(subject.image_name, "hostname.dev", "33.33.33.33", "3000")
299
+ expect(Dockistrano::Docker).to receive(:run).with(subject.full_image_name, name: subject.image_name, link: links, e: environment, v: volumes, p: ports, d: true)
284
300
  subject.start
285
301
  end
286
302
 
287
- it "registers multiple hosts with Hipache" do
288
- allow(subject).to receive(:host).and_return({ "hostname.dev" => "8000" })
289
- expect(subject).to receive(:ip_address).and_return("33.33.33.33")
290
- expect(hipache).to receive(:register).with(subject.image_name, "hostname.dev", "33.33.33.33", "8000")
303
+ it "updates Hipache" do
304
+ expect(subject).to receive(:update_hipache)
291
305
  subject.start
292
306
  end
293
307
  end
@@ -297,8 +311,8 @@ describe Dockistrano::Service do
297
311
  allow(subject).to receive(:full_image_name_with_fallback).and_return("image:develop")
298
312
  allow(subject).to receive(:environment_variables).and_return(environment = double)
299
313
  allow(subject).to receive(:volumes).and_return(volumes = double)
300
- allow(subject).to receive(:ports).and_return(ports = double)
301
- expect(Dockistrano::Docker).to receive(:run).with(subject.full_image_name_with_fallback, e: environment, v: volumes, p: ports, command: "foobar")
314
+ allow(subject).to receive(:link_backing_services).and_return(link = double)
315
+ expect(Dockistrano::Docker).to receive(:run).with(subject.full_image_name_with_fallback, link: link, e: environment, v: volumes, command: "foobar")
302
316
  subject.run("foobar")
303
317
  end
304
318
  end
@@ -308,9 +322,9 @@ describe Dockistrano::Service do
308
322
  allow(subject).to receive(:full_image_name_with_fallback).and_return("image:develop")
309
323
  allow(subject).to receive(:environment_variables).and_return(environment = double)
310
324
  allow(subject).to receive(:volumes).and_return(volumes = double)
311
- allow(subject).to receive(:ports).and_return(ports = double)
325
+ allow(subject).to receive(:link_backing_services).and_return(link = double)
312
326
  expect(subject).to receive(:create_data_directories)
313
- expect(Dockistrano::Docker).to receive(:exec).with(subject.full_image_name_with_fallback, e: environment, v: volumes, p: ports, command: "foobar")
327
+ expect(Dockistrano::Docker).to receive(:exec).with(subject.full_image_name_with_fallback, link: link, e: environment, v: volumes, command: "foobar")
314
328
  subject.exec("foobar")
315
329
  end
316
330
  end
@@ -320,9 +334,9 @@ describe Dockistrano::Service do
320
334
  allow(subject).to receive(:full_image_name_with_fallback).and_return("image:develop")
321
335
  allow(subject).to receive(:environment_variables).and_return(environment = double)
322
336
  allow(subject).to receive(:volumes).and_return(volumes = double)
323
- allow(subject).to receive(:ports).and_return(ports = double)
337
+ allow(subject).to receive(:link_backing_services).and_return(link = double)
324
338
  expect(subject).to receive(:create_data_directories)
325
- expect(Dockistrano::Docker).to receive(:console).with(subject.full_image_name_with_fallback, e: environment, v: volumes, p: ports, command: "foobar")
339
+ expect(Dockistrano::Docker).to receive(:console).with(subject.full_image_name_with_fallback, link: link, e: environment, v: volumes, command: "foobar")
326
340
  subject.console("foobar")
327
341
  end
328
342
  end
@@ -345,13 +359,23 @@ describe Dockistrano::Service do
345
359
  end
346
360
  end
347
361
 
362
+ context "#link_backing_services" do
363
+ it "returns an array with image names of backing services" do
364
+ allow(subject).to receive(:backing_services).and_return({
365
+ "postgresql" => double(image_name: "postgresql"),
366
+ "redis" => double(image_name: "redis")
367
+ })
368
+ expect(subject.link_backing_services).to eq(["postgresql:postgresql", "redis:redis"])
369
+ end
370
+ end
371
+
348
372
  context "#environment_variables" do
349
373
  let(:backing_service){
350
374
  double(
351
375
  ip_address: "172.0.0.1",
352
376
  port: "1245",
353
377
  backing_service_env: { database: "dockistrano_development" },
354
- provided_environment_variables: { "DATABASE_URL" => "postgres://postgres@$POSTGRESQL_IP/$POSTGRESQL_DATABASE"}
378
+ provided_environment_variables: { "DATABASE_URL" => "postgres://postgres@172.0.0.1/$POSTGRESQL_DATABASE"}
355
379
  )
356
380
  }
357
381
 
@@ -365,11 +389,6 @@ describe Dockistrano::Service do
365
389
  expect(subject.environment_variables["RAILS_ENV"]).to eq("test")
366
390
  end
367
391
 
368
- it "includes environment variables with the ip and port of each backing service" do
369
- expect(subject.environment_variables).to include("POSTGRESQL_IP")
370
- expect(subject.environment_variables).to include("POSTGRESQL_PORT")
371
- end
372
-
373
392
  it "includes variables for the backing service provided in the local configuration" do
374
393
  expect(subject.environment_variables).to include("POSTGRESQL_DATABASE")
375
394
  expect(subject.environment_variables["POSTGRESQL_DATABASE"]).to eq("dockistrano_development")
@@ -383,6 +402,11 @@ describe Dockistrano::Service do
383
402
  it "interpolates environment variables with present values" do
384
403
  expect(subject.environment_variables["DATABASE_URL"]).to eq("postgres://postgres@172.0.0.1/dockistrano_development")
385
404
  end
405
+
406
+ it "leaves variables in tact that could not be replaced" do
407
+ subject.config = { "environment" => { "rails_env" => "test$FOOBAR" } }
408
+ expect(subject.environment_variables["RAILS_ENV"]).to eq("test$FOOBAR")
409
+ end
386
410
  end
387
411
 
388
412
  context "#provided_environment_variables" do
@@ -400,8 +424,8 @@ describe Dockistrano::Service do
400
424
  end
401
425
 
402
426
  it "includes a source mount when configured" do
403
- allow(subject).to receive(:mount_src).and_return("/home/app")
404
- expect(subject.volumes).to include("/dockistrano/image/src:/home/app")
427
+ allow(subject).to receive(:mount_src).and_return({ "/home/vagrant/src/app2" => "/home/app" })
428
+ expect(subject.volumes).to include("/home/vagrant/src/app2:/home/app")
405
429
  end
406
430
  end
407
431
 
@@ -453,53 +477,55 @@ describe Dockistrano::Service do
453
477
  end
454
478
  end
455
479
 
456
- context "#ip_address" do
457
- it "returns the ip address of the running container" do
458
- allow(subject).to receive(:running?).and_return(true)
459
- allow(subject).to receive(:container_settings).and_return({ "NetworkSettings" => { "IPAddress" => "33.33.33.10" }})
460
- expect(subject.ip_address).to eq("33.33.33.10")
461
- end
462
-
463
- it "returns nil when the container is not running" do
464
- allow(subject).to receive(:running?).and_return(false)
465
- expect(subject.ip_address).to be_nil
466
- end
467
- end
468
-
469
- context "#port" do
470
- it "returns the ip address of the running container" do
480
+ context "#ip_address_for_port" do
481
+ it "returns the ip address at which the port is listening" do
471
482
  allow(subject).to receive(:running?).and_return(true)
472
- allow(subject).to receive(:container_settings).and_return({ "NetworkSettings" => { "PortMapping" => { "Tcp" => { "8000" => "80" } } } })
473
- expect(subject.port).to eq("8000")
474
- end
475
-
476
- it "returns nil when the container is not running" do
477
- allow(subject).to receive(:running?).and_return(false)
478
- expect(subject.port).to be_nil
483
+ allow(subject).to receive(:container_settings).and_return({ "NetworkSettings" => { "Ports" => {
484
+ "3000/tcp" => [
485
+ {
486
+ "HostIp" => "127.0.0.1",
487
+ "HostPort" => "3000"
488
+ }
489
+ ]
490
+ }}})
491
+ expect(subject.ip_address_for_port(3000)).to eq("127.0.0.1")
479
492
  end
480
493
  end
481
494
 
482
495
  context "#ports" do
483
496
  it "returns a string representation of the port mappings" do
484
497
  subject.config = { "ports" => { "1234" => "5678" } }
485
- expect(subject.ports).to eq(["1234:5678"])
498
+ expect(subject.ports).to eq(["172.17.42.1:1234:5678"])
499
+ end
500
+
501
+ it "returns the ip address included in the configuration" do
502
+ subject.config = { "ports" => { "33.33.33.10:1234" => "5678" } }
503
+ expect(subject.ports).to eq(["33.33.33.10:1234:5678"])
486
504
  end
487
505
  end
488
506
 
489
507
  context "#attach" do
490
508
  it "attaches to the output of the container" do
491
- expect(Dockistrano::Docker).to receive(:attach).with("123456")
492
- expect(Dockistrano::Docker).to receive(:running_container_id).with(subject.full_image_name).and_return("123456")
509
+ expect(Dockistrano::Docker).to receive(:attach).with(subject.image_name)
493
510
  subject.attach
494
511
  end
512
+
513
+ it "attaches to the output of the container when additional command given" do
514
+ expect(Dockistrano::Docker).to receive(:attach).with("#{subject.image_name}_worker")
515
+ subject.attach("worker")
516
+ end
495
517
  end
496
518
 
497
519
  context "#logs" do
498
520
  it "returns the logs of the last run of the container" do
499
- expect(Dockistrano::Docker).to receive(:logs).with("123456")
500
- expect(Dockistrano::Docker).to receive(:last_run_container_id).with(subject.full_image_name).and_return("123456")
521
+ expect(Dockistrano::Docker).to receive(:logs).with(subject.image_name)
501
522
  subject.logs
502
523
  end
524
+
525
+ it "returns the logs of the last run of the container when additional command given" do
526
+ expect(Dockistrano::Docker).to receive(:logs).with("#{subject.image_name}_worker")
527
+ subject.logs("worker")
528
+ end
503
529
  end
504
530
 
505
531
  context "#create_data_directories" do
@@ -514,6 +540,7 @@ describe Dockistrano::Service do
514
540
  v: volumes,
515
541
  e: environment_variables,
516
542
  u: "root",
543
+ rm: true,
517
544
  command: "/bin/bash -c 'mkdir -p /dockistrano/data/logs; chown app:app /dockistrano/data/logs'"
518
545
  )
519
546
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: dockistrano
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.5
4
+ version: 0.0.6
5
5
  platform: ruby
6
6
  authors:
7
7
  - Edwin Vlieg
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2013-10-28 00:00:00.000000000 Z
11
+ date: 2013-11-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: thor
@@ -136,6 +136,20 @@ dependencies:
136
136
  - - '>='
137
137
  - !ruby/object:Gem::Version
138
138
  version: '0'
139
+ - !ruby/object:Gem::Dependency
140
+ name: guard-shell
141
+ requirement: !ruby/object:Gem::Requirement
142
+ requirements:
143
+ - - '>='
144
+ - !ruby/object:Gem::Version
145
+ version: '0'
146
+ type: :development
147
+ prerelease: false
148
+ version_requirements: !ruby/object:Gem::Requirement
149
+ requirements:
150
+ - - '>='
151
+ - !ruby/object:Gem::Version
152
+ version: '0'
139
153
  - !ruby/object:Gem::Dependency
140
154
  name: terminal-notifier-guard
141
155
  requirement: !ruby/object:Gem::Requirement
@@ -169,7 +183,6 @@ email:
169
183
  - edwin@moneybird.com
170
184
  executables:
171
185
  - doc
172
- - docker
173
186
  extensions: []
174
187
  extra_rdoc_files: []
175
188
  files:
@@ -181,7 +194,6 @@ files:
181
194
  - README.md
182
195
  - Rakefile
183
196
  - bin/doc
184
- - bin/docker
185
197
  - dockistrano.gemspec
186
198
  - lib/dockistrano.rb
187
199
  - lib/dockistrano/cli.rb
data/bin/docker DELETED
Binary file