Provision EC2 Instances for a MongoDB Cluster with Terraform

Amazon Web Services EC2 instances provide a ubiquitous platform to quickly spin up Linux servers for any purpose, including a MongoDB cluster. The HashiCorp Terraform provisioning tool makes it easy to automate build and teardown of servers in a consistent and repeatable way. This blog entry will work through simple Terraform code to build servers for a three-node MongoDB replica set.

We will build on the “labvpc” created by Build a Disposable AWS VPC with Terraform, although the code can be easily adapted to create the EC2 instances in any VPC, including the default. This gives the option to spread the three nodes across separate availability zones, so we will take advantage of that.

The main parameters for the EC2 instance in our use case are:

  • AMI – we will choose the latest Ubuntu LTS image (20.04)
  • Key name – using a public key previously uploaded. using the AWS GUI, as the “npxlab” key pair
  • Security group – this is the more involved part, setting up a custom security group to allow SSH and MongoDB on ports 22 and 27017
  • Subnet – from the VPC

The Terraform code is organized around each of the above items and kept simple by hard-coding all values, instead of defining variables.

Provider setup

First, we pull in the AWS provider, specifying a fixed version for stability over time. (Note that the AWS provider requires the AWS CLI to be installed with credentials configured for the user running Terraform.)

terraform {
  required_providers {
    aws = {
      source = "hashicorp/aws"
      version = "3.25"
    }
  }
}

provider "aws" {
  region = "us-east-1"
}

AMI Lookup

Use the data source to find the most recent matching image from Canonical matching the filters, by name and virtualization type.

# Latest Ubuntu 20.04 AMI
data "aws_ami" "ubuntu" {
  most_recent = true

  filter {
    name   = "name"
    values = ["ubuntu/images/hvm-ssd/ubuntu-focal-20.04-amd64-server-*"]
  }

  filter {
    name   = "virtualization-type"
    values = ["hvm"]
  }

  owners = ["099720109477"] # Canonical
}

Subnets Lookup

Use the data source to pull in VPC information from AWS, searching for “labvpc”, created in the earlier blog entry. (The second data source reads all subnets in the VPC, returning the subnet IDs in a “set” data type, which will need some special syntax to use later.)

# Find the VPC
data "aws_vpc" "labvpc" {
    tags = {
        Name = "labvpc"
    }
}

# Get the subnet IDs
data "aws_subnet_ids" "labvpc_subnets" {
  vpc_id = data.aws_vpc.labvpc.id
}

This can be modified to search for a different VPC by name, still using the remainder of the code, as long as the VPC has at least three subnets. Slightly different code can plug in the default VPC instead.

# Find the default VPC
data "aws_vpc" "labvpc" {
  default = "true"
}

Security Group Creation

We will create a separate security group for this MongoDB cluster. Even though ingress and egress rules can be defined inline on the security group, we define them separately as a best practice for maximum flexibility.

With this security group definition, the MongoDB port is exposed to the world. That will be great if we want to connect with MongoDB Compass to interact with our test cluster, but this would be a very bad idea for any real application data.

# Security Group
resource "aws_security_group" "mongo_sg" {
    name_prefix = "mongo_sg"
    description = "Allow ports for MongoDB cluster"
    vpc_id = data.aws_vpc.labvpc.id
}

resource "aws_security_group_rule" "mongo_sg_ingress_ssh" {
    type = "ingress"
    from_port = 22
    to_port = 22
    protocol = "tcp"
    cidr_blocks = ["0.0.0.0/0"]
    security_group_id = aws_security_group.mongo_sg.id 
    description = "Allow inbound SSH from anywhere"
}

resource "aws_security_group_rule" "mongo_sg_ingress_mongo" {
    type = "ingress"
    from_port = 27017
    to_port = 27017
    protocol = "tcp"
    cidr_blocks = ["0.0.0.0/0"]
    security_group_id = aws_security_group.mongo_sg.id 
    description = "Allow inbound MongoDB port from anywhere"
}

resource "aws_security_group_rule" "mongo_sg_egress_all" {
    type = "egress"
    from_port = 0
    to_port = 0
    protocol = "-1"
    cidr_blocks = ["0.0.0.0/0"]
    security_group_id = aws_security_group.mongo_sg.id 
    description = "Allow all output"
}

