convection 2.2.9 → 2.2.10
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/bin/convection +65 -2
- 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: f7c478ce35a94d9130d3d2657a092bdb5436f505
|
4
|
+
data.tar.gz: d5dff048c6a317a79b0b8df5743f148768e0b368
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 4690a2b22a2988cd38cb7ae2d8e2dceac1bdd7f0b2080d3a2a42190b2ff2ed6033733b6ddfad97e6afd44c409e92a0c5a97f8220346f62f68ca37e871f03de7f
|
7
|
+
data.tar.gz: 1104ceadddfcc37b30dc12804e8e65b3fd580328421788da03fd6f90a3eb5f5df0ecac2da0bafa1d1a535668c7c4ba30092365521365d0fe28d544662f61b779
|
data/bin/convection
CHANGED
@@ -13,6 +13,7 @@ module Convection
|
|
13
13
|
include Thor::Actions
|
14
14
|
|
15
15
|
DEFAULT_MODULE_PATH = 'root'.freeze
|
16
|
+
S3_URI_REGEX = %r(^s3://(?<bucket>[^/]+)/(?<key>.+)).freeze
|
16
17
|
|
17
18
|
def initialize(*args)
|
18
19
|
super
|
@@ -119,6 +120,38 @@ module Convection
|
|
119
120
|
describe_stack_resources(options[:stack], options[:format], options[:properties], options[:type])
|
120
121
|
end
|
121
122
|
|
123
|
+
desc 'terraForm-compare-resources', 'Compare resources in CloudFormation and in terraform state'
|
124
|
+
option :stack_name, desc: 'The CloudFormation stack name (Stack#cloud_name)'
|
125
|
+
option :stack_region, desc: 'The region where the stack resides', required: true
|
126
|
+
option :state, desc: 'The source terraform state file (can be an s3:// uri)', required: true
|
127
|
+
option :state_region, desc: 'The region where the state resides (required to load remote state)'
|
128
|
+
def terraform_compare_resources
|
129
|
+
terraform_resources = tfstate['modules'].flat_map { |m|
|
130
|
+
m['resources'].reject { |k, _| k.start_with?('data.') }
|
131
|
+
}.reduce({}, &:merge)
|
132
|
+
cf = Aws::CloudFormation::Client.new(region: options[:stack_region])
|
133
|
+
cf_resources = cf.describe_stack_resources(stack_name: options[:stack_name]).stack_resources
|
134
|
+
cf_resources.each do |cf_resource|
|
135
|
+
say "Resource '#{cf_resource.physical_resource_id}':"
|
136
|
+
say " * CloudFormation Logical ID #{cf_resource.logical_resource_id}"
|
137
|
+
|
138
|
+
tf_resource_name, tf_resource = terraform_resources.find do |_, tf_resource|
|
139
|
+
next true if tf_resource['primary'].key(cf_resource.physical_resource_id)
|
140
|
+
tf_resource['primary'].values.any? { |v| v.is_a?(String) && v.include?(cf_resource.physical_resource_id) }
|
141
|
+
end
|
142
|
+
tf_key = tf_resource && tf_resource['primary'].key(cf_resource.physical_resource_id)
|
143
|
+
fuzzy_match = tf_key.nil?
|
144
|
+
tf_key ||= tf_resource && tf_resource['primary'].find { |v| v.include?(cf_resource.physical_resource_id) }
|
145
|
+
if tf_key && fuzzy_match
|
146
|
+
say " * Found physical ID included in Terraform resource #{tf_resource_name} under attribute #{tf_key} with value '#{tf_resource['primary'][tf_key]}'. Please validate this resource is included in state and configuration.", :yellow
|
147
|
+
elsif tf_key && !fuzzy_match
|
148
|
+
say " * Found physical ID exactly in Terraform resource #{tf_resource_name} under attribute #{tf_key} with value '#{tf_resource['primary'][tf_key]}'.", :cyan
|
149
|
+
else
|
150
|
+
say " * Unable to find physical ID in the provided Terraform state.", :red
|
151
|
+
end
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
122
155
|
# rubocop:disable Style/AsciiComments
|
123
156
|
|
124
157
|
desc 'terraform-export STACK', 'Create terraform configuration for a given stack (including `terraform import` commands)'
|
@@ -140,7 +173,8 @@ module Convection
|
|
140
173
|
end
|
141
174
|
|
142
175
|
init_cloud
|
143
|
-
|
176
|
+
@stack = @cloud.stacks.fetch(stack_name)
|
177
|
+
template = @stack.template
|
144
178
|
|
145
179
|
# Beware of 🐲. This patches this instance to include terraform compatible intrinsic functions where possible.
|
146
180
|
#
|
@@ -243,6 +277,32 @@ module Convection
|
|
243
277
|
|
244
278
|
private
|
245
279
|
|
280
|
+
def load_local_terraform_state(statefile)
|
281
|
+
JSON.load(File.open(statefile))
|
282
|
+
end
|
283
|
+
|
284
|
+
def load_remote_terraform_state(bucket, key)
|
285
|
+
unless options[:state_region] && !options[:state_region].empty?
|
286
|
+
say 'ERROR: --state-region must be specified to load remote state.', :red
|
287
|
+
exit 1
|
288
|
+
end
|
289
|
+
|
290
|
+
s3 = Aws::S3::Client.new(region: options[:state_region])
|
291
|
+
object = s3.get_object(bucket: bucket, key: key)
|
292
|
+
JSON.load(object.body)
|
293
|
+
end
|
294
|
+
|
295
|
+
def tfstate
|
296
|
+
return @tfstate if @tfstate
|
297
|
+
|
298
|
+
match_data = options[:state].match(S3_URI_REGEX)
|
299
|
+
if match_data
|
300
|
+
@tfstate = load_remote_terraform_state(match_data['bucket'], match_data['key'])
|
301
|
+
else
|
302
|
+
@tfstate = load_local_terraform_state(options[:state])
|
303
|
+
end
|
304
|
+
end
|
305
|
+
|
246
306
|
def import_resources(_resource_name, resource)
|
247
307
|
empty_directory options[:output_directory] if resource.respond_to?(:to_hcl_json) || resource.respond_to?(:additional_hcl_files)
|
248
308
|
if resource.respond_to?(:to_hcl_json)
|
@@ -263,7 +323,9 @@ module Convection
|
|
263
323
|
end
|
264
324
|
|
265
325
|
if resource.respond_to?(:terraform_import_commands)
|
266
|
-
|
326
|
+
destination = File.join(options[:output_directory], "terraform-import-#{resource_name.underscore}-#{@stack._original_region}-#{@stack._original_cloud}.sh")
|
327
|
+
lines = resource.terraform_import_commands(module_path: options[:module_path])
|
328
|
+
lines.each do |line|
|
267
329
|
comment = line.start_with?('#')
|
268
330
|
if options[:omit_comments]
|
269
331
|
next if comment || line.strip.empty?
|
@@ -272,6 +334,7 @@ module Convection
|
|
272
334
|
color = comment ? :bold : :cyan
|
273
335
|
say line, color
|
274
336
|
end
|
337
|
+
create_file destination, lines.join("\n")
|
275
338
|
else
|
276
339
|
say "# Unable to determine terraform import commands for #{resource.class}. Define #{resource.class}#terraform_import_commands to do so.", :yellow
|
277
340
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: convection
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.2.
|
4
|
+
version: 2.2.10
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- John Manero
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2017-12-
|
11
|
+
date: 2017-12-22 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activesupport
|