Day 21: Workspaces for Environment Management

I'm a cloud-native enthusiast and tech blogger, sharing insights on Kubernetes, AWS, CI/CD, and Linux across my blog and Facebook page. Passionate about modern infrastructure and microservices, I aim to help others understand and leverage cloud-native technologies for scalable, efficient solutions.
Welcome to Week 4! This week focuses on advanced Terraform techniques. Today we’ll master workspaces - a powerful feature for managing multiple environments with the same configuration.
🎯 Today’s Goals
Understand Terraform workspaces
Create and manage workspaces
Use workspaces for environment isolation
Learn workspace best practices and limitations
🌍 What Are Workspaces?
Workspaces allow you to manage multiple instances of a single configuration. Each workspace has its own state file.
Same Configuration → Multiple Workspaces → Separate States
my-infrastructure/
├── main.tf (shared)
├── terraform.tfstate.d/
│ ├── dev/terraform.tfstate
│ ├── staging/terraform.tfstate
│ └── prod/terraform.tfstate
📚 Workspace Commands
# List workspaces
terraform workspace list
# Show current workspace
terraform workspace show
# Create new workspace
terraform workspace new dev
# Switch workspace
terraform workspace select dev
# Delete workspace (must be empty)
terraform workspace delete dev
🔧 Using Workspaces
Basic Usage
# main.tf
resource "aws_instance" "app" {
ami = "ami-12345"
instance_type = terraform.workspace == "prod" ? "t3.large" : "t2.micro"
tags = {
Name = "app-${terraform.workspace}"
Environment = terraform.workspace
}
}
Workspace-Specific Values
locals {
env_config = {
dev = {
instance_type = "t2.micro"
instance_count = 1
}
staging = {
instance_type = "t2.small"
instance_count = 2
}
prod = {
instance_type = "t3.large"
instance_count = 3
}
}
config = local.env_config[terraform.workspace]
}
resource "aws_instance" "app" {
count = local.config.instance_count
ami = data.aws_ami.amazon_linux.id
instance_type = local.config.instance_type
tags = {
Name = "${terraform.workspace}-app-${count.index}"
}
}
🧪 Hands-On Lab
Step 1: Create Project
mkdir terraform-workspaces-lab
cd terraform-workspaces-lab
main.tf:
terraform {
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0"
}
}
}
provider "aws" {
region = "us-east-1"
}
locals {
environments = {
dev = {
instance_type = "t2.micro"
instance_count = 1
cidr = "10.0.0.0/16"
}
staging = {
instance_type = "t2.small"
instance_count = 2
cidr = "10.1.0.0/16"
}
prod = {
instance_type = "t3.medium"
instance_count = 3
cidr = "10.2.0.0/16"
}
}
env = local.environments[terraform.workspace]
}
resource "aws_vpc" "main" {
cidr_block = local.env.cidr
tags = {
Name = "${terraform.workspace}-vpc"
Environment = terraform.workspace
}
}
resource "aws_subnet" "public" {
vpc_id = aws_vpc.main.id
cidr_block = cidrsubnet(local.env.cidr, 8, 1)
tags = {
Name = "${terraform.workspace}-subnet"
}
}
data "aws_ami" "amazon_linux" {
most_recent = true
owners = ["amazon"]
filter {
name = "name"
values = ["amzn2-ami-hvm-*-x86_64-gp2"]
}
}
resource "aws_instance" "app" {
count = local.env.instance_count
ami = data.aws_ami.amazon_linux.id
instance_type = local.env.instance_type
subnet_id = aws_subnet.public.id
tags = {
Name = "${terraform.workspace}-app-${count.index + 1}"
Environment = terraform.workspace
}
}
output "workspace" {
value = terraform.workspace
}
output "vpc_id" {
value = aws_vpc.main.id
}
output "instance_ids" {
value = aws_instance.app[*].id
}
Step 2: Use Workspaces
# Initialize
terraform init
# Create dev workspace
terraform workspace new dev
terraform plan
terraform apply -auto-approve
# Create staging workspace
terraform workspace new staging
terraform plan
terraform apply -auto-approve
# Switch to dev
terraform workspace select dev
terraform output
# List all workspaces
terraform workspace list
# View state files
ls -la terraform.tfstate.d/
# Clean up
terraform workspace select dev
terraform destroy -auto-approve
terraform workspace select staging
terraform destroy -auto-approve
terraform workspace select default
terraform workspace delete dev
terraform workspace delete staging
⚖️ Workspaces vs Directories
Workspaces
✅ Same code for all environments ✅ Easy to switch between environments ✅ Less code duplication ❌ All environments must be similar. ❌ Easy to accidentally apply to wrong environment
Separate Directories
✅ Complete isolation ✅ Different configurations per environment ✅ Safer (harder to make mistakes) ❌ More code duplication ❌ Harder to keep in sync
Recommendation
Use directories for production environments:
terraform/
├── dev/
├── staging/
└── prod/
Use workspaces for:
Feature branches
Temporary environments
Testing
Development
📝 Summary
Today you learned:
✅ Terraform workspaces
✅ Workspace commands
✅ Environment-specific configurations
✅ Workspaces vs directories