EC2 Instances Creation

With all of the above in place, we can finally proceed to create the EC2 instances. A count of three, each using the same settings, except iteration over the first three subnets in the VPC and the name tag. (It is not clear if sorting of the subnets is deterministic, but it will use three different subnets or throw an error if there are less than three.) We will return the public DNS names for the three instances for easy access to use in subsequent MongoDB configurations.

# EC2
resource "aws_instance" "mongo_cluster" {
  count = 3
  ami = data.aws_ami.ubuntu.id
  instance_type = "t2.micro"
  key_name = "npxlab"
  security_groups = [aws_security_group.mongo_sg.id]
  subnet_id = tolist(data.aws_subnet_ids.labvpc_subnets.ids)[count.index]
  tags = {
    Name = "mongo${count.index}"
  }
}

output "ec2_dns_names" {
    value = [aws_instance.mongo_cluster.*.public_dns]
}

With this setup, we can take as many passes as we like setting up MongoDB, starting over with a clean slate whenever we want. This enables trying different options and getting back into a known state any time. That assumes we will also automate the MongoDB setup with infrastructure-as-code. Of course we will!

Coda

Let’s close out with some output from Terraform commands, making use of all the code snippets above, pasted into file named “main.tf” in a clean directory.

First, we run “terraform init” to download and install the provider (among other setup.)

paul@ansible3:~/ec2_mongodb_demo$ ls -A
main.tf
paul@ansible3:~/ec2_mongodb_demo$ terraform init

Initializing the backend...

Initializing provider plugins...
- Finding hashicorp/aws versions matching "3.25.0"...
- Installing hashicorp/aws v3.25.0...
- Installed hashicorp/aws v3.25.0 (signed by HashiCorp)

Terraform has created a lock file .terraform.lock.hcl to record the provider
selections it made above. Include this file in your version control repository
so that Terraform can guarantee to make the same selections by default when
you run "terraform init" in the future.

Terraform has been successfully initialized!

You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.

If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.
paul@ansible3:~/ec2_mongodb_demo$ ls -A
main.tf  .terraform  .terraform.lock.hcl

Now we can run “terraform apply” to create the EC2 instances. (The usual step of “terraform plan” is skipped here for brevity of outputs.)

paul@ansible3:~/ec2_mongodb_demo$ terraform apply

An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
  + create

