kumo_dockercloud 3.3.2 → 3.4.0
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 +4 -4
- data/kumo_dockercloud.gemspec +1 -1
- data/lib/kumo_dockercloud.rb +1 -0
- data/lib/kumo_dockercloud/credentials_decrypter.rb +14 -0
- data/lib/kumo_dockercloud/haproxy_service.rb +2 -2
- data/lib/kumo_dockercloud/service.rb +3 -4
- data/lib/kumo_dockercloud/stack.rb +14 -6
- data/lib/kumo_dockercloud/version.rb +1 -1
- data/spec/kumo_dockercloud/credentials_decrypter_spec.rb +30 -0
- data/spec/kumo_dockercloud/stack_spec.rb +60 -4
- metadata +7 -4
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA1:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 08dfdf02e230230624971977dfb4b67c661b444b
|
|
4
|
+
data.tar.gz: 5d3d3a527876ab7c443d8add610511bf45b22808
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 619c42a20c04490590d85a3ff8dcae5c09c5bdf184eb5f26ea718121efa03ee4747d520e179f811c1739ca59e669095b9b34c84f62954ee1c39feff962f22fc0
|
|
7
|
+
data.tar.gz: 6ed1c218ea519652b5cec5da8c25a0563252ac6cab43361eceaf389f7fb8039c91594a303e9d44f3d955f3a112b6a6c122b239a3894c5672366aec04e15ab8e2
|
data/kumo_dockercloud.gemspec
CHANGED
|
@@ -20,7 +20,7 @@ Gem::Specification.new do |spec|
|
|
|
20
20
|
|
|
21
21
|
spec.add_runtime_dependency 'httpi', '~> 2.4'
|
|
22
22
|
spec.add_runtime_dependency 'docker_cloud', '~> 0.1'
|
|
23
|
-
spec.add_runtime_dependency 'kumo_ki', '~>1.
|
|
23
|
+
spec.add_runtime_dependency 'kumo_ki', '~> 1.1'
|
|
24
24
|
|
|
25
25
|
spec.add_development_dependency 'bundler', '~> 1.6'
|
|
26
26
|
spec.add_development_dependency 'rake', '~> 10.0'
|
data/lib/kumo_dockercloud.rb
CHANGED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
module KumoDockerCloud
|
|
2
|
+
class CredentialsDecrypter
|
|
3
|
+
def decrypt(credentials)
|
|
4
|
+
kms = KumoKi::KMS.new
|
|
5
|
+
|
|
6
|
+
{
|
|
7
|
+
username: kms.decrypt(credentials[:encrypted_dockercloud_user][5..-1]),
|
|
8
|
+
api_key: kms.decrypt(credentials[:encrypted_dockercloud_apikey][5..-1])
|
|
9
|
+
}
|
|
10
|
+
rescue
|
|
11
|
+
raise Error.new("Could not decrypt deployment credentials")
|
|
12
|
+
end
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
module KumoDockerCloud
|
|
2
2
|
class HaproxyService < Service
|
|
3
|
-
def initialize(stack_name)
|
|
4
|
-
super(stack_name, 'haproxy')
|
|
3
|
+
def initialize(stack_name, docker_cloud_api = DockerCloudApi.new)
|
|
4
|
+
super(stack_name, 'haproxy', docker_cloud_api)
|
|
5
5
|
|
|
6
6
|
@client = docker_cloud_api.client
|
|
7
7
|
end
|
|
@@ -1,12 +1,11 @@
|
|
|
1
|
-
require 'timeout'
|
|
2
|
-
|
|
3
1
|
module KumoDockerCloud
|
|
4
2
|
class Service
|
|
5
3
|
attr_reader :name
|
|
6
4
|
|
|
7
|
-
def initialize(stack_name, service_name)
|
|
5
|
+
def initialize(stack_name, service_name, docker_cloud_api = DockerCloudApi.new)
|
|
8
6
|
@stack_name = stack_name
|
|
9
7
|
@name = service_name
|
|
8
|
+
@docker_cloud_api = docker_cloud_api
|
|
10
9
|
end
|
|
11
10
|
|
|
12
11
|
def self.service_by_resource_uri(resource_uri)
|
|
@@ -76,7 +75,7 @@ module KumoDockerCloud
|
|
|
76
75
|
end
|
|
77
76
|
|
|
78
77
|
def docker_cloud_api
|
|
79
|
-
@docker_cloud_api
|
|
78
|
+
@docker_cloud_api
|
|
80
79
|
end
|
|
81
80
|
|
|
82
81
|
def get_service
|
|
@@ -4,8 +4,7 @@ module KumoDockerCloud
|
|
|
4
4
|
class Stack
|
|
5
5
|
attr_reader :stack_name, :app_name, :options
|
|
6
6
|
|
|
7
|
-
|
|
8
|
-
def initialize(app_name, env_name, options = { contactable: true })
|
|
7
|
+
def initialize(app_name, env_name, options = {})
|
|
9
8
|
@app_name = app_name
|
|
10
9
|
@stack_name = "#{app_name}-#{env_name}"
|
|
11
10
|
@options = options
|
|
@@ -15,15 +14,15 @@ module KumoDockerCloud
|
|
|
15
14
|
validate_params(service_name, 'Service name')
|
|
16
15
|
validate_params(version, 'Version')
|
|
17
16
|
|
|
18
|
-
service = Service.new(stack_name, service_name)
|
|
17
|
+
service = Service.new(stack_name, service_name, docker_cloud_api)
|
|
19
18
|
service.deploy(version)
|
|
20
19
|
checker.verify(service)
|
|
21
20
|
end
|
|
22
21
|
|
|
23
22
|
def deploy_blue_green(service_names, version, checker = ServiceChecker.new)
|
|
24
|
-
haproxy_service = HaproxyService.new(@stack_name)
|
|
23
|
+
haproxy_service = HaproxyService.new(@stack_name, docker_cloud_api)
|
|
25
24
|
|
|
26
|
-
services = service_names.map { |name| Service.new(stack_name, name) }
|
|
25
|
+
services = service_names.map { |name| Service.new(stack_name, name, docker_cloud_api) }
|
|
27
26
|
ordered_deployment(services).each do |service|
|
|
28
27
|
begin
|
|
29
28
|
ConsoleJockey.write_line("Attempting to put #{service.name} into maintenance mode in HAProxy")
|
|
@@ -59,8 +58,17 @@ module KumoDockerCloud
|
|
|
59
58
|
raise KumoDockerCloud::Error.new("#{param_name} cannot be empty") if param_value.empty?
|
|
60
59
|
end
|
|
61
60
|
|
|
61
|
+
def kms
|
|
62
|
+
@kms ||= KumoKi::KMS.new
|
|
63
|
+
end
|
|
64
|
+
|
|
62
65
|
def docker_cloud_api
|
|
63
|
-
|
|
66
|
+
dockercloud_api_options = {}
|
|
67
|
+
if @options[:encrypted_dockercloud_user] && @options[:encrypted_dockercloud_apikey]
|
|
68
|
+
dockercloud_api_options.merge! KumoDockerCloud::CredentialsDecrypter.new.decrypt(@options)
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
@docker_cloud_api ||= DockerCloudApi.new(dockercloud_api_options)
|
|
64
72
|
end
|
|
65
73
|
end
|
|
66
74
|
end
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
require 'spec_helper'
|
|
2
|
+
|
|
3
|
+
describe KumoDockerCloud::CredentialsDecrypter do
|
|
4
|
+
describe '#decrypt' do
|
|
5
|
+
let(:encrypted_user) { 'encrypted_user' }
|
|
6
|
+
let(:encrypted_apikey) { 'encrypted_apikey' }
|
|
7
|
+
let(:plaintext_user) { 'plaintext_user' }
|
|
8
|
+
let(:plaintext_apikey) { 'plaintext_apikey' }
|
|
9
|
+
let(:encrypted) { { encrypted_dockercloud_user: "[ENC,#{encrypted_user}", encrypted_dockercloud_apikey: "[ENC,#{encrypted_apikey}" } }
|
|
10
|
+
|
|
11
|
+
let(:kms) { instance_double(KumoKi::KMS) }
|
|
12
|
+
|
|
13
|
+
subject { described_class.new.decrypt(encrypted) }
|
|
14
|
+
|
|
15
|
+
before do
|
|
16
|
+
allow(KumoKi::KMS).to receive(:new).and_return(kms)
|
|
17
|
+
allow(kms).to receive(:decrypt).with(encrypted_user).and_return(plaintext_user)
|
|
18
|
+
allow(kms).to receive(:decrypt).with(encrypted_apikey).and_return(plaintext_apikey)
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
it 'decrypts encrypted credentials' do
|
|
22
|
+
expect(subject).to eq({ username: plaintext_user, api_key: plaintext_apikey })
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
it 'throws an exception if the credentials cannot be encrypted' do
|
|
26
|
+
allow(kms).to receive(:decrypt).and_raise(KumoKi::DecryptionError)
|
|
27
|
+
expect { subject }.to raise_error(KumoDockerCloud::Error, 'Could not decrypt deployment credentials')
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
end
|
|
@@ -9,14 +9,41 @@ describe KumoDockerCloud::Stack do
|
|
|
9
9
|
let(:version) { '1' }
|
|
10
10
|
let(:checker) { instance_double(KumoDockerCloud::ServiceChecker, verify: nil) }
|
|
11
11
|
let(:service) { instance_double(KumoDockerCloud::Service) }
|
|
12
|
+
let(:dockercloud_api) { instance_double(KumoDockerCloud::DockerCloudApi) }
|
|
12
13
|
|
|
13
14
|
before do
|
|
14
|
-
allow(KumoDockerCloud::
|
|
15
|
+
allow(KumoDockerCloud::DockerCloudApi).to receive(:new).with({}).and_return(dockercloud_api)
|
|
16
|
+
allow(KumoDockerCloud::Service).to receive(:new).with(stack_name, service_name, dockercloud_api).and_return(service)
|
|
15
17
|
allow(service).to receive(:deploy).with(version)
|
|
16
18
|
end
|
|
17
19
|
|
|
18
20
|
subject { stack.deploy(service_name, version) }
|
|
19
21
|
|
|
22
|
+
context 'with encrypted credentials' do
|
|
23
|
+
let(:encrypted_creds) { { encrypted_dockercloud_user: "[ENC,#{encrypted_user}", encrypted_dockercloud_apikey: "[ENC,#{encrypted_apikey}" } }
|
|
24
|
+
let(:stack_with_encrypted_creds) { described_class.new(app_name, environment_name, encrypted_creds) }
|
|
25
|
+
let(:credentials_decrypter) { instance_double(KumoDockerCloud::CredentialsDecrypter) }
|
|
26
|
+
let(:encrypted_user) { 'encrypted_user' }
|
|
27
|
+
let(:encrypted_apikey) { 'encrypted_apikey' }
|
|
28
|
+
let(:plaintext_user) { 'plaintext_user' }
|
|
29
|
+
let(:plaintext_apikey) { 'plaintext_apikey' }
|
|
30
|
+
let(:decrypted_creds) { { username: plaintext_user, api_key: plaintext_apikey } }
|
|
31
|
+
|
|
32
|
+
subject { stack_with_encrypted_creds.deploy(service_name, version) }
|
|
33
|
+
|
|
34
|
+
before do
|
|
35
|
+
allow(KumoDockerCloud::CredentialsDecrypter).to receive(:new).and_return(credentials_decrypter)
|
|
36
|
+
allow(credentials_decrypter).to receive(:decrypt).with(encrypted_creds).and_return(decrypted_creds)
|
|
37
|
+
allow(KumoDockerCloud::DockerCloudApi).to receive(:new).with(decrypted_creds).and_return(dockercloud_api)
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
it 'decrypts the credentials and uses them to authenticate with docker cloud' do
|
|
41
|
+
expect(KumoDockerCloud::Service).to receive(:new).with(stack_name, service_name, dockercloud_api).and_return(service)
|
|
42
|
+
|
|
43
|
+
subject
|
|
44
|
+
end
|
|
45
|
+
end
|
|
46
|
+
|
|
20
47
|
it 'deploys the version of my service' do
|
|
21
48
|
expect(service).to receive(:deploy).with(version)
|
|
22
49
|
subject
|
|
@@ -74,11 +101,13 @@ describe KumoDockerCloud::Stack do
|
|
|
74
101
|
let(:service_a) { instance_double(KumoDockerCloud::Service, :service_a, state: 'Running', deploy: nil, name: 'service_a') }
|
|
75
102
|
let(:service_b) { instance_double(KumoDockerCloud::Service, :service_b, state: 'Running', deploy: nil, name: 'service_b') }
|
|
76
103
|
let(:haproxy) { instance_double(KumoDockerCloud::HaproxyService, :haproxy_svc, disable_service: nil, enable_service: nil) }
|
|
104
|
+
let(:dockercloud_api) { instance_double(KumoDockerCloud::DockerCloudApi) }
|
|
77
105
|
|
|
78
106
|
before do
|
|
79
|
-
allow(KumoDockerCloud::
|
|
80
|
-
allow(KumoDockerCloud::Service).to receive(:new).with(stack_name, 'service-
|
|
81
|
-
allow(KumoDockerCloud::
|
|
107
|
+
allow(KumoDockerCloud::DockerCloudApi).to receive(:new).with({}).and_return(dockercloud_api)
|
|
108
|
+
allow(KumoDockerCloud::Service).to receive(:new).with(stack_name, 'service-a', dockercloud_api).and_return(service_a)
|
|
109
|
+
allow(KumoDockerCloud::Service).to receive(:new).with(stack_name, 'service-b', dockercloud_api).and_return(service_b)
|
|
110
|
+
allow(KumoDockerCloud::HaproxyService).to receive(:new).with(stack_name, dockercloud_api).and_return(haproxy)
|
|
82
111
|
allow(KumoDockerCloud::ConsoleJockey).to receive(:write_line)
|
|
83
112
|
end
|
|
84
113
|
|
|
@@ -128,6 +157,33 @@ describe KumoDockerCloud::Stack do
|
|
|
128
157
|
allow(checker).to receive(:verify).with(service_a).and_raise(KumoDockerCloud::ServiceDeployError)
|
|
129
158
|
expect { subject }.to raise_error(KumoDockerCloud::ServiceDeployError)
|
|
130
159
|
end
|
|
160
|
+
|
|
161
|
+
context 'with encrypted credentials' do
|
|
162
|
+
let(:encrypted_creds) { { encrypted_dockercloud_user: "[ENC,#{encrypted_user}", encrypted_dockercloud_apikey: "[ENC,#{encrypted_apikey}" } }
|
|
163
|
+
let(:stack_with_encrypted_creds) { described_class.new(app_name, environment_name, encrypted_creds) }
|
|
164
|
+
let(:credentials_decrypter) { instance_double(KumoDockerCloud::CredentialsDecrypter) }
|
|
165
|
+
let(:encrypted_user) { 'encrypted_user' }
|
|
166
|
+
let(:encrypted_apikey) { 'encrypted_apikey' }
|
|
167
|
+
let(:plaintext_user) { 'plaintext_user' }
|
|
168
|
+
let(:plaintext_apikey) { 'plaintext_apikey' }
|
|
169
|
+
let(:decrypted_creds) { { username: plaintext_user, api_key: plaintext_apikey } }
|
|
170
|
+
|
|
171
|
+
subject { stack_with_encrypted_creds.deploy_blue_green(service_names, version, checker) }
|
|
172
|
+
|
|
173
|
+
before do
|
|
174
|
+
allow(KumoDockerCloud::CredentialsDecrypter).to receive(:new).and_return(credentials_decrypter)
|
|
175
|
+
allow(credentials_decrypter).to receive(:decrypt).with(encrypted_creds).and_return(decrypted_creds)
|
|
176
|
+
allow(KumoDockerCloud::DockerCloudApi).to receive(:new).with(decrypted_creds).and_return(dockercloud_api)
|
|
177
|
+
end
|
|
178
|
+
|
|
179
|
+
it 'decrypts the credentials and uses them to authenticate with docker cloud' do
|
|
180
|
+
expect(KumoDockerCloud::Service).to receive(:new).with(stack_name, 'service-a', dockercloud_api).and_return(service_a)
|
|
181
|
+
expect(KumoDockerCloud::Service).to receive(:new).with(stack_name, 'service-b', dockercloud_api).and_return(service_b)
|
|
182
|
+
expect(KumoDockerCloud::HaproxyService).to receive(:new).with(stack_name, dockercloud_api).and_return(haproxy)
|
|
183
|
+
|
|
184
|
+
subject
|
|
185
|
+
end
|
|
186
|
+
end
|
|
131
187
|
end
|
|
132
188
|
|
|
133
189
|
describe '#services' do
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: kumo_dockercloud
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 3.
|
|
4
|
+
version: 3.4.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Redbubble
|
|
@@ -10,7 +10,7 @@ authors:
|
|
|
10
10
|
autorequire:
|
|
11
11
|
bindir: bin
|
|
12
12
|
cert_chain: []
|
|
13
|
-
date: 2016-06-
|
|
13
|
+
date: 2016-06-07 00:00:00.000000000 Z
|
|
14
14
|
dependencies:
|
|
15
15
|
- !ruby/object:Gem::Dependency
|
|
16
16
|
name: httpi
|
|
@@ -46,14 +46,14 @@ dependencies:
|
|
|
46
46
|
requirements:
|
|
47
47
|
- - "~>"
|
|
48
48
|
- !ruby/object:Gem::Version
|
|
49
|
-
version: '1.
|
|
49
|
+
version: '1.1'
|
|
50
50
|
type: :runtime
|
|
51
51
|
prerelease: false
|
|
52
52
|
version_requirements: !ruby/object:Gem::Requirement
|
|
53
53
|
requirements:
|
|
54
54
|
- - "~>"
|
|
55
55
|
- !ruby/object:Gem::Version
|
|
56
|
-
version: '1.
|
|
56
|
+
version: '1.1'
|
|
57
57
|
- !ruby/object:Gem::Dependency
|
|
58
58
|
name: bundler
|
|
59
59
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -158,6 +158,7 @@ files:
|
|
|
158
158
|
- kumo_dockercloud.gemspec
|
|
159
159
|
- lib/kumo_dockercloud.rb
|
|
160
160
|
- lib/kumo_dockercloud/console_jockey.rb
|
|
161
|
+
- lib/kumo_dockercloud/credentials_decrypter.rb
|
|
161
162
|
- lib/kumo_dockercloud/deployment.rb
|
|
162
163
|
- lib/kumo_dockercloud/docker_cloud_api.rb
|
|
163
164
|
- lib/kumo_dockercloud/environment.rb
|
|
@@ -184,6 +185,7 @@ files:
|
|
|
184
185
|
- spec/fixtures/stack.yml.erb
|
|
185
186
|
- spec/kumo_docker_cloud_spec.rb
|
|
186
187
|
- spec/kumo_dockercloud/console_jockey_spec.rb
|
|
188
|
+
- spec/kumo_dockercloud/credentials_decrypter_spec.rb
|
|
187
189
|
- spec/kumo_dockercloud/docker_cloud_api_spec.rb
|
|
188
190
|
- spec/kumo_dockercloud/environment_config_spec.rb
|
|
189
191
|
- spec/kumo_dockercloud/environment_spec.rb
|
|
@@ -229,6 +231,7 @@ test_files:
|
|
|
229
231
|
- spec/fixtures/stack.yml.erb
|
|
230
232
|
- spec/kumo_docker_cloud_spec.rb
|
|
231
233
|
- spec/kumo_dockercloud/console_jockey_spec.rb
|
|
234
|
+
- spec/kumo_dockercloud/credentials_decrypter_spec.rb
|
|
232
235
|
- spec/kumo_dockercloud/docker_cloud_api_spec.rb
|
|
233
236
|
- spec/kumo_dockercloud/environment_config_spec.rb
|
|
234
237
|
- spec/kumo_dockercloud/environment_spec.rb
|