terraform: check terraform configuration

4 min read | by Jordi Prats

While working with terraform we might find some configuration or syntax errors using terraform plan. While we won't break anything anyway, it take a lot of time to realize we have a syntax error due to a typo. This is specially true if we are working with a remote terraform state. To avoid wasting time we can use terraform validate

By using terraform validate, terraform us going to validate the configuration files in the directory, referring only to the configuration and not accessing any remote services such as remote state, provider APIs, etc. It is just checking whether a configuration is syntactically valid and internally consistent, regardless of any provided variables or existing state.

We can even run this command automatically, it won't make any change neither on the resources or the state. Although to be able to run we need to have an initialized working directory with all the referenced plugins and modules installed. We can do it as usual using terraform init

$ terraform init
Initializing modules...

Initializing the backend...

Initializing provider plugins...
- terraform.io/builtin/terraform is built in to Terraform
- Reusing previous version of hashicorp/aws from the dependency lock file
- Reusing previous version of hashicorp/time from the dependency lock file
- Reusing previous version of hashicorp/helm from the dependency lock file
- Reusing previous version of hashicorp/kubernetes from the dependency lock file
- Using previously-installed hashicorp/aws v3.23.0
- Using previously-installed hashicorp/time v0.7.0
- Using previously-installed hashicorp/helm v1.3.2
- Using previously-installed hashicorp/kubernetes v1.13.3

Terraform has been successfully initialized!

You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.

If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.

But by adding -backend=false we can skip the backend initialization:

$  terraform init -backend=false
Initializing modules...

Initializing provider plugins...
- terraform.io/builtin/terraform is built in to Terraform
- Reusing previous version of hashicorp/time from the dependency lock file
- Reusing previous version of hashicorp/helm from the dependency lock file
- Reusing previous version of hashicorp/kubernetes from the dependency lock file
- Reusing previous version of hashicorp/aws from the dependency lock file
- Using previously-installed hashicorp/kubernetes v1.13.3
- Using previously-installed hashicorp/aws v3.23.0
- Using previously-installed hashicorp/time v0.7.0
- Using previously-installed hashicorp/helm v1.3.2

Terraform has been successfully initialized!

You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.

If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.

Once we have the working directory initialized we can use it to detect any syntax error or inconsistent usage of variables, for example:

$ terraform validate
╷
│ Error: Reference to undeclared resource
│    on .terraform/modules/ampa/main.tf line 102, in resource "helm_release" "ampa":
│  102:       INSTANCE_ROLE_ARN        = data.aws_iam_role.ampa_role.arn
│  A data resource "aws_iam_role" "ampa_role" has not been declared in module.ampa.
╵

If there's no error it will return a success:

$ terraform validate
Success! The configuration is valid.

The code can still be inconsistent with the terraform state, hence terraform validate is not going to pick up some of the problems and you might still face some issues while creating the terraform plan:

$ terraform plan
Acquiring state lock. This may take a few moments...
(...)
╷
│ Error: error reading IAM Role (ampa_role): NoSuchEntity: The role with name ampa_role cannot be found.
│   status code: 404, request id: 943ffed8-6083-47f0-8a28-c9fe29760f7f
│    with module.ampa.module.ampa_role.data.aws_iam_role.ampa_role,
│   on /home/jprats/git/tf-ampa/modules/ampa_role/output.tf line 1, in data "aws_iam_role" "ampa_role":
│    1: data "aws_iam_role" "ampa_role" { 
╵
Releasing state lock. This may take a few moments...

Posted on 11/06/2021

Categories