11 useful terraform commands

11 useful terraform commands
  • Init project: terraform init. This command will setup modules, download provider modules, and create the .terraform.lock.hcl lock file.

If there is an error with this command, you can delete .terraform directory and .terraform.lock.hcl and re-run terraform init.

  • Show update plan: terraform plan.
    User -target=<resource> to specify a resource.
  • Confirm and apply update: terraform apply.
    User -target=<resource> to specify a resource.

When running in non interactive environment, use terraform apply -input=false -auto-approve.

  • Pull remote state: terraform state pull.
  • Push (overwrite) remote state: terraform push <file path>.
  • Display specific resource state: terraform state show <resource name>.
  • Remove resource: terraform state rm <resource name>.
  • Import resource: terraform import <resource name> <args>. <args> depends on the resource definition.
  • Rename resource: terraform mv <old name> <new name>.
  • Move resource between 2 projects with remote backend:
#!/usr/bin/env bash
set -xEeuo pipefail

src=/home/transang/terraform/project1
dst=/home/transang/terraform/sub/dir/project2/
resources=(
	aws_s3_bucket.bucket1
	aws_iam_role.role2
	aws_iam_user.user1
	aws_s3_bucket.bucket2
	aws_iam_policy.policy2
)

main() {
	cd $src
	terraform state pull >/tmp/source.tfstate
	cd $dst
	terraform state pull >/tmp/target.tfstate
	for resource in "${resources[@]}"; do
		terraform state mv -state=/tmp/source.tfstate -state-out=/tmp/target.tfstate "${resource}" "${resource}"
	done
	terraform state push /tmp/target.tfstate
	cd $src
	terraform state push /tmp/source.tfstate
}

(main)

Note: there are several resources that are not supported by terraforming, such as: certificate, cloudfront, cloudwatch, ... You need to inspect them manually with import then show.

Note: if your resource exists in multiple regions, do not forget to switch the region and re-run the script.

AWS_ACCESS_KEY_ID=<put your key>
AWS_SECRET_ACCESS_KEY=<put your key>
AWS_REGION=<put your region>
sources=(
	alb             # ALB
	asg             # AutoScaling Group
	cwa             # CloudWatch Alarm
	dbpg            # Database Parameter Group
	dbsg            # Database Security Group
	dbsn            # Database Subnet Group
	ddb             # DynamoDB
	ec2             # EC2
	ecc             # ElastiCache Cluster
	ecsn            # ElastiCache Subnet Group
	efs             # EFS File System
	eip             # EIP
	elb             # ELB
	help            # Describe available commands or one specific command
	iamg            # IAM Group
	iamgm           # IAM Group Membership
	iamgp           # IAM Group Policy
	iamip           # IAM Instance Profile
	iamp            # IAM Policy
	iampa           # IAM Policy Attachment
	iamr            # IAM Role
	iamrp           # IAM Role Policy
	iamu            # IAM User
	iamup           # IAM User Policy
	igw             # Internet Gateway
	kmsa            # KMS Key Alias
	kmsk            # KMS Key
	lc              # Launch Configuration
	nacl            # Network ACL
	nat             # NAT Gateway
	nif             # Network Interface
	r53r            # Route53 Record
	r53z            # Route53 Hosted Zone
	rds             # RDS
	rs              # Redshift
	rt              # Route Table
	rta             # Route Table Association
	s3              # S3
	sg              # Security Group
	sn              # Subnet
	snst            # SNS Topic
	snss            # SNS Subscription
	sqs             # SQS
	vgw             # VPN Gateway
	vpc             # VPC
)

mkdir -p imports
for source in "${sources[@]}"; do
	docker run \
		--rm \
		--name terraforming \
		-e AWS_ACCESS_KEY_ID=${AWS_ACCESS_KEY_ID} \
		-e AWS_SECRET_ACCESS_KEY=${AWS_SECRET_ACCESS_KEY} \
		-e AWS_REGION=xx-yyyy-0 \
		quay.io/dtan4/terraforming:latest \
		terraforming $source \
		> imports/$source.tf
	docker run \
		--rm \
		--name terraforming \
		-e AWS_ACCESS_KEY_ID=${AWS_ACCESS_KEY_ID} \
		-e AWS_SECRET_ACCESS_KEY=${AWS_SECRET_ACCESS_KEY} \
		-e AWS_REGION=xx-yyyy-0 \
		quay.io/dtan4/terraforming:latest \
		terraforming $source --tfstate \
		> imports/$source.tfstate
done