hashicorp / terraform-provider-aws

The AWS Provider enables Terraform to manage AWS resources.
https://registry.terraform.io/providers/hashicorp/aws
Mozilla Public License 2.0
9.73k stars 9.09k forks source link

[Bug]: use of aws_elastic_beanstalk_environment resource setting namespace: "aws:elb:listener" and certain configuration(s) results in a permadiff #35233

Open colinbjohnson opened 8 months ago

colinbjohnson commented 8 months ago

Terraform Core Version

1.6.5

AWS Provider Version

5.31.0

Affected Resource(s)

Expected Behavior

No "permanent diff" (i.e. on each run of terraform plan or terraform apply a diff is shown) is expected when using a configuration that contains the following setting:

resource "aws_elastic_beanstalk_environment" "environment" {
  name                = "options-testing-test"
  application         = aws_elastic_beanstalk_application.application.name
  solution_stack_name = "64bit Amazon Linux 2023 v4.1.2 running Docker"
  setting {
    namespace = "aws:elb:listener"
    name      = "ListenerProtocol"
    value     = "TCP"
  }
}

Actual Behavior

There is a permanent diff.

Relevant Error/Panic Output Snippet

No response

Terraform Configuration Files

data "aws_availability_zones" "available" {
  state = "available"
}

data "aws_iam_policy_document" "assume_role" {
  statement {
    effect = "Allow"

    principals {
      type        = "Service"
      identifiers = ["ec2.amazonaws.com"]
    }

    actions = ["sts:AssumeRole"]
  }
}

resource "aws_iam_role" "elastic_beanstalk_role" {
  name               = "options-testing-role"
  assume_role_policy = data.aws_iam_policy_document.assume_role.json
}

resource "aws_iam_role_policy_attachment" "attach_web_tier" {
  role       = aws_iam_role.elastic_beanstalk_role.name
  policy_arn = "arn:aws:iam::aws:policy/AWSElasticBeanstalkWebTier"
}

resource "aws_iam_instance_profile" "instance_profile" {
  name = "options-testing-instance-profile"
  role = aws_iam_role.elastic_beanstalk_role.name
}

resource "aws_vpc" "vpc" {
  cidr_block         = "10.0.0.0/24"
}

resource "aws_subnet" "publicsubnet01" {
  availability_zone = data.aws_availability_zones.available.names[0]
  cidr_block        = "10.0.0.0/25"
  vpc_id            = aws_vpc.vpc.id
}

resource "aws_subnet" "publicsubnet02" {
  availability_zone = data.aws_availability_zones.available.names[1]
  cidr_block        = "10.0.0.128/25"
  vpc_id            = aws_vpc.vpc.id
}

resource "aws_internet_gateway" "aws_internet_gateway" {
  vpc_id = aws_vpc.vpc.id
}

resource "aws_route_table" "public_aws_route_table" {
  vpc_id = aws_vpc.vpc.id
}

resource "aws_route_table_association" "publicsubnet01_route_table_association" {
  subnet_id      = aws_subnet.publicsubnet01.id
  route_table_id = aws_route_table.public_aws_route_table.id
}

resource "aws_route_table_association" "publicsubnet02_route_table_association" {
  subnet_id      = aws_subnet.publicsubnet02.id
  route_table_id = aws_route_table.public_aws_route_table.id
}

resource "aws_route" "public_internet_gateway" {
  route_table_id         = aws_route_table.public_aws_route_table.id
  destination_cidr_block = "0.0.0.0/0"
  gateway_id             = aws_internet_gateway.aws_internet_gateway.id
}

resource "aws_elastic_beanstalk_application" "application" {
  name = "options-testing"
}

resource "aws_elastic_beanstalk_environment" "environment" {
  name                = "options-testing-test"
  application         = aws_elastic_beanstalk_application.application.name
  solution_stack_name = "64bit Amazon Linux 2023 v4.1.2 running Docker"

  setting {
    namespace = "aws:ec2:vpc"
    name      = "VPCId"
    value     = aws_vpc.vpc.id
  }

  setting {
    namespace = "aws:ec2:vpc"
    name      = "Subnets"
    # I know there is a better way to do the below - just can't remember it at the moment
    value     = join(",", [ aws_subnet.publicsubnet01.id, aws_subnet.publicsubnet02.id])
  }

  setting {
    namespace = "aws:ec2:vpc"
    name      = "ELBSubnets"
    # I know there is a better way to do the below - just can't remember it at the moment
    value     = join(",", [ aws_subnet.publicsubnet01.id, aws_subnet.publicsubnet02.id])
  }

  setting {
    namespace = "aws:ec2:vpc"
    name      = "AssociatePublicIpAddress"
    value     = "true"
  }

  setting {
    namespace = "aws:autoscaling:launchconfiguration"
    name      = "IamInstanceProfile"
    value     = aws_iam_instance_profile.instance_profile.name
  }

  setting {
    namespace = "aws:elb:listener"
    name      = "ListenerProtocol"
    value     = "TCP"
  }

  setting {
    namespace = "aws:ec2:instances"
    name      = "InstanceTypes"
    value     = "t3.small"
  }

  setting {
    namespace = "aws:elasticbeanstalk:environment"
    name      = "EnvironmentType"
    value     = "LoadBalanced"
  }
}

Steps to Reproduce

Run terraform apply twice.

Debug Output

terraform-debug.txt

Panic Output

No response

Important Factoids

To workaround this issue you can utilize the following:

setting {
  namespace = "aws:elb:listener:80" # notice "aws:elb:listener:80" instead of "aws:elb:listener"
  name      = "ListenerProtocol"
  value     = "TCP"
}

References

No response

Would you like to implement a fix?

None

github-actions[bot] commented 8 months ago

Community Note

Voting for Prioritization

Volunteering to Work on This Issue