cumulus-aws 0.11.1
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 +15 -0
- data/.gitignore +3 -0
- data/.travis.yml +12 -0
- data/Gemfile +4 -0
- data/Gemfile.lock +29 -0
- data/LICENSE +202 -0
- data/README.md +41 -0
- data/autocomplete +137 -0
- data/bin/cumulus +658 -0
- data/cumulus +2 -0
- data/cumulus-aws.gemspec +20 -0
- data/lib/autoscaling/AutoScaling.rb +40 -0
- data/lib/autoscaling/loader/Loader.rb +56 -0
- data/lib/autoscaling/manager/Manager.rb +360 -0
- data/lib/autoscaling/models/AlarmConfig.rb +165 -0
- data/lib/autoscaling/models/AlarmDiff.rb +172 -0
- data/lib/autoscaling/models/AutoScalingDiff.rb +178 -0
- data/lib/autoscaling/models/GroupConfig.rb +330 -0
- data/lib/autoscaling/models/PolicyConfig.rb +135 -0
- data/lib/autoscaling/models/PolicyDiff.rb +73 -0
- data/lib/autoscaling/models/ScheduledActionDiff.rb +53 -0
- data/lib/autoscaling/models/ScheduledConfig.rb +96 -0
- data/lib/aws_extensions/ec2/DhcpOptions.rb +41 -0
- data/lib/aws_extensions/ec2/Instance.rb +29 -0
- data/lib/aws_extensions/ec2/NetworkAcl.rb +25 -0
- data/lib/aws_extensions/ec2/NetworkInterface.rb +14 -0
- data/lib/aws_extensions/ec2/RouteTable.rb +26 -0
- data/lib/aws_extensions/ec2/SecurityGroup.rb +16 -0
- data/lib/aws_extensions/ec2/Subnet.rb +28 -0
- data/lib/aws_extensions/ec2/Volume.rb +24 -0
- data/lib/aws_extensions/ec2/Vpc.rb +14 -0
- data/lib/aws_extensions/ec2/VpcEndpoint.rb +11 -0
- data/lib/aws_extensions/elb/BackendServerDescription.rb +12 -0
- data/lib/aws_extensions/elb/PolicyDescription.rb +14 -0
- data/lib/aws_extensions/kinesis/StreamDescription.rb +12 -0
- data/lib/aws_extensions/route53/AliasTarget.rb +21 -0
- data/lib/aws_extensions/s3/Bucket.rb +33 -0
- data/lib/aws_extensions/s3/BucketAcl.rb +28 -0
- data/lib/aws_extensions/s3/BucketCors.rb +17 -0
- data/lib/aws_extensions/s3/BucketLifecycle.rb +21 -0
- data/lib/aws_extensions/s3/BucketLogging.rb +18 -0
- data/lib/aws_extensions/s3/BucketNotification.rb +23 -0
- data/lib/aws_extensions/s3/BucketPolicy.rb +18 -0
- data/lib/aws_extensions/s3/BucketTagging.rb +15 -0
- data/lib/aws_extensions/s3/BucketVersioning.rb +14 -0
- data/lib/aws_extensions/s3/BucketWebsite.rb +49 -0
- data/lib/aws_extensions/s3/CORSRule.rb +27 -0
- data/lib/aws_extensions/s3/ReplicationConfiguration.rb +22 -0
- data/lib/cloudfront/CloudFront.rb +83 -0
- data/lib/cloudfront/loader/Loader.rb +31 -0
- data/lib/cloudfront/manager/Manager.rb +183 -0
- data/lib/cloudfront/models/CacheBehaviorConfig.rb +237 -0
- data/lib/cloudfront/models/CacheBehaviorDiff.rb +211 -0
- data/lib/cloudfront/models/CustomOriginConfig.rb +51 -0
- data/lib/cloudfront/models/CustomOriginDiff.rb +74 -0
- data/lib/cloudfront/models/DistributionConfig.rb +183 -0
- data/lib/cloudfront/models/DistributionDiff.rb +131 -0
- data/lib/cloudfront/models/InvalidationConfig.rb +37 -0
- data/lib/cloudfront/models/OriginConfig.rb +144 -0
- data/lib/cloudfront/models/OriginDiff.rb +86 -0
- data/lib/cloudfront/models/OriginSslProtocols.rb +28 -0
- data/lib/cloudfront/models/OriginSslProtocolsDiff.rb +39 -0
- data/lib/common/BaseLoader.rb +80 -0
- data/lib/common/manager/Manager.rb +148 -0
- data/lib/common/models/Diff.rb +114 -0
- data/lib/common/models/ListChange.rb +21 -0
- data/lib/common/models/TagsDiff.rb +55 -0
- data/lib/common/models/UTCTimeSource.rb +17 -0
- data/lib/conf/Configuration.rb +365 -0
- data/lib/ec2/EC2.rb +503 -0
- data/lib/ec2/IPProtocolMapping.rb +165 -0
- data/lib/ec2/loaders/EbsLoader.rb +19 -0
- data/lib/ec2/loaders/InstanceLoader.rb +32 -0
- data/lib/ec2/managers/EbsManager.rb +176 -0
- data/lib/ec2/managers/InstanceManager.rb +509 -0
- data/lib/ec2/models/EbsGroupConfig.rb +133 -0
- data/lib/ec2/models/EbsGroupDiff.rb +48 -0
- data/lib/ec2/models/InstanceConfig.rb +202 -0
- data/lib/ec2/models/InstanceDiff.rb +95 -0
- data/lib/elb/ELB.rb +148 -0
- data/lib/elb/loader/Loader.rb +65 -0
- data/lib/elb/manager/Manager.rb +581 -0
- data/lib/elb/models/AccessLogConfig.rb +82 -0
- data/lib/elb/models/AccessLogDiff.rb +47 -0
- data/lib/elb/models/HealthCheckConfig.rb +91 -0
- data/lib/elb/models/HealthCheckDiff.rb +50 -0
- data/lib/elb/models/ListenerConfig.rb +99 -0
- data/lib/elb/models/ListenerDiff.rb +91 -0
- data/lib/elb/models/LoadBalancerConfig.rb +239 -0
- data/lib/elb/models/LoadBalancerDiff.rb +265 -0
- data/lib/iam/IAM.rb +36 -0
- data/lib/iam/loader/Loader.rb +117 -0
- data/lib/iam/manager/IamGroups.rb +98 -0
- data/lib/iam/manager/IamResource.rb +288 -0
- data/lib/iam/manager/IamRoles.rb +112 -0
- data/lib/iam/manager/IamUsers.rb +54 -0
- data/lib/iam/manager/Manager.rb +29 -0
- data/lib/iam/migration/AssumeRoleUnifier.rb +34 -0
- data/lib/iam/migration/PolicyUnifier.rb +90 -0
- data/lib/iam/models/GroupConfig.rb +40 -0
- data/lib/iam/models/IamDiff.rb +132 -0
- data/lib/iam/models/PolicyConfig.rb +67 -0
- data/lib/iam/models/ResourceWithPolicy.rb +208 -0
- data/lib/iam/models/RoleConfig.rb +53 -0
- data/lib/iam/models/StatementConfig.rb +35 -0
- data/lib/iam/models/UserConfig.rb +21 -0
- data/lib/kinesis/Kinesis.rb +94 -0
- data/lib/kinesis/loader/Loader.rb +19 -0
- data/lib/kinesis/manager/Manager.rb +206 -0
- data/lib/kinesis/models/StreamConfig.rb +75 -0
- data/lib/kinesis/models/StreamDiff.rb +58 -0
- data/lib/lambda/Lambda.rb +41 -0
- data/lib/route53/loader/Loader.rb +32 -0
- data/lib/route53/manager/Manager.rb +241 -0
- data/lib/route53/models/AliasTarget.rb +86 -0
- data/lib/route53/models/RecordConfig.rb +178 -0
- data/lib/route53/models/RecordDiff.rb +140 -0
- data/lib/route53/models/Vpc.rb +24 -0
- data/lib/route53/models/ZoneConfig.rb +156 -0
- data/lib/route53/models/ZoneDiff.rb +118 -0
- data/lib/s3/S3.rb +89 -0
- data/lib/s3/loader/Loader.rb +66 -0
- data/lib/s3/manager/Manager.rb +296 -0
- data/lib/s3/models/BucketConfig.rb +321 -0
- data/lib/s3/models/BucketDiff.rb +167 -0
- data/lib/s3/models/GrantConfig.rb +189 -0
- data/lib/s3/models/GrantDiff.rb +50 -0
- data/lib/s3/models/LifecycleConfig.rb +142 -0
- data/lib/s3/models/LifecycleDiff.rb +46 -0
- data/lib/s3/models/LoggingConfig.rb +81 -0
- data/lib/s3/models/NotificationConfig.rb +157 -0
- data/lib/s3/models/NotificationDiff.rb +62 -0
- data/lib/s3/models/ReplicationConfig.rb +133 -0
- data/lib/s3/models/ReplicationDiff.rb +60 -0
- data/lib/s3/models/WebsiteConfig.rb +107 -0
- data/lib/security/SecurityGroups.rb +39 -0
- data/lib/security/loader/Loader.rb +94 -0
- data/lib/security/manager/Manager.rb +246 -0
- data/lib/security/models/RuleConfig.rb +161 -0
- data/lib/security/models/RuleDiff.rb +72 -0
- data/lib/security/models/RuleMigration.rb +127 -0
- data/lib/security/models/SecurityGroupConfig.rb +172 -0
- data/lib/security/models/SecurityGroupDiff.rb +112 -0
- data/lib/sns/SNS.rb +40 -0
- data/lib/sqs/SQS.rb +62 -0
- data/lib/sqs/loader/Loader.rb +34 -0
- data/lib/sqs/manager/Manager.rb +128 -0
- data/lib/sqs/models/DeadLetterConfig.rb +70 -0
- data/lib/sqs/models/DeadLetterDiff.rb +35 -0
- data/lib/sqs/models/QueueConfig.rb +115 -0
- data/lib/sqs/models/QueueDiff.rb +89 -0
- data/lib/util/Colors.rb +111 -0
- data/lib/util/StatusCodes.rb +51 -0
- data/lib/vpc/loader/Loader.rb +73 -0
- data/lib/vpc/manager/Manager.rb +954 -0
- data/lib/vpc/models/AclEntryConfig.rb +150 -0
- data/lib/vpc/models/AclEntryDiff.rb +54 -0
- data/lib/vpc/models/DhcpConfig.rb +100 -0
- data/lib/vpc/models/DhcpDiff.rb +90 -0
- data/lib/vpc/models/EndpointConfig.rb +76 -0
- data/lib/vpc/models/EndpointDiff.rb +69 -0
- data/lib/vpc/models/NetworkAclConfig.rb +87 -0
- data/lib/vpc/models/NetworkAclDiff.rb +116 -0
- data/lib/vpc/models/RouteConfig.rb +82 -0
- data/lib/vpc/models/RouteDiff.rb +50 -0
- data/lib/vpc/models/RouteTableConfig.rb +92 -0
- data/lib/vpc/models/RouteTableDiff.rb +101 -0
- data/lib/vpc/models/SubnetConfig.rb +113 -0
- data/lib/vpc/models/SubnetDiff.rb +78 -0
- data/lib/vpc/models/VpcConfig.rb +173 -0
- data/lib/vpc/models/VpcDiff.rb +315 -0
- data/rakefile.rb +8 -0
- metadata +245 -0
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
require "conf/Configuration"
|
|
2
|
+
require "ec2/models/EbsGroupDiff"
|
|
3
|
+
|
|
4
|
+
require "json"
|
|
5
|
+
|
|
6
|
+
module Cumulus
|
|
7
|
+
module EC2
|
|
8
|
+
|
|
9
|
+
VolumeGroup = Struct.new(:size, :type, :iops, :count, :encrypted, :kms_key) do
|
|
10
|
+
def to_hash
|
|
11
|
+
{
|
|
12
|
+
"size" => self.size,
|
|
13
|
+
"type" => self.type,
|
|
14
|
+
"iops" => self.iops,
|
|
15
|
+
"count" => self.count,
|
|
16
|
+
"encrypted" => self.encrypted,
|
|
17
|
+
"kms-key" => self.kms_key
|
|
18
|
+
}.reject { |k, v| v.nil? }
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
def description
|
|
22
|
+
[
|
|
23
|
+
"#{self.size}GiB",
|
|
24
|
+
"#{self.type}",
|
|
25
|
+
if self.type == "io1" then "#{self.iops} IOPS" end,
|
|
26
|
+
if self.encrypted then "encrypted" else "unencrypted" end,
|
|
27
|
+
if self.kms_key then "KMS #{self.kms_key}" end,
|
|
28
|
+
].reject(&:nil?).join("/")
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
def hash_key
|
|
32
|
+
"#{self.size}|#{self.type}|#{self.iops}|#{self.encrypted}|#{self.kms_key}"
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
# Public: An object representing configuration for a group of EBS volumes
|
|
37
|
+
class EbsGroupConfig
|
|
38
|
+
attr_reader :name
|
|
39
|
+
attr_reader :volume_groups
|
|
40
|
+
attr_reader :availability_zone
|
|
41
|
+
|
|
42
|
+
# Public: Constructor
|
|
43
|
+
#
|
|
44
|
+
# json - a hash containing the JSON configuration for the group
|
|
45
|
+
def initialize(name, json = nil)
|
|
46
|
+
@name = name
|
|
47
|
+
if !json.nil?
|
|
48
|
+
@availability_zone = json["availability-zone"]
|
|
49
|
+
@volume_groups = (json["volumes"] || []).map do |vg_json|
|
|
50
|
+
VolumeGroup.new(
|
|
51
|
+
vg_json["size"],
|
|
52
|
+
vg_json["type"],
|
|
53
|
+
if vg_json["type"] == "io1" then vg_json["iops"] end,
|
|
54
|
+
vg_json["count"],
|
|
55
|
+
vg_json["encrypted"] || false,
|
|
56
|
+
if vg_json["encrypted"] then vg_json["kms-key"] end
|
|
57
|
+
)
|
|
58
|
+
end
|
|
59
|
+
end
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
def to_hash
|
|
63
|
+
{
|
|
64
|
+
"availability-zone" => @availability_zone,
|
|
65
|
+
"volumes" => @volume_groups.map(&:to_hash),
|
|
66
|
+
}
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
# Public: Populate a config object with AWS configuration
|
|
70
|
+
#
|
|
71
|
+
# aws - the ebs volumes in the group. All volumes should be in the same AZ
|
|
72
|
+
def populate!(aws)
|
|
73
|
+
# Group the aws volumes by size, type, iops, encryped, kms-key
|
|
74
|
+
vol_groups = aws.group_by { |vol| "#{vol.size}|#{vol.volume_type}|#{vol.iops}|#{vol.encrypted}|#{vol.kms_key_id}" }
|
|
75
|
+
|
|
76
|
+
@volume_groups = vol_groups.map do |_, vols|
|
|
77
|
+
VolumeGroup.new(
|
|
78
|
+
vols.first.size,
|
|
79
|
+
vols.first.volume_type,
|
|
80
|
+
if vols.first.volume_type == "io1" then vols.first.iops end,
|
|
81
|
+
vols.length,
|
|
82
|
+
vols.first.encrypted,
|
|
83
|
+
vols.first.kms_key_id
|
|
84
|
+
)
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
# Get the AZ of the first volume
|
|
88
|
+
@availability_zone = aws.first.availability_zone
|
|
89
|
+
|
|
90
|
+
self
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
# Public: Produce an array of differences between this local configuration and the
|
|
94
|
+
# configuration in AWS
|
|
95
|
+
#
|
|
96
|
+
# aws - the AWS resource
|
|
97
|
+
#
|
|
98
|
+
# Returns an array of the EbsGroupDiffs that were found
|
|
99
|
+
def diff(aws)
|
|
100
|
+
diffs = []
|
|
101
|
+
|
|
102
|
+
if @availability_zone != aws.availability_zone
|
|
103
|
+
diffs << EbsGroupDiff.new(EbsGroupChange::AZ, aws.availability_zone, @availability_zone)
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
# Group the aws and local versions by hash_key
|
|
107
|
+
aws_grouped = Hash[aws.volume_groups.map { |vg| [vg.hash_key, vg] }]
|
|
108
|
+
local_grouped = Hash[@volume_groups.map { |vg| [vg.hash_key, vg] }]
|
|
109
|
+
|
|
110
|
+
# added
|
|
111
|
+
local_grouped.reject { |key, vg| aws_grouped.has_key? key }.each do |key, vg|
|
|
112
|
+
diffs << EbsGroupDiff.new(EbsGroupChange::VG_ADDED, nil, vg)
|
|
113
|
+
end
|
|
114
|
+
|
|
115
|
+
# removed
|
|
116
|
+
aws_grouped.reject { |key, vg| local_grouped.has_key? key }.each do |key, vg|
|
|
117
|
+
diffs << EbsGroupDiff.new(EbsGroupChange::VG_REMOVED, vg, nil)
|
|
118
|
+
end
|
|
119
|
+
|
|
120
|
+
# count is different
|
|
121
|
+
local_grouped.select { |key, vg| aws_grouped.has_key? key }.each do |key, local_vg|
|
|
122
|
+
aws_vg = aws_grouped[key]
|
|
123
|
+
if local_vg.count != aws_vg.count
|
|
124
|
+
diffs << EbsGroupDiff.new(EbsGroupDiff::VG_COUNT, aws_vg, local_vg)
|
|
125
|
+
end
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
diffs.sort_by { |diff| diff.type }
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
end
|
|
132
|
+
end
|
|
133
|
+
end
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
require "common/models/Diff"
|
|
2
|
+
require "util/Colors"
|
|
3
|
+
|
|
4
|
+
require 'json'
|
|
5
|
+
|
|
6
|
+
module Cumulus
|
|
7
|
+
module EC2
|
|
8
|
+
# Public: The types of changes that can be made to an EBS volume group
|
|
9
|
+
module EbsGroupChange
|
|
10
|
+
include Common::DiffChange
|
|
11
|
+
|
|
12
|
+
AZ = Common::DiffChange.next_change_id
|
|
13
|
+
VG_ADDED = Common::DiffChange.next_change_id
|
|
14
|
+
VG_REMOVED = Common::DiffChange.next_change_id
|
|
15
|
+
VG_COUNT = Common::DiffChange.next_change_id
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
# Public: Represents a single difference between local configuration and AWS configuration
|
|
19
|
+
class EbsGroupDiff < Common::Diff
|
|
20
|
+
include EbsGroupChange
|
|
21
|
+
|
|
22
|
+
def asset_type
|
|
23
|
+
"EBS Volume Group"
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
def aws_name
|
|
27
|
+
@aws.name
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def diff_string
|
|
31
|
+
case @type
|
|
32
|
+
when AZ
|
|
33
|
+
[
|
|
34
|
+
"Availability Zone:",
|
|
35
|
+
Colors.aws_changes("\tAWS - #{aws}"),
|
|
36
|
+
Colors.local_changes("\tLocal - #{local}"),
|
|
37
|
+
].join("\n")
|
|
38
|
+
when VG_ADDED
|
|
39
|
+
Colors.added("Volume Group Added: #{local.count} x #{local.description}")
|
|
40
|
+
when VG_REMOVED
|
|
41
|
+
Colors.unmanaged("Volume Group Unmanaged: #{aws.count} x #{aws.description}")
|
|
42
|
+
when VG_COUNT
|
|
43
|
+
Colors.local_changes("Count changed from #{aws.count} to #{local.count}: #{local.description}")
|
|
44
|
+
end
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
end
|
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
require "common/models/ListChange"
|
|
2
|
+
require "conf/Configuration"
|
|
3
|
+
require "ec2/models/EbsGroupConfig"
|
|
4
|
+
require "ec2/models/EbsGroupDiff"
|
|
5
|
+
require "ec2/models/InstanceDiff"
|
|
6
|
+
require "ec2/EC2"
|
|
7
|
+
require "security/SecurityGroups"
|
|
8
|
+
|
|
9
|
+
require "json"
|
|
10
|
+
|
|
11
|
+
module Cumulus
|
|
12
|
+
module EC2
|
|
13
|
+
|
|
14
|
+
# Public: An object representing configuration for a network interface
|
|
15
|
+
class InstanceConfig
|
|
16
|
+
attr_reader :name
|
|
17
|
+
attr_reader :ebs_optimized
|
|
18
|
+
attr_reader :placement_group
|
|
19
|
+
attr_reader :profile
|
|
20
|
+
attr_reader :image
|
|
21
|
+
attr_reader :key_name
|
|
22
|
+
attr_reader :monitoring
|
|
23
|
+
attr_reader :network_interfaces
|
|
24
|
+
attr_reader :source_dest_check
|
|
25
|
+
attr_reader :private_ip_address
|
|
26
|
+
attr_reader :security_groups
|
|
27
|
+
attr_reader :subnet
|
|
28
|
+
attr_reader :tenancy
|
|
29
|
+
attr_reader :type
|
|
30
|
+
attr_reader :user_data
|
|
31
|
+
attr_reader :volume_groups
|
|
32
|
+
attr_reader :tags
|
|
33
|
+
|
|
34
|
+
# Public: Constructor
|
|
35
|
+
#
|
|
36
|
+
# json - a hash containing the JSON configuration for the group
|
|
37
|
+
def initialize(name, json = nil)
|
|
38
|
+
@name = name
|
|
39
|
+
if !json.nil?
|
|
40
|
+
@ebs_optimized = json["ebs-optimized"] || false
|
|
41
|
+
@placement_group = json["placement-group"]
|
|
42
|
+
@profile = json["profile"]
|
|
43
|
+
@image = json["image"]
|
|
44
|
+
@key_name = json["key-name"]
|
|
45
|
+
@monitoring = json["monitoring"] || false
|
|
46
|
+
@network_interfaces = json["network-interfaces"] || 0
|
|
47
|
+
@source_dest_check = json["source-dest-check"]
|
|
48
|
+
@private_ip_address = json["private-ip-address"]
|
|
49
|
+
@security_groups = json["security-groups"] || []
|
|
50
|
+
@subnet = json["subnet"]
|
|
51
|
+
@tenancy = json["tenancy"] || "default"
|
|
52
|
+
@type = json["type"]
|
|
53
|
+
@user_data = json["user-data"]
|
|
54
|
+
@volume_groups = json["volume-groups"] || []
|
|
55
|
+
@tags = json["tags"] || {}
|
|
56
|
+
end
|
|
57
|
+
end
|
|
58
|
+
|
|
59
|
+
def to_hash
|
|
60
|
+
{
|
|
61
|
+
"ebs-optimized" => @ebs_optimized,
|
|
62
|
+
"placement-group" => @placement_group,
|
|
63
|
+
"profile" => @profile,
|
|
64
|
+
"image" => @image,
|
|
65
|
+
"key-name" => @key_name,
|
|
66
|
+
"monitoring" => @monitoring,
|
|
67
|
+
"network-interfaces" => @network_interfaces,
|
|
68
|
+
"source-dest-check" => @source_dest_check,
|
|
69
|
+
"private-ip-address" => @private_ip_address,
|
|
70
|
+
"security-groups" => @security_groups,
|
|
71
|
+
"subnet" => @subnet,
|
|
72
|
+
"tenancy" => @tenancy,
|
|
73
|
+
"type" => @type,
|
|
74
|
+
"user-data" => @user_data,
|
|
75
|
+
"volume-groups" => @volume_groups,
|
|
76
|
+
"tags" => @tags,
|
|
77
|
+
}
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
# Public: Populate a config object with AWS configuration
|
|
81
|
+
#
|
|
82
|
+
# aws_instance - the instance from AWS
|
|
83
|
+
# user_data_file - the name of the user data script file
|
|
84
|
+
# tags - a Hash of tags for the instance
|
|
85
|
+
def populate!(aws_instance, user_data_file, tags)
|
|
86
|
+
@ebs_optimized = aws_instance.ebs_optimized
|
|
87
|
+
@placement_group = aws_instance.placement.group_name
|
|
88
|
+
if @placement_group.empty? then @placement_group = nil end
|
|
89
|
+
|
|
90
|
+
profile_arn = (aws_instance.iam_instance_profile.arn rescue nil)
|
|
91
|
+
@profile = if profile_arn then profile_arn[profile_arn.rindex("/") + 1 .. profile_arn.length] end
|
|
92
|
+
|
|
93
|
+
@image = aws_instance.image_id
|
|
94
|
+
@key_name = aws_instance.key_name
|
|
95
|
+
@monitoring = ["enabled", "pending"].include? aws_instance.monitoring.state
|
|
96
|
+
@network_interfaces = aws_instance.network_interfaces.length
|
|
97
|
+
@source_dest_check = aws_instance.source_dest_check
|
|
98
|
+
@private_ip_address = aws_instance.private_ip_address
|
|
99
|
+
@security_groups = aws_instance.security_groups.map(&:group_id).map { |id| SecurityGroups::id_security_groups[id].group_name }.sort
|
|
100
|
+
@subnet = EC2::id_subnets[aws_instance.subnet_id].name
|
|
101
|
+
@tenancy = aws_instance.placement.tenancy
|
|
102
|
+
@type = aws_instance.instance_type
|
|
103
|
+
@user_data = user_data_file
|
|
104
|
+
|
|
105
|
+
# Get the volumes for each device mapping
|
|
106
|
+
@volume_groups = aws_instance.nonroot_devices.map do |m|
|
|
107
|
+
EC2::id_ebs_volumes[m.ebs.volume_id]
|
|
108
|
+
end.map(&:group).reject(&:nil?).uniq.sort
|
|
109
|
+
|
|
110
|
+
@tags = tags
|
|
111
|
+
|
|
112
|
+
self
|
|
113
|
+
end
|
|
114
|
+
|
|
115
|
+
# Public: Produce an array of differences between this local configuration and the
|
|
116
|
+
# configuration in AWS
|
|
117
|
+
#
|
|
118
|
+
# aws - the AWS resource
|
|
119
|
+
#
|
|
120
|
+
# Returns an array of the InterfaceDiffs that were found
|
|
121
|
+
def diff(aws)
|
|
122
|
+
diffs = []
|
|
123
|
+
|
|
124
|
+
if aws.ebs_optimized != @ebs_optimized
|
|
125
|
+
diffs << InstanceDiff.new(InstanceChange::EBS, aws.ebs_optimized, @ebs_optimized)
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
if aws.profile != @profile
|
|
129
|
+
diffs << InstanceDiff.new(InstanceChange::PROFILE, aws.profile, @profile)
|
|
130
|
+
end
|
|
131
|
+
|
|
132
|
+
if aws.monitoring != @monitoring
|
|
133
|
+
diffs << InstanceDiff.new(InstanceChange::MONITORING, aws.monitoring, @monitoring)
|
|
134
|
+
end
|
|
135
|
+
|
|
136
|
+
if aws.network_interfaces != @network_interfaces
|
|
137
|
+
diffs << InstanceDiff.new(InstanceChange::INTERFACES, aws.network_interfaces, @network_interfaces)
|
|
138
|
+
end
|
|
139
|
+
|
|
140
|
+
if aws.source_dest_check != @source_dest_check
|
|
141
|
+
diffs << InstanceDiff.new(InstanceChange::SDCHECK, aws.source_dest_check, @source_dest_check)
|
|
142
|
+
end
|
|
143
|
+
|
|
144
|
+
if aws.security_groups.sort != @security_groups.sort
|
|
145
|
+
changes = Common::ListChange::simple_list_diff(aws.security_groups, @security_groups)
|
|
146
|
+
diffs << InstanceDiff.new(InstanceChange::SECURITY_GROUPS, aws.security_groups, @security_groups, changes)
|
|
147
|
+
end
|
|
148
|
+
|
|
149
|
+
if aws.subnet != @subnet
|
|
150
|
+
diffs << InstanceDiff.new(InstanceChange::SUBNET, aws.subnet, @subnet)
|
|
151
|
+
end
|
|
152
|
+
|
|
153
|
+
if aws.type != @type
|
|
154
|
+
diffs << InstanceDiff.new(InstanceChange::TYPE, aws.type, @type)
|
|
155
|
+
end
|
|
156
|
+
|
|
157
|
+
if aws.tenancy != @tenancy
|
|
158
|
+
diffs << InstanceDiff.new(InstanceChange::TENANCY, aws.tenancy, @tenancy)
|
|
159
|
+
end
|
|
160
|
+
|
|
161
|
+
if aws.tags != @tags
|
|
162
|
+
diffs << InstanceDiff.new(InstanceChange::TAGS, aws.tags, @tags)
|
|
163
|
+
end
|
|
164
|
+
|
|
165
|
+
# Check for diffs in volume groups and diffs in how many volumes are attached
|
|
166
|
+
|
|
167
|
+
# Get the volumes that are attached to the instance
|
|
168
|
+
aws_instance = EC2::named_instances[aws.name]
|
|
169
|
+
attached_volumes = aws_instance.nonroot_devices.map do |m|
|
|
170
|
+
EC2::id_ebs_volumes[m.ebs.volume_id]
|
|
171
|
+
end
|
|
172
|
+
# Group by volume group, reject nil groups
|
|
173
|
+
group_volumes = attached_volumes.group_by(&:group).reject { |k, v| k.nil? }
|
|
174
|
+
|
|
175
|
+
aws_ebs_groups = Hash[group_volumes.map { |group, vols| [group, EbsGroupConfig.new(group).populate!(vols)] }]
|
|
176
|
+
local_ebs_groups = Hash[@volume_groups.map { |vg| [vg, EC2::group_ebs_volumes[vg]] }]
|
|
177
|
+
|
|
178
|
+
added_groups = Hash[local_ebs_groups.reject { |k, v| aws_ebs_groups.has_key?(k) }.map do |group_name, group_config|
|
|
179
|
+
[group_name, EbsGroupDiff.added(group_config)]
|
|
180
|
+
end]
|
|
181
|
+
removed_groups = Hash[aws_ebs_groups.reject { |k, v| aws_ebs_groups.has_key?(k) }.map do |group_name, group_config|
|
|
182
|
+
[group_name, EbsGroupDiff.unmanaged(group_config)]
|
|
183
|
+
end]
|
|
184
|
+
changed_groups = Hash[local_ebs_groups.select { |k, v| aws_ebs_groups.has_key?(k) }.map do |group_name, group_config|
|
|
185
|
+
aws_config = aws_ebs_groups[group_name]
|
|
186
|
+
group_diffs = group_config.diff(aws_config)
|
|
187
|
+
if !group_diffs.empty?
|
|
188
|
+
[group_name, EbsGroupDiff.modified(aws_config, group_config, group_diffs)]
|
|
189
|
+
end
|
|
190
|
+
end].reject { |k, v| v.nil? }
|
|
191
|
+
|
|
192
|
+
ebs_changes = Common::ListChange.new(added_groups, removed_groups, changed_groups)
|
|
193
|
+
if !ebs_changes.empty?
|
|
194
|
+
diffs << InstanceDiff.new(InstanceChange::VOLUME_GROUPS, aws_ebs_groups, local_ebs_groups, ebs_changes)
|
|
195
|
+
end
|
|
196
|
+
|
|
197
|
+
diffs
|
|
198
|
+
end
|
|
199
|
+
|
|
200
|
+
end
|
|
201
|
+
end
|
|
202
|
+
end
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
require "common/models/Diff"
|
|
2
|
+
require "common/models/TagsDiff"
|
|
3
|
+
require "util/Colors"
|
|
4
|
+
|
|
5
|
+
require 'json'
|
|
6
|
+
|
|
7
|
+
module Cumulus
|
|
8
|
+
module EC2
|
|
9
|
+
# Public: The types of changes that can be made to an EBS volume group
|
|
10
|
+
module InstanceChange
|
|
11
|
+
include Common::DiffChange
|
|
12
|
+
|
|
13
|
+
EBS = Common::DiffChange.next_change_id
|
|
14
|
+
PROFILE = Common::DiffChange.next_change_id
|
|
15
|
+
MONITORING = Common::DiffChange.next_change_id
|
|
16
|
+
INTERFACES = Common::DiffChange.next_change_id
|
|
17
|
+
SDCHECK = Common::DiffChange.next_change_id
|
|
18
|
+
SECURITY_GROUPS = Common::DiffChange.next_change_id
|
|
19
|
+
SUBNET = Common::DiffChange.next_change_id
|
|
20
|
+
TYPE = Common::DiffChange.next_change_id
|
|
21
|
+
TENANCY = Common::DiffChange.next_change_id
|
|
22
|
+
VOLUME_GROUPS = Common::DiffChange.next_change_id
|
|
23
|
+
TAGS = Common::DiffChange.next_change_id
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
# Public: Represents a single difference between local configuration and AWS configuration
|
|
27
|
+
class InstanceDiff < Common::Diff
|
|
28
|
+
include InstanceChange
|
|
29
|
+
include Common::TagsDiff
|
|
30
|
+
|
|
31
|
+
def asset_type
|
|
32
|
+
case @type
|
|
33
|
+
when EBS then "EBS Optimized"
|
|
34
|
+
when PROFILE then "Instance Profile"
|
|
35
|
+
when MONITORING then "Monitoring"
|
|
36
|
+
when INTERFACES then "Network Interfaces"
|
|
37
|
+
when SDCHECK then "Source Dest Check"
|
|
38
|
+
when SECURITY_GROUPS then "Security Groups"
|
|
39
|
+
when SUBNET then "Subnet"
|
|
40
|
+
when TYPE then "Type"
|
|
41
|
+
when TENANCY then "Tenancy"
|
|
42
|
+
when VOLUME_GROUPS then "Volume Groups"
|
|
43
|
+
when TAGS then "Tags"
|
|
44
|
+
else
|
|
45
|
+
"EC2 Instance"
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
def aws_name
|
|
50
|
+
@aws.name
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def local_tags
|
|
54
|
+
@local
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
def aws_tags
|
|
58
|
+
@aws
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def diff_string
|
|
62
|
+
case @type
|
|
63
|
+
when EBS, PROFILE, MONITORING, INTERFACES, SDCHECK, SUBNET, TYPE, TENANCY
|
|
64
|
+
[
|
|
65
|
+
"#{asset_type}:",
|
|
66
|
+
Colors.aws_changes("\tAWS - #{aws}"),
|
|
67
|
+
Colors.local_changes("\tLocal - #{local}"),
|
|
68
|
+
].join("\n")
|
|
69
|
+
when SECURITY_GROUPS
|
|
70
|
+
[
|
|
71
|
+
"#{asset_type}:",
|
|
72
|
+
@changes.removed.map { |sg| Colors.unmanaged("\t#{sg}") },
|
|
73
|
+
@changes.added.map { |sg| Colors.added("\t#{sg}") }
|
|
74
|
+
].flatten.join("\n")
|
|
75
|
+
when VOLUME_GROUPS
|
|
76
|
+
[
|
|
77
|
+
"#{asset_type}:",
|
|
78
|
+
@changes.removed.map { |vg, _| Colors.unmanaged("\t#{vg} is attached but not managed by Cumulus") },
|
|
79
|
+
@changes.added.map { |vg, _| Colors.added("\t#{vg} will be attached to the instance") },
|
|
80
|
+
@changes.modified.map do |vg, diff|
|
|
81
|
+
[
|
|
82
|
+
"\t#{vg}:",
|
|
83
|
+
diff.changes.map do |diff|
|
|
84
|
+
diff.to_s.lines.map { |l| "\t\t#{l}".chomp("\n") }
|
|
85
|
+
end
|
|
86
|
+
]
|
|
87
|
+
end
|
|
88
|
+
].flatten.join("\n")
|
|
89
|
+
when TAGS
|
|
90
|
+
tags_diff_string
|
|
91
|
+
end
|
|
92
|
+
end
|
|
93
|
+
end
|
|
94
|
+
end
|
|
95
|
+
end
|