Skip to content

Latest commit

 

History

11 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Multi-Environment Terraform Infrastructure as Code (IaC)

Production-inspired multi-environment AWS infrastructure using reusable Terraform modules, isolated remote state, tag-based IAM, and an approval-gated GitHub Actions deployment pipeline.


Project Overview

This project demonstrates how infrastructure can be promoted through Development → Staging → Production using Infrastructure as Code (IaC) while following governance practices commonly used in regulated environments.

Instead of maintaining three separate Terraform codebases, a single reusable module provisions each environment with different configurations, isolated state files, dedicated IAM permissions, and manual approval gates before higher-environment deployments.


Problem Statement

Organizations operating in regulated industries (Banking, FinTech, Healthcare, Government) cannot deploy infrastructure directly into production.

Infrastructure changes should:

  • follow a controlled promotion path
  • isolate each environment
  • enforce least-privilege permissions
  • require human approval before production deployment
  • maintain independent Terraform state

This project demonstrates that workflow using Terraform and GitHub Actions.


Architecture

                    Reusable Terraform Module
                           modules/network
                                   │
        ┌──────────────────────────┼──────────────────────────┐
        ▼                          ▼                          ▼

   Development                 Staging                  Production
  10.10.0.0/16              10.20.0.0/16              10.30.0.0/16
      2 AZs                     2 AZs                     3 AZs

        │                          │                          │

 terraform-dev-role     terraform-staging-role    terraform-prod-role

        │                          │                          │

     dev.tfstate             staging.tfstate            prod.tfstate

        │
        ▼

GitHub Actions Pipeline

deploy-dev
      │
      ▼
Manual Approval
      │
      ▼
deploy-staging
      │
      ▼
Manual Approval
      │
      ▼
deploy-prod

Repository Structure

terraform-multi-env-iac/
│
├── modules/
│   └── network/
│       ├── main.tf
│       ├── variables.tf
│       └── outputs.tf
│
├── environments/
│   ├── dev/
│   ├── staging/
│   └── prod/
│
├── iam/
│   ├── trust-policy.json
│   ├── dev-policy.json
│   ├── staging-policy.json
│   └── prod-policy.json
│
└── .github/
    └── workflows/
        └── deploy.yml

AWS Services & Technologies

Service Purpose
Terraform Infrastructure as Code
Terraform Modules Reusable infrastructure components
Amazon VPC Network isolation
Public & Private Subnets Environment networking
Internet Gateway Public connectivity
Route Tables Network routing
Amazon S3 Remote Terraform state
IAM Least-privilege access
GitHub Actions CI/CD pipeline
GitHub Environments Manual deployment approvals

Key Features

  • Reusable Terraform module
  • Three isolated environments
  • Independent Terraform state for every environment
  • Tag-based IAM permissions
  • Environment-specific IAM roles
  • GitHub Actions deployment pipeline
  • Manual approval gates for Staging and Production
  • Environment promotion:
    • Dev
    • Staging
    • Production
  • Non-overlapping CIDR design
  • Dynamic subnet creation using count and cidrsubnet()

Deployment Workflow

Developer Push

        │

        ▼

GitHub Actions

        │

        ▼

Deploy Development
        │
        ▼

Manual Approval

        │

        ▼

Deploy Staging
        │
        ▼

Manual Approval

        │

        ▼

Deploy Production

Prerequisites

  • Terraform
  • AWS CLI
  • Configured AWS credentials
  • Amazon S3 backend
  • GitHub repository secrets

Deploy

Development

cd environments/dev
terraform init
terraform apply

Staging

cd environments/staging
terraform init
terraform apply

Production

cd environments/prod
terraform init
terraform apply

CI/CD Deployment

Any push affecting

modules/**
environments/**

automatically triggers the GitHub Actions pipeline.

Deployment flow:

Development
      ↓
Manual Approval
      ↓
Staging
      ↓
Manual Approval
      ↓
Production

Design Decisions

Single reusable module

Only one Terraform module is maintained.

Benefits:

  • eliminates duplicated infrastructure code
  • reduces configuration drift
  • simplifies maintenance

Required module inputs

The module requires:

  • environment
  • vpc_cidr
  • azs

No defaults are used to avoid accidental environment overlap.


Dynamic subnet generation

Subnets are generated using:

  • count
  • cidrsubnet()

The same module supports:

  • Dev (2 AZs)
  • Staging (2 AZs)
  • Production (3 AZs)

without modification.


Remote state isolation

A shared S3 bucket stores Terraform state.

Each environment uses an independent state key.

This prevents one environment from affecting another.


Tag-based IAM

IAM permissions are controlled using the resource tag:

Environment

instead of resource name matching.

This provides cleaner least-privilege access and scales better as infrastructure grows.


Manual approval gates

GitHub Environments enforce approvals before:

  • Staging
  • Production

Development deploys automatically.


Ordered environment promotion

GitHub Actions uses job dependencies (needs) so environments are promoted in order:

Development

↓

Staging

↓

Production

Higher environments cannot deploy unless lower environments succeed.


Validation

The project was successfully validated for:

  • Development deployment
  • Staging deployment
  • GitHub Environment approval gates
  • Environment isolation
  • Remote state isolation
  • Independent IAM roles

During validation, the Production deployment approval gate functioned correctly. A subsequent deployment attempt encountered a temporary GitHub Actions service availability issue while downloading hosted runner actions. This was unrelated to the Terraform configuration or project implementation.


Cost Management

This project was designed with cost awareness.

Resources were:

  • deployed
  • verified
  • destroyed

after testing.

The primary ongoing AWS cost was minimal Amazon S3 storage used for Terraform remote state.


Teardown

Destroy each environment independently.

cd environments/dev
terraform destroy
cd environments/staging
terraform destroy
cd environments/prod
terraform destroy

Verify cleanup:

aws ec2 describe-vpcs \
--region ap-south-2 \
--query 'Vpcs[?Tags[?Key==`Environment`]]'

Expected result:

[]

Lessons Learned

  • Build reusable modules instead of duplicating Terraform code.
  • Separate Terraform state for every environment.
  • Use resource tags to implement scalable least-privilege IAM.
  • GitHub Environment approvals provide an effective deployment governance mechanism.
  • Infrastructure promotion should be enforced by the pipeline rather than relying on manual process.
  • Small CI/CD details (such as workflow path filters) can prevent pipelines from triggering correctly and are important to validate early.

Skills Demonstrated

  • Terraform
  • Infrastructure as Code
  • Terraform Modules
  • AWS Networking
  • Amazon VPC
  • IAM
  • Amazon S3 Backend
  • GitHub Actions
  • CI/CD
  • GitHub Environments
  • Deployment Governance
  • Multi-Environment Infrastructure
  • Infrastructure Automation
  • Cloud Architecture

Author

Musaab Mohamedani

Cloud & DevOps Engineer

About

Production-inspired multi-environment AWS infrastructure using reusable Terraform modules, isolated remote state, tag-based IAM, and approval-gated GitHub Actions.

Topics

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages