1. Package and Imports
-
package test
: Defines this file as a test package. -
Imports standard Go packages like
fmt
,strings
, andtesting
. -
Imports Terratest modules:
-
aws
: AWS helper functions (to inspect AWS resources like S3 buckets, EC2, etc.). -
http-helper
: For making HTTP requests and validating HTTP responses. -
terraform
: For running Terraform commands (init, apply, destroy).
-
-
Imports
assert
fromstretchr/testify
for easy test assertions.
2. Test Function Declaration
-
TestTerraformS3EC2ALB
is the test entry point (recognized by Go testing). -
t *testing.T
: Provides the testing framework's handle. -
t.Parallel()
allows tests to run concurrently with others for faster testing.
3. Terraform Options Setup
-
This configures how Terratest will run Terraform.
-
TerraformDir
: The folder containing your Terraform code (yourdev
environment). -
Vars
: Passes variables to Terraform (e.g., VPC name and Security Group ID). -
You must replace
"sg-xxxxxx"
with your actual security group.
4. Clean Up with defer terraform.Destroy
-
Ensures that after the test finishes (pass/fail), Terraform destroys all resources created.
-
This avoids resource leaks and unwanted costs.
5. Run terraform init
and apply
-
Initializes the Terraform working directory.
-
Applies the Terraform configuration (creates resources).
-
If this fails, the test fails here.
6. S3 Bucket Tests
-
Retrieves the S3 bucket name and AWS region from Terraform outputs.
-
Uses Terratest AWS helpers to:
-
Check if versioning is enabled (validates your dynamic block worked).
-
Retrieve the tags on the bucket, then asserts they match expected values (
team
,owner
,Environment
).
-
-
If any assertion fails, the test fails with a descriptive message.
7. EC2 Instance Tests
-
Retrieves all EC2 instance IDs from Terraform outputs.
-
Checks that at least one EC2 instance was created.
-
For each instance:
-
Verifies the instance type is
t3.micro
. -
Checks the
Name
tag contains"dev-ec2"
.
-
-
Checks EBS volumes attached dynamically:
-
Ensures at least one volume is attached (your dynamic EBS block test).
-
Validates volume size (20 GiB) and type (
gp2
).
-
-
These assertions confirm both static and dynamic block configurations in Terraform worked.
8. Application Load Balancer (ALB) Tests
-
Gets ALB DNS name and confirms it includes the AWS ELB domain.
-
Checks at least one target group was created dynamically.
-
Constructs an HTTP URL from the ALB DNS name.
-
Sends an HTTP GET request to the ALB.
-
Asserts the HTTP response code is
200 OK
. -
Asserts the response body contains
"Service running"
— matching your fixed-response listener in Terraform. -
Validates ALB works and serves traffic as expected.
Summary
This test automates end-to-end verification of your Terraform project:
-
Runs Terraform to create infrastructure.
-
Validates that all dynamic features (versioning, EBS volumes, target groups) are correctly provisioned.
-
Confirms tags and configurations.
-
Validates live infrastructure via AWS SDK calls and HTTP requests.
-
Cleans up resources after testing.
In short:
-
Terratest triggers Terraform to create resources.
-
It validates those Terraform-created resources using AWS SDK calls, HTTP requests, etc.
-
Finally, it destroys the resources with
terraform destroy
(if you usedefer terraform.Destroy()
), cleaning up after testing.
Terratest run ->
terraform init & apply (creates resources) ->
AWS SDK & HTTP API calls to validate resources ->
terraform destroy (cleans up resources)
Q1: Will Terratest create and delete resources every time?
-
Terratest calls Terraform apply and destroy by default in tests.
-
If your Terratest uses
defer terraform.Destroy()
, it will destroy all resources defined in that Terraform code at the end of the test. -
So if you run Terratest against your real infrastructure, it WILL delete those resources when the test finishes — this is risky in production or shared environments.
Q2: How to test updates (like tags or new properties) without deleting your existing resources?
Here are two approaches:
Approach 1: Use a separate test environment (recommended)
-
Create a dedicated test AWS account or separate environment.
-
Your Terratest runs Terraform on this clean, isolated environment.
-
After test finishes, Terratest destroys all created resources — no risk to production or existing infra.
-
This is how Terratest is meant to be used — test infrastructure code in disposable environments.
Approach 2: Run Terratest without destroy & manually test updates
-
You can skip
terraform.Destroy()
in Terratest so it does not delete resources after test. -
Run
terraform apply
via Terratest — it updates existing resources according to your new code (e.g., adds tags, new S3 settings). -
Then Terratest runs tests/assertions to verify updates are applied.
-
But this means resources persist, so you should be careful not to run these tests in production accidentally.
Summary of your exact case:
Step | Behavior | What to do |
---|---|---|
Initial Terraform run | Creates 2 EC2 + 1 S3 | Run Terraform normally |
Update code | Add tag to EC2, new S3 property | Run terraform apply to update resources |
Test with Terratest | terraform apply runs, updates resources; terraform destroy deletes them if called | Remove destroy call or run tests in test environment |
No comments:
Post a Comment