Terraform will perform the following actions:

  # aws_instance.mongo_cluster[0] will be created
  + resource "aws_instance" "mongo_cluster" {
      + ami                          = "ami-0074ee617a234808d"
      + arn                          = (known after apply)
      + associate_public_ip_address  = (known after apply)
      + availability_zone            = (known after apply)
      + cpu_core_count               = (known after apply)
      + cpu_threads_per_core         = (known after apply)
      + get_password_data            = false
      + host_id                      = (known after apply)
      + id                           = (known after apply)
      + instance_state               = (known after apply)
      + instance_type                = "t2.micro"
      + ipv6_address_count           = (known after apply)
      + ipv6_addresses               = (known after apply)
      + key_name                     = "npxlab"
      + outpost_arn                  = (known after apply)
      + password_data                = (known after apply)
      + placement_group              = (known after apply)
      + primary_network_interface_id = (known after apply)
      + private_dns                  = (known after apply)
      + private_ip                   = (known after apply)
      + public_dns                   = (known after apply)
      + public_ip                    = (known after apply)
      + secondary_private_ips        = (known after apply)
      + security_groups              = (known after apply)
      + source_dest_check            = true
      + subnet_id                    = "subnet-09ca96855c4c280c3"
      + tags                         = {
          + "Name" = "mongo0"
        }
      + tenancy                      = (known after apply)
      + vpc_security_group_ids       = (known after apply)

      + ebs_block_device {
          + delete_on_termination = (known after apply)
          + device_name           = (known after apply)
          + encrypted             = (known after apply)
          + iops                  = (known after apply)
          + kms_key_id            = (known after apply)
          + snapshot_id           = (known after apply)
          + tags                  = (known after apply)
          + throughput            = (known after apply)
          + volume_id             = (known after apply)
          + volume_size           = (known after apply)
          + volume_type           = (known after apply)
        }

      + enclave_options {
          + enabled = (known after apply)
        }

      + ephemeral_block_device {
          + device_name  = (known after apply)
          + no_device    = (known after apply)
          + virtual_name = (known after apply)
        }

      + metadata_options {
          + http_endpoint               = (known after apply)
          + http_put_response_hop_limit = (known after apply)
          + http_tokens                 = (known after apply)
        }

      + network_interface {
          + delete_on_termination = (known after apply)
          + device_index          = (known after apply)
          + network_interface_id  = (known after apply)
        }

      + root_block_device {
          + delete_on_termination = (known after apply)
          + device_name           = (known after apply)
          + encrypted             = (known after apply)
          + iops                  = (known after apply)
          + kms_key_id            = (known after apply)
          + tags                  = (known after apply)
          + throughput            = (known after apply)
          + volume_id             = (known after apply)
          + volume_size           = (known after apply)
          + volume_type           = (known after apply)
        }
    }

  # aws_instance.mongo_cluster[1] will be created
  + resource "aws_instance" "mongo_cluster" {
      + ami                          = "ami-0074ee617a234808d"
      + arn                          = (known after apply)
      + associate_public_ip_address  = (known after apply)
      + availability_zone            = (known after apply)
      + cpu_core_count               = (known after apply)
      + cpu_threads_per_core         = (known after apply)
      + get_password_data            = false
      + host_id                      = (known after apply)
      + id                           = (known after apply)
      + instance_state               = (known after apply)
      + instance_type                = "t2.micro"
      + ipv6_address_count           = (known after apply)
      + ipv6_addresses               = (known after apply)
      + key_name                     = "npxlab"
      + outpost_arn                  = (known after apply)
      + password_data                = (known after apply)
      + placement_group              = (known after apply)
      + primary_network_interface_id = (known after apply)
      + private_dns                  = (known after apply)
      + private_ip                   = (known after apply)
      + public_dns                   = (known after apply)
      + public_ip                    = (known after apply)
      + secondary_private_ips        = (known after apply)
      + security_groups              = (known after apply)
      + source_dest_check            = true
      + subnet_id                    = "subnet-0b3c475080900cb7b"
      + tags                         = {
          + "Name" = "mongo1"
        }
      + tenancy                      = (known after apply)
      + vpc_security_group_ids       = (known after apply)

      + ebs_block_device {
          + delete_on_termination = (known after apply)
          + device_name           = (known after apply)
          + encrypted             = (known after apply)
          + iops                  = (known after apply)
          + kms_key_id            = (known after apply)
          + snapshot_id           = (known after apply)
          + tags                  = (known after apply)
          + throughput            = (known after apply)
          + volume_id             = (known after apply)
          + volume_size           = (known after apply)
          + volume_type           = (known after apply)
        }

      + enclave_options {
          + enabled = (known after apply)
        }

      + ephemeral_block_device {
          + device_name  = (known after apply)
          + no_device    = (known after apply)
          + virtual_name = (known after apply)
        }

      + metadata_options {
          + http_endpoint               = (known after apply)
          + http_put_response_hop_limit = (known after apply)
          + http_tokens                 = (known after apply)
        }

      + network_interface {
          + delete_on_termination = (known after apply)
          + device_index          = (known after apply)
          + network_interface_id  = (known after apply)
        }

      + root_block_device {
          + delete_on_termination = (known after apply)
          + device_name           = (known after apply)
          + encrypted             = (known after apply)
          + iops                  = (known after apply)
          + kms_key_id            = (known after apply)
          + tags                  = (known after apply)
          + throughput            = (known after apply)
          + volume_id             = (known after apply)
          + volume_size           = (known after apply)
          + volume_type           = (known after apply)
        }
    }

  # aws_instance.mongo_cluster[2] will be created
  + resource "aws_instance" "mongo_cluster" {
      + ami                          = "ami-0074ee617a234808d"
      + arn                          = (known after apply)
      + associate_public_ip_address  = (known after apply)
      + availability_zone            = (known after apply)
      + cpu_core_count               = (known after apply)
      + cpu_threads_per_core         = (known after apply)
      + get_password_data            = false
      + host_id                      = (known after apply)
      + id                           = (known after apply)
      + instance_state               = (known after apply)
      + instance_type                = "t2.micro"
      + ipv6_address_count           = (known after apply)
      + ipv6_addresses               = (known after apply)
      + key_name                     = "npxlab"
      + outpost_arn                  = (known after apply)
      + password_data                = (known after apply)
      + placement_group              = (known after apply)
      + primary_network_interface_id = (known after apply)
      + private_dns                  = (known after apply)
      + private_ip                   = (known after apply)
      + public_dns                   = (known after apply)
      + public_ip                    = (known after apply)
      + secondary_private_ips        = (known after apply)
      + security_groups              = (known after apply)
      + source_dest_check            = true
      + subnet_id                    = "subnet-0d5afcf140b10051b"
      + tags                         = {
          + "Name" = "mongo2"
        }
      + tenancy                      = (known after apply)
      + vpc_security_group_ids       = (known after apply)

      + ebs_block_device {
          + delete_on_termination = (known after apply)
          + device_name           = (known after apply)
          + encrypted             = (known after apply)
          + iops                  = (known after apply)
          + kms_key_id            = (known after apply)
          + snapshot_id           = (known after apply)
          + tags                  = (known after apply)
          + throughput            = (known after apply)
          + volume_id             = (known after apply)
          + volume_size           = (known after apply)
          + volume_type           = (known after apply)
        }

      + enclave_options {
          + enabled = (known after apply)
        }

      + ephemeral_block_device {
          + device_name  = (known after apply)
          + no_device    = (known after apply)
          + virtual_name = (known after apply)
        }

      + metadata_options {
          + http_endpoint               = (known after apply)
          + http_put_response_hop_limit = (known after apply)
          + http_tokens                 = (known after apply)
        }

      + network_interface {
          + delete_on_termination = (known after apply)
          + device_index          = (known after apply)
          + network_interface_id  = (known after apply)
        }

      + root_block_device {
          + delete_on_termination = (known after apply)
          + device_name           = (known after apply)
          + encrypted             = (known after apply)
          + iops                  = (known after apply)
          + kms_key_id            = (known after apply)
          + tags                  = (known after apply)
          + throughput            = (known after apply)
          + volume_id             = (known after apply)
          + volume_size           = (known after apply)
          + volume_type           = (known after apply)
        }
    }

  # aws_security_group.mongo_sg will be created
  + resource "aws_security_group" "mongo_sg" {
      + arn                    = (known after apply)
      + description            = "Allow ports for MongoDB cluster"
      + egress                 = (known after apply)
      + id                     = (known after apply)
      + ingress                = (known after apply)
      + name                   = (known after apply)
      + name_prefix            = "mongo_sg"
      + owner_id               = (known after apply)
      + revoke_rules_on_delete = false
      + vpc_id                 = "vpc-0925e171615d10e1c"
    }

  # aws_security_group_rule.mongo_sg_egress_all will be created
  + resource "aws_security_group_rule" "mongo_sg_egress_all" {
      + cidr_blocks              = [
          + "0.0.0.0/0",
        ]
      + description              = "Allow all output"
      + from_port                = 0
      + id                       = (known after apply)
      + protocol                 = "-1"
      + security_group_id        = (known after apply)
      + self                     = false
      + source_security_group_id = (known after apply)
      + to_port                  = 0
      + type                     = "egress"
    }

  # aws_security_group_rule.mongo_sg_ingress_mongo will be created
  + resource "aws_security_group_rule" "mongo_sg_ingress_mongo" {
      + cidr_blocks              = [
          + "0.0.0.0/0",
        ]
      + description              = "Allow inbound MongoDB port from anywhere"
      + from_port                = 27017
      + id                       = (known after apply)
      + protocol                 = "tcp"
      + security_group_id        = (known after apply)
      + self                     = false
      + source_security_group_id = (known after apply)
      + to_port                  = 27017
      + type                     = "ingress"
    }

  # aws_security_group_rule.mongo_sg_ingress_ssh will be created
  + resource "aws_security_group_rule" "mongo_sg_ingress_ssh" {
      + cidr_blocks              = [
          + "0.0.0.0/0",
        ]
      + description              = "Allow inbound SSH from anywhere"
      + from_port                = 22
      + id                       = (known after apply)
      + protocol                 = "tcp"
      + security_group_id        = (known after apply)
      + self                     = false
      + source_security_group_id = (known after apply)
      + to_port                  = 22
      + type                     = "ingress"
    }

