diff --git a/aws/data_source_aws_ebs_volume.go b/aws/data_source_aws_ebs_volume.go index df47570a16ad..f4aeb09a218d 100644 --- a/aws/data_source_aws_ebs_volume.go +++ b/aws/data_source_aws_ebs_volume.go @@ -55,6 +55,10 @@ func dataSourceAwsEbsVolume() *schema.Resource { Type: schema.TypeString, Computed: true, }, + "outpost_arn": { + Type: schema.TypeString, + Computed: true, + }, "volume_id": { Type: schema.TypeString, Computed: true, @@ -141,6 +145,7 @@ func volumeDescriptionAttributes(d *schema.ResourceData, client *AWSClient, volu d.Set("size", volume.Size) d.Set("snapshot_id", volume.SnapshotId) d.Set("volume_type", volume.VolumeType) + d.Set("outpost_arn", volume.OutpostArn) if err := d.Set("tags", keyvaluetags.Ec2KeyValueTags(volume.Tags).IgnoreAws().Map()); err != nil { return fmt.Errorf("error setting tags: %s", err) diff --git a/aws/data_source_aws_ebs_volume_test.go b/aws/data_source_aws_ebs_volume_test.go index 3539896872a7..366bbc73027d 100644 --- a/aws/data_source_aws_ebs_volume_test.go +++ b/aws/data_source_aws_ebs_volume_test.go @@ -21,6 +21,7 @@ func TestAccAWSEbsVolumeDataSource_basic(t *testing.T) { resource.TestCheckResourceAttr("data.aws_ebs_volume.ebs_volume", "size", "40"), resource.TestCheckResourceAttr("data.aws_ebs_volume.ebs_volume", "tags.%", "1"), resource.TestCheckResourceAttr("data.aws_ebs_volume.ebs_volume", "tags.Name", "External Volume"), + resource.TestCheckResourceAttr("data.aws_ebs_volume.ebs_volume", "outpost_arn", ""), ), }, }, diff --git a/aws/resource_aws_ebs_volume.go b/aws/resource_aws_ebs_volume.go index 89add9e1a8b4..7f639dfbc781 100644 --- a/aws/resource_aws_ebs_volume.go +++ b/aws/resource_aws_ebs_volume.go @@ -67,6 +67,12 @@ func resourceAwsEbsVolume() *schema.Resource { Computed: true, ForceNew: true, }, + "outpost_arn": { + Type: schema.TypeString, + Optional: true, + ForceNew: true, + ValidateFunc: validateArn, + }, "type": { Type: schema.TypeString, Optional: true, @@ -96,6 +102,9 @@ func resourceAwsEbsVolumeCreate(d *schema.ResourceData, meta interface{}) error if value, ok := d.GetOk("snapshot_id"); ok { request.SnapshotId = aws.String(value.(string)) } + if value, ok := d.GetOk("outpost_arn"); ok { + request.OutpostArn = aws.String(value.(string)) + } // IOPs are only valid, and required for, storage type io1. The current minimu // is 100. Instead of a hard validation we we only apply the IOPs to the @@ -264,6 +273,7 @@ func resourceAwsEbsVolumeRead(d *schema.ResourceData, meta interface{}) error { d.Set("kms_key_id", aws.StringValue(volume.KmsKeyId)) d.Set("size", aws.Int64Value(volume.Size)) d.Set("snapshot_id", aws.StringValue(volume.SnapshotId)) + d.Set("outpost_arn", aws.StringValue(volume.OutpostArn)) if err := d.Set("tags", keyvaluetags.Ec2KeyValueTags(volume.Tags).IgnoreAws().Map()); err != nil { return fmt.Errorf("error setting tags: %s", err) diff --git a/aws/resource_aws_ebs_volume_test.go b/aws/resource_aws_ebs_volume_test.go index be65651d090e..83033f9812e6 100644 --- a/aws/resource_aws_ebs_volume_test.go +++ b/aws/resource_aws_ebs_volume_test.go @@ -3,6 +3,7 @@ package aws import ( "fmt" "log" + "os" "regexp" "testing" @@ -87,6 +88,7 @@ func TestAccAWSEBSVolume_basic(t *testing.T) { resource.TestCheckResourceAttr(resourceName, "size", "1"), resource.TestCheckResourceAttr(resourceName, "tags.%", "0"), resource.TestCheckResourceAttr(resourceName, "type", "gp2"), + resource.TestCheckResourceAttr(resourceName, "outpost_arn", ""), ), }, { @@ -311,6 +313,40 @@ func TestAccAWSEBSVolume_withTags(t *testing.T) { }) } +func TestAccAWSEBSVolume_outpost(t *testing.T) { + var v ec2.Volume + resourceName := "aws_ebs_volume.test" + + outpostArn := os.Getenv("AWS_OUTPOST_ARN") + if outpostArn == "" { + t.Skip( + "Environment variable AWS_OUTPOST_ARN is not set. " + + "This environment variable must be set to the ARN of " + + "a deployed Outpost to enable this test.") + } + + resource.ParallelTest(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + IDRefreshName: resourceName, + Providers: testAccProviders, + CheckDestroy: testAccCheckVolumeDestroy, + Steps: []resource.TestStep{ + { + Config: testAccAwsEbsVolumeConfigOutpost(outpostArn), + Check: resource.ComposeTestCheckFunc( + testAccCheckVolumeExists(resourceName, &v), + resource.TestCheckResourceAttr(resourceName, "outpost_arn", outpostArn), + ), + }, + { + ResourceName: resourceName, + ImportState: true, + ImportStateVerify: true, + }, + }, + }) +} + func testAccCheckVolumeDestroy(s *terraform.State) error { conn := testAccProvider.Meta().(*AWSClient).ec2conn @@ -608,3 +644,18 @@ resource "aws_ebs_volume" "test" { } } ` + +func testAccAwsEbsVolumeConfigOutpost(outpostArn string) string { + return fmt.Sprintf(` +data "aws_availability_zones" "available" {} + +resource "aws_ebs_volume" "test" { + availability_zone = "${data.aws_availability_zones.available.names[0]}" + size = 1 + outpost_arn = "%s" + tags = { + Name = "tf-acc-volume-outpost" + } +} +`, outpostArn) +} diff --git a/website/docs/d/ebs_volume.html.markdown b/website/docs/d/ebs_volume.html.markdown index f801729495ff..47fa92d7e296 100644 --- a/website/docs/d/ebs_volume.html.markdown +++ b/website/docs/d/ebs_volume.html.markdown @@ -52,6 +52,7 @@ In addition to all arguments above, the following attributes are exported: * `iops` - The amount of IOPS for the disk. * `size` - The size of the drive in GiBs. * `snapshot_id` - The snapshot_id the EBS volume is based off. +* `outpost_arn` - The Amazon Resource Name (ARN) of the Outpost. * `volume_type` - The type of EBS volume. * `kms_key_id` - The ARN for the KMS encryption key. * `tags` - A mapping of tags for the resource. diff --git a/website/docs/r/ebs_volume.html.markdown b/website/docs/r/ebs_volume.html.markdown index b7a23a80cd3b..ba94350b246c 100644 --- a/website/docs/r/ebs_volume.html.markdown +++ b/website/docs/r/ebs_volume.html.markdown @@ -34,6 +34,7 @@ The following arguments are supported: * `iops` - (Optional) The amount of IOPS to provision for the disk. * `size` - (Optional) The size of the drive in GiBs. * `snapshot_id` (Optional) A snapshot to base the EBS volume off of. +* `outpost_arn` - (Optional) The Amazon Resource Name (ARN) of the Outpost. * `type` - (Optional) The type of EBS volume. Can be "standard", "gp2", "io1", "sc1" or "st1" (Default: "gp2"). * `kms_key_id` - (Optional) The ARN for the KMS encryption key. When specifying `kms_key_id`, `encrypted` needs to be set to true. * `tags` - (Optional) A mapping of tags to assign to the resource.