Terraform

Using Terraform fmt Command to Format Your Terraform Code

Formatting Terraform Code With the Terraform fmt Command

In this post, we will look at the terraform fmt command, explaining what it does and when to run it, looking at the operation it performs, and showing some useful examples using the available options.

What we will cover:

  1. What is Terraform fmt?
  2. Why is it important to run Terraform fmt?
  3. Using the Terraform fmt command with examples
  4. Troubleshooting when Terraform fmt is not working

What is Terraform fmt?

The terraform fmt command is used to format your configuration files into a canonical format and style. This command applies a subset of the Terraform language style conventions, along with other minor adjustments for readability.

Usage:

terraform fmt [options] [TARGET]

The TARGET can be a directory or a single file name. If no target is specified, terraform fmt applies to the current directory by default.

terraform fmt has the following optional flags:

  • -list=false – Don’t list the files containing formatting inconsistencies.
  • -write=false – Don’t overwrite the input files. (This is implied by -check or when the input is STDIN.)
  • -diff – Display diffs of formatting changes
  • -check – Check if the input is formatted. The exit status will be 0 if all input is properly formatted and non-zero otherwise.
  • -recursive – Also, process files in subdirectories. By default, only the given directory (or current directory) is processed.

Why is it important to run Terraform fmt?

As a best practice, terraform fmt should always be run on your configuration files, so formatting standards and language style conventions are applied across your configuration in a uniform manner. This helps code readability and ensures all configuration files are formatted the same, no matter which team member is writing the file. Consistency can help your team understand the code more quickly and easily, making the use of terraform fmt very important.

Each version of Terraform may introduce changes to the way the terraform fmt command actually adjusts your configuration files, so it should be run each time a different version of Terraform is used. 

It should be noted that Hashicorp acknowledges that formatting decisions are always subjective, and not everyone may agree on the style they have chosen. However, having a standard and providing a command to automatically format the configuration consistently achieves the primary goal.

Note: New versions of Terraform are placed under the BUSL license, but everything created before version 1.5.x stays open-source. OpenTofu is an open-source version of Terraform that expands on Terraform’s existing concepts and offerings. It is a viable alternative to HashiCorp’s Terraform, being forked from Terraform version 1.5.6.

Terraform fmt command in automation

It is prudent to insert a step into your CI/CD pipeline or run automated checks to ensure terraform fmt has been run on the configuration files. One way of doing this is to use the -check option. If changes are required, it will return a non-zero code (1 for error); if there are no changes, it will return a zero code and should be allowed to pass to the next stage.

If a non-zero error code is returned, the -diff option can be used to display the diffs of the formatting changes that the fmt command will make. If there are no diffs, then the pipeline stage should be allowed to pass as complete, if there are diffs, then the pipeline should fail, and the writer of the configuration file should be notified that they need to run the terraform fmt command on their configuration files before committing to source control.

Using the terraform fmt command with examples

To understand how the terraform fmt command options work in practice, let’s look at some examples.

We have a main.tf file that looks like this — note the bad formatting!

terraform fmt example main tf
terraform fmt file example
  • Terraform lists the main.tf file after my terraform fmtcommand to show that it was changed. To stop this from being listed, the -list=false option can be used. Alternatively, the -write=false option will list the files to be changed but not actually write the changes.
  • The extra spaces in the backend block and in the ad_group module call are not removed automatically. If necessary, that must be done manually.

Example: Using the terraform fmt -diff option

terraform fmt main tf error

Note that even though the error is generated, the file formatting is still corrected.

To resolve this error on a Windows machine, you can install GNU diffutils using chocolatey. Chocolately is a popular package manager for Windows. Once installed, you can simply run the following command in an elevated command prompt:

choco install diffutils
terraform fmt install choco

Once installed, restart your terminal, and the diff will be successfully generated:

terraform fmt diff

Example: Using the terraform fmt -check option

The terraform fmt -check option is used to verify if your files comply with the formatting conventions. This does not modify any files but instead exists with a non-0 exit code if any formatting issues are encountered.

This option is especially useful in CI/CD pipelines to enforce consistent formatting before any changes are made to the main branch.

If you have nested directories, to check if everything is formatted correctly, you should also leverage the -recursive option. In the end, your command will look like this:

terraform fmt -check -recursive

Example: Using the terraform fmt -recursive option

The -recursive option is useful to make sure all the Terraform configuration files in the directory structure are formatted. By default, terraform fmt only formats files in the current directory, not the subdirectories. Usually, project configuration files are separated into logical folders or contain submodules, which will also need to be formatted correctly.

By default, terraform fmt, will format the Terraform configuration files only from the root directory, but imagine if you had a structure like this:

.
├── main.tf
├── variables.tf
├── modules/
│   ├── network/
│   │   ├── main.tf
│   │   ├── outputs.tf
│   │   └── variables.tf
│   └── compute/
│       ├── main.tf
│       ├── outputs.tf
│       └── variables.tf

By running terraform fmt, from the root directory, you would only format the main.tf and variables.tf files.

If you want to format all the files from the modules folder, you can simply run:

terraform fmt -recursive

Troubleshooting when terraform fmt is not working

If the terraform fmt command isn’t working as expected, consider the following potential reasons and troubleshooting steps.

  1. Correct directory: Make sure you’re running the command in the correct directory. The terraform fmt command needs to be executed in a directory containing .tf files.
  2. File permissions: If the .tf files are read-only or have restricted permissions, terraform fmt may not work. Make sure you have the appropriate permissions to modify the files.
  3. Already formatted files: If the files are already formatted, terraform fmt will not make any changes.
  4. Syntax errors: If there are syntax errors or corrupted .tf files, terraform fmt may not work. Try validating the files with terraform validate command.
  5. Terraform version compatibility: Make sure the version of Terraform you’re using supports the fmt command. Older versions may behave differently.

Deploying Terraform resources with Spacelift

Terraform is really powerful, but to achieve an end-to-end secure Gitops approach, you need to use a product that can run your Terraform workflows. Spacelift takes managing Terraform to the next level by giving you access to a powerful CI/CD workflow and unlocking features such as:

  • Policies (based on Open Policy Agent) – You can control how many approvals you need for runs, what kind of resources you can create, and what kind of parameters these resources can have, and you can also control the behavior when a pull request is open or merged.
  • Multi-IaC workflows – Combine Terraform with Kubernetes, Ansible, and other infrastructure-as-code (IaC) tools such as OpenTofu, Pulumi, and CloudFormation,  create dependencies among them, and share outputs
  • Build self-service infrastructure – You can use Blueprints to build self-service infrastructure; simply complete a form to provision infrastructure based on Terraform and other supported tools.
  • Integrations with any third-party tools – You can integrate with your favorite third-party tools and even build policies for them. For example, see how to integrate security tools in your workflows using Custom Inputs.

Spacelift enables you to create private workers inside your infrastructure, which helps you execute Spacelift-related workflows on your end. For more information on configuring private workers, refer to the documentation.

Key points

This blog post explained how to format your Terraform code using the Terraform fmt command.

If you’re interested in learning how to use Spacelift to manage and automate your Terraform deployments, check out our Terraform documentation and sign up for a free trial or book a demo with our engineering team.

Manage Terraform Better with Spacelift

Build more complex workflows based on Terraform using policy as code, programmatic configuration, context sharing, drift detection, resource visualization, and many more.

Learn more

The Practitioner’s Guide to Scaling Infrastructure as Code

Transform your IaC management to scale

securely, efficiently, and productively

into the future.

ebook global banner
Share your data and download the guide