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

Support EKS cluster private access #8024

Merged
merged 3 commits into from
Mar 20, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
8 changes: 8 additions & 0 deletions aws/data_source_aws_eks_cluster.go
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,14 @@ func dataSourceAwsEksCluster() *schema.Resource {
Computed: true,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"endpoint_private_access": {
Type: schema.TypeBool,
Computed: true,
},
"endpoint_public_access": {
Type: schema.TypeBool,
Computed: true,
},
"security_group_ids": {
Type: schema.TypeSet,
Computed: true,
Expand Down
2 changes: 2 additions & 0 deletions aws/data_source_aws_eks_cluster_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ func TestAccAWSEksClusterDataSource_basic(t *testing.T) {
resource.TestCheckResourceAttrPair(resourceName, "role_arn", dataSourceResourceName, "role_arn"),
resource.TestCheckResourceAttrPair(resourceName, "version", dataSourceResourceName, "version"),
resource.TestCheckResourceAttr(dataSourceResourceName, "vpc_config.#", "1"),
resource.TestCheckResourceAttrPair(resourceName, "vpc_config.0.endpoint_private_access", dataSourceResourceName, "vpc_config.0.endpoint_private_access"),
resource.TestCheckResourceAttrPair(resourceName, "vpc_config.0.endpoint_public_access", dataSourceResourceName, "vpc_config.0.endpoint_public_access"),
resource.TestCheckResourceAttrPair(resourceName, "vpc_config.0.security_group_ids.#", dataSourceResourceName, "vpc_config.0.security_group_ids.#"),
resource.TestCheckResourceAttrPair(resourceName, "vpc_config.0.subnet_ids.#", dataSourceResourceName, "vpc_config.0.subnet_ids.#"),
resource.TestCheckResourceAttrPair(resourceName, "vpc_config.0.vpc_id", dataSourceResourceName, "vpc_config.0.vpc_id"),
Expand Down
65 changes: 58 additions & 7 deletions aws/resource_aws_eks_cluster.go
Original file line number Diff line number Diff line change
Expand Up @@ -82,9 +82,18 @@ func resourceAwsEksCluster() *schema.Resource {
MinItems: 1,
MaxItems: 1,
Required: true,
ForceNew: true,
Elem: &schema.Resource{
Schema: map[string]*schema.Schema{
"endpoint_private_access": {
Type: schema.TypeBool,
Optional: true,
Default: false,
},
"endpoint_public_access": {
Type: schema.TypeBool,
Optional: true,
Default: true,
},
"security_group_ids": {
Type: schema.TypeSet,
Optional: true,
Expand Down Expand Up @@ -236,7 +245,32 @@ func resourceAwsEksClusterUpdate(d *schema.ResourceData, meta interface{}) error

err = waitForUpdateEksCluster(conn, d.Id(), updateID, d.Timeout(schema.TimeoutUpdate))
if err != nil {
return fmt.Errorf("error waiting for EKS Cluster (%s) update (%s): %s", d.Id(), updateID, err)
return fmt.Errorf("error waiting for EKS Cluster (%s) version update (%s): %s", d.Id(), updateID, err)
}
}

if d.HasChange("vpc_config") {
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 why this is not acting like it seems it should, be needed to change this to check the nested attributes. 🙁

if d.HasChange("vpc_config.0.endpoint_private_access") || d.HasChange("vpc_config.0.endpoint_public_access") {

Previous output from acceptance testing:

--- FAIL: TestAccAWSEksCluster_Version (2519.24s)
   testing.go:538: Step 2 error: Error applying: 1 error occurred:
                * aws_eks_cluster.test: 1 error occurred:
                * aws_eks_cluster.test: error updating EKS Cluster (tf-acc-test-zdu6h) config: InvalidParameterException: Cluster is already at the desired configuration with endpointPrivateAccess: false and endpointPublicAccess: true

Even though the acceptance test debug logs were correctly only showing:

UPDATE: aws_eks_cluster.test
  version: "1.10" => "1.11"

Output from acceptance testing:

--- PASS: TestAccAWSEksClusterDataSource_basic (1320.87s)

--- PASS: TestAccAWSEksCluster_basic (1295.89s)
--- PASS: TestAccAWSEksCluster_VpcConfig_SecurityGroupIds (1327.26s)
--- PASS: TestAccAWSEksCluster_VpcConfig_EndpointPrivateAccess (1490.80s)
--- PASS: TestAccAWSEksCluster_VpcConfig_EndpointPublicAccess (1526.63s)
--- PASS: TestAccAWSEksCluster_Version (2552.56s)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I think it's a schema.TypeList vs. schema.TypeSet thing for the vpc_config attribute maybe?

input := &eks.UpdateClusterConfigInput{
Name: aws.String(d.Id()),
ResourcesVpcConfig: expandEksVpcConfigUpdateRequest(d.Get("vpc_config").([]interface{})),
}

log.Printf("[DEBUG] Updating EKS Cluster (%s) config: %s", d.Id(), input)
output, err := conn.UpdateClusterConfig(input)

if err != nil {
return fmt.Errorf("error updating EKS Cluster (%s) config: %s", d.Id(), err)
}

if output == nil || output.Update == nil || output.Update.Id == nil {
return fmt.Errorf("error determining EKS Cluster (%s) config update ID: empty response", d.Id())
}

updateID := aws.StringValue(output.Update.Id)

err = waitForUpdateEksCluster(conn, d.Id(), updateID, d.Timeout(schema.TimeoutUpdate))
bflad marked this conversation as resolved.
Show resolved Hide resolved
if err != nil {
return fmt.Errorf("error waiting for EKS Cluster (%s) config update (%s): %s", d.Id(), updateID, err)
}
}

Expand Down Expand Up @@ -289,8 +323,23 @@ func expandEksVpcConfigRequest(l []interface{}) *eks.VpcConfigRequest {
m := l[0].(map[string]interface{})

return &eks.VpcConfigRequest{
SecurityGroupIds: expandStringSet(m["security_group_ids"].(*schema.Set)),
SubnetIds: expandStringSet(m["subnet_ids"].(*schema.Set)),
EndpointPrivateAccess: aws.Bool(m["endpoint_private_access"].(bool)),
bflad marked this conversation as resolved.
Show resolved Hide resolved
EndpointPublicAccess: aws.Bool(m["endpoint_public_access"].(bool)),
SecurityGroupIds: expandStringSet(m["security_group_ids"].(*schema.Set)),
SubnetIds: expandStringSet(m["subnet_ids"].(*schema.Set)),
}
}

func expandEksVpcConfigUpdateRequest(l []interface{}) *eks.VpcConfigRequest {
if len(l) == 0 {
return nil
}

m := l[0].(map[string]interface{})

return &eks.VpcConfigRequest{
EndpointPrivateAccess: aws.Bool(m["endpoint_private_access"].(bool)),
EndpointPublicAccess: aws.Bool(m["endpoint_public_access"].(bool)),
}
}

Expand All @@ -312,9 +361,11 @@ func flattenEksVpcConfigResponse(vpcConfig *eks.VpcConfigResponse) []map[string]
}

m := map[string]interface{}{
"security_group_ids": schema.NewSet(schema.HashString, flattenStringList(vpcConfig.SecurityGroupIds)),
"subnet_ids": schema.NewSet(schema.HashString, flattenStringList(vpcConfig.SubnetIds)),
"vpc_id": aws.StringValue(vpcConfig.VpcId),
"endpoint_private_access": aws.BoolValue(vpcConfig.EndpointPrivateAccess),
"endpoint_public_access": aws.BoolValue(vpcConfig.EndpointPublicAccess),
"security_group_ids": schema.NewSet(schema.HashString, flattenStringList(vpcConfig.SecurityGroupIds)),
"subnet_ids": schema.NewSet(schema.HashString, flattenStringList(vpcConfig.SubnetIds)),
"vpc_id": aws.StringValue(vpcConfig.VpcId),
}

return []map[string]interface{}{m}
Expand Down
132 changes: 132 additions & 0 deletions aws/resource_aws_eks_cluster_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,8 @@ func TestAccAWSEksCluster_basic(t *testing.T) {
resource.TestMatchResourceAttr(resourceName, "role_arn", regexp.MustCompile(fmt.Sprintf("%s$", rName))),
resource.TestMatchResourceAttr(resourceName, "version", regexp.MustCompile(`^\d+\.\d+$`)),
resource.TestCheckResourceAttr(resourceName, "vpc_config.#", "1"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.endpoint_private_access", "false"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.endpoint_public_access", "true"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.security_group_ids.#", "0"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.subnet_ids.#", "2"),
resource.TestMatchResourceAttr(resourceName, "vpc_config.0.vpc_id", regexp.MustCompile(`^vpc-.+`)),
Expand Down Expand Up @@ -171,6 +173,98 @@ func TestAccAWSEksCluster_VpcConfig_SecurityGroupIds(t *testing.T) {
})
}

func TestAccAWSEksCluster_VpcConfig_EndpointPrivateAccess(t *testing.T) {
var cluster1, cluster2, cluster3 eks.Cluster

rName := fmt.Sprintf("tf-acc-test-%s", acctest.RandString(5))
resourceName := "aws_eks_cluster.test"

resource.ParallelTest(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
Providers: testAccProviders,
CheckDestroy: testAccCheckAWSEksClusterDestroy,
Steps: []resource.TestStep{
{
Config: testAccAWSEksClusterConfig_VpcConfig_EndpointPrivateAccess(rName, true),
Check: resource.ComposeTestCheckFunc(
testAccCheckAWSEksClusterExists(resourceName, &cluster1),
resource.TestCheckResourceAttr(resourceName, "vpc_config.#", "1"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.endpoint_private_access", "true"),
),
},
{
ResourceName: resourceName,
ImportState: true,
ImportStateVerify: true,
},
{
Config: testAccAWSEksClusterConfig_VpcConfig_EndpointPrivateAccess(rName, false),
Check: resource.ComposeTestCheckFunc(
testAccCheckAWSEksClusterExists(resourceName, &cluster2),
testAccCheckAWSEksClusterNotRecreated(&cluster1, &cluster2),
resource.TestCheckResourceAttr(resourceName, "vpc_config.#", "1"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.endpoint_private_access", "false"),
),
},
{
Config: testAccAWSEksClusterConfig_VpcConfig_EndpointPrivateAccess(rName, true),
Check: resource.ComposeTestCheckFunc(
testAccCheckAWSEksClusterExists(resourceName, &cluster3),
testAccCheckAWSEksClusterNotRecreated(&cluster2, &cluster3),
resource.TestCheckResourceAttr(resourceName, "vpc_config.#", "1"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.endpoint_private_access", "true"),
),
},
},
})
}

func TestAccAWSEksCluster_VpcConfig_EndpointPublicAccess(t *testing.T) {
var cluster1, cluster2, cluster3 eks.Cluster

rName := fmt.Sprintf("tf-acc-test-%s", acctest.RandString(5))
resourceName := "aws_eks_cluster.test"

resource.ParallelTest(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
Providers: testAccProviders,
CheckDestroy: testAccCheckAWSEksClusterDestroy,
Steps: []resource.TestStep{
{
Config: testAccAWSEksClusterConfig_VpcConfig_EndpointPublicAccess(rName, false),
Check: resource.ComposeTestCheckFunc(
testAccCheckAWSEksClusterExists(resourceName, &cluster1),
resource.TestCheckResourceAttr(resourceName, "vpc_config.#", "1"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.endpoint_public_access", "false"),
),
},
{
ResourceName: resourceName,
ImportState: true,
ImportStateVerify: true,
},
{
Config: testAccAWSEksClusterConfig_VpcConfig_EndpointPublicAccess(rName, true),
Check: resource.ComposeTestCheckFunc(
testAccCheckAWSEksClusterExists(resourceName, &cluster2),
testAccCheckAWSEksClusterNotRecreated(&cluster1, &cluster2),
resource.TestCheckResourceAttr(resourceName, "vpc_config.#", "1"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.endpoint_public_access", "true"),
),
},
{
Config: testAccAWSEksClusterConfig_VpcConfig_EndpointPublicAccess(rName, false),
Check: resource.ComposeTestCheckFunc(
testAccCheckAWSEksClusterExists(resourceName, &cluster3),
testAccCheckAWSEksClusterNotRecreated(&cluster2, &cluster3),
resource.TestCheckResourceAttr(resourceName, "vpc_config.#", "1"),
resource.TestCheckResourceAttr(resourceName, "vpc_config.0.endpoint_public_access", "false"),
),
},
},
})
}

func testAccCheckAWSEksClusterExists(resourceName string, cluster *eks.Cluster) resource.TestCheckFunc {
return func(s *terraform.State) error {
rs, ok := s.RootModule().Resources[resourceName]
Expand Down Expand Up @@ -365,3 +459,41 @@ resource "aws_eks_cluster" "test" {
}
`, testAccAWSEksClusterConfig_Base(rName), rName)
}

func testAccAWSEksClusterConfig_VpcConfig_EndpointPrivateAccess(rName string, endpointPrivateAccess bool) string {
return fmt.Sprintf(`
%[1]s

resource "aws_eks_cluster" "test" {
name = %[2]q
role_arn = "${aws_iam_role.test.arn}"

vpc_config {
endpoint_private_access = %[3]t
endpoint_public_access = true
subnet_ids = ["${aws_subnet.test.*.id[0]}", "${aws_subnet.test.*.id[1]}"]
}

depends_on = ["aws_iam_role_policy_attachment.test-AmazonEKSClusterPolicy", "aws_iam_role_policy_attachment.test-AmazonEKSServicePolicy"]
}
`, testAccAWSEksClusterConfig_Base(rName), rName, endpointPrivateAccess)
}

func testAccAWSEksClusterConfig_VpcConfig_EndpointPublicAccess(rName string, endpointPublicAccess bool) string {
return fmt.Sprintf(`
%[1]s

resource "aws_eks_cluster" "test" {
name = %[2]q
role_arn = "${aws_iam_role.test.arn}"

vpc_config {
endpoint_private_access = true
endpoint_public_access = %[3]t
subnet_ids = ["${aws_subnet.test.*.id[0]}", "${aws_subnet.test.*.id[1]}"]
}

depends_on = ["aws_iam_role_policy_attachment.test-AmazonEKSClusterPolicy", "aws_iam_role_policy_attachment.test-AmazonEKSServicePolicy"]
}
`, testAccAWSEksClusterConfig_Base(rName), rName, endpointPublicAccess)
}
2 changes: 1 addition & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ require (
github.com/apparentlymart/go-cidr v1.0.0 // indirect
github.com/apparentlymart/go-textseg v1.0.0 // indirect
github.com/armon/go-radix v1.0.0 // indirect
github.com/aws/aws-sdk-go v1.18.3
github.com/aws/aws-sdk-go v1.18.5
github.com/beevik/etree v1.0.1
github.com/bgentry/speakeasy v0.1.0 // indirect
github.com/blang/semver v3.5.1+incompatible // indirect
Expand Down
4 changes: 2 additions & 2 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -31,8 +31,8 @@ github.com/armon/go-radix v1.0.0 h1:F4z6KzEeeQIMeLFa97iZU6vupzoecKdU5TX24SNppXI=
github.com/armon/go-radix v1.0.0/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8=
github.com/aws/aws-sdk-go v1.14.31/go.mod h1:mFuSZ37Z9YOHbQEwBWztmVzqXrEkub65tZoCYDt7FT0=
github.com/aws/aws-sdk-go v1.16.36/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo=
github.com/aws/aws-sdk-go v1.18.3 h1:6BkQIKBFCXw0zVQl5KC7o+J/zYTyz+DKWxL3Uy0XUjg=
github.com/aws/aws-sdk-go v1.18.3/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo=
github.com/aws/aws-sdk-go v1.18.5 h1:S6j4o4AoJpq98DRc7wQrQsPZg73NyntGtUj6K6NPnuY=
github.com/aws/aws-sdk-go v1.18.5/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo=
github.com/beevik/etree v0.0.0-20171015221209-af219c0c7ea1/go.mod h1:r8Aw8JqVegEf0w2fDnATrX9VpkMcyFeM0FhwO62wh+A=
github.com/beevik/etree v1.0.1 h1:lWzdj5v/Pj1X360EV7bUudox5SRipy4qZLjY0rhb0ck=
github.com/beevik/etree v1.0.1/go.mod h1:r8Aw8JqVegEf0w2fDnATrX9VpkMcyFeM0FhwO62wh+A=
Expand Down
9 changes: 6 additions & 3 deletions vendor/github.com/aws/aws-sdk-go/aws/ec2metadata/api.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions vendor/github.com/aws/aws-sdk-go/aws/request/retryer.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion vendor/github.com/aws/aws-sdk-go/aws/version.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading