Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

r+d/aws_launch_template: Add IPv4 & IPv6 prefix and PrivateDnsName options #23365

Merged
merged 37 commits into from
Mar 18, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
37 commits
Select commit Hold shift + click to select a range
b97edfa
feat: add ipv4 & ipv6 prefix options to aws_launch_template resource
zachfeld Feb 24, 2022
3b968e7
fix: validation function should check for CIDR range
zachfeld Feb 24, 2022
de77415
feat: add ipv4 & ipv6 prefix options to aws_launch_template resource
zachfeld Feb 24, 2022
869f0fa
fix: validation function should check for CIDR range
zachfeld Feb 24, 2022
cd77a67
Revert "fix: validation function should check for CIDR range"
ewbankkit Mar 15, 2022
2e430d0
Revert "feat: add ipv4 & ipv6 prefix options to aws_launch_template r…
ewbankkit Mar 15, 2022
a0238c2
r/aws_launch_template: Alphabetize attributes.
ewbankkit Mar 15, 2022
97fa683
r/aws_launch_template: Start to tidy up resource Create.
ewbankkit Mar 15, 2022
1e95f35
r/aws_launch_template: Add and use 'FindLaunchTemplateByID'.
ewbankkit Mar 15, 2022
c73b2b4
r/aws_launch_template: Add and use 'FindLaunchTemplateVersionByTwoPar…
ewbankkit Mar 15, 2022
8f9fa51
r/aws_launch_template: Tidy up resource Delete.
ewbankkit Mar 15, 2022
ecf7ceb
r/aws_launch_template: Tidy up resource Read.
ewbankkit Mar 15, 2022
b6b3528
Merge branch 'main' into tmp-pr23365
ewbankkit Mar 15, 2022
501d248
r/aws_launch_template: Tidy up resource Update.
ewbankkit Mar 16, 2022
9212a8c
r/aws_launch_template: Tidy up acceptance tests.
ewbankkit Mar 16, 2022
543f23c
Use EC2 endpoint ID for 'acctest.ErrorCheck', not AutoScaling.
ewbankkit Mar 16, 2022
9710b31
r/aws_launch_template: Skip error indicating Licese Manager ResourceL…
ewbankkit Mar 16, 2022
a4cebe5
r/aws_launch_template: Tidy up expanders.
ewbankkit Mar 16, 2022
0b40da4
r/aws_launch_template: Tidy up flatteners.
ewbankkit Mar 17, 2022
e773d5e
d/aws_launch_template: Alphabetize attributes.
ewbankkit Mar 17, 2022
e67c9d0
d/aws_launch_template: Use 'flattenResponseLaunchTemplateData'.
ewbankkit Mar 17, 2022
c179f9b
r/aws_launch_template: Acceptance tests passing.
ewbankkit Mar 17, 2022
be4b706
d+r/aws_launch_template: Add `ipv4_prefixes`, `ipv4_prefix_count`, `i…
ewbankkit Mar 17, 2022
79a9d1a
Merge branch 'tmp-pr23365' into HEAD
ewbankkit Mar 17, 2022
2756b3c
Fix terrafmt errors in acceptance test configurations.
ewbankkit Mar 17, 2022
715a622
d+r/aws_launch_template: Add `capacity_reservation_resource_group_arn…
ewbankkit Mar 17, 2022
b5a5de0
Fix golangci-lint error 'SA9003: empty branch (staticcheck)'.
ewbankkit Mar 18, 2022
b4bc260
r/aws_launch_template: Alphabetize arguments in documentation.
ewbankkit Mar 18, 2022
1bcc935
d+r/aws_launch_template: Add `private_dns_name_options` configuration…
ewbankkit Mar 18, 2022
36871b9
Add 'FindCapacityReservationByID'.
ewbankkit Mar 18, 2022
06697ac
r/aws_ec2_capacity_reservation: Use '_Values' functions (#14601).
ewbankkit Mar 18, 2022
6b1d9b5
r/aws_ec2_capacity_reservation: Tidy up resource Create.
ewbankkit Mar 18, 2022
0f90e0a
r/aws_ec2_capacity_reservation: Tidy up resource Delete.
ewbankkit Mar 18, 2022
2251936
r/aws_ec2_capacity_reservation: Tidy up resource Update.
ewbankkit Mar 18, 2022
0b41890
r/aws_ec2_capacity_reservation: Tidy up resource Read.
ewbankkit Mar 18, 2022
8217368
r/aws_ec2_capacity_reservation: Tidy up acceptance tests.
ewbankkit Mar 18, 2022
09e741c
r/aws_ec2_capacity_reservation: State transitions.
ewbankkit Mar 18, 2022
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 27 additions & 0 deletions .changelog/23365.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
```release-note:enhancement
data-source/aws_launch_template: Add `capacity_reservation_specification`, `cpu_options`, `elastic_inference_accelerator` and `license_specification` attributes
```

```release-note:enhancement
resource/aws_launch_template: Add `ipv4_prefixes`, `ipv4_prefix_count`, `ipv6_prefixes` and `ipv6_prefix_count` arguments to the `network_interfaces` configuration block
```

```release-note:enhancement
data-source/aws_launch_template: Add `ipv4_prefixes`, `ipv4_prefix_count`, `ipv6_prefixes` and `ipv6_prefix_count` attributes to the `network_interfaces` configuration block
```

```release-note:enhancement
resource/aws_launch_template: Add `capacity_reservation_resource_group_arn` argument to the `capacity_reservation_specification.capacity_reservation_target` configuration block
```

```release-note:enhancement
data-source/aws_launch_template: Add `capacity_reservation_resource_group_arn` attribute to the `capacity_reservation_specification.capacity_reservation_target` configuration block
```

```release-note:enhancement
resource/aws_launch_template: Add `private_dns_name_options` argument
```

```release-note:enhancement
data-source/aws_launch_template: Add `private_dns_name_options` attribute
```
8 changes: 4 additions & 4 deletions docs/contributing/data-handling-and-conversion.md
Original file line number Diff line number Diff line change
Expand Up @@ -461,9 +461,9 @@ To read:
input := service.ExampleOperationInput{}

if v, ok := d.GetOk("attribute_name"); ok {
t, _ := time.Parse(time.RFC3339, v.(string))
v, _ := time.Parse(time.RFC3339, v.(string))

input.AttributeName = aws.Time(t)
input.AttributeName = aws.Time(v)
}
```

Expand Down Expand Up @@ -806,9 +806,9 @@ func expandStructure(tfMap map[string]interface{}) *service.Structure {
// ...

if v, ok := tfMap["nested_attribute_name"].(string); ok && v != "" {
t, _ := time.Parse(time.RFC3339, v.(string))
v, _ := time.Parse(time.RFC3339, v)

apiObject.NestedAttributeName = aws.Time(t)
apiObject.NestedAttributeName = aws.Time(v)
}

// ...
Expand Down
185 changes: 83 additions & 102 deletions internal/service/ec2/capacity_reservation.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import (
"github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation"
"github.com/hashicorp/terraform-provider-aws/internal/conns"
tftags "github.com/hashicorp/terraform-provider-aws/internal/tags"
"github.com/hashicorp/terraform-provider-aws/internal/tfresource"
"github.com/hashicorp/terraform-provider-aws/internal/verify"
)

Expand All @@ -33,6 +34,10 @@ func ResourceCapacityReservation() *schema.Resource {
CustomizeDiff: verify.SetTagsDiff,

Schema: map[string]*schema.Schema{
"arn": {
Type: schema.TypeString,
Computed: true,
},
"availability_zone": {
Type: schema.TypeString,
Required: true,
Expand All @@ -50,13 +55,10 @@ func ResourceCapacityReservation() *schema.Resource {
ValidateFunc: validation.IsRFC3339Time,
},
"end_date_type": {
Type: schema.TypeString,
Optional: true,
Default: ec2.EndDateTypeUnlimited,
ValidateFunc: validation.StringInSlice([]string{
ec2.EndDateTypeUnlimited,
ec2.EndDateTypeLimited,
}, false),
Type: schema.TypeString,
Optional: true,
Default: ec2.EndDateTypeUnlimited,
ValidateFunc: validation.StringInSlice(ec2.EndDateType_Values(), false),
},
"ephemeral_storage": {
Type: schema.TypeBool,
Expand All @@ -69,32 +71,17 @@ func ResourceCapacityReservation() *schema.Resource {
Required: true,
},
"instance_match_criteria": {
Type: schema.TypeString,
Optional: true,
ForceNew: true,
Default: ec2.InstanceMatchCriteriaOpen,
ValidateFunc: validation.StringInSlice([]string{
ec2.InstanceMatchCriteriaOpen,
ec2.InstanceMatchCriteriaTargeted,
}, false),
Type: schema.TypeString,
Optional: true,
ForceNew: true,
Default: ec2.InstanceMatchCriteriaOpen,
ValidateFunc: validation.StringInSlice(ec2.InstanceMatchCriteria_Values(), false),
},
"instance_platform": {
Type: schema.TypeString,
Required: true,
ForceNew: true,
ValidateFunc: validation.StringInSlice([]string{
ec2.CapacityReservationInstancePlatformLinuxUnix,
ec2.CapacityReservationInstancePlatformRedHatEnterpriseLinux,
ec2.CapacityReservationInstancePlatformSuselinux,
ec2.CapacityReservationInstancePlatformWindows,
ec2.CapacityReservationInstancePlatformWindowswithSqlserver,
ec2.CapacityReservationInstancePlatformWindowswithSqlserverEnterprise,
ec2.CapacityReservationInstancePlatformWindowswithSqlserverStandard,
ec2.CapacityReservationInstancePlatformWindowswithSqlserverWeb,
ec2.CapacityReservationInstancePlatformLinuxwithSqlserverStandard,
ec2.CapacityReservationInstancePlatformLinuxwithSqlserverWeb,
ec2.CapacityReservationInstancePlatformLinuxwithSqlserverEnterprise,
}, false),
Type: schema.TypeString,
Required: true,
ForceNew: true,
ValidateFunc: validation.StringInSlice(ec2.CapacityReservationInstancePlatform_Values(), false),
},
"instance_type": {
Type: schema.TypeString,
Expand All @@ -113,18 +100,11 @@ func ResourceCapacityReservation() *schema.Resource {
"tags": tftags.TagsSchema(),
"tags_all": tftags.TagsSchemaComputed(),
"tenancy": {
Type: schema.TypeString,
Optional: true,
ForceNew: true,
Default: ec2.CapacityReservationTenancyDefault,
ValidateFunc: validation.StringInSlice([]string{
ec2.CapacityReservationTenancyDefault,
ec2.CapacityReservationTenancyDedicated,
}, false),
},
"arn": {
Type: schema.TypeString,
Computed: true,
Type: schema.TypeString,
Optional: true,
ForceNew: true,
Default: ec2.CapacityReservationTenancyDefault,
ValidateFunc: validation.StringInSlice(ec2.CapacityReservationTenancy_Values(), false),
},
},
}
Expand All @@ -135,7 +115,7 @@ func resourceCapacityReservationCreate(d *schema.ResourceData, meta interface{})
defaultTagsConfig := meta.(*conns.AWSClient).DefaultTagsConfig
tags := defaultTagsConfig.MergeTags(tftags.New(d.Get("tags").(map[string]interface{})))

opts := &ec2.CreateCapacityReservationInput{
input := &ec2.CreateCapacityReservationInput{
AvailabilityZone: aws.String(d.Get("availability_zone").(string)),
EndDateType: aws.String(d.Get("end_date_type").(string)),
InstanceCount: aws.Int64(int64(d.Get("instance_count").(int))),
Expand All @@ -145,40 +125,44 @@ func resourceCapacityReservationCreate(d *schema.ResourceData, meta interface{})
}

if v, ok := d.GetOk("ebs_optimized"); ok {
opts.EbsOptimized = aws.Bool(v.(bool))
input.EbsOptimized = aws.Bool(v.(bool))
}

if v, ok := d.GetOk("end_date"); ok {
t, err := time.Parse(time.RFC3339, v.(string))
if err != nil {
return fmt.Errorf("Error parsing EC2 Capacity Reservation end date: %s", err.Error())
}
opts.EndDate = aws.Time(t)
v, _ := time.Parse(time.RFC3339, v.(string))

input.EndDate = aws.Time(v)
}

if v, ok := d.GetOk("ephemeral_storage"); ok {
opts.EphemeralStorage = aws.Bool(v.(bool))
input.EphemeralStorage = aws.Bool(v.(bool))
}

if v, ok := d.GetOk("instance_match_criteria"); ok {
opts.InstanceMatchCriteria = aws.String(v.(string))
input.InstanceMatchCriteria = aws.String(v.(string))
}

if v, ok := d.GetOk("outpost_arn"); ok {
opts.OutpostArn = aws.String(v.(string))
input.OutpostArn = aws.String(v.(string))
}

if v, ok := d.GetOk("tenancy"); ok {
opts.Tenancy = aws.String(v.(string))
input.Tenancy = aws.String(v.(string))
}

log.Printf("[DEBUG] Capacity reservation: %s", opts)
log.Printf("[DEBUG] Creating EC2 Capacity Reservation: %s", input)
output, err := conn.CreateCapacityReservation(input)

out, err := conn.CreateCapacityReservation(opts)
if err != nil {
return fmt.Errorf("Error creating EC2 Capacity Reservation: %s", err)
return fmt.Errorf("error creating EC2 Capacity Reservation: %w", err)
}

d.SetId(aws.StringValue(output.CapacityReservation.CapacityReservationId))

if _, err := WaitCapacityReservationActive(conn, d.Id()); err != nil {
return fmt.Errorf("error waiting for EC2 Capacity Reservation (%s) create: %w", d.Id(), err)
}
d.SetId(aws.StringValue(out.CapacityReservation.CapacityReservationId))

return resourceCapacityReservationRead(d, meta)
}

Expand All @@ -187,39 +171,26 @@ func resourceCapacityReservationRead(d *schema.ResourceData, meta interface{}) e
defaultTagsConfig := meta.(*conns.AWSClient).DefaultTagsConfig
ignoreTagsConfig := meta.(*conns.AWSClient).IgnoreTagsConfig

resp, err := conn.DescribeCapacityReservations(&ec2.DescribeCapacityReservationsInput{
CapacityReservationIds: []*string{aws.String(d.Id())},
})

if err != nil {
if tfawserr.ErrCodeEquals(err, "InvalidCapacityReservationId.NotFound") {
log.Printf("[WARN] EC2 Capacity Reservation (%s) not found, removing from state", d.Id())
d.SetId("")
return nil
}
return fmt.Errorf("error reading EC2 Capacity Reservation %s: %s", d.Id(), err)
}
reservation, err := FindCapacityReservationByID(conn, d.Id())

if resp == nil || len(resp.CapacityReservations) == 0 || resp.CapacityReservations[0] == nil {
return fmt.Errorf("error reading EC2 Capacity Reservation (%s): empty response", d.Id())
}

reservation := resp.CapacityReservations[0]

if aws.StringValue(reservation.State) == ec2.CapacityReservationStateCancelled || aws.StringValue(reservation.State) == ec2.CapacityReservationStateExpired {
log.Printf("[WARN] EC2 Capacity Reservation (%s) no longer active, removing from state", d.Id())
if !d.IsNewResource() && tfresource.NotFound(err) {
log.Printf("[WARN] EC2 Capacity Reservation %s not found, removing from state", d.Id())
d.SetId("")
return nil
}

if err != nil {
return fmt.Errorf("error reading EC2 Capacity Reservation (%s): %w", d.Id(), err)
}

d.Set("arn", reservation.CapacityReservationArn)
d.Set("availability_zone", reservation.AvailabilityZone)
d.Set("ebs_optimized", reservation.EbsOptimized)

d.Set("end_date", "")
if reservation.EndDate != nil {
d.Set("end_date", aws.TimeValue(reservation.EndDate).Format(time.RFC3339))
} else {
d.Set("end_date", nil)
}

d.Set("end_date_type", reservation.EndDateType)
d.Set("ephemeral_storage", reservation.EphemeralStorage)
d.Set("instance_count", reservation.TotalInstanceCount)
Expand All @@ -228,6 +199,7 @@ func resourceCapacityReservationRead(d *schema.ResourceData, meta interface{}) e
d.Set("instance_type", reservation.InstanceType)
d.Set("outpost_arn", reservation.OutpostArn)
d.Set("owner_id", reservation.OwnerId)
d.Set("tenancy", reservation.Tenancy)

tags := KeyValueTags(reservation.Tags).IgnoreAWS().IgnoreConfig(ignoreTagsConfig)

Expand All @@ -240,34 +212,35 @@ func resourceCapacityReservationRead(d *schema.ResourceData, meta interface{}) e
return fmt.Errorf("error setting tags_all: %w", err)
}

d.Set("tenancy", reservation.Tenancy)
d.Set("arn", reservation.CapacityReservationArn)

return nil
}

func resourceCapacityReservationUpdate(d *schema.ResourceData, meta interface{}) error {
conn := meta.(*conns.AWSClient).EC2Conn

opts := &ec2.ModifyCapacityReservationInput{
CapacityReservationId: aws.String(d.Id()),
EndDateType: aws.String(d.Get("end_date_type").(string)),
InstanceCount: aws.Int64(int64(d.Get("instance_count").(int))),
}
if d.HasChangesExcept("tags", "tags_all") {
input := &ec2.ModifyCapacityReservationInput{
CapacityReservationId: aws.String(d.Id()),
EndDateType: aws.String(d.Get("end_date_type").(string)),
InstanceCount: aws.Int64(int64(d.Get("instance_count").(int))),
}

if v, ok := d.GetOk("end_date"); ok {
t, err := time.Parse(time.RFC3339, v.(string))
if err != nil {
return fmt.Errorf("Error parsing EC2 Capacity Reservation end date: %s", err.Error())
if v, ok := d.GetOk("end_date"); ok {
v, _ := time.Parse(time.RFC3339, v.(string))

input.EndDate = aws.Time(v)
}
opts.EndDate = aws.Time(t)
}

log.Printf("[DEBUG] Capacity reservation: %s", opts)
log.Printf("[DEBUG] Updating EC2 Capacity Reservation: %s", input)
_, err := conn.ModifyCapacityReservation(input)

_, err := conn.ModifyCapacityReservation(opts)
if err != nil {
return fmt.Errorf("Error modifying EC2 Capacity Reservation: %s", err)
if err != nil {
return fmt.Errorf("error updating EC2 Capacity Reservation (%s): %w", d.Id(), err)
}

if _, err := WaitCapacityReservationActive(conn, d.Id()); err != nil {
return fmt.Errorf("error waiting for EC2 Capacity Reservation (%s) update: %w", d.Id(), err)
}
}

if d.HasChange("tags_all") {
Expand All @@ -284,13 +257,21 @@ func resourceCapacityReservationUpdate(d *schema.ResourceData, meta interface{})
func resourceCapacityReservationDelete(d *schema.ResourceData, meta interface{}) error {
conn := meta.(*conns.AWSClient).EC2Conn

opts := &ec2.CancelCapacityReservationInput{
log.Printf("[DEBUG] Deleting EC2 Capacity Reservation: %s", d.Id())
_, err := conn.CancelCapacityReservation(&ec2.CancelCapacityReservationInput{
CapacityReservationId: aws.String(d.Id()),
})

if tfawserr.ErrCodeEquals(err, ErrCodeInvalidCapacityReservationIdNotFound) {
return nil
}

_, err := conn.CancelCapacityReservation(opts)
if err != nil {
return fmt.Errorf("Error cancelling EC2 Capacity Reservation: %s", err)
return fmt.Errorf("error deleting EC2 Capacity Reservation (%s): %w", d.Id(), err)
}

if _, err := WaitCapacityReservationDeleted(conn, d.Id()); err != nil {
return fmt.Errorf("error waiting for EC2 Capacity Reservation (%s) delete: %w", d.Id(), err)
}

return nil
Expand Down
Loading