A tiny protective layer on top of terraform
In terraform it is incredibly easy to destroy things with terraform apply
. If you run apply
terraform shows a huge output and sometimes you may overlook a thing being "replaced" instead of updated. Once upon a time I destroyed a MongoDB Atlas Cluster this way and lost all its data, because the "must be replaced" was hidden in a lot of terraform output and I simply didn't see it. I only realized when terraform logged "Still destroying cluster..." to the console.
Some terraform resources, like Amazon ECS Services, are not idempotent, so they change on every apply. This cluttered my terminal with stuff I could ignore on every change as well as unnecessary updates to the infra (ECS Services being replaced despite no changes were made).
To prevent this, I forced myself to only use terraform with the -target
switch, and this tiny script helps me accomplish that.
In Bash and zsh, a function named terraform_save
is created which is then assigned with an alias to terraform
, so whenever terraform
is run it is executed "through" the bash function.
Install it by adding the function and alias to a shell config file like .bashrc
or .bash_profile
.
# ~/.bashrc
$ cat terraform.bash >> ~/.bashrc
# OR ~/.bash_profile
$ cat terraform.bash >> ~/.bash_profile
$ cat terraform.bash >> ~/.zshrc
Copy or link terraform.fish
into your fish config directory.
Copy
$ cp terraform.fish ~/.config/fish/functions/terraform.fish
Link
$ ln -s (pwd)/terraform.fish ~/.config/fish/functions/terraform.fish
The script creates an alias so you can use terraform just like you would. It's a drop-in tool.
- Install as described above
- Run
terraform apply
- The script will tell you to run
terraform apply
with-target
set - Run
terraform apply -target=module.my_thing
- 💶💶💶
-target
is a terraform option that allows you to only run terraform on a subset of resources. Consider the following example.
module "my-module" {
source = "git::git@github.com:someorg/somemodules?ref=1.0"
}
module "my-other-module" {
source = "git::git@github.com:someorg/somemodules?ref=1.0"
}
If you run terraform apply
both my-module
and my-other-module
are provisioned. Depending on what the modules do there may be a lot of output on the CLI and it'll be very hard to go through all the stuff. We can make our live easier by using -target
to deploy one after the other.
$ terraform apply -target=module.my-module
This will only provision the resources defined in my-module
.
You can find out more in the terraform docs in the sections about the apply command and resource naming and addressing.
Of course you'll sometimes want to run apply without a target, for example when bootstrapping a new project. In this case you can execute the script with the TERRAFORM_SAVE_DISABLE_I_KNOW_WHAT_I_DO
variable set to 1.
$ TERRAFORM_SAVE_DISABLE_I_KNOW_WHAT_I_DO=1 terraform apply
You can also export the variable for the current shell in fish or bash
/zsh
bash
and zsh
$ export TERRAFORM_SAVE_DISABLE_I_KNOW_WHAT_I_DO=1
$ terraform apply
And for fish
$ set -x TERRAFORM_SAVE_DISABLE_I_KNOW_WHAT_I_DO 1
$ terraform apply
We love and welcome every form of contribution, be it code, documentation, or management (issues, answering questions, etc.).
Here are some good places to start:
- Issues with label Good first issue
- Issues with label Documentation
- Translating documentation
You are expected to follow our code of conduct when interacting with the project via issues, pull requests or in any other form. Many thanks to the awesome contributor covenant initiative!
See LICENSE file.