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

d/acm_certificate Explicitly define key types requested #8553

Merged
merged 6 commits into from
Jun 28, 2019

Conversation

pselle
Copy link
Contributor

@pselle pselle commented May 7, 2019

AWS doesn't give all key types by default without this filter, so explicitly request the key types documented as supported.

Community Note

  • Please vote on this pull request by adding a 👍 reaction to the original pull request comment to help the community and maintainers prioritize this request
  • Please do not leave "+1" comments, they generate extra noise for pull request followers and do not help prioritize the request

Fixes #7553

Release note for CHANGELOG:

Exposes non-2048 certificates when reading for the acm_certificate data source

Output from acceptance testing:

Where tf-4096.example.com has been created with a 4096 RSA key, and tf-2048 has been created with a 2048 RSA key:

$ AWS_PROFILE=default ACM_CERTIFICATE_SINGLE_ISSUED_DOMAIN=tf-4096.example.com ACM_CERTIFICATE_ROOT_DOMAIN=example.com TF_LOG_PATH=log.txt TF_LOG=debug TF_ACC=1 go test ./aws -v -timeout 120m -parallel 20 -run='TestAccAWSAcmCertificateDataSource_single'
=== RUN   TestAccAWSAcmCertificateDataSource_singleIssued
=== PAUSE TestAccAWSAcmCertificateDataSource_singleIssued
=== CONT  TestAccAWSAcmCertificateDataSource_singleIssued
--- PASS: TestAccAWSAcmCertificateDataSource_singleIssued (11.01s)
PASS
ok  	github.com/terraform-providers/terraform-provider-aws/aws	13.007s

$ AWS_PROFILE=default ACM_CERTIFICATE_SINGLE_ISSUED_DOMAIN=tf-2048.example.com ACM_CERTIFICATE_ROOT_DOMAIN=example.com TF_LOG_PATH=log.txt TF_LOG=debug TF_ACC=1 go test ./aws -v -timeout 120m -parallel 20 -run='TestAccAWSAcmCertificateDataSource_single'
=== RUN   TestAccAWSAcmCertificateDataSource_singleIssued
=== PAUSE TestAccAWSAcmCertificateDataSource_singleIssued
=== CONT  TestAccAWSAcmCertificateDataSource_singleIssued
--- PASS: TestAccAWSAcmCertificateDataSource_singleIssued (21.62s)
PASS
ok  	github.com/terraform-providers/terraform-provider-aws/aws	22.395s

Otherwise, AWS doesn't give all key types. Addresses hashicorp#7553
@ghost ghost added size/XS Managed by automation to categorize the size of a PR. service/acm Issues and PRs that pertain to the acm service. labels May 7, 2019
@pselle pselle changed the title [WIP] d/acm_certificate Explicitly define key types requested d/acm_certificate Explicitly define key types requested May 7, 2019
@pselle pselle marked this pull request as ready for review May 7, 2019 21:15
@pselle pselle requested a review from a team May 7, 2019 21:15
@pselle pselle requested a review from bflad May 13, 2019 19:48
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 @pselle 👋 Thanks for submitting this! I left two inline feedback items but it might be worth discussing some larger items outside that feedback. Namely:

  • Adding covering acceptance testing
  • Allowing operators to opt out searching all key algorithms by providing a new data source argument

With both these addressed/discussed, we should be able to get this in. 🚀


For the acceptance testing this functionality, we can use the newer aws_acm_certificate resource support for importing the certificate body and private key to generate a certificate that lies outside the existing ListCertificates key algorithms. The tls_private_key resource looks like it supports configuring the amount of RSA bits or using EDCSA.

A test configuration like the below should get this started with a RSA 4096 certificate in ACM:

resource "tls_private_key" "test" {
  algorithm = "RSA"
  rsa_bits  = 4096
}

resource "tls_self_signed_cert" "test" {
  allowed_uses = [
    "key_encipherment",
    "digital_signature",
    "server_auth",
  ]

  key_algorithm         = "RSA"
  private_key_pem       = "${tls_private_key.test.private_key_pem}"
  validity_period_hours = 12

  subject {
    common_name  = "example.com"
    organization = "ACME Examples, Inc"
  }
}

resource "aws_acm_certificate" "test" {
  certificate_body = "${tls_self_signed_cert.test.cert_pem}"
  private_key      = "${tls_private_key.test.private_key_pem}"
}

data "aws_acm_certificate" "test" {
  domain = "${aws_acm_certificate.test.domain_name}"
}

Taking that as a starting point, we can setup the acceptance test similar to the following:

func TestAccAWSAcmCertificateDataSource_Rsa4096(t *testing.T) {
	resourceName := "aws_acm_certificate.test"
	dataSourceName := "data.aws_acm_certificate.test"

	resource.ParallelTest(t, resource.TestCase{
		PreCheck:     func() { testAccPreCheck(t) },
		Providers:    testAccProvidersWithTLS,
		CheckDestroy: testAccCheckAcmCertificateDestroy,
		Steps: []resource.TestStep{
			{
				Config: testAccAwsAcmCertificateDataSourceConfigRsa4096(),
				Check: resource.ComposeTestCheckFunc(
					resource.TestCheckResourceAttrPair(resourceName, "arn", dataSourceName, "arn"),
				),
			},
		},
	})
}