Plan: 7 to add, 0 to change, 0 to destroy.

Changes to Outputs:
  + ec2_dns_names = [
      + [
          + (known after apply),
          + (known after apply),
          + (known after apply),
        ],
    ]

Do you want to perform these actions?
  Terraform will perform the actions described above.
  Only 'yes' will be accepted to approve.

  Enter a value: yes

aws_security_group.mongo_sg: Creating...
aws_security_group.mongo_sg: Creation complete after 1s [id=sg-03d304cafd1e39817]
aws_instance.mongo_cluster[0]: Creating...
aws_security_group_rule.mongo_sg_ingress_ssh: Creating...
aws_security_group_rule.mongo_sg_egress_all: Creating...
aws_instance.mongo_cluster[2]: Creating...
aws_instance.mongo_cluster[1]: Creating...
aws_security_group_rule.mongo_sg_ingress_mongo: Creating...
aws_security_group_rule.mongo_sg_egress_all: Creation complete after 1s [id=sgrule-557593393]
aws_security_group_rule.mongo_sg_ingress_ssh: Creation complete after 1s [id=sgrule-314324160]
aws_security_group_rule.mongo_sg_ingress_mongo: Creation complete after 2s [id=sgrule-3098770330]
aws_instance.mongo_cluster[0]: Still creating... [10s elapsed]
aws_instance.mongo_cluster[2]: Still creating... [10s elapsed]
aws_instance.mongo_cluster[1]: Still creating... [10s elapsed]
aws_instance.mongo_cluster[0]: Still creating... [20s elapsed]
aws_instance.mongo_cluster[2]: Still creating... [20s elapsed]
aws_instance.mongo_cluster[1]: Still creating... [20s elapsed]
aws_instance.mongo_cluster[2]: Creation complete after 23s [id=i-09ee542deb3591c5a]
aws_instance.mongo_cluster[0]: Still creating... [30s elapsed]
aws_instance.mongo_cluster[1]: Still creating... [30s elapsed]
aws_instance.mongo_cluster[0]: Creation complete after 33s [id=i-0a3636fc455b07f0b]
aws_instance.mongo_cluster[1]: Creation complete after 33s [id=i-0dbe178e09c6c869e]

