chef-provisioning-aws 1.3.1 → 1.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/README.md +70 -69
- data/Rakefile +22 -2
- data/lib/chef/provider/aws_auto_scaling_group.rb +3 -2
- data/lib/chef/provider/aws_cache_cluster.rb +3 -2
- data/lib/chef/provider/aws_cache_replication_group.rb +5 -4
- data/lib/chef/provider/aws_cache_subnet_group.rb +5 -4
- data/lib/chef/provider/aws_cloudsearch_domain.rb +163 -0
- data/lib/chef/provider/aws_dhcp_options.rb +9 -6
- data/lib/chef/provider/aws_ebs_volume.rb +7 -3
- data/lib/chef/provider/aws_eip_address.rb +8 -7
- data/lib/chef/provider/aws_image.rb +8 -3
- data/lib/chef/provider/aws_instance.rb +14 -2
- data/lib/chef/provider/aws_key_pair.rb +2 -1
- data/lib/chef/provider/aws_launch_configuration.rb +4 -2
- data/lib/chef/provider/aws_load_balancer.rb +18 -0
- data/lib/chef/provider/aws_network_acl.rb +6 -2
- data/lib/chef/provider/aws_network_interface.rb +11 -24
- data/lib/chef/provider/aws_rds_instance.rb +66 -0
- data/lib/chef/provider/aws_rds_subnet_group.rb +89 -0
- data/lib/chef/provider/aws_route_table.rb +42 -23
- data/lib/chef/provider/aws_s3_bucket.rb +32 -8
- data/lib/chef/provider/aws_security_group.rb +11 -4
- data/lib/chef/provider/aws_server_certificate.rb +23 -0
- data/lib/chef/provider/aws_sns_topic.rb +4 -3
- data/lib/chef/provider/aws_sqs_queue.rb +3 -2
- data/lib/chef/provider/aws_subnet.rb +10 -7
- data/lib/chef/provider/aws_vpc.rb +54 -21
- data/lib/chef/provider/aws_vpc_peering_connection.rb +88 -0
- data/lib/chef/provisioning/aws_driver.rb +8 -0
- data/lib/chef/provisioning/aws_driver/aws_provider.rb +45 -76
- data/lib/chef/provisioning/aws_driver/aws_rds_resource.rb +11 -0
- data/lib/chef/provisioning/aws_driver/aws_resource.rb +14 -2
- data/lib/chef/provisioning/aws_driver/aws_resource_with_entry.rb +2 -8
- data/lib/chef/provisioning/aws_driver/aws_taggable.rb +18 -0
- data/lib/chef/provisioning/aws_driver/aws_tagger.rb +61 -0
- data/lib/chef/provisioning/aws_driver/credentials2.rb +51 -0
- data/lib/chef/provisioning/aws_driver/driver.rb +214 -162
- data/lib/chef/provisioning/aws_driver/tagging_strategy/ec2.rb +64 -0
- data/lib/chef/provisioning/aws_driver/tagging_strategy/elb.rb +39 -0
- data/lib/chef/provisioning/aws_driver/tagging_strategy/rds.rb +92 -0
- data/lib/chef/provisioning/aws_driver/tagging_strategy/s3.rb +41 -0
- data/lib/chef/provisioning/aws_driver/version.rb +1 -1
- data/lib/chef/resource/aws_cache_cluster.rb +1 -2
- data/lib/chef/resource/aws_cloudsearch_domain.rb +46 -0
- data/lib/chef/resource/aws_dhcp_options.rb +2 -0
- data/lib/chef/resource/aws_ebs_volume.rb +3 -1
- data/lib/chef/resource/aws_eip_address.rb +0 -3
- data/lib/chef/resource/aws_image.rb +3 -0
- data/lib/chef/resource/aws_instance.rb +7 -2
- data/lib/chef/resource/aws_internet_gateway.rb +2 -0
- data/lib/chef/resource/aws_load_balancer.rb +3 -0
- data/lib/chef/resource/aws_network_acl.rb +2 -0
- data/lib/chef/resource/aws_network_interface.rb +3 -1
- data/lib/chef/resource/aws_rds_instance.rb +42 -0
- data/lib/chef/resource/aws_rds_subnet_group.rb +29 -0
- data/lib/chef/resource/aws_route_table.rb +7 -5
- data/lib/chef/resource/aws_s3_bucket.rb +3 -0
- data/lib/chef/resource/aws_security_group.rb +2 -7
- data/lib/chef/resource/aws_server_certificate.rb +21 -0
- data/lib/chef/resource/aws_subnet.rb +2 -0
- data/lib/chef/resource/aws_vpc.rb +4 -1
- data/lib/chef/resource/aws_vpc_peering_connection.rb +73 -0
- data/spec/acceptance/aws_ebs_volume/nodes/ettores-mbp.lan.json +3 -0
- data/spec/aws_support.rb +25 -8
- data/spec/aws_support/aws_resource_run_wrapper.rb +5 -1
- data/spec/aws_support/deep_matcher/match_values_failure_messages.rb +19 -0
- data/spec/aws_support/matchers/create_an_aws_object.rb +1 -1
- data/spec/aws_support/matchers/destroy_an_aws_object.rb +1 -1
- data/spec/aws_support/matchers/have_aws_object_tags.rb +9 -15
- data/spec/aws_support/matchers/match_an_aws_object.rb +1 -1
- data/spec/aws_support/matchers/update_an_aws_object.rb +1 -1
- data/spec/integration/aws_cloudsearch_domain_spec.rb +31 -0
- data/spec/integration/aws_dhcp_options_spec.rb +73 -0
- data/spec/integration/aws_ebs_volume_spec.rb +97 -0
- data/spec/integration/aws_network_acl_spec.rb +51 -0
- data/spec/integration/aws_network_interface_spec.rb +89 -0
- data/spec/integration/aws_rds_instance_spec.rb +150 -0
- data/spec/integration/aws_rds_subnet_group_spec.rb +105 -0
- data/spec/integration/aws_route_table_spec.rb +94 -7
- data/spec/integration/aws_s3_bucket_spec.rb +88 -0
- data/spec/integration/aws_security_group_spec.rb +47 -0
- data/spec/integration/aws_server_certificate_spec.rb +24 -0
- data/spec/integration/aws_subnet_spec.rb +51 -2
- data/spec/integration/aws_vpc_peering_connection_spec.rb +99 -0
- data/spec/integration/aws_vpc_spec.rb +73 -0
- data/spec/integration/load_balancer_spec.rb +101 -0
- data/spec/integration/machine_image_spec.rb +61 -6
- data/spec/integration/machine_spec.rb +26 -0
- data/spec/spec_helper.rb +3 -0
- data/spec/unit/{aws_driver → chef/provisioning/aws_driver}/credentials_spec.rb +0 -0
- data/spec/unit/chef/provisioning/aws_driver/driver_spec.rb +88 -0
- metadata +63 -20
- data/spec/integration/aws_tagged_items_spec.rb +0 -166
@@ -1,7 +1,10 @@
|
|
1
1
|
require 'chef/provisioning/aws_driver/aws_provider'
|
2
|
-
require 'retryable'
|
3
2
|
|
4
3
|
class Chef::Provider::AwsDhcpOptions < Chef::Provisioning::AWSDriver::AWSProvider
|
4
|
+
include Chef::Provisioning::AWSDriver::TaggingStrategy::EC2ConvergeTags
|
5
|
+
|
6
|
+
provides :aws_dhcp_options
|
7
|
+
|
5
8
|
protected
|
6
9
|
|
7
10
|
def create_aws_object
|
@@ -10,7 +13,7 @@ class Chef::Provider::AwsDhcpOptions < Chef::Provisioning::AWSDriver::AWSProvide
|
|
10
13
|
options[:domain_name_servers] = "AmazonProvidedDNS"
|
11
14
|
end
|
12
15
|
|
13
|
-
converge_by "create
|
16
|
+
converge_by "create DHCP options #{new_resource.name} in #{region}" do
|
14
17
|
dhcp_options = new_resource.driver.ec2.dhcp_options.create(options)
|
15
18
|
retry_with_backoff(AWS::EC2::Errors::InvalidDhcpOptionsID::NotFound) do
|
16
19
|
dhcp_options.tags['Name'] = new_resource.name
|
@@ -35,17 +38,17 @@ class Chef::Provider::AwsDhcpOptions < Chef::Provisioning::AWSDriver::AWSProvide
|
|
35
38
|
if action_handler.should_perform_actions
|
36
39
|
dhcp_options = AWS.ec2(config: dhcp_options.config).dhcp_options.create(config.merge(desired_options))
|
37
40
|
end
|
38
|
-
action_handler.report_progress "create
|
41
|
+
action_handler.report_progress "create DHCP options #{dhcp_options.id} with new attributes in #{region}"
|
39
42
|
|
40
43
|
# attach dhcp_options to existing vpcs
|
41
44
|
old_dhcp_options.vpcs.each do |vpc|
|
42
|
-
action_handler.perform_action "attach
|
45
|
+
action_handler.perform_action "attach DHCP options #{dhcp_options.id} to vpc #{vpc.id}" do
|
43
46
|
vpc.dhcp_options = dhcp_options
|
44
47
|
end
|
45
48
|
end
|
46
49
|
|
47
50
|
# delete old dhcp_options
|
48
|
-
action_handler.perform_action "delete
|
51
|
+
action_handler.perform_action "delete DHCP options #{old_dhcp_options.id}" do
|
49
52
|
old_dhcp_options.delete
|
50
53
|
end
|
51
54
|
|
@@ -54,7 +57,7 @@ class Chef::Provider::AwsDhcpOptions < Chef::Provisioning::AWSDriver::AWSProvide
|
|
54
57
|
end
|
55
58
|
|
56
59
|
def destroy_aws_object(dhcp_options)
|
57
|
-
converge_by "delete
|
60
|
+
converge_by "delete DHCP options #{new_resource.name} in #{region}" do
|
58
61
|
dhcp_options.delete
|
59
62
|
end
|
60
63
|
end
|
@@ -4,6 +4,10 @@ require 'date'
|
|
4
4
|
require 'retryable'
|
5
5
|
|
6
6
|
class Chef::Provider::AwsEbsVolume < Chef::Provisioning::AWSDriver::AWSProvider
|
7
|
+
include Chef::Provisioning::AWSDriver::TaggingStrategy::EC2ConvergeTags
|
8
|
+
|
9
|
+
provides :aws_ebs_volume
|
10
|
+
|
7
11
|
class VolumeNotFoundError < RuntimeError
|
8
12
|
def initialize(new_resource)
|
9
13
|
super("#{new_resource} does not exist!")
|
@@ -34,7 +38,7 @@ class Chef::Provider::AwsEbsVolume < Chef::Provisioning::AWSDriver::AWSProvider
|
|
34
38
|
|
35
39
|
def create_aws_object
|
36
40
|
volume = nil
|
37
|
-
converge_by "create
|
41
|
+
converge_by "create #{new_resource} in #{region}" do
|
38
42
|
volume = new_resource.driver.ec2.volumes.create(initial_options)
|
39
43
|
retry_with_backoff(AWS::EC2::Errors::InvalidVolumeID::NotFound) do
|
40
44
|
volume.tags['Name'] = new_resource.name
|
@@ -119,12 +123,12 @@ class Chef::Provider::AwsEbsVolume < Chef::Provisioning::AWSDriver::AWSProvider
|
|
119
123
|
#
|
120
124
|
# If we were told to attach the volume to a machine, do so
|
121
125
|
#
|
122
|
-
if expected_instance.is_a?(AWS::EC2::Instance)
|
126
|
+
if expected_instance.is_a?(AWS::EC2::Instance) || expected_instance.is_a?(::Aws::EC2::Instance)
|
123
127
|
case status
|
124
128
|
when :in_use
|
125
129
|
# We don't want to attempt to reattach to the same instance and device
|
126
130
|
attachment = current_attachment(volume)
|
127
|
-
if attachment.instance != expected_instance || attachment.device != new_resource.device
|
131
|
+
if attachment.instance.id != expected_instance.id || attachment.device != new_resource.device
|
128
132
|
detach(volume)
|
129
133
|
attach(volume)
|
130
134
|
end
|
@@ -4,6 +4,7 @@ require 'chef/provisioning/machine_spec'
|
|
4
4
|
require 'cheffish'
|
5
5
|
|
6
6
|
class Chef::Provider::AwsEipAddress < Chef::Provisioning::AWSDriver::AWSProvider
|
7
|
+
provides :aws_eip_address
|
7
8
|
|
8
9
|
def action_create
|
9
10
|
elastic_ip = super
|
@@ -16,10 +17,10 @@ class Chef::Provider::AwsEipAddress < Chef::Provisioning::AWSDriver::AWSProvider
|
|
16
17
|
protected
|
17
18
|
|
18
19
|
def create_aws_object
|
19
|
-
converge_by "create
|
20
|
+
converge_by "create Elastic IP address in #{region}" do
|
20
21
|
associate_to_vpc = new_resource.associate_to_vpc
|
21
22
|
if associate_to_vpc.nil?
|
22
|
-
if desired_instance.is_a?(AWS::EC2::Instance)
|
23
|
+
if desired_instance.is_a?(AWS::EC2::Instance) || desired_instance.is_a?(::Aws::EC2::Instance)
|
23
24
|
associate_to_vpc = !!desired_instance.vpc_id
|
24
25
|
Chef::Log.debug "Since associate_to_vpc is not specified and instance #{new_resource.machine} (#{desired_instance.id}) and #{associate_to_vpc ? "is" : "is not"} in a VPC, setting associate_to_vpc to #{associate_to_vpc}."
|
25
26
|
end
|
@@ -39,11 +40,11 @@ class Chef::Provider::AwsEipAddress < Chef::Provisioning::AWSDriver::AWSProvider
|
|
39
40
|
def destroy_aws_object(elastic_ip)
|
40
41
|
#if it's attached to something in a vpc, disassociate first
|
41
42
|
if elastic_ip.instance_id != nil && elastic_ip.domain == 'vpc'
|
42
|
-
converge_by "dissociate Elastic IP
|
43
|
+
converge_by "dissociate Elastic IP address #{new_resource.name} (#{elastic_ip.public_ip}) from #{elastic_ip.instance_id}" do
|
43
44
|
elastic_ip.disassociate
|
44
45
|
end
|
45
46
|
end
|
46
|
-
converge_by "delete Elastic IP
|
47
|
+
converge_by "delete Elastic IP address #{new_resource.name} (#{elastic_ip.public_ip}) in #{region}" do
|
47
48
|
elastic_ip.delete
|
48
49
|
end
|
49
50
|
end
|
@@ -65,9 +66,9 @@ class Chef::Provider::AwsEipAddress < Chef::Provisioning::AWSDriver::AWSProvider
|
|
65
66
|
#
|
66
67
|
# If we were told to associate the IP to a machine, do so
|
67
68
|
#
|
68
|
-
if desired_instance.is_a?(AWS::EC2::Instance)
|
69
|
+
if desired_instance.is_a?(AWS::EC2::Instance) || desired_instance.is_a?(::Aws::EC2::Instance)
|
69
70
|
if desired_instance.id != elastic_ip.instance_id
|
70
|
-
converge_by "associate Elastic IP
|
71
|
+
converge_by "associate Elastic IP address #{new_resource.name} (#{elastic_ip.public_ip}) with #{new_resource.machine} (#{desired_instance.id})" do
|
71
72
|
elastic_ip.associate instance: desired_instance.id
|
72
73
|
end
|
73
74
|
end
|
@@ -77,7 +78,7 @@ class Chef::Provider::AwsEipAddress < Chef::Provisioning::AWSDriver::AWSProvider
|
|
77
78
|
#
|
78
79
|
else
|
79
80
|
if elastic_ip.associated?
|
80
|
-
converge_by "disassociate Elastic IP
|
81
|
+
converge_by "disassociate Elastic IP address #{new_resource.name} (#{elastic_ip.public_ip}) from #{elastic_ip.instance_id} in #{region}" do
|
81
82
|
aws_object.disassociate
|
82
83
|
end
|
83
84
|
end
|
@@ -1,13 +1,18 @@
|
|
1
1
|
require 'chef/provisioning/aws_driver/aws_provider'
|
2
|
+
require 'chef/provisioning/aws_driver/tagging_strategy/ec2'
|
2
3
|
|
3
4
|
class Chef::Provider::AwsImage < Chef::Provisioning::AWSDriver::AWSProvider
|
5
|
+
include Chef::Provisioning::AWSDriver::TaggingStrategy::EC2ConvergeTags
|
6
|
+
|
7
|
+
provides :aws_image
|
8
|
+
|
4
9
|
def destroy_aws_object(image)
|
5
|
-
instance_id = image.tags['
|
6
|
-
Chef::Log.debug("Found
|
10
|
+
instance_id = image.tags['from-instance']
|
11
|
+
Chef::Log.debug("Found from-instance tag [#{instance_id}] on #{image.id}")
|
7
12
|
unless instance_id
|
8
13
|
# This is an old image and doesn't have the tag added - lets try and find it from the block device mapping
|
9
14
|
image.block_device_mappings.map do |dev, opts|
|
10
|
-
snapshot = ec2.snapshots[opts[:snapshot_id]]
|
15
|
+
snapshot = new_resource.driver.ec2.snapshots[opts[:snapshot_id]]
|
11
16
|
desc = snapshot.description
|
12
17
|
m = /CreateImage\(([^\)]+)\)/.match(desc)
|
13
18
|
if m
|
@@ -1,6 +1,11 @@
|
|
1
1
|
require 'chef/provisioning/aws_driver/aws_provider'
|
2
|
+
require 'chef/provisioning/aws_driver/tagging_strategy/ec2'
|
2
3
|
|
3
4
|
class Chef::Provider::AwsInstance < Chef::Provisioning::AWSDriver::AWSProvider
|
5
|
+
include Chef::Provisioning::AWSDriver::TaggingStrategy::EC2ConvergeTags
|
6
|
+
|
7
|
+
provides :aws_instance
|
8
|
+
|
4
9
|
def create_aws_object(instance); end
|
5
10
|
|
6
11
|
def update_aws_object(instance); end
|
@@ -10,12 +15,19 @@ class Chef::Provider::AwsInstance < Chef::Provisioning::AWSDriver::AWSProvider
|
|
10
15
|
message += " in VPC #{instance.vpc.id}" unless instance.vpc.nil?
|
11
16
|
message += " in #{region}"
|
12
17
|
converge_by message do
|
13
|
-
instance.
|
18
|
+
instance.terminate
|
14
19
|
end
|
15
20
|
converge_by "waited until instance #{new_resource} is :terminated" do
|
16
21
|
# When purging, we must wait until the instance is fully terminated - thats the only way
|
17
22
|
# to delete the network interface that I can see
|
18
|
-
|
23
|
+
instance.wait_until_terminated do |w|
|
24
|
+
# TODO look at `wait_for_status` - delay and max_attempts should be configurable
|
25
|
+
w.delay = 5
|
26
|
+
w.max_attempts = 60
|
27
|
+
w.before_wait do |attempts, response|
|
28
|
+
action_handler.report_progress "waited #{(attempts-1)*5}/#{60*5}s for #{instance.id} status to terminate..."
|
29
|
+
end
|
30
|
+
end
|
19
31
|
end
|
20
32
|
end
|
21
33
|
end
|
@@ -2,6 +2,8 @@ require 'chef/provisioning/aws_driver/aws_provider'
|
|
2
2
|
require 'chef/resource/aws_image'
|
3
3
|
|
4
4
|
class Chef::Provider::AwsLaunchConfiguration < Chef::Provisioning::AWSDriver::AWSProvider
|
5
|
+
provides :aws_launch_configuration
|
6
|
+
|
5
7
|
protected
|
6
8
|
|
7
9
|
def create_aws_object
|
@@ -9,7 +11,7 @@ class Chef::Provider::AwsLaunchConfiguration < Chef::Provisioning::AWSDriver::AW
|
|
9
11
|
instance_type = new_resource.instance_type || new_resource.driver.default_instance_type
|
10
12
|
options = AWSResource.lookup_options(new_resource.options || options, resource: new_resource)
|
11
13
|
|
12
|
-
converge_by "
|
14
|
+
converge_by "create launch configuration #{new_resource.name} in #{region}" do
|
13
15
|
new_resource.driver.auto_scaling.launch_configurations.create(
|
14
16
|
new_resource.name,
|
15
17
|
image,
|
@@ -35,7 +37,7 @@ class Chef::Provider::AwsLaunchConfiguration < Chef::Provisioning::AWSDriver::AW
|
|
35
37
|
end
|
36
38
|
|
37
39
|
def destroy_aws_object(launch_configuration)
|
38
|
-
converge_by "delete
|
40
|
+
converge_by "delete launch configuration #{new_resource.name} in #{region}" do
|
39
41
|
# TODO add a timeout here.
|
40
42
|
# TODO is InUse really a status guaranteed to go away??
|
41
43
|
begin
|
@@ -1,6 +1,24 @@
|
|
1
1
|
require 'chef/provisioning/aws_driver/aws_provider'
|
2
2
|
|
3
3
|
class Chef::Provider::AwsLoadBalancer < Chef::Provisioning::AWSDriver::AWSProvider
|
4
|
+
|
5
|
+
def aws_tagger
|
6
|
+
@aws_tagger ||= begin
|
7
|
+
elb_strategy = Chef::Provisioning::AWSDriver::TaggingStrategy::ELB.new(
|
8
|
+
new_resource.driver.elb_client,
|
9
|
+
new_resource.name,
|
10
|
+
new_resource.aws_tags
|
11
|
+
)
|
12
|
+
Chef::Provisioning::AWSDriver::AWSTagger.new(elb_strategy, action_handler)
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
def converge_tags
|
17
|
+
aws_tagger.converge_tags
|
18
|
+
end
|
19
|
+
|
20
|
+
provides :aws_load_balancer
|
21
|
+
|
4
22
|
def destroy_aws_object(load_balancer)
|
5
23
|
converge_by "delete load balancer #{new_resource.name} (#{load_balancer.name}) in #{region}" do
|
6
24
|
load_balancer.delete
|
@@ -3,6 +3,10 @@ require 'chef/resource/aws_vpc'
|
|
3
3
|
require 'retryable'
|
4
4
|
|
5
5
|
class Chef::Provider::AwsNetworkAcl < Chef::Provisioning::AWSDriver::AWSProvider
|
6
|
+
include Chef::Provisioning::AWSDriver::TaggingStrategy::EC2ConvergeTags
|
7
|
+
|
8
|
+
provides :aws_network_acl
|
9
|
+
|
6
10
|
def action_create
|
7
11
|
network_acl = super
|
8
12
|
|
@@ -12,7 +16,7 @@ class Chef::Provider::AwsNetworkAcl < Chef::Provisioning::AWSDriver::AWSProvider
|
|
12
16
|
protected
|
13
17
|
|
14
18
|
def create_aws_object
|
15
|
-
converge_by "create
|
19
|
+
converge_by "create network ACL #{new_resource.name} in #{region}" do
|
16
20
|
options = {}
|
17
21
|
options[:vpc] = new_resource.vpc if new_resource.vpc
|
18
22
|
options = AWSResource.lookup_options(options, resource: new_resource)
|
@@ -87,7 +91,7 @@ class Chef::Provider::AwsNetworkAcl < Chef::Provisioning::AWSDriver::AWSProvider
|
|
87
91
|
end
|
88
92
|
|
89
93
|
unless replace_rules.empty? && desired_rules.empty? && current_rules.empty?
|
90
|
-
action_handler.report_progress "update
|
94
|
+
action_handler.report_progress "update network ACL #{new_resource.name} #{direction.to_s} rules"
|
91
95
|
replace_rules(network_acl, replace_rules)
|
92
96
|
add_rules(network_acl, desired_rules)
|
93
97
|
remove_rules(network_acl, current_rules)
|
@@ -4,11 +4,9 @@ require 'date'
|
|
4
4
|
require 'retryable'
|
5
5
|
|
6
6
|
class Chef::Provider::AwsNetworkInterface < Chef::Provisioning::AWSDriver::AWSProvider
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
end
|
11
|
-
end
|
7
|
+
include Chef::Provisioning::AWSDriver::TaggingStrategy::EC2ConvergeTags
|
8
|
+
|
9
|
+
provides :aws_network_interface
|
12
10
|
|
13
11
|
class NetworkInterfaceStatusTimeoutError < TimeoutError
|
14
12
|
def initialize(new_resource, initial_status, expected_status)
|
@@ -43,7 +41,7 @@ class Chef::Provider::AwsNetworkInterface < Chef::Provisioning::AWSDriver::AWSPr
|
|
43
41
|
end
|
44
42
|
|
45
43
|
converge_by "wait for new #{new_resource} in #{region} to become available" do
|
46
|
-
|
44
|
+
wait_for_status(eni, :available)
|
47
45
|
eni
|
48
46
|
end
|
49
47
|
end
|
@@ -122,14 +120,14 @@ class Chef::Provider::AwsNetworkInterface < Chef::Provisioning::AWSDriver::AWSPr
|
|
122
120
|
#
|
123
121
|
# If we were told to attach the network interface to a machine, do so
|
124
122
|
#
|
125
|
-
if expected_instance.is_a?(AWS::EC2::Instance)
|
123
|
+
if expected_instance.is_a?(AWS::EC2::Instance) || expected_instance.is_a?(::Aws::EC2::Instance)
|
126
124
|
case status
|
127
125
|
when :available
|
128
126
|
attach(eni)
|
129
127
|
when :in_use
|
130
128
|
# We don't want to attempt to reattach to the same instance or device index
|
131
129
|
attachment = current_attachment(eni)
|
132
|
-
if attachment.instance != expected_instance || (options[:device_index] && attachment.device_index != new_resource.device_index)
|
130
|
+
if attachment.instance.id != expected_instance.id || (options[:device_index] && attachment.device_index != new_resource.device_index)
|
133
131
|
detach(eni)
|
134
132
|
attach(eni)
|
135
133
|
end
|
@@ -153,38 +151,27 @@ class Chef::Provider::AwsNetworkInterface < Chef::Provisioning::AWSDriver::AWSPr
|
|
153
151
|
eni
|
154
152
|
end
|
155
153
|
|
156
|
-
def wait_for_eni_status(eni, expected_status)
|
157
|
-
initial_status = eni.status
|
158
|
-
log_callback = proc {
|
159
|
-
Chef::Log.info("waiting for #{new_resource} status to change to #{expected_status}...")
|
160
|
-
}
|
161
|
-
|
162
|
-
Retryable.retryable(:tries => 30, :sleep => 2, :on => NetworkInterfaceStatusTimeoutError, :ensure => log_callback) do
|
163
|
-
raise NetworkInterfaceStatusTimeoutError.new(new_resource, initial_status, expected_status) if eni.status != expected_status
|
164
|
-
end
|
165
|
-
end
|
166
|
-
|
167
154
|
def detach(eni)
|
168
155
|
attachment = current_attachment(eni)
|
169
156
|
instance = attachment.instance
|
170
157
|
|
171
|
-
converge_by "detach #{new_resource} from #{instance.
|
158
|
+
converge_by "detach #{new_resource} from #{instance.id}" do
|
172
159
|
eni.detach
|
173
160
|
end
|
174
161
|
|
175
162
|
converge_by "wait for #{new_resource} to detach" do
|
176
|
-
|
163
|
+
wait_for_status(eni, :available)
|
177
164
|
eni
|
178
165
|
end
|
179
166
|
end
|
180
167
|
|
181
168
|
def attach(eni)
|
182
|
-
converge_by "attach #{new_resource} to #{new_resource.machine} (#{expected_instance.
|
183
|
-
eni.attach(expected_instance, options)
|
169
|
+
converge_by "attach #{new_resource} to #{new_resource.machine} (#{expected_instance.id})" do
|
170
|
+
eni.attach(expected_instance.id, options)
|
184
171
|
end
|
185
172
|
|
186
173
|
converge_by "wait for #{new_resource} to attach" do
|
187
|
-
|
174
|
+
wait_for_status(eni, :in_use)
|
188
175
|
eni
|
189
176
|
end
|
190
177
|
end
|
@@ -0,0 +1,66 @@
|
|
1
|
+
require 'chef/provisioning/aws_driver/aws_provider'
|
2
|
+
require 'chef/provisioning/aws_driver/tagging_strategy/rds'
|
3
|
+
|
4
|
+
class Chef::Provider::AwsRdsInstance < Chef::Provisioning::AWSDriver::AWSProvider
|
5
|
+
include Chef::Provisioning::AWSDriver::TaggingStrategy::RDSConvergeTags
|
6
|
+
|
7
|
+
provides :aws_rds_instance
|
8
|
+
|
9
|
+
REQUIRED_OPTIONS = %i(db_instance_identifier allocated_storage engine
|
10
|
+
db_instance_class master_username master_user_password)
|
11
|
+
|
12
|
+
OTHER_OPTIONS = %i(engine_version multi_az iops publicly_accessible db_name port db_subnet_group_name)
|
13
|
+
|
14
|
+
def update_aws_object(instance)
|
15
|
+
Chef::Log.warn("aws_rds_instance does not support modifying a started instance")
|
16
|
+
# There are required optiosn (like `allocated_storage`) that the use may not
|
17
|
+
# specify on a resource to perform an update. For example, they may want to
|
18
|
+
# only specify iops to modify that attribute on an update after initial
|
19
|
+
# creation. In this case we need to load the required options from the existing
|
20
|
+
# aws_object and only override it if the user has specified a value in the
|
21
|
+
# resource. Ideally, it would be nice to mark values as required on the
|
22
|
+
# resource but right now there is not a `required_on_create`. This would
|
23
|
+
# also be different if chef-provisioning performed resource cloning, which
|
24
|
+
# it does not.
|
25
|
+
end
|
26
|
+
|
27
|
+
def create_aws_object
|
28
|
+
converge_by "create RDS instance #{new_resource.db_instance_identifier} in #{region}" do
|
29
|
+
new_resource.driver.rds.client.create_db_instance(options_hash)
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def destroy_aws_object(instance)
|
34
|
+
converge_by "delete RDS instance #{new_resource.db_instance_identifier} in #{region}" do
|
35
|
+
instance.delete(skip_final_snapshot: true)
|
36
|
+
end
|
37
|
+
# Wait up to 10 minutes for the db instance to shutdown
|
38
|
+
converge_by "waited until RDS instance #{new_resource.name} was deleted" do
|
39
|
+
wait_for(
|
40
|
+
aws_object: instance,
|
41
|
+
query_method: :exists?,
|
42
|
+
expected_responses: [false],
|
43
|
+
acceptable_errors: [AWS::RDS::Errors::DBInstanceNotFound],
|
44
|
+
tries: 60,
|
45
|
+
sleep: 10
|
46
|
+
)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
# Sets the additional options then overrides it with all required options from
|
51
|
+
# the resource as well as optional options
|
52
|
+
def options_hash
|
53
|
+
@options_hash ||= begin
|
54
|
+
opts = Hash[new_resource.additional_options.map{|(k,v)| [k.to_sym,v]}]
|
55
|
+
REQUIRED_OPTIONS.each do |opt|
|
56
|
+
opts[opt] = new_resource.send(opt)
|
57
|
+
end
|
58
|
+
OTHER_OPTIONS.each do |opt|
|
59
|
+
opts[opt] = new_resource.send(opt) if ! new_resource.send(opt).nil?
|
60
|
+
end
|
61
|
+
AWSResource.lookup_options(opts, resource: new_resource)
|
62
|
+
opts
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
end
|
@@ -0,0 +1,89 @@
|
|
1
|
+
require 'chef/provisioning/aws_driver/aws_provider'
|
2
|
+
require 'chef/provisioning/aws_driver/tagging_strategy/rds'
|
3
|
+
|
4
|
+
class Chef::Provider::AwsRdsSubnetGroup < Chef::Provisioning::AWSDriver::AWSProvider
|
5
|
+
include Chef::Provisioning::AWSDriver::TaggingStrategy::RDSConvergeTags
|
6
|
+
|
7
|
+
provides :aws_rds_subnet_group
|
8
|
+
|
9
|
+
def create_aws_object
|
10
|
+
converge_by "create RDS subnet group #{new_resource.name} in #{region}" do
|
11
|
+
driver.create_db_subnet_group(desired_options)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
def destroy_aws_object(object)
|
16
|
+
converge_by "delete RDS subnet group #{new_resource.name} in #{region}" do
|
17
|
+
driver.delete_db_subnet_group(db_subnet_group_name: new_resource.name)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def update_aws_object(object)
|
22
|
+
updates = required_updates(object)
|
23
|
+
if ! updates.empty?
|
24
|
+
converge_by updates do
|
25
|
+
driver.modify_db_subnet_group(desired_options)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
def desired_options
|
31
|
+
@desired_options ||= begin
|
32
|
+
opts = {}
|
33
|
+
opts[:db_subnet_group_name] = new_resource.name
|
34
|
+
opts[:db_subnet_group_description] = new_resource.description
|
35
|
+
opts[:subnet_ids] = new_resource.subnets
|
36
|
+
AWSResource.lookup_options(opts, resource: new_resource)
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
# Given an existing object, return an array of update descriptions
|
41
|
+
# representing the updates that need to be made.
|
42
|
+
#
|
43
|
+
# If no updates are needed, an empty array is returned.
|
44
|
+
#
|
45
|
+
def required_updates(object)
|
46
|
+
ret = []
|
47
|
+
if desired_options[:db_subnet_group_description] != object[:db_subnet_group_description]
|
48
|
+
ret << " set group description to #{desired_options[:db_subnet_group_description]}"
|
49
|
+
end
|
50
|
+
|
51
|
+
if ! xor_array(desired_options[:subnet_ids], subnet_ids(object[:subnets])).empty?
|
52
|
+
ret << " set subnets to #{desired_options[:subnet_ids]}"
|
53
|
+
end
|
54
|
+
|
55
|
+
if ! (desired_options[:aws_tags].nil? || desired_options[:aws_tags].empty?)
|
56
|
+
# modify_db_subnet_group doesn't support the tags key according to
|
57
|
+
# http://docs.aws.amazon.com/AWSRubySDK/latest/AWS/RDS/Client.html#modify_db_subnet_group-instance_method
|
58
|
+
Chef::Log.warn "Updating tags for RDS subnet groups is not supported."
|
59
|
+
end
|
60
|
+
|
61
|
+
ret.unshift("update RDS subnet group #{new_resource.name} in #{region}") unless ret.empty?
|
62
|
+
ret
|
63
|
+
end
|
64
|
+
|
65
|
+
|
66
|
+
private
|
67
|
+
|
68
|
+
def subnet_ids(subnets)
|
69
|
+
subnets.map {|i| i[:subnet_identifier] }
|
70
|
+
end
|
71
|
+
|
72
|
+
def xor_array(a, b)
|
73
|
+
(a | b) - (a & b)
|
74
|
+
end
|
75
|
+
|
76
|
+
# To be in line with the other resources. The aws_tags property
|
77
|
+
# takes a hash. But we actually need an array.
|
78
|
+
def tag_hash_to_array(tag_hash)
|
79
|
+
ret = []
|
80
|
+
tag_hash.each do |key, value|
|
81
|
+
ret << {:key => key, :value => value}
|
82
|
+
end
|
83
|
+
ret
|
84
|
+
end
|
85
|
+
|
86
|
+
def driver
|
87
|
+
new_resource.driver.rds.client
|
88
|
+
end
|
89
|
+
end
|