func testAccAwsAcmCertificateDataSourceConfigRsa4096() string {
	return fmt.Sprintf(`
resource "tls_private_key" "test" {
  algorithm = "RSA"
  rsa_bits  = 4096
}

resource "tls_self_signed_cert" "test" {
  allowed_uses = [
    "key_encipherment",
    "digital_signature",
    "server_auth",
  ]

  key_algorithm         = "RSA"
  private_key_pem       = "${tls_private_key.test.private_key_pem}"
  validity_period_hours = 12

  subject {
    common_name  = "example.com"
    organization = "ACME Examples, Inc"
  }
}

resource "aws_acm_certificate" "test" {
  certificate_body = "${tls_self_signed_cert.test.cert_pem}"
  private_key      = "${tls_private_key.test.private_key_pem}"
}

data "aws_acm_certificate" "test" {
  domain = "${aws_acm_certificate.test.domain_name}"
}
`)
}

Which should fail without this change and should pass with this change. 👍


Relating to the second item, I'm a little worried operators may not want to opt out of searching all key algorithms for some of the following reasons:

  • Their environments may have overlapping ACM certificates with different key algorithms, in which this update could be a breaking change
  • Their environments may have a large number of ACM certificates, in which searching all key algorithms could further exasperate any throttling issues
  • Their compliance regulations may require only using certain key algorithms, in which a Sentinel policy could be used to limit searches

Given the above, we may want to consider adding a new and optional key_algorithm argument for the data source. I think the data source can still default to searching all algorithms as changed by this pull request (for operator simplicity), but providing an escape hatch that overrides this behavior would be helpful.

If we do go down this route, we should include an acceptance test (or test step) that verifies the new argument prevents finding a certificate of a different key algorithm. 👍

aws/data_source_aws_acm_certificate.go Outdated Show resolved Hide resolved
aws/data_source_aws_acm_certificate.go Outdated Show resolved Hide resolved
@bflad bflad added enhancement Requests to existing resources that expand the functionality or scope. waiting-response Maintainers are waiting on response from community or contributor. labels May 15, 2019
@ghost ghost added tests PRs: expanded test coverage. Issues: expanded coverage, enhancements to test infrastructure. size/M Managed by automation to categorize the size of a PR. and removed size/XS Managed by automation to categorize the size of a PR. labels May 17, 2019
@pselle
Copy link
Contributor Author

pselle commented May 17, 2019

@bflad Thanks so much for the feedback! I've implemented suggested changes, and am trying out the suggested acceptance test, although I'll take a little time to make sure I understand how it works/what it's doing.

As to "searching all algorithms might be a bad idea for some folks" I think this is very valid, since the change as is essentially is covering up AWS's current list behavior and modifying it, which could indeed be breaking to people expecting it to work as it has. So the suggestion here:

Allowing operators to opt out searching all key algorithms by providing a new data source argument

Makes me almost think that "do what AWS does, but give people an option to modify that behavior" might be a more palatable path actually? Basically, should we come at the problem from the other direction? I like the addition of an optional key_algorithms [updated to plural] in general, but seeing the possible failure modes makes it less palatable to change current behavior.

So this suggestion would be:

  • Without key_algorithms, no Filters are added
  • With key_algorithms, apply those filters
  • ❓ Maybe call it key_types to match the API?

@pselle pselle removed the waiting-response Maintainers are waiting on response from community or contributor. label May 17, 2019
@pselle pselle requested a review from bflad May 17, 2019 20:32
@bflad
Copy link
Contributor

bflad commented Jun 6, 2019

Hi again @pselle 👋 Sorry for the delayed response. I'm 👍 a new attribute on the data source that does as you say, optionally adding the Filters if defined with elements.

A schema definition like this should get you close:

"key_types": {
	Type: schema.TypeSet,
	Optional: true,
	Elem: &schema.Schema{Type: schema.TypeString},
	ValidateFunc: validation.StringInSlice([]string{
		acm.KeyAlgorithmEcPrime256v1,
		acm.KeyAlgorithmEcSecp384r1,
		acm.KeyAlgorithmEcSecp521r1,
		acm.KeyAlgorithmRsa1024,
		acm.KeyAlgorithmRsa2048,
		acm.KeyAlgorithmRsa4096,
	}, false),
},

Then in the code we can optionally use it with something like the below. 😄

params := &acm.ListCertificatesInput{}

if v := d.Get("key_types").(*schema.Set); v.Len() > 0 {
	params.Includes = &acm.Filters{
		KeyTypes: expandStringSet(v),
	},
}

Add the new argument to the documentation in website/docs/d/acm_certificate.html.markdown and hopefully this should be good to go! Thanks again!

@bflad bflad added the waiting-response Maintainers are waiting on response from community or contributor. label Jun 6, 2019
@bflad bflad added this to the v2.17.0 milestone Jun 28, 2019
@bflad bflad merged commit 16f2839 into hashicorp:master Jun 28, 2019
bflad added a commit that referenced this pull request Jun 28, 2019
… algorithm handling

Reference: #8553 (comment)

Output from acceptance testing:

```
--- PASS: TestAccAWSAcmCertificateDataSource_KeyTypes (17.32s)
```
@bflad
Copy link
Contributor

bflad commented Jun 28, 2019

Hey again @pselle 👋 Since I know you're busy in your new role and we would like to get this released today, I have performed the followup activities described in #8553 (comment) in a followup commit c160a98. Thanks so much for your work and discussion here! 🚀

bflad added a commit that referenced this pull request Jun 28, 2019
@bflad
Copy link
Contributor

bflad commented Jun 28, 2019

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

For further feature requests or bug reports with this functionality, please create a new GitHub issue following the template for triage. Thanks!

@ghost
Copy link

ghost commented Nov 3, 2019

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 Nov 3, 2019
@ghost ghost removed the waiting-response Maintainers are waiting on response from community or contributor. label Nov 3, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
enhancement Requests to existing resources that expand the functionality or scope. service/acm Issues and PRs that pertain to the acm service. size/M 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.

aws_acm_certificate does not work with 4096-bit RSA keys
2 participants