Created
September 12, 2018 15:29
-
-
Save mmarseglia/97e643b9f39d62621285e960ee7da6db to your computer and use it in GitHub Desktop.
Terraform Makefile
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
APP_NAME = ${TF_VAR_app_name} | |
REGION = ${TF_VAR_region} | |
KEY = 'terraform.state' | |
PROFILE = ${TF_VAR_profile} | |
AWS_ACCOUNT = ${TF_VAR_aws_account} | |
BUCKET = "${APP_NAME}-${AWS_ACCOUNT}" | |
ROOT_DIR:=$(shell dirname $(realpath $(lastword $(MAKEFILE_LIST)))) | |
.PHONY: help | |
help: ## This help message. | |
@grep -E '^[a-zA-Z_-]+:.*?## .*$$' $(MAKEFILE_LIST) | sort | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m%-30s\033[0m %s\n", $$1, $$2}' | |
.PHONY: clean | |
clean: ## Clean up local after a terraform init, plan or run. | |
rm -rf terraform/.terraform terraform/*.tfstate output.json inspec.json bucket | |
.PHONY: all | |
all: plan apply test output | |
.PHONY: backend | |
backend: bucket ## Initialize terraform backend | |
@cd terraform; \ | |
terraform init \ | |
--backend-config="bucket=$(BUCKET)" \ | |
--backend-config="region=$(REGION)" \ | |
--backend-config="key=$(KEY)" \ | |
--backend-config="profile=$(PROFILE)" | |
bucket: ## Attempts to create or verify the S3 bucket is available as a backend | |
@aws --profile $(PROFILE) s3 ls $(BUCKET) && echo $(BUCKET) > bucket || aws --profile $(PROFILE) s3 mb s3://$(BUCKET); \ | |
if [ $$? -ne 0 ]; then \ | |
echo "Bucket $(BUCKET) exists and we don't own it or your credentials are incorrect."; \ | |
exit 1; \ | |
fi; | |
.PHONY: validate | |
validate: terraform/*.tf ## Runs `terraform validate` against all the .tf files | |
@cd terraform; \ | |
for i in $$(find . -type f -name "*.tf" -prune -o -name '.terraform' -exec dirname {} \;); do \ | |
terraform validate "$$i"; \ | |
if [ $$? -ne 0 ]; then \ | |
echo "Failed Terraform file validation on file $${i}"; \ | |
echo; \ | |
exit 1; \ | |
fi; \ | |
done | |
.PHONY: update | |
update: | |
@cd terraform; \ | |
terraform get -update=true 1>/dev/null | |
plan: backend update validate ## Display all the changes that Terraform is going to make. | |
@cd terraform && \ | |
terraform plan \ | |
-input=false | |
plan-target: backend update validate ## Shows what a plan looks like for applying a specific resource | |
@tput setaf 3; tput bold; echo -n "[INFO] "; tput sgr0; echo "Example to type for the following question: module.rds.aws_route53_record.rds-master" | |
@read -p "PLAN target: " DATA &&\ | |
terraform plan \ | |
-input=true \ | |
-target=$$DATA | |
plan-destroy: backend update validate ## Creates a destruction plan. | |
@terraform plan \ | |
-input=false \ | |
-destroy | |
show: backend ## Show terraform resources. | |
@cd terraform; \ | |
terraform show -module-depth=-1 | |
graph: ## Output the `dot` graph of all the built Terraform resources | |
@rm -f graph.png | |
@terraform graph -draw-cycles -module-depth=-1 | dot -Tpng > graph.png | |
@shotwell graph.png | |
apply: ## Apply builds/changes resources. You should ALWAYS run a plan first. | |
@cd terraform && \ | |
terraform apply \ | |
-input=true \ | |
-refresh=true \ | |
-auto-approve | |
apply-target: backend update ## Apply a specific resource and any chained resources. | |
@tput setaf 3; tput bold; echo -n "[INFO] "; tput sgr0; echo "Specifically APPLY a piece of Terraform data." | |
@tput setaf 3; tput bold; echo -n "[INFO] "; tput sgr0; echo "Example to type for the following question: module.rds.aws_route53_record.rds-master" | |
@tput setaf 1; tput bold; echo -n "[DANGER] "; tput sgr0; echo "You are about to apply a new state." | |
@tput setaf 1; tput bold; echo -n "[DANGER] "; tput sgr0; echo "This has the potential to break your infrastructure." | |
@read -p "APPLY target: " DATA &&\ | |
terraform apply \ | |
-input=true \ | |
-refresh=true \ | |
-target=$$DATA | |
.PHONY: output | |
output: output.json ## Generate all output files. | |
output.json: terraform/outputs.tf apply ## Display all outputs from the remote state file and save as JSON. | |
@cd terraform && \ | |
if [ -n $(MODULE) ]; then\ | |
terraform output -json > ../output.json;\ | |
else\ | |
terraform output -module=$(MODULE);\ | |
fi | |
taint: backend update ## Taint a resource for destruction upon next `apply` | |
@echo "Tainting involves specifying a module and a resource" | |
@read -p "Module: " MODULE && \ | |
read -p "Resource: " RESOURCE && \ | |
terraform taint \ | |
-module=$$MODULE $$RESOURCE | |
@echo "You will now want to run a plan to see what changes will take place" | |
destroy: backend update ## Destroys everything. There is a prompt before destruction. | |
@cd terraform && \ | |
terraform destroy | |
destroy-target: backend update ## Destroy a specific resource. Caution though, this destroys chained resources. | |
@echo "Specifically destroy a piece of Terraform data." | |
@echo | |
@echo "Example to type for the following question: module.rds.aws_route53_record.rds-master" | |
@echo | |
@read -p "Destroy target: " DATA &&\ | |
terraform destroy \ | |
-target=$$DATA | |
.PHONY: test | |
test: inspec.json ## Run all tests. | |
inspec.json: output ## Run inspec tests and output results as JSON. | |
@inspec exec test \ | |
-t aws://us-east-1/$(APP_NAME) \ | |
--reporter json \ | |
json:/$(ROOT_DIR)/inspec.json% |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment