stack_master 1.5.0 → 1.6.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.
Files changed (122) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +3 -0
  3. data/lib/stack_master/commands/terminal_helper.rb +14 -1
  4. data/lib/stack_master/parameter_resolvers/secret.rb +7 -2
  5. data/lib/stack_master/version.rb +1 -1
  6. metadata +21 -216
  7. data/.gitignore +0 -18
  8. data/.rspec +0 -2
  9. data/.travis.yml +0 -12
  10. data/CODE_OF_CONDUCT.md +0 -73
  11. data/Gemfile +0 -4
  12. data/LICENSE.txt +0 -22
  13. data/Rakefile +0 -27
  14. data/apply_demo.gif +0 -0
  15. data/example/simple/Gemfile +0 -3
  16. data/example/simple/parameters/myapp_vpc.yml +0 -1
  17. data/example/simple/parameters/myapp_web.yml +0 -2
  18. data/example/simple/stack_master.yml +0 -13
  19. data/example/simple/templates/myapp_vpc.rb +0 -39
  20. data/example/simple/templates/myapp_web.rb +0 -16
  21. data/features/apply.feature +0 -392
  22. data/features/apply_with_compile_time_parameters.feature +0 -93
  23. data/features/apply_with_env_parameters.feature +0 -49
  24. data/features/apply_with_parameter_store_parameters.feature +0 -47
  25. data/features/apply_with_s3.feature +0 -106
  26. data/features/delete.feature +0 -29
  27. data/features/diff.feature +0 -179
  28. data/features/events.feature +0 -33
  29. data/features/init.feature +0 -6
  30. data/features/outputs.feature +0 -45
  31. data/features/region_aliases.feature +0 -62
  32. data/features/resources.feature +0 -42
  33. data/features/stack_defaults.feature +0 -82
  34. data/features/status.feature +0 -118
  35. data/features/step_definitions/parameter_store_steps.rb +0 -14
  36. data/features/step_definitions/stack_steps.rb +0 -71
  37. data/features/support/env.rb +0 -16
  38. data/features/validate.feature +0 -46
  39. data/logo.png +0 -0
  40. data/script/buildkite/bundle.sh +0 -5
  41. data/script/buildkite/clean.sh +0 -3
  42. data/script/buildkite_rspec.sh +0 -27
  43. data/spec/fixtures/parameters/myapp_vpc.yml +0 -1
  44. data/spec/fixtures/parameters/myapp_vpc_with_secrets.yml +0 -3
  45. data/spec/fixtures/sparkle_pack_integration/my_sparkle_pack/lib/my_sparkle_pack.rb +0 -1
  46. data/spec/fixtures/sparkle_pack_integration/my_sparkle_pack/lib/sparkleformation/dynamics/my_dynamic.rb +0 -5
  47. data/spec/fixtures/sparkle_pack_integration/templates/dynamics/local_dynamic.rb +0 -5
  48. data/spec/fixtures/sparkle_pack_integration/templates/template_with_dynamic.rb +0 -3
  49. data/spec/fixtures/sparkle_pack_integration/templates/template_with_dynamic_from_pack.rb +0 -3
  50. data/spec/fixtures/stack_master.yml +0 -49
  51. data/spec/fixtures/templates/json/valid_myapp_vpc.json +0 -53
  52. data/spec/fixtures/templates/myapp_vpc.json +0 -1
  53. data/spec/fixtures/templates/rb/cfndsl/sample.json +0 -28
  54. data/spec/fixtures/templates/rb/cfndsl/sample.rb +0 -16
  55. data/spec/fixtures/templates/yml/valid_myapp_vpc.yml +0 -35
  56. data/spec/fixtures/test/.gitkeep +0 -0
  57. data/spec/spec_helper.rb +0 -102
  58. data/spec/stack_master/aws_driver/s3_spec.rb +0 -130
  59. data/spec/stack_master/change_set_spec.rb +0 -70
  60. data/spec/stack_master/command_spec.rb +0 -66
  61. data/spec/stack_master/commands/apply_spec.rb +0 -259
  62. data/spec/stack_master/commands/delete_spec.rb +0 -40
  63. data/spec/stack_master/commands/init_spec.rb +0 -17
  64. data/spec/stack_master/commands/status_spec.rb +0 -44
  65. data/spec/stack_master/commands/validate_spec.rb +0 -27
  66. data/spec/stack_master/config_spec.rb +0 -153
  67. data/spec/stack_master/paged_response_accumulator_spec.rb +0 -39
  68. data/spec/stack_master/parameter_loader_spec.rb +0 -110
  69. data/spec/stack_master/parameter_resolver_spec.rb +0 -148
  70. data/spec/stack_master/parameter_resolvers/ami_finder_spec.rb +0 -68
  71. data/spec/stack_master/parameter_resolvers/env_spec.rb +0 -35
  72. data/spec/stack_master/parameter_resolvers/latest_ami_by_tags_spec.rb +0 -33
  73. data/spec/stack_master/parameter_resolvers/latest_ami_spec.rb +0 -46
  74. data/spec/stack_master/parameter_resolvers/parameter_store_spec.rb +0 -50
  75. data/spec/stack_master/parameter_resolvers/secret_spec.rb +0 -66
  76. data/spec/stack_master/parameter_resolvers/security_group_spec.rb +0 -19
  77. data/spec/stack_master/parameter_resolvers/security_groups_spec.rb +0 -32
  78. data/spec/stack_master/parameter_resolvers/sns_topic_name_spec.rb +0 -43
  79. data/spec/stack_master/parameter_resolvers/stack_output_spec.rb +0 -127
  80. data/spec/stack_master/prompter_spec.rb +0 -23
  81. data/spec/stack_master/resolver_array_spec.rb +0 -42
  82. data/spec/stack_master/security_group_finder_spec.rb +0 -49
  83. data/spec/stack_master/sns_topic_finder_spec.rb +0 -25
  84. data/spec/stack_master/sparkle_formation/compile_time/allowed_pattern_validator_spec.rb +0 -47
  85. data/spec/stack_master/sparkle_formation/compile_time/allowed_values_validator_spec.rb +0 -47
  86. data/spec/stack_master/sparkle_formation/compile_time/definitions_validator_spec.rb +0 -36
  87. data/spec/stack_master/sparkle_formation/compile_time/empty_validator_spec.rb +0 -47
  88. data/spec/stack_master/sparkle_formation/compile_time/max_length_validator_spec.rb +0 -37
  89. data/spec/stack_master/sparkle_formation/compile_time/max_size_validator_spec.rb +0 -27
  90. data/spec/stack_master/sparkle_formation/compile_time/min_length_validator_spec.rb +0 -36
  91. data/spec/stack_master/sparkle_formation/compile_time/min_size_validator_spec.rb +0 -28
  92. data/spec/stack_master/sparkle_formation/compile_time/number_validator_spec.rb +0 -41
  93. data/spec/stack_master/sparkle_formation/compile_time/parameters_validator_spec.rb +0 -65
  94. data/spec/stack_master/sparkle_formation/compile_time/state_builder_spec.rb +0 -28
  95. data/spec/stack_master/sparkle_formation/compile_time/string_validator_spec.rb +0 -35
  96. data/spec/stack_master/sparkle_formation/compile_time/value_build_spec.rb +0 -52
  97. data/spec/stack_master/sparkle_formation/compile_time/value_validator_factory_spec.rb +0 -40
  98. data/spec/stack_master/sparkle_formation/template_file_spec.rb +0 -147
  99. data/spec/stack_master/stack_definition_spec.rb +0 -70
  100. data/spec/stack_master/stack_differ_spec.rb +0 -46
  101. data/spec/stack_master/stack_events/fetcher_spec.rb +0 -40
  102. data/spec/stack_master/stack_events/presenter_spec.rb +0 -18
  103. data/spec/stack_master/stack_events/streamer_spec.rb +0 -47
  104. data/spec/stack_master/stack_spec.rb +0 -184
  105. data/spec/stack_master/template_compiler_spec.rb +0 -39
  106. data/spec/stack_master/template_compilers/cfndsl_spec.rb +0 -22
  107. data/spec/stack_master/template_compilers/json_spec.rb +0 -32
  108. data/spec/stack_master/template_compilers/sparkle_formation_spec.rb +0 -116
  109. data/spec/stack_master/template_compilers/yaml_spec.rb +0 -20
  110. data/spec/stack_master/template_utils_spec.rb +0 -21
  111. data/spec/stack_master/test_driver/cloud_formation_spec.rb +0 -64
  112. data/spec/stack_master/test_driver/s3_spec.rb +0 -17
  113. data/spec/stack_master/utils_spec.rb +0 -30
  114. data/spec/stack_master/validator_spec.rb +0 -56
  115. data/spec/stack_master_spec.rb +0 -81
  116. data/spec/support/gemfiles/Gemfile.activesupport-4.0.0 +0 -5
  117. data/spec/support/validator_spec.rb +0 -23
  118. data/stack_master.gemspec +0 -46
  119. data/stacktemplates/parameter_region.yml +0 -3
  120. data/stacktemplates/parameter_stack_name.yml +0 -3
  121. data/stacktemplates/stack.json.erb +0 -20
  122. data/stacktemplates/stack_master.yml.erb +0 -6