Apply complete! Resources: 7 added, 0 changed, 0 destroyed.

Outputs:

ec2_dns_names = [
  [
    "ec2-54-164-82-167.compute-1.amazonaws.com",
    "ec2-3-85-225-71.compute-1.amazonaws.com",
    "ec2-3-239-38-218.compute-1.amazonaws.com",
  ],
]

Finally, to clean up (and save our money) we can run “terraform destroy”. (Another common step, skipped here again, is to run “terraform show” to see what Terraform thinks it has out there.)

paul@ansible3:~/ec2_mongodb_demo$ terraform destroy

An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
  - destroy

Terraform will perform the following actions:

  # aws_instance.mongo_cluster[0] will be destroyed
  - resource "aws_instance" "mongo_cluster" {
      - ami                          = "ami-0074ee617a234808d" -> null
      - arn                          = "arn:aws:ec2:us-east-1:2xxxxxxxxxx4:instance/i-0a3636fc455b07f0b" -> null
      - associate_public_ip_address  = true -> null
      - availability_zone            = "us-east-1a" -> null
      - cpu_core_count               = 1 -> null
      - cpu_threads_per_core         = 1 -> null
      - disable_api_termination      = false -> null
      - ebs_optimized                = false -> null
      - get_password_data            = false -> null
      - hibernation                  = false -> null
      - id                           = "i-0a3636fc455b07f0b" -> null
      - instance_state               = "running" -> null
      - instance_type                = "t2.micro" -> null
      - ipv6_address_count           = 0 -> null
      - ipv6_addresses               = [] -> null
      - key_name                     = "npxlab" -> null
      - monitoring                   = false -> null
      - primary_network_interface_id = "eni-071622e458a4f43d0" -> null
      - private_dns                  = "ip-10-54-14-5.ec2.internal" -> null
      - private_ip                   = "10.54.14.5" -> null
      - public_dns                   = "ec2-54-164-82-167.compute-1.amazonaws.com" -> null
      - public_ip                    = "54.164.82.167" -> null
      - secondary_private_ips        = [] -> null
      - security_groups              = [
          - "sg-03d304cafd1e39817",
        ] -> null
      - source_dest_check            = true -> null
      - subnet_id                    = "subnet-09ca96855c4c280c3" -> null
      - tags                         = {
          - "Name" = "mongo0"
        } -> null
      - tenancy                      = "default" -> null
      - vpc_security_group_ids       = [
          - "sg-03d304cafd1e39817",
        ] -> null

      - credit_specification {
          - cpu_credits = "standard" -> null
        }

      - enclave_options {
          - enabled = false -> null
        }

      - metadata_options {
          - http_endpoint               = "enabled" -> null
          - http_put_response_hop_limit = 1 -> null
          - http_tokens                 = "optional" -> null
        }

      - root_block_device {
          - delete_on_termination = true -> null
          - device_name           = "/dev/sda1" -> null
          - encrypted             = false -> null
          - iops                  = 100 -> null
          - tags                  = {} -> null
          - throughput            = 0 -> null
          - volume_id             = "vol-056a97377e6635581" -> null
          - volume_size           = 8 -> null
          - volume_type           = "gp2" -> null
        }
    }

  # aws_instance.mongo_cluster[1] will be destroyed
  - resource "aws_instance" "mongo_cluster" {
      - ami                          = "ami-0074ee617a234808d" -> null
      - arn                          = "arn:aws:ec2:us-east-1:2xxxxxxxxxx4:instance/i-0dbe178e09c6c869e" -> null
      - associate_public_ip_address  = true -> null
      - availability_zone            = "us-east-1b" -> null
      - cpu_core_count               = 1 -> null
      - cpu_threads_per_core         = 1 -> null
      - disable_api_termination      = false -> null
      - ebs_optimized                = false -> null
      - get_password_data            = false -> null
      - hibernation                  = false -> null
      - id                           = "i-0dbe178e09c6c869e" -> null
      - instance_state               = "running" -> null
      - instance_type                = "t2.micro" -> null
      - ipv6_address_count           = 0 -> null
      - ipv6_addresses               = [] -> null
      - key_name                     = "npxlab" -> null
      - monitoring                   = false -> null
      - primary_network_interface_id = "eni-0d02a9d066c89fa3f" -> null
      - private_dns                  = "ip-10-54-16-231.ec2.internal" -> null
      - private_ip                   = "10.54.16.231" -> null
      - public_dns                   = "ec2-3-85-225-71.compute-1.amazonaws.com" -> null
      - public_ip                    = "3.85.225.71" -> null
      - secondary_private_ips        = [] -> null
      - security_groups              = [
          - "sg-03d304cafd1e39817",
        ] -> null
      - source_dest_check            = true -> null
      - subnet_id                    = "subnet-0b3c475080900cb7b" -> null
      - tags                         = {
          - "Name" = "mongo1"
        } -> null
      - tenancy                      = "default" -> null
      - vpc_security_group_ids       = [
          - "sg-03d304cafd1e39817",
        ] -> null

      - credit_specification {
          - cpu_credits = "standard" -> null
        }

      - enclave_options {
          - enabled = false -> null
        }

      - metadata_options {
          - http_endpoint               = "enabled" -> null
          - http_put_response_hop_limit = 1 -> null
          - http_tokens                 = "optional" -> null
        }

      - root_block_device {
          - delete_on_termination = true -> null
          - device_name           = "/dev/sda1" -> null
          - encrypted             = false -> null
          - iops                  = 100 -> null
          - tags                  = {} -> null
          - throughput            = 0 -> null
          - volume_id             = "vol-0ca5c38e10d8f0ffa" -> null
          - volume_size           = 8 -> null
          - volume_type           = "gp2" -> null
        }
    }

  # aws_instance.mongo_cluster[2] will be destroyed
  - resource "aws_instance" "mongo_cluster" {
      - ami                          = "ami-0074ee617a234808d" -> null
      - arn                          = "arn:aws:ec2:us-east-1:2xxxxxxxxxx4:instance/i-09ee542deb3591c5a" -> null
      - associate_public_ip_address  = true -> null
      - availability_zone            = "us-east-1c" -> null
      - cpu_core_count               = 1 -> null
      - cpu_threads_per_core         = 1 -> null
      - disable_api_termination      = false -> null
      - ebs_optimized                = false -> null
      - get_password_data            = false -> null
      - hibernation                  = false -> null
      - id                           = "i-09ee542deb3591c5a" -> null
      - instance_state               = "running" -> null
      - instance_type                = "t2.micro" -> null
      - ipv6_address_count           = 0 -> null
      - ipv6_addresses               = [] -> null
      - key_name                     = "npxlab" -> null
      - monitoring                   = false -> null
      - primary_network_interface_id = "eni-0a8604900df357cea" -> null
      - private_dns                  = "ip-10-54-24-34.ec2.internal" -> null
      - private_ip                   = "10.54.24.34" -> null
      - public_dns                   = "ec2-3-239-38-218.compute-1.amazonaws.com" -> null
      - public_ip                    = "3.239.38.218" -> null
      - secondary_private_ips        = [] -> null
      - security_groups              = [
          - "sg-03d304cafd1e39817",
        ] -> null
      - source_dest_check            = true -> null
      - subnet_id                    = "subnet-0d5afcf140b10051b" -> null
      - tags                         = {
          - "Name" = "mongo2"
        } -> null
      - tenancy                      = "default" -> null
      - vpc_security_group_ids       = [
          - "sg-03d304cafd1e39817",
        ] -> null

      - credit_specification {
          - cpu_credits = "standard" -> null
        }

      - enclave_options {
          - enabled = false -> null
        }

      - metadata_options {
          - http_endpoint               = "enabled" -> null
          - http_put_response_hop_limit = 1 -> null
          - http_tokens                 = "optional" -> null
        }

      - root_block_device {
          - delete_on_termination = true -> null
          - device_name           = "/dev/sda1" -> null
          - encrypted             = false -> null
          - iops                  = 100 -> null
          - tags                  = {} -> null
          - throughput            = 0 -> null
          - volume_id             = "vol-006e44c5a2278e9af" -> null
          - volume_size           = 8 -> null
          - volume_type           = "gp2" -> null
        }
    }

  # aws_security_group.mongo_sg will be destroyed
  - resource "aws_security_group" "mongo_sg" {
      - arn                    = "arn:aws:ec2:us-east-1:2xxxxxxxxxx4:security-group/sg-03d304cafd1e39817" -> null
      - description            = "Allow ports for MongoDB cluster" -> null
      - egress                 = [] -> null
      - id                     = "sg-03d304cafd1e39817" -> null
      - ingress                = [] -> null
      - name                   = "mongo_sg20210129015922750200000001" -> null
      - name_prefix            = "mongo_sg" -> null
      - owner_id               = "2xxxxxxxxxx4" -> null
      - revoke_rules_on_delete = false -> null
      - vpc_id                 = "vpc-0925e171615d10e1c" -> null
    }

  # aws_security_group_rule.mongo_sg_egress_all will be destroyed
  - resource "aws_security_group_rule" "mongo_sg_egress_all" {
      - cidr_blocks       = [
          - "0.0.0.0/0",
        ] -> null
      - description       = "Allow all output" -> null
      - from_port         = 0 -> null
      - id                = "sgrule-557593393" -> null
      - protocol          = "-1" -> null
      - security_group_id = "sg-03d304cafd1e39817" -> null
      - self              = false -> null
      - to_port           = 0 -> null
      - type              = "egress" -> null
    }

  # aws_security_group_rule.mongo_sg_ingress_mongo will be destroyed
  - resource "aws_security_group_rule" "mongo_sg_ingress_mongo" {
      - cidr_blocks       = [
          - "0.0.0.0/0",
        ] -> null
      - description       = "Allow inbound MongoDB port from anywhere" -> null
      - from_port         = 27017 -> null
      - id                = "sgrule-3098770330" -> null
      - protocol          = "tcp" -> null
      - security_group_id = "sg-03d304cafd1e39817" -> null
      - self              = false -> null
      - to_port           = 27017 -> null
      - type              = "ingress" -> null
    }

  # aws_security_group_rule.mongo_sg_ingress_ssh will be destroyed
  - resource "aws_security_group_rule" "mongo_sg_ingress_ssh" {
      - cidr_blocks       = [
          - "0.0.0.0/0",
        ] -> null
      - description       = "Allow inbound SSH from anywhere" -> null
      - from_port         = 22 -> null
      - id                = "sgrule-314324160" -> null
      - protocol          = "tcp" -> null
      - security_group_id = "sg-03d304cafd1e39817" -> null
      - self              = false -> null
      - to_port           = 22 -> null
      - type              = "ingress" -> null
    }

