kumogata 0.4.15 → 0.4.16
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +10 -7
- data/bin/kumogata +3 -1
- data/lib/kumogata/argument_parser.rb +25 -24
- data/lib/kumogata/client.rb +20 -8
- data/lib/kumogata/ext/string_ext.rb +1 -1
- data/lib/kumogata/version.rb +1 -1
- data/spec/kumogata_create_spec.rb +45 -0
- data/spec/kumogata_delete_spec.rb +21 -0
- data/spec/kumogata_update_spec.rb +44 -0
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 16f21794bd4f613c8c5f3133c79d6e67cebb080a
|
4
|
+
data.tar.gz: d95ccdfa1ff170a28a1adb035813fb653bd5af44
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 6acff55885a8c9a9628e843a35d7aae4454e6cc21323b23e2f772c277c879f1f699ebb9f31f58d9d5ae6ee2b0647ca97cc344a532c66e5a9d5ed699bf990101f
|
7
|
+
data.tar.gz: 9bb83190ca997c3f8498b76edc2bf374b6a327b9000be5023dfbcd71c7b2c5d11610da53e899b1f7d4453ba26f74ec6de6e463802a2813812e83626223638c1d
|
data/README.md
CHANGED
@@ -5,8 +5,8 @@
|
|
5
5
|
|
6
6
|
Kumogata is a tool for [AWS CloudFormation](https://aws.amazon.com/cloudformation/).
|
7
7
|
|
8
|
-
[![Gem Version](https://badge.fury.io/rb/kumogata.png?
|
9
|
-
[![Build Status](https://drone.io/github.com/winebarrel/kumogata/status.png?
|
8
|
+
[![Gem Version](https://badge.fury.io/rb/kumogata.png?201406151300)](http://badge.fury.io/rb/kumogata)
|
9
|
+
[![Build Status](https://drone.io/github.com/winebarrel/kumogata/status.png?201406151300)](https://drone.io/github.com/winebarrel/kumogata/latest)
|
10
10
|
|
11
11
|
It can define a template in Ruby DSL, such as:
|
12
12
|
|
@@ -34,11 +34,13 @@ Resources do
|
|
34
34
|
InstanceType { Ref "InstanceType" }
|
35
35
|
KeyName "your_key_name"
|
36
36
|
|
37
|
-
UserData
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
37
|
+
UserData do
|
38
|
+
Fn__Base64 (<<-EOS).undent
|
39
|
+
#!/bin/bash
|
40
|
+
yum install -y httpd
|
41
|
+
service httpd start
|
42
|
+
EOS
|
43
|
+
end
|
42
44
|
end
|
43
45
|
end
|
44
46
|
end
|
@@ -98,6 +100,7 @@ Options:
|
|
98
100
|
--timeout MINUTES
|
99
101
|
--result-log PATH
|
100
102
|
--command-result-log PATH
|
103
|
+
--detach
|
101
104
|
--force
|
102
105
|
-w, --ignore-all-space
|
103
106
|
--color
|
data/bin/kumogata
CHANGED
@@ -65,7 +65,9 @@ begin
|
|
65
65
|
|
66
66
|
out = Kumogata::Client.new(options).send(command, *arguments)
|
67
67
|
|
68
|
-
if
|
68
|
+
if [:create, :update, :delete].include?(command) and options.detach?
|
69
|
+
puts '[detached]'
|
70
|
+
elsif output_result and out
|
69
71
|
puts out
|
70
72
|
end
|
71
73
|
rescue Exception => e
|
@@ -82,30 +82,31 @@ class Kumogata::ArgumentParser
|
|
82
82
|
|
83
83
|
begin
|
84
84
|
supported_formats = [:ruby, :json, :yaml]
|
85
|
-
opt.on('-k', '--access-key ACCESS_KEY') {|v| options[:access_key_id]
|
86
|
-
opt.on('-s', '--secret-key SECRET_KEY') {|v| options[:secret_access_key]
|
87
|
-
opt.on('-r', '--region REGION') {|v| options[:region]
|
88
|
-
opt.on('' , '--config PATH') {|v| options[:config_path]
|
89
|
-
opt.on('' , '--profile CONFIG_PROFILE') {|v| options[:config_profile]
|
90
|
-
opt.on('' , '--format TMPLATE_FORMAT', supported_formats) {|v| options[:format]
|
91
|
-
opt.on('' , '--output-format FORMAT', supported_formats) {|v| options[:output_format]
|
92
|
-
opt.on('' , '--skip-replace-underscore') { options[:skip_replace_underscore]
|
93
|
-
opt.on('' , '--deletion-policy-retain') { options[:deletion_policy_retain]
|
94
|
-
opt.on('-p', '--parameters KEY_VALUES', Array) {|v| options[:parameters]
|
95
|
-
opt.on('-e', '--encrypt-parameters KEYS', Array) {|v| options[:encrypt_parameters]
|
96
|
-
opt.on('', '--encryption-password PASS') {|v| options[:encryption_password]
|
97
|
-
opt.on('', '--skip-send-password') { options[:skip_send_password]
|
98
|
-
opt.on('' , '--capabilities CAPABILITIES', Array) {|v| options[:capabilities]
|
99
|
-
opt.on('' , '--disable-rollback') { options[:disable_rollback]
|
100
|
-
opt.on('' , '--notify SNS_TOPICS', Array) {|v| options[:notify]
|
101
|
-
opt.on('' , '--timeout MINUTES', Integer) {|v| options[:timeout]
|
102
|
-
opt.on('' , '--result-log PATH') {|v| options[:result_log]
|
103
|
-
opt.on('' , '--command-result-log PATH') {|v| options[:command]
|
104
|
-
opt.on('' , '--
|
105
|
-
opt.on('
|
106
|
-
opt.on(''
|
107
|
-
opt.on('' , '--
|
108
|
-
opt.on('' , '--
|
85
|
+
opt.on('-k', '--access-key ACCESS_KEY') {|v| options[:access_key_id] = v }
|
86
|
+
opt.on('-s', '--secret-key SECRET_KEY') {|v| options[:secret_access_key] = v }
|
87
|
+
opt.on('-r', '--region REGION') {|v| options[:region] = v }
|
88
|
+
opt.on('' , '--config PATH') {|v| options[:config_path] = v }
|
89
|
+
opt.on('' , '--profile CONFIG_PROFILE') {|v| options[:config_profile] = v }
|
90
|
+
opt.on('' , '--format TMPLATE_FORMAT', supported_formats) {|v| options[:format] = v }
|
91
|
+
opt.on('' , '--output-format FORMAT', supported_formats) {|v| options[:output_format] = v }
|
92
|
+
opt.on('' , '--skip-replace-underscore') { options[:skip_replace_underscore] = false }
|
93
|
+
opt.on('' , '--deletion-policy-retain') { options[:deletion_policy_retain] = true }
|
94
|
+
opt.on('-p', '--parameters KEY_VALUES', Array) {|v| options[:parameters] = v }
|
95
|
+
opt.on('-e', '--encrypt-parameters KEYS', Array) {|v| options[:encrypt_parameters] = v }
|
96
|
+
opt.on('', '--encryption-password PASS') {|v| options[:encryption_password] = v }
|
97
|
+
opt.on('', '--skip-send-password') { options[:skip_send_password] = true }
|
98
|
+
opt.on('' , '--capabilities CAPABILITIES', Array) {|v| options[:capabilities] = v }
|
99
|
+
opt.on('' , '--disable-rollback') { options[:disable_rollback] = true }
|
100
|
+
opt.on('' , '--notify SNS_TOPICS', Array) {|v| options[:notify] = v }
|
101
|
+
opt.on('' , '--timeout MINUTES', Integer) {|v| options[:timeout] = v }
|
102
|
+
opt.on('' , '--result-log PATH') {|v| options[:result_log] = v }
|
103
|
+
opt.on('' , '--command-result-log PATH') {|v| options[:command] = v }
|
104
|
+
opt.on('' , '--detach') { options[:detach] = true }
|
105
|
+
opt.on('' , '--force') { options[:force] = true }
|
106
|
+
opt.on('-w', '--ignore-all-space') { options[:ignore_all_space] = true }
|
107
|
+
opt.on('' , '--color') { options[:color] = true }
|
108
|
+
opt.on('' , '--no-color') { options[:color] = false }
|
109
|
+
opt.on('' , '--debug') { options[:debug] = true }
|
109
110
|
opt.parse!
|
110
111
|
|
111
112
|
unless (command = ARGV.shift)
|
data/lib/kumogata/client.rb
CHANGED
@@ -16,10 +16,12 @@ class Kumogata::Client
|
|
16
16
|
add_encryption_password(template)
|
17
17
|
|
18
18
|
outputs = create_stack(template, stack_name)
|
19
|
-
@outputs_filter.filter!(outputs)
|
20
|
-
@post_processing.run(:create, outputs)
|
21
19
|
|
22
|
-
|
20
|
+
unless @options.detach?
|
21
|
+
@outputs_filter.filter!(outputs)
|
22
|
+
@post_processing.run(:create, outputs)
|
23
|
+
outputs
|
24
|
+
end
|
23
25
|
end
|
24
26
|
|
25
27
|
def validate(path_or_url)
|
@@ -60,10 +62,12 @@ class Kumogata::Client
|
|
60
62
|
add_encryption_password(template)
|
61
63
|
|
62
64
|
outputs = update_stack(template, stack_name)
|
63
|
-
@outputs_filter.filter!(outputs)
|
64
|
-
@post_processing.run(:update, outputs)
|
65
65
|
|
66
|
-
|
66
|
+
unless @options.detach?
|
67
|
+
@outputs_filter.filter!(outputs)
|
68
|
+
@post_processing.run(:update, outputs)
|
69
|
+
outputs
|
70
|
+
end
|
67
71
|
end
|
68
72
|
|
69
73
|
def delete(stack_name)
|
@@ -73,7 +77,9 @@ class Kumogata::Client
|
|
73
77
|
delete_stack(stack_name)
|
74
78
|
end
|
75
79
|
|
76
|
-
|
80
|
+
unless @options.detach?
|
81
|
+
true
|
82
|
+
end
|
77
83
|
end
|
78
84
|
|
79
85
|
def list(stack_name = nil)
|
@@ -210,7 +216,6 @@ class Kumogata::Client
|
|
210
216
|
def evaluate_after_trigger(template)
|
211
217
|
triggers = template.delete('_after')
|
212
218
|
return {} unless triggers
|
213
|
-
|
214
219
|
end
|
215
220
|
|
216
221
|
def devaluate_template(template)
|
@@ -295,6 +300,9 @@ class Kumogata::Client
|
|
295
300
|
|
296
301
|
Kumogata.logger.info("Creating stack: #{stack_name}".cyan)
|
297
302
|
stack = @cloud_formation.stacks.create(stack_name, template.to_json, build_create_options)
|
303
|
+
|
304
|
+
return if @options.detach?
|
305
|
+
|
298
306
|
event_log = {}
|
299
307
|
|
300
308
|
unless while_in_progress(stack, 'CREATE_COMPLETE', event_log)
|
@@ -324,6 +332,8 @@ class Kumogata::Client
|
|
324
332
|
event_log = create_event_log(stack)
|
325
333
|
stack.update(build_update_options(template.to_json))
|
326
334
|
|
335
|
+
return if @options.detach?
|
336
|
+
|
327
337
|
unless while_in_progress(stack, 'UPDATE_COMPLETE', event_log)
|
328
338
|
errmsgs = ['Update failed']
|
329
339
|
errmsgs << stack_name
|
@@ -346,6 +356,8 @@ class Kumogata::Client
|
|
346
356
|
event_log = create_event_log(stack)
|
347
357
|
stack.delete
|
348
358
|
|
359
|
+
return if @options.detach?
|
360
|
+
|
349
361
|
completed = false
|
350
362
|
|
351
363
|
begin
|
@@ -11,7 +11,7 @@ class String
|
|
11
11
|
end
|
12
12
|
end # of class methods
|
13
13
|
|
14
|
-
Term::ANSIColor::Attribute.named_attributes.
|
14
|
+
Term::ANSIColor::Attribute.named_attributes.each do |attribute|
|
15
15
|
class_eval(<<-EOS, __FILE__, __LINE__ + 1)
|
16
16
|
def #{attribute.name}
|
17
17
|
if @@colorize
|
data/lib/kumogata/version.rb
CHANGED
@@ -59,6 +59,51 @@ end
|
|
59
59
|
end
|
60
60
|
end
|
61
61
|
|
62
|
+
it 'create a stack from Ruby template (detach)' do
|
63
|
+
template = <<-EOS
|
64
|
+
Resources do
|
65
|
+
myEC2Instance do
|
66
|
+
Type "AWS::EC2::Instance"
|
67
|
+
Properties do
|
68
|
+
ImageId "ami-XXXXXXXX"
|
69
|
+
InstanceType "t1.micro"
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
|
74
|
+
Outputs do
|
75
|
+
AZ do
|
76
|
+
Value do
|
77
|
+
Fn__GetAtt "myEC2Instance", "AvailabilityZone"
|
78
|
+
end
|
79
|
+
end
|
80
|
+
end
|
81
|
+
EOS
|
82
|
+
|
83
|
+
out = run_client(:create, :template => template, :options => {:detach => true}) do |client, cf|
|
84
|
+
json = eval_template(template, :update_deletion_policy => true).to_json
|
85
|
+
client.should_not_receive(:print_event_log)
|
86
|
+
client.should_not_receive(:create_event_log)
|
87
|
+
|
88
|
+
stack = make_double('stack') do |obj|
|
89
|
+
obj.should_not_receive(:status)
|
90
|
+
obj.should_not_receive(:outputs)
|
91
|
+
obj.should_not_receive(:resource_summaries)
|
92
|
+
obj.should_not_receive(:delete)
|
93
|
+
end
|
94
|
+
|
95
|
+
stacks = make_double('stacks') do |obj|
|
96
|
+
obj.should_receive(:create)
|
97
|
+
.with('kumogata-user-host-XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX', json, {}) { stack }
|
98
|
+
obj.should_not_receive(:[])
|
99
|
+
end
|
100
|
+
|
101
|
+
cf.should_receive(:stacks).once { stacks }
|
102
|
+
end
|
103
|
+
|
104
|
+
expect(out).to be_nil
|
105
|
+
end
|
106
|
+
|
62
107
|
it 'create a stack from Ruby template and run command' do
|
63
108
|
template = <<-TEMPLATE
|
64
109
|
Resources do
|
@@ -18,4 +18,25 @@ describe 'Kumogata::Client#delete' do
|
|
18
18
|
cf.should_receive(:stacks) { stacks }
|
19
19
|
end
|
20
20
|
end
|
21
|
+
|
22
|
+
it 'update a stack from Ruby template (detach)' do
|
23
|
+
out = run_client(:delete, :arguments => ['MyStack'], :options => {:force => true, :detach => true}) do |client, cf|
|
24
|
+
client.should_not_receive(:print_event_log)
|
25
|
+
client.should_receive(:create_event_log).once
|
26
|
+
|
27
|
+
stack = make_double('stack') do |obj|
|
28
|
+
obj.should_receive(:delete).with(no_args())
|
29
|
+
obj.should_receive(:status).once
|
30
|
+
end
|
31
|
+
|
32
|
+
stacks = make_double('stacks') do |obj|
|
33
|
+
obj.should_receive(:[])
|
34
|
+
.with('MyStack') { stack }
|
35
|
+
end
|
36
|
+
|
37
|
+
cf.should_receive(:stacks) { stacks }
|
38
|
+
end
|
39
|
+
|
40
|
+
expect(out).to be_nil
|
41
|
+
end
|
21
42
|
end
|
@@ -56,6 +56,50 @@ end
|
|
56
56
|
end
|
57
57
|
end
|
58
58
|
|
59
|
+
it 'update a stack from Ruby template (detach)' do
|
60
|
+
template = <<-EOS
|
61
|
+
Resources do
|
62
|
+
myEC2Instance do
|
63
|
+
Type "AWS::EC2::Instance"
|
64
|
+
Properties do
|
65
|
+
ImageId "ami-XXXXXXXX"
|
66
|
+
InstanceType "t1.micro"
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
Outputs do
|
72
|
+
AZ do
|
73
|
+
Value do
|
74
|
+
Fn__GetAtt "myEC2Instance", "AvailabilityZone"
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
78
|
+
EOS
|
79
|
+
|
80
|
+
out = run_client(:update, :arguments => ['MyStack'], :template => template, :options => {:detach => true}) do |client, cf|
|
81
|
+
json = eval_template(template).to_json
|
82
|
+
client.should_not_receive(:print_event_log)
|
83
|
+
client.should_receive(:create_event_log).once
|
84
|
+
|
85
|
+
stack = make_double('stack') do |obj|
|
86
|
+
obj.should_receive(:update).with(:template => json)
|
87
|
+
obj.should_receive(:status).once
|
88
|
+
obj.should_not_receive(:outputs)
|
89
|
+
obj.should_not_receive(:resource_summaries)
|
90
|
+
end
|
91
|
+
|
92
|
+
stacks = make_double('stacks') do |obj|
|
93
|
+
obj.should_receive(:[])
|
94
|
+
.with('MyStack') { stack }
|
95
|
+
end
|
96
|
+
|
97
|
+
cf.should_receive(:stacks) { stacks }
|
98
|
+
end
|
99
|
+
|
100
|
+
expect(out).to be_nil
|
101
|
+
end
|
102
|
+
|
59
103
|
it 'update a stack from Ruby template with deletion policy retain' do
|
60
104
|
template = <<-EOS
|
61
105
|
Resources do
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: kumogata
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.4.
|
4
|
+
version: 0.4.16
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Genki Sugawara
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-
|
11
|
+
date: 2014-06-15 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: aws-sdk
|