@@ -1,46 +0,0 @@
1
- RSpec.describe StackMaster::StackDiffer do
2
- subject(:differ) { described_class.new(proposed_stack, stack) }
3
- let(:current_params) { Hash.new }
4
- let(:proposed_params) { { 'param1' => 'hello'} }
5
- let(:stack) { StackMaster::Stack.new(stack_name: stack_name,
6
- region: region,
7
- stack_id: 123,
8
- template_body: '{}',
9
- template_format: :json,
10
- parameters: current_params) }
11
- let(:proposed_stack) { StackMaster::Stack.new(stack_name: stack_name,
12
- region: region,
13
- parameters: proposed_params,
14
- template_body: "{\"a\": 1}",
15
- template_format: :json) }
16
- let(:stack_name) { 'myapp-vpc' }
17
- let(:region) { 'us-east-1' }
18
-
19
- describe "#proposed_parameters" do
20
- let(:current_params) { { 'param1' => 'hello',
21
- 'param2' => '****'} }
22
- it "stars out noecho params" do
23
- expect(differ.proposed_parameters).to eq "---\nparam1: hello\nparam2: \"****\"\n"
24
- end
25
- end
26
-
27
- describe "#output_diff" do
28
- context "entirely new stack" do
29
- let(:stack) { nil }
30
-
31
- it "outputs the entire stack" do
32
- expect { differ.output_diff }.to output(/\+ \"a\"\: 1/).to_stdout
33
- expect { differ.output_diff }.to output(/param1\: hello/).to_stdout
34
- expect { differ.output_diff }.to output(/No stack found/).to_stdout
35
- end
36
- end
37
-
38
- context "stack update" do
39
- it "outputs the stack diff" do
40
- expect { differ.output_diff }.to output(/\+ \"a\"\: 1/).to_stdout
41
- expect { differ.output_diff }.to output(/param1\: hello/).to_stdout
42
- expect { differ.output_diff }.to_not output(/No stack found/).to_stdout
43
- end
44
- end
45
- end
46
- end
@@ -1,40 +0,0 @@
1
- RSpec.describe StackMaster::StackEvents::Fetcher do
2
- let(:cf) { Aws::CloudFormation::Client.new }
3
- let(:stack_name) { 'blah' }
4
-
5
- before do
6
- allow(Aws::CloudFormation::Client).to receive(:new).and_return(cf)
7
- allow(StackMaster::StackEvents::Streamer).to receive(:stream)
8
- allow(StackMaster::PagedResponseAccumulator).to receive(:call).with(StackMaster.cloud_formation_driver, :describe_stack_events, { stack_name: stack_name }, :stack_events).and_return(OpenStruct.new(stack_events: events))
9
- end
10
-
11
- context 'with 2 stack events' do
12
- let(:events) { [
13
- OpenStruct.new(event_id: '1', stack_id: '1', stack_name: 'blah', timestamp: Time.now),
14
- OpenStruct.new(event_id: '2', stack_id: '1', stack_name: 'blah', timestamp: Time.now)
15
- ] }
16
-
17
- it 'returns stack events' do
18
- events = StackMaster::StackEvents::Fetcher.fetch(stack_name, 'us-east-1')
19
- expect(events.count).to eq 2
20
- end
21
- end
22
-
23
- context 'filtering with a from timestamp' do
24
- let(:two_pm) { Time.parse('2015-10-27 14:00') }
25
- let(:three_pm) { Time.parse('2015-10-27 15:00') }
26
- let(:four_pm) { Time.parse('2015-10-27 16:00') }
27
-
28
- let(:events) {
29
- [
30
- OpenStruct.new(event_id: '1', stack_id: '1', stack_name: 'blah', timestamp: two_pm),
31
- OpenStruct.new(event_id: '2', stack_id: '1', stack_name: 'blah', timestamp: four_pm),
32
- ]
33
- }
34
-
35
- it 'only returns events after the timestamp' do
36
- events = StackMaster::StackEvents::Fetcher.fetch(stack_name, 'us-east-1', from: three_pm)
37
- expect(events.map(&:event_id)).to eq ['2']
38
- end
39
- end
40
- end
@@ -1,18 +0,0 @@
1
- RSpec.describe StackMaster::StackEvents::Presenter do
2
- describe "#print_event" do
3
- let(:time) { Time.new(2001,1,1,2,2,2) }
4
- let(:event) do
5
- double(:event,
6
- timestamp: time,
7
- logical_resource_id: 'MyAwesomeQueue',
8
- resource_type: 'AWS::SQS::Queue',
9
- resource_status: 'CREATE_IN_PROGRESS',
10
- resource_status_reason: 'Resource creation Initiated')
11
- end
12
- subject(:print_event) { described_class.print_event($stdout, event) }
13
-
14
- it "nicely presents event data" do
15
- expect { print_event }.to output("\e[0;33;49m2001-01-01 02:02:02 #{time.strftime('%z')} MyAwesomeQueue AWS::SQS::Queue CREATE_IN_PROGRESS Resource creation Initiated\e[0m\n").to_stdout
16
- end
17
- end
18
- end
@@ -1,47 +0,0 @@
1
- RSpec.describe StackMaster::StackEvents::Streamer do
2
- let(:events_first_call) { [
3
- OpenStruct.new(event_id: '1', resource_status: 'BLAH', timestamp: Time.now),
4
- OpenStruct.new(event_id: '2', resource_status: 'BLAH', timestamp: Time.now),
5
- OpenStruct.new(event_id: '3', resource_status: 'BLAH', timestamp: Time.now),
6
- ] }
7
- let(:events_second_call) {
8
- events_first_call + [
9
- OpenStruct.new(event_id: '4', resource_status: 'UPDATE_COMPLETE', resource_type: 'AWS::CloudFormation::Stack', logical_resource_id: stack_name, timestamp: Time.now)
10
- ]
11
- }
12
- let(:stack_name) { 'stack-name' }
13
- let(:region) { 'us-east-1' }
14
- let(:now) { Time.now }
15
-
16
- before do
17
- allow(StackMaster::StackEvents::Fetcher).to receive(:fetch).with(stack_name, region, from: now).and_return(events_first_call, events_second_call)
18
- allow(Time).to receive(:now).and_return(now)
19
- end
20
-
21
- it 'returns after seeing a finish state' do
22
- events = []
23
- StackMaster::StackEvents::Streamer.stream(stack_name, region, sleep_between_fetches: 0) do |event|
24
- events << event
25
- end
26
- end
27
-
28
- it 'streams events to an io object' do
29
- io = StringIO.new
30
- StackMaster::StackEvents::Streamer.stream(stack_name, region, sleep_between_fetches: 0, io: io)
31
- expect(io.string).to include('UPDATE_COMPLETE')
32
- end
33
-
34
- context "the stack is in a failed state" do
35
- let(:events_second_call) {
36
- events_first_call + [
37
- OpenStruct.new(event_id: '4', resource_status: 'ROLLBACK_FAILED', resource_type: 'AWS::CloudFormation::Stack', logical_resource_id: stack_name, timestamp: Time.now)
38
- ]
39
- }
40
-
41
- it 'raises an error on failure' do
42
- expect {
43
- StackMaster::StackEvents::Streamer.stream(stack_name, region, sleep_between_fetches: 0)
44
- }.to raise_error(StackMaster::StackEvents::Streamer::StackFailed)
45
- end
46
- end
47
- end
@@ -1,184 +0,0 @@
1
- RSpec.describe StackMaster::Stack do
2
- let(:region) { 'us-east-1' }
3
- let(:stack_name) { 'myapp_vpc' }
4
- let(:stack_id) { '1' }
5
- let(:stack_policy_body) { '{}' }
6
- let(:cf) { Aws::CloudFormation::Client.new }
7
- subject(:stack) { StackMaster::Stack.find(region, stack_name) }
8
-
9
- before do
10
- allow(Aws::CloudFormation::Client).to receive(:new).and_return(cf)
11
- end
12
-
13
- describe '.find' do
14
- context 'when the stack exists in AWS' do
15
- let(:parameters) {
16
- [
17
- {parameter_key: 'param1', parameter_value: 'value1'},
18
- {parameter_key: 'param2', parameter_value: 'value2'}
19
- ]
20
- }
21
- before do
22
- cf.stub_responses(:describe_stacks, stacks: [{stack_id: stack_id, stack_name: stack_name, creation_time: Time.now, stack_status: 'UPDATE_COMPLETE', parameters: parameters, notification_arns: ['test_arn'], role_arn: 'test_service_role_arn'}])
23
- cf.stub_responses(:get_template, template_body: "{}")
24
- cf.stub_responses(:get_stack_policy, stack_policy_body: stack_policy_body)
25
- end
26
-
27
- it 'returns a stack object with a stack_id' do
28
- expect(stack.stack_id).to eq stack_id
29
- end
30
-
31
- it "returns a template body" do
32
- expect(stack.template_body).to eq "{}"
33
- end
34
-
35
- it 'parses parameters into a hash' do
36
- expect(stack.parameters).to eq({'param1' => 'value1', 'param2' => 'value2'})
37
- end
38
-
39
- it 'sets role_arn' do
40
- expect(stack.role_arn).to eq('test_service_role_arn')
41
- end
42
-
43
- it 'sets notification_arns' do
44
- expect(stack.notification_arns).to eq(['test_arn'])
45
- end
46
-
47
- it 'sets the stack policy' do
48
- expect(stack.stack_policy_body).to eq stack_policy_body
49
- end
50
- end
51
-
52
- context 'when the stack does not exist in AWS' do
53
- before do
54
- cf.stub_responses(:describe_stacks, Aws::CloudFormation::Errors::ValidationError.new('a', 'b'))
55
- end
56
-
57
- it 'returns nil' do
58
- stack = StackMaster::Stack.find(region, stack_name)
59
- expect(stack).to be_nil
60
- end
61
- end
62
-
63
- context 'when CF returns no stacks' do
64
- before do
65
- cf.stub_responses(:describe_stacks, stacks: [])
66
- end
67
-
68
- it 'returns nil' do
69
- stack = StackMaster::Stack.find(region, stack_name)
70
- expect(stack).to be_nil
71
- end
72
- end
73
- end
74
-
75
- describe '.generate' do
76
- let(:tags) { {'tag1' => 'value1'} }
77
- let(:stack_definition) { StackMaster::StackDefinition.new(region: region, stack_name: stack_name, tags: tags, base_dir: '/base_dir', template: template_file_name, notification_arns: ['test_arn'], role_arn: 'test_service_role_arn', stack_policy_file: 'no_replace_rds.json') }
78
- let(:config) { StackMaster::Config.new({'stacks' => {}}, '/base_dir') }
79
- subject(:stack) { StackMaster::Stack.generate(stack_definition, config) }
80
- let(:parameter_hash) { {template_parameters: {'DbPassword' => {'secret' => 'db_password'}}, compile_time_parameters: {}} }
81
- let(:resolved_template_parameters) { {'DbPassword' => 'sdfgjkdhlfjkghdflkjghdflkjg', 'InstanceType' => 't2.medium'} }
82
- let(:resolved_compile_time_parameters) { {} }
83
- let(:template_file_name) { 'template.rb' }
84
- let(:template_body) { '{"Parameters": { "VpcId": { "Description": "VPC ID" }, "InstanceType": { "Description": "Instance Type", "Default": "t2.micro" }} }' }
85
- let(:template_format) { :json }
86
- let(:stack_policy_body) { '{}' }
87
-
88
- before do
89
- allow(StackMaster::ParameterLoader).to receive(:load).and_return(parameter_hash)
90
- allow(StackMaster::ParameterResolver).to receive(:resolve).with(config,stack_definition,parameter_hash[:template_parameters]).and_return(resolved_template_parameters)
91
- allow(StackMaster::ParameterResolver).to receive(:resolve).with(config,stack_definition,parameter_hash[:compile_time_parameters]).and_return(resolved_compile_time_parameters)
92
- allow(StackMaster::TemplateCompiler).to receive(:compile).with(config, stack_definition.template_file_path, resolved_compile_time_parameters, stack_definition.compiler_options).and_return(template_body)
93
- allow(File).to receive(:read).with(stack_definition.stack_policy_file_path).and_return(stack_policy_body)
94
- end
95
-
96
- it 'has the stack definitions region' do
97
- expect(stack.region).to eq region
98
- end
99
-
100
- it 'has the stack definitions name' do
101
- expect(stack.stack_name).to eq stack_name
102
- end
103
-
104
- it 'has the stack definitions tags' do
105
- expect(stack.tags).to eq tags
106
- end
107
-
108
- it 'resolves the parameters' do
109
- expect(stack.parameters).to eq resolved_template_parameters
110
- end
111
-
112
- it 'compiles the template body' do
113
- expect(stack.template_body).to eq template_body
114
- end
115
-
116
- it 'has role_arn' do
117
- expect(stack.role_arn).to eq 'test_service_role_arn'
118
- end
119
-
120
- it 'has notification_arns' do
121
- expect(stack.notification_arns).to eq ['test_arn']
122
- end
123
-
124
- it 'has the stack policy' do
125
- expect(stack.stack_policy_body).to eq stack_policy_body
126
- end
127
-
128
- it 'extracts default template parameters' do
129
- expect(stack.template_default_parameters).to eq('VpcId' => nil, 'InstanceType' => 't2.micro')
130
- end
131
-
132
- it 'exposes parameters with defaults taken into account' do
133
- expect(stack.parameters_with_defaults).to eq('DbPassword' => 'sdfgjkdhlfjkghdflkjghdflkjg', 'InstanceType' => 't2.medium', 'VpcId' => nil)
134
- end
135
- end
136
-
137
- describe '#too_big?' do
138
- let(:big_stack) { described_class.new(template_body: "{\"a\":\"#{'x' * 500000}\"}") }
139
- let(:medium_stack) { described_class.new(template_body: "{\"a\":\"#{'x' * 60000}\"}") }
140
- let(:little_stack) { described_class.new(template_body: "{\"a\":\"#{'x' * 1000}\"}") }
141
-
142
- context 'when not using S3' do
143
- it 'returns true for big stacks' do
144
- expect(big_stack.too_big?).to be_truthy
145
- end
146
- it 'returns true for medium stacks' do
147
- expect(medium_stack.too_big?).to be_truthy
148
- end
149
- it 'returns false for small stacks' do
150
- expect(little_stack.too_big?).to be_falsey
151
- end
152
- end
153
-
154
- context 'when using S3' do
155
- it 'returns true for big stacks' do
156
- expect(big_stack.too_big?(true)).to be_truthy
157
- end
158
- it 'returns false for medium stacks' do
159
- expect(medium_stack.too_big?(true)).to be_falsey
160
- end
161
- it 'returns false for small stacks' do
162
- expect(little_stack.too_big?(true)).to be_falsey
163
- end
164
- end
165
- end
166
-
167
- describe '#missing_parameters?' do
168
- subject { stack.missing_parameters? }
169
-
170
- let(:stack) { StackMaster::Stack.new(parameters: parameters, template_body: '{}', template_format: :json) }
171
-
172
- context 'when a parameter has a nil value' do
173
- let(:parameters) { {'my_param' => nil} }
174
-
175
- it { should eq true }
176
- end
177
-
178
- context 'when no parameers have a nil value' do
179
- let(:parameters) { {'my_param' => '1'} }
180
-
181
- it { should eq false }
182
- end
183
- end
184
- end
@@ -1,39 +0,0 @@
1
- RSpec.describe StackMaster::TemplateCompiler do
2
- describe '.compile' do
3
- let(:config) { double(template_compilers: { fab: :test_template_compiler }) }
4
- let(:template_file_path) { '/base_dir/templates/template.fab' }
5
- let(:compile_time_parameters) { { 'InstanceType' => 't2.medium' } }
6
-
7
- class TestTemplateCompiler
8
- def self.require_dependencies; end
9
- def self.compile(template_file_path, compile_time_parameters, compile_options); end
10
- end
11
-
12
- context 'when a template compiler is registered for the given file type' do
13
- before {
14
- StackMaster::TemplateCompiler.register(:test_template_compiler, TestTemplateCompiler)
15
- }
16
-
17
- it 'compiles the template using the relevant template compiler' do
18
- expect(TestTemplateCompiler).to receive(:compile).with(template_file_path, compile_time_parameters, anything)
19
- StackMaster::TemplateCompiler.compile(config, template_file_path, compile_time_parameters, compile_time_parameters)
20
- end
21
-
22
- it 'passes compile_options to the template compiler' do
23
- opts = {foo: 1, bar: true, baz: "meh"}
24
- expect(TestTemplateCompiler).to receive(:compile).with(template_file_path, compile_time_parameters, opts)
25
- StackMaster::TemplateCompiler.compile(config, template_file_path, compile_time_parameters,opts)
26
- end
27
-
28
- context 'when template compilation fails' do
29
- before { allow(TestTemplateCompiler).to receive(:compile).and_raise(RuntimeError) }
30
-
31
- it 'raise TemplateCompilationFailed exception' do
32
- expect{ StackMaster::TemplateCompiler.compile(config, template_file_path, compile_time_parameters, compile_time_parameters)
33
- }.to raise_error(
34
- StackMaster::TemplateCompiler::TemplateCompilationFailed,"Failed to compile #{template_file_path}.")
35
- end
36
- end
37
- end
38
- end
39
- end
@@ -1,22 +0,0 @@
1
- RSpec.describe StackMaster::TemplateCompilers::Cfndsl do
2
-
3
- let(:compile_time_parameters) { {'InstanceType' => 't2.medium'} }
4
-
5
- before(:all) { described_class.require_dependencies }
6
-
7
- describe '.compile' do
8
- def compile
9
- described_class.compile(template_file_path, compile_time_parameters)
10
- end
11
-
12
- context 'valid cfndsl template' do
13
- let(:template_file_path) { 'spec/fixtures/templates/rb/cfndsl/sample.rb' }
14
- let(:valid_compiled_json_path) { 'spec/fixtures/templates/rb/cfndsl/sample.json' }
15
-
16
- it 'produces valid JSON' do
17
- valid_compiled_json = File.read(valid_compiled_json_path)
18
- expect(JSON.parse(compile)).to eq(JSON.parse(valid_compiled_json))
19
- end
20
- end
21
- end
22
- end
@@ -1,32 +0,0 @@
1
- RSpec.describe StackMaster::TemplateCompilers::Json do
2
-
3
- let(:compile_time_parameters) { { 'InstanceType' => 't2.medium' } }
4
-
5
- describe '.compile' do
6
- def compile
7
- described_class.compile(template_file_path, compile_time_parameters)
8
- end
9
-
10
- let(:template_file_path) { '/base_dir/templates/template.json' }
11
-
12
- context "small json template" do
13
- before do
14
- allow(File).to receive(:read).with(template_file_path).and_return('{ }')
15
- end
16
-
17
- it "reads from the template file path" do
18
- expect(compile).to eq('{ }')
19
- end
20
- end
21
-
22
- context 'extra big json template' do
23
- before do
24
- allow(File).to receive(:read).with(template_file_path).and_return("{ #{' ' * 60000} }")
25
- end
26
-
27
- it "reads from the template file path" do
28
- expect(compile).to eq('{}')
29
- end
30
- end
31
- end
32
- end
@@ -1,116 +0,0 @@
1
- RSpec.describe StackMaster::TemplateCompilers::SparkleFormation do
2
-
3
- describe '.compile' do
4
- def compile
5
- described_class.compile(template_file_path, compile_time_parameters, compiler_options)
6
- end
7
-
8
- let(:template_file_path) { '/base_dir/templates/template.rb' }
9
- let(:compile_time_parameters) { {'Ip' => '10.0.0.0', 'Name' => 'Something'} }
10
- let(:compiler_options) { {} }
11
- let(:compile_time_parameter_definitions) { {} }
12
-
13
- let(:sparkle_template) { instance_double(::SparkleFormation) }
14
- let(:definitions_validator) { instance_double(StackMaster::SparkleFormation::CompileTime::DefinitionsValidator) }
15
- let(:parameters_validator) { instance_double(StackMaster::SparkleFormation::CompileTime::ParametersValidator) }
16
- let(:state_builder) { instance_double(StackMaster::SparkleFormation::CompileTime::StateBuilder) }
17
-
18
- let(:sparkle_double) { instance_double(::SparkleFormation::SparkleCollection) }
19
-
20
- before do
21
- allow(::SparkleFormation).to receive(:compile).with(template_file_path, :sparkle).and_return(sparkle_template)
22
- allow(::SparkleFormation::Sparkle).to receive(:new)
23
- allow(StackMaster::SparkleFormation::CompileTime::DefinitionsValidator).to receive(:new).and_return(definitions_validator)
24
- allow(StackMaster::SparkleFormation::CompileTime::ParametersValidator).to receive(:new).and_return(parameters_validator)
25
- allow(StackMaster::SparkleFormation::CompileTime::StateBuilder).to receive(:new).and_return(state_builder)
26
- allow(::SparkleFormation::SparkleCollection).to receive(:new).and_return(sparkle_double)
27
-
28
- allow(sparkle_template).to receive(:parameters).and_return(compile_time_parameter_definitions)
29
- allow(sparkle_template).to receive(:sparkle).and_return(sparkle_double)
30
- allow(sparkle_double).to receive(:apply)
31
- allow(sparkle_double).to receive(:set_root)
32
- allow(definitions_validator).to receive(:validate)
33
- allow(parameters_validator).to receive(:validate)
34
- allow(state_builder).to receive(:build).and_return({})
35
- allow(sparkle_template).to receive(:compile_time_parameter_setter).and_yield
36
- allow(sparkle_template).to receive(:compile_state=)
37
- allow(sparkle_template).to receive(:to_json).and_return("{\n}")
38
- end
39
-
40
- it 'compiles with sparkleformation' do
41
- expect(compile).to eq("{\n}")
42
- end
43
-
44
- it 'sets the appropriate sparkle_path' do
45
- compile
46
- expect(::SparkleFormation.sparkle_path).to eq File.dirname(template_file_path)
47
- end
48
-
49
- it 'should validate the compile time definitions' do
50
- expect(StackMaster::SparkleFormation::CompileTime::DefinitionsValidator).to receive(:new).with(compile_time_parameter_definitions)
51
- expect(definitions_validator).to receive(:validate)
52
- compile
53
- end
54
-
55
- it 'should validate the parameters against any compile time definitions' do
56
- expect(StackMaster::SparkleFormation::CompileTime::ParametersValidator).to receive(:new).with(compile_time_parameter_definitions, compile_time_parameters)
57
- expect(parameters_validator).to receive(:validate)
58
- compile
59
- end
60
-
61
- it 'should create the compile state' do
62
- expect(StackMaster::SparkleFormation::CompileTime::StateBuilder).to receive(:new).with(compile_time_parameter_definitions, compile_time_parameters)
63
- expect(state_builder).to receive(:build)
64
- compile
65
- end
66
-
67
- it 'should set the compile state' do
68
- expect(sparkle_template).to receive(:compile_state=).with({})
69
- compile
70
- end
71
-
72
- context 'with a custom sparkle_path' do
73
- let(:compiler_options) { {'sparkle_path' => '../foo'} }
74
-
75
- it 'does not use the default path' do
76
- compile
77
- expect(::SparkleFormation.sparkle_path).to_not eq File.dirname(template_file_path)
78
- end
79
-
80
- it 'expands the given path' do
81
- compile
82
- expect(::SparkleFormation.sparkle_path).to match %r{^/.+/foo}
83
- end
84
- end
85
-
86
- end
87
-
88
- describe '.compile with sparkle packs' do
89
- let(:compile_time_parameters) { {} }
90
- subject(:compile) { described_class.compile(template_file_path, compile_time_parameters, compiler_options)}
91
-
92
- context 'with a sparkle_pack loaded' do
93
- let(:template_file_path) { File.join(File.dirname(__FILE__), "..", "..", "fixtures", "sparkle_pack_integration", "templates", "template_with_dynamic_from_pack.rb")}
94
- let(:compiler_options) { {"sparkle_packs" => ["my_sparkle_pack"]} }
95
-
96
- before do
97
- lib = File.join(File.dirname(__FILE__), "..", "..", "fixtures", "sparkle_pack_integration", "my_sparkle_pack", "lib")
98
- puts "Loading from #{lib}"
99
- $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
100
- end
101
-
102
- it 'pulls the dynamic from the sparkle pack' do
103
- expect(compile).to eq(%Q({\n \"Outputs\": {\n \"Foo\": {\n \"Value\": \"bar\"\n }\n }\n}))
104
- end
105
- end
106
-
107
- context 'without a sparkle_pack loaded' do
108
- let(:template_file_path) { File.join(File.dirname(__FILE__), "..", "..", "fixtures", "sparkle_pack_integration", "templates", "template_with_dynamic.rb")}
109
- let(:compiler_options) { {} }
110
-
111
- it 'pulls the dynamic from the local path' do
112
- expect(compile).to eq(%Q({\n \"Outputs\": {\n \"Bar\": {\n \"Value\": \"local_dynamic\"\n }\n }\n}))
113
- end
114
- end
115
- end
116
- end