Plan: 0 to add, 0 to change, 7 to destroy.

Changes to Outputs:
  - ec2_dns_names = [
      - [
          - "ec2-54-164-82-167.compute-1.amazonaws.com",
          - "ec2-3-85-225-71.compute-1.amazonaws.com",
          - "ec2-3-239-38-218.compute-1.amazonaws.com",
        ],
    ] -> null

Do you really want to destroy all resources?
  Terraform will destroy all your managed infrastructure, as shown above.
  There is no undo. Only 'yes' will be accepted to confirm.

  Enter a value: yes

aws_instance.mongo_cluster[2]: Destroying... [id=i-09ee542deb3591c5a]
aws_instance.mongo_cluster[1]: Destroying... [id=i-0dbe178e09c6c869e]
aws_instance.mongo_cluster[0]: Destroying... [id=i-0a3636fc455b07f0b]
aws_security_group_rule.mongo_sg_ingress_ssh: Destroying... [id=sgrule-314324160]
aws_security_group_rule.mongo_sg_egress_all: Destroying... [id=sgrule-557593393]
aws_security_group_rule.mongo_sg_ingress_mongo: Destroying... [id=sgrule-3098770330]
aws_security_group_rule.mongo_sg_ingress_mongo: Destruction complete after 0s
aws_security_group_rule.mongo_sg_ingress_ssh: Destruction complete after 1s
aws_security_group_rule.mongo_sg_egress_all: Destruction complete after 1s
aws_instance.mongo_cluster[2]: Still destroying... [id=i-09ee542deb3591c5a, 10s elapsed]
aws_instance.mongo_cluster[0]: Still destroying... [id=i-0a3636fc455b07f0b, 10s elapsed]
aws_instance.mongo_cluster[1]: Still destroying... [id=i-0dbe178e09c6c869e, 10s elapsed]
aws_instance.mongo_cluster[2]: Still destroying... [id=i-09ee542deb3591c5a, 20s elapsed]
aws_instance.mongo_cluster[1]: Still destroying... [id=i-0dbe178e09c6c869e, 20s elapsed]
aws_instance.mongo_cluster[0]: Still destroying... [id=i-0a3636fc455b07f0b, 20s elapsed]
aws_instance.mongo_cluster[2]: Destruction complete after 30s
aws_instance.mongo_cluster[0]: Still destroying... [id=i-0a3636fc455b07f0b, 30s elapsed]
aws_instance.mongo_cluster[1]: Still destroying... [id=i-0dbe178e09c6c869e, 30s elapsed]
aws_instance.mongo_cluster[1]: Still destroying... [id=i-0dbe178e09c6c869e, 40s elapsed]
aws_instance.mongo_cluster[0]: Still destroying... [id=i-0a3636fc455b07f0b, 40s elapsed]
aws_instance.mongo_cluster[0]: Destruction complete after 40s
aws_instance.mongo_cluster[1]: Still destroying... [id=i-0dbe178e09c6c869e, 50s elapsed]
aws_instance.mongo_cluster[1]: Destruction complete after 50s
aws_security_group.mongo_sg: Destroying... [id=sg-03d304cafd1e39817]
aws_security_group.mongo_sg: Destruction complete after 1s

Destroy complete! Resources: 7 destroyed.

2 comments

Leave a comment

Your email address will not be published. Required fields are marked *