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

Adds the S3 Replication AccessControlTranslation and Account arguments #3577

Merged
merged 2 commits into from
Oct 10, 2018

Conversation

jrstarke
Copy link
Contributor

@jrstarke jrstarke commented Mar 1, 2018

This allows the S3 Replication to translate the owner of the objects on replication (GH-3575). This is particularly useful when you're replicating to a separate AWS Account, because otherwise, objects are by default not accessible beyond the original account. With translation, or replication, the replica account becomes the owner of the replica objects.

I'm new to Go and contributing to the Terraform Providers, so I'd love some feedback/guidance. But this feature is important enough to me that I felt it was worth the effort to learn.

I'm unsure how to set up an acceptance test for this feature, because it is, by design, cross account.

I tried running the acceptance tests, without modification, and they didn't seem to run as I would have expected

make testacc TESTARGS="-run 'TestAccAWSS3Bucket_'"
==> Checking that code complies with gofmt requirements...
TF_ACC=1 go test ./... -v -run -timeout 120m
?   	github.com/terraform-providers/terraform-provider-aws	[no test files]
testing: warning: no tests to run
PASS
ok  	github.com/terraform-providers/terraform-provider-aws/aws	0.879s [no tests to run]
make: *** No rule to make target `'TestAccAWSS3Bucket_''.  Stop.

I would appreciate whatever help or guidance you can provide, as I'd love to see this feature complete.

@ghost ghost added the size/M Managed by automation to categorize the size of a PR. label Mar 1, 2018
@radeksimko radeksimko added enhancement Requests to existing resources that expand the functionality or scope. service/s3 Issues and PRs that pertain to the s3 service. labels Mar 1, 2018
@ghost ghost added size/M Managed by automation to categorize the size of a PR. size/L Managed by automation to categorize the size of a PR. and removed size/M Managed by automation to categorize the size of a PR. labels Mar 12, 2018
@seanscofield
Copy link

Just expressing my interest in this as well. I run a bunch of EC2 instances that continually write stuff to S3 (which then get replicated to another account), and the lack of this feature means that I have to pause my cluster and let things drain out for a few hours before I can deploy my terraform; deploying breaks the replication configuration, at which point I need to use aws cli to reset it

@caarl
Copy link

caarl commented May 18, 2018

A +1 from me for this feature too. I'm in a similar position to @seanscofield with data continually being written to a bucket. Unfortunately in my scenario I cannot pause the data coming in which leaves me with an issue if Terraform resets the rules and data is replicated before reapplying outside of it.

Can anyone give an indication on when this feature is likely to become available @radeksimko ?

@mdlavin
Copy link
Contributor

mdlavin commented Jun 1, 2018

If anybody is interested in testing out this feature in a patched v1.21.0 version, I've made some Alpine Linux x64 binaries available here: https://github.com/lifeomic/terraform-provider-aws/releases/tag/v1.21.0_patched_5f7d0def

@mdlavin
Copy link
Contributor

mdlavin commented Sep 7, 2018

@radeksimko is there anything I can do to help this get merged into an official release?

@jrstarke jrstarke changed the title [WIP] Adds the S3 Replication AccessControlTranslation and Account arguments Adds the S3 Replication AccessControlTranslation and Account arguments Sep 7, 2018
@jrstarke
Copy link
Contributor Author

jrstarke commented Sep 7, 2018

I'd be happy to make any changes necessary to get this in too. I'd especially love some feedback on the code and tests

@ghost ghost added the size/L Managed by automation to categorize the size of a PR. label Sep 8, 2018
@jrstarke
Copy link
Contributor Author

$ make testacc TESTARGS="-run 'TestAccAWSS3Bucket_Replication'"
=== RUN   TestAccAWSS3Bucket_Replication
--- PASS: TestAccAWSS3Bucket_Replication (266.92s)
=== RUN   TestAccAWSS3Bucket_ReplicationWithoutStorageClass
--- PASS: TestAccAWSS3Bucket_ReplicationWithoutStorageClass (238.43s)
=== RUN   TestAccAWSS3Bucket_ReplicationExpectVersioningValidationError
--- PASS: TestAccAWSS3Bucket_ReplicationExpectVersioningValidationError (38.94s)
PASS
ok  	github.com/terraform-providers/terraform-provider-aws/aws	544.363s

@jrstarke
Copy link
Contributor Author

Ok, I run the whole set of s3 bucket acceptance tests. They seem to be inconsistent.

$ make testacc TESTARGS="-run 'TestAccAWSS3Bucket_'"
Enter MFA code for arn:aws:iam::972822414733:mfa/jamie-cli:
==> Checking that code complies with gofmt requirements...
TF_ACC=1 go test ./... -v -run 'TestAccAWSS3Bucket_' -timeout 120m
?     github.com/terraform-providers/terraform-provider-aws [no test files]
=== RUN   TestAccAWSS3Bucket_importBasic
--- PASS: TestAccAWSS3Bucket_importBasic (18.00s)
=== RUN   TestAccAWSS3Bucket_importWithPolicy
--- PASS: TestAccAWSS3Bucket_importWithPolicy (18.91s)
=== RUN   TestAccAWSS3Bucket_basic
--- PASS: TestAccAWSS3Bucket_basic (28.70s)
=== RUN   TestAccAWSS3Bucket_namePrefix
--- PASS: TestAccAWSS3Bucket_namePrefix (15.34s)
=== RUN   TestAccAWSS3Bucket_generatedName
--- PASS: TestAccAWSS3Bucket_generatedName (14.99s)
=== RUN   TestAccAWSS3Bucket_region
--- PASS: TestAccAWSS3Bucket_region (43.15s)
=== RUN   TestAccAWSS3Bucket_acceleration
--- PASS: TestAccAWSS3Bucket_acceleration (40.76s)
=== RUN   TestAccAWSS3Bucket_RequestPayer
--- PASS: TestAccAWSS3Bucket_RequestPayer (26.65s)
=== RUN   TestAccAWSS3Bucket_Policy
--- PASS: TestAccAWSS3Bucket_Policy (36.72s)
=== RUN   TestAccAWSS3Bucket_UpdateAcl
--- PASS: TestAccAWSS3Bucket_UpdateAcl (27.86s)
=== RUN   TestAccAWSS3Bucket_Website_Simple
--- PASS: TestAccAWSS3Bucket_Website_Simple (39.43s)
=== RUN   TestAccAWSS3Bucket_WebsiteRedirect
--- FAIL: TestAccAWSS3Bucket_WebsiteRedirect (28.45s)
    testing.go:527: Step 1 error: After applying this step and refreshing, the plan was not empty:

        DIFF:

        UPDATE: aws_s3_bucket.bucket
          website.0.redirect_all_requests_to: "hashicorp.com?my=query" => "https://hashicorp.com?my=query"

        STATE:

        aws_s3_bucket.bucket:
          ID = tf-test-bucket-8128057372481047653
          provider = provider.aws
          acceleration_status =
          acl = public-read
          arn = arn:aws:s3:::tf-test-bucket-8128057372481047653
          bucket = tf-test-bucket-8128057372481047653
          bucket_domain_name = tf-test-bucket-8128057372481047653.s3.amazonaws.com
          bucket_regional_domain_name = tf-test-bucket-8128057372481047653.s3.us-west-2.amazonaws.com
          cors_rule.# = 0
          force_destroy = false
          hosted_zone_id = Z3BJ6K6RIION7M
          logging.# = 0
          region = us-west-2
          replication_configuration.# = 0
          request_payer = BucketOwner
          server_side_encryption_configuration.# = 0
          tags.% = 0
          versioning.# = 1
          versioning.0.enabled = false
          versioning.0.mfa_delete = false
          website.# = 1
          website.0.error_document =
          website.0.index_document =
          website.0.redirect_all_requests_to = hashicorp.com?my=query
          website.0.routing_rules =
          website_domain = s3-website-us-west-2.amazonaws.com
          website_endpoint = tf-test-bucket-8128057372481047653.s3-website-us-west-2.amazonaws.com
=== RUN   TestAccAWSS3Bucket_WebsiteRoutingRules
--- PASS: TestAccAWSS3Bucket_WebsiteRoutingRules (28.88s)
=== RUN   TestAccAWSS3Bucket_enableDefaultEncryption_whenTypical
--- PASS: TestAccAWSS3Bucket_enableDefaultEncryption_whenTypical (37.99s)
=== RUN   TestAccAWSS3Bucket_enableDefaultEncryption_whenAES256IsUsed
--- PASS: TestAccAWSS3Bucket_enableDefaultEncryption_whenAES256IsUsed (15.08s)
=== RUN   TestAccAWSS3Bucket_disableDefaultEncryption_whenDefaultEncryptionIsEnabled
--- PASS: TestAccAWSS3Bucket_disableDefaultEncryption_whenDefaultEncryptionIsEnabled (28.00s)
=== RUN   TestAccAWSS3Bucket_shouldFailNotFound
--- PASS: TestAccAWSS3Bucket_shouldFailNotFound (9.82s)
=== RUN   TestAccAWSS3Bucket_Versioning
--- FAIL: TestAccAWSS3Bucket_Versioning (36.19s)
    testing.go:527: Step 2 error: Check failed: Check 2/2 error: bad error versioning status, expected: Suspended, got Enabled
=== RUN   TestAccAWSS3Bucket_Cors
--- FAIL: TestAccAWSS3Bucket_Cors (51.75s)
    testing.go:527: Step 1 error: Check failed: Check 2/2 error: bad error cors rule, expected: [{
          AllowedHeaders: ["*"],
          AllowedMethods: ["PUT","POST"],
          AllowedOrigins: ["https://www.example.com"],
          ExposeHeaders: ["x-amz-server-side-encryption","ETag"],
          MaxAgeSeconds: 3000
        }], got [{
          AllowedHeaders: ["*"],
          AllowedMethods: ["GET"],
          AllowedOrigins: ["https://www.example.com"]
        }]
    testing.go:527: Step 0 error: Check failed: Check 2/2 error: NoSuchBucket: The specified bucket does not exist
          status code: 404, request id: 05A7772F9FB4A77D, host id: 2bhuZ1A6X5EqXFQq/jNdO2j/l8NDFdNh6K/CBWFHrCkOdw5LLKsuGrZZK4uaz/7oVfze41l7/BI=
=== RUN   TestAccAWSS3Bucket_Logging
--- PASS: TestAccAWSS3Bucket_Logging (22.99s)
=== RUN   TestAccAWSS3Bucket_Lifecycle
--- PASS: TestAccAWSS3Bucket_Lifecycle (39.53s)
=== RUN   TestAccAWSS3Bucket_LifecycleExpireMarkerOnly
--- PASS: TestAccAWSS3Bucket_LifecycleExpireMarkerOnly (26.65s)
=== RUN   TestAccAWSS3Bucket_Replication
--- FAIL: TestAccAWSS3Bucket_Replication (80.26s)
    testing.go:527: Step 1 error: Check failed: Check 2/6 error: aws_s3_bucket.bucket: Attribute 'replication_configuration.#' expected "1", got "0"
=== RUN   TestAccAWSS3Bucket_ReplicationWithoutStorageClass
--- PASS: TestAccAWSS3Bucket_ReplicationWithoutStorageClass (57.88s)
=== RUN   TestAccAWSS3Bucket_ReplicationExpectVersioningValidationError
--- PASS: TestAccAWSS3Bucket_ReplicationExpectVersioningValidationError (37.13s)
FAIL
FAIL  github.com/terraform-providers/terraform-provider-aws/aws 811.156s
make: *** [testacc] Error 1
$ make testacc TESTARGS="-run 'TestAccAWSS3Bucket_WebsiteRedirect'"
==> Checking that code complies with gofmt requirements...
TF_ACC=1 go test ./... -v -run 'TestAccAWSS3Bucket_WebsiteRedirect' -timeout 120m
?     github.com/terraform-providers/terraform-provider-aws [no test files]
=== RUN   TestAccAWSS3Bucket_WebsiteRedirect
--- PASS: TestAccAWSS3Bucket_WebsiteRedirect (41.64s)
PASS
ok    github.com/terraform-providers/terraform-provider-aws/aws 41.676s
$ make testacc TESTARGS="-run 'TestAccAWSS3Bucket_Versioning'"
==> Checking that code complies with gofmt requirements...
TF_ACC=1 go test ./... -v -run 'TestAccAWSS3Bucket_Versioning' -timeout 120m
?     github.com/terraform-providers/terraform-provider-aws [no test files]
=== RUN   TestAccAWSS3Bucket_Versioning
--- PASS: TestAccAWSS3Bucket_Versioning (38.33s)
PASS
ok    github.com/terraform-providers/terraform-provider-aws/aws 38.362s
$ make testacc TESTARGS="-run 'TestAccAWSS3Bucket_Cors'"
==> Checking that code complies with gofmt requirements...
TF_ACC=1 go test ./... -v -run 'TestAccAWSS3Bucket_Cors' -timeout 120m
?     github.com/terraform-providers/terraform-provider-aws [no test files]
=== RUN   TestAccAWSS3Bucket_Cors
--- PASS: TestAccAWSS3Bucket_Cors (61.15s)
PASS
ok    github.com/terraform-providers/terraform-provider-aws/aws 61.187s
TF_ACC=1 go test ./... -v -run 'TestAccAWSS3Bucket_Replication' -timeout 120m
?     github.com/terraform-providers/terraform-provider-aws [no test files]
=== RUN   TestAccAWSS3Bucket_Replication
--- PASS: TestAccAWSS3Bucket_Replication (212.57s)
=== RUN   TestAccAWSS3Bucket_ReplicationWithoutStorageClass
--- PASS: TestAccAWSS3Bucket_ReplicationWithoutStorageClass (75.38s)
=== RUN   TestAccAWSS3Bucket_ReplicationExpectVersioningValidationError
--- PASS: TestAccAWSS3Bucket_ReplicationExpectVersioningValidationError (36.19s)
PASS
ok    github.com/terraform-providers/terraform-provider-aws/aws 324.205s

@mdlavin
Copy link
Contributor

mdlavin commented Sep 13, 2018

If anybody is interested in testing out this feature in a patched v1.36.0 version, I've made some Alpine Linux x64 binaries available here: https://github.com/lifeomic/terraform-provider-aws/releases/tag/v1.36.0_patched_f2d0f833c

@ghost ghost added documentation Introduces or discusses updates to documentation. tests PRs: expanded test coverage. Issues: expanded coverage, enhancements to test infrastructure. labels Oct 1, 2018
@@ -377,6 +377,10 @@ func resourceAwsS3Bucket() *schema.Resource {
Set: destinationHash,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"account": {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd suggest renaming this to account_id to match similar places in the code base.
Also can add ValidateFunc: validateAwsAccountId,.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Both these seem reasonable and will be updated on merge.

bflad added a commit that referenced this pull request Oct 10, 2018
* Switch replication rule destination access_control_translation from TypeSet to TypeList
* Add replication rule destination account validation
* Add replication rule destination access_control_translation owner validation
* Split replication rule destination access_control_translation acceptance testing into its own function and add non-encrypted configuration TestStep
* Ensure testAccCheckAWSS3BucketReplicationRules can translate HIL references in Rule.Destination.Account
@bflad bflad added this to the v1.40.0 milestone Oct 10, 2018
@bflad
Copy link
Contributor

bflad commented Oct 10, 2018

@ewbankkit thanks for the feedback here - I have some in-flight changes already and will try to incorporate some of your feedback.

Copy link
Contributor

@bflad bflad left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi @jrstarke 👋 Thank you so much for submitting this and your patience! Overall it was in fantastic shape. I hope you don't mind I made a few minor adjustments in a followup commit on merge (a9c5649) based on mine and @ewbankkit's feedback below just so we could get this released today.

LGTM after running the acceptance testing multiple passes. 🚀

{
ID: aws.String("foobar"),
Destination: &s3.Destination{
Account: aws.String("${data.aws_caller_identity.current.account_id}"),
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure how this was passing previously, but I needed to add the HIL translation for this parameter in testAccCheckAWSS3BucketReplicationRules for the testing to pass for me. 😄

if account := dest.Account; account != nil && strings.HasPrefix(aws.StringValue(dest.Account), "${") {
	resourceReference := strings.Replace(aws.StringValue(dest.Account), "${", "", 1)
	resourceReference = strings.Replace(resourceReference, "}", "", 1)
	resourceReferenceParts := strings.Split(resourceReference, ".")
	resourceAttribute := resourceReferenceParts[len(resourceReferenceParts)-1]
	resourceName := strings.Join(resourceReferenceParts[:len(resourceReferenceParts)-1], ".")
	value := s.RootModule().Resources[resourceName].Primary.Attributes[resourceAttribute]
	dest.Account = aws.String(value)
}

We should probably move this logic to its own function so it can be reused in other testing. 😅

@@ -731,6 +731,42 @@ func TestAccAWSS3Bucket_Cors_EmptyOrigin(t *testing.T) {
),
),
},
{
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We generally prefer to create new, separate acceptance test functions for new attributes 👍

}
if v.Destination.AccessControlTranslation != nil {
rdt := make(map[string]interface{})
rdt["owner"] = *v.Destination.AccessControlTranslation.Owner
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To prevent potential panics, we prefer to use the AWS Go SDK provided methods for dereferencing, e.g. aws.StringValue(v.Destination.AccessControlTranslation.Owner) 👍

bflad added a commit that referenced this pull request Oct 10, 2018
* Switch replication rule destination access_control_translation from TypeSet to TypeList
* Change replication rule destination account attribute naming to account_id
* Add replication rule destination account_id validation
* Add replication rule destination access_control_translation owner validation
* Split replication rule destination access_control_translation acceptance testing into its own function and add non-encrypted configuration TestStep
* Ensure testAccCheckAWSS3BucketReplicationRules can translate HIL references in Rule.Destination.Account
@bflad bflad merged commit 4518e09 into hashicorp:master Oct 10, 2018
bflad added a commit that referenced this pull request Oct 10, 2018
@bflad
Copy link
Contributor

bflad commented Oct 10, 2018

This has been released in version 1.40.0 of the AWS provider. Please see the Terraform documentation on provider versioning or reach out if you need any assistance upgrading.

@ghost
Copy link

ghost commented Apr 2, 2020

I'm going to lock this issue because it has been closed for 30 days ⏳. This helps our maintainers find and focus on the active issues.

If you feel this issue should be reopened, we encourage creating a new issue linking back to this one for added context. Thanks!

@ghost ghost locked and limited conversation to collaborators Apr 2, 2020
@jrstarke jrstarke deleted the s3AclTranslation branch October 8, 2020 20:23
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
documentation Introduces or discusses updates to documentation. enhancement Requests to existing resources that expand the functionality or scope. service/s3 Issues and PRs that pertain to the s3 service. size/L Managed by automation to categorize the size of a PR. tests PRs: expanded test coverage. Issues: expanded coverage, enhancements to test infrastructure.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants