TerraformPilot

DevOps

How to Install and Use TFLint for Terraform Linting

Install TFLint on macOS, Linux, Windows, or Docker and lint your Terraform code. Covers .tflint.hcl config, AWS/Azure/GCP plugins, and CI/CD integration.

LLuca Berton3 min read
How to Install and Use TFLint for Terraform Linting

What Is TFLint?

#

TFLint is a linter for Terraform that catches errors terraform validate misses. It checks for:

  • Invalid instance types (t2.gigantic doesn't exist)
  • Deprecated resource attributes
  • Naming convention violations
  • Provider-specific best practices (AWS, Azure, GCP)
  • Missing required tags

terraform validate only checks syntax. TFLint checks whether your configuration makes sense.

Install TFLint

#

macOS (Homebrew)

#
brew install tflint

The recommended way to install TFLint on macOS is through Homebrew. After installation, keep TFLint updated by running brew upgrade tflint periodically. This gives you the latest version with all supported output formats and cloud provider plugins.

Linux (binary install)

#
curl -s https://raw.githubusercontent.com/terraform-linters/tflint/master/install_linux.sh | bash

This script downloads the prebuilt tflint Linux binary for your architecture and places it on your PATH — no package manager required. The binary supports all output formats including machine-readable options like --format json, --format sarif, --format junit, and --format checkstyle for CI/CD pipeline integration.

Windows (Chocolatey)

#
choco install tflint

Docker

#
docker run --rm -v $(pwd):/data -t ghcr.io/terraform-linters/tflint

Verify installation:

$ tflint --version
TFLint version 0.53.0

Quick Start

#
cd my-terraform-project/
tflint --init    # Download plugins
tflint           # Run linter

That's it. TFLint scans all .tf files in the current directory.

Configure TFLint: .tflint.hcl

#

Create .tflint.hcl in your project root:

# .tflint.hcl
 
# Enable the AWS plugin
plugin "aws" {
  enabled = true
  version = "0.32.0"
  source  = "github.com/terraform-linters/tflint-ruleset-aws"
}
 
# Enforce naming conventions
rule "terraform_naming_convention" {
  enabled = true
}
 
# Require descriptions on variables
rule "terraform_documented_variables" {
  enabled = true
}
 
# Require descriptions on outputs
rule "terraform_documented_outputs" {
  enabled = true
}
 
# Disallow deprecated syntax
rule "terraform_deprecated_interpolation" {
  enabled = true
}
 
# Enforce standard module structure
rule "terraform_standard_module_structure" {
  enabled = true
}

Then initialize:

$ tflint --init
Installing `aws` plugin...
Installed `aws` (source: github.com/terraform-linters/tflint-ruleset-aws, version: 0.32.0)

What TFLint Catches (That terraform validate Doesn't)

#

Invalid Instance Types

#
resource "aws_instance" "web" {
  ami           = "ami-12345678"
  instance_type = "t2.superduper"  # Doesn't exist!
}
$ tflint
1 issue(s) found:
 
Error: "t2.superduper" is an invalid value as instance_type (aws_instance_invalid_type)
 
  on main.tf line 3:
   3:   instance_type = "t2.superduper"

terraform validate would pass this. terraform apply would fail after waiting for the API call.

Invalid AMI

#
resource "aws_instance" "web" {
  ami = "not-an-ami"
}

TFLint catches the invalid AMI format before you waste time on a failed plan.

Deprecated Syntax

#
# Old interpolation-only syntax
resource "aws_instance" "web" {
  instance_type = "${var.instance_type}"  # Deprecated since Terraform 0.12
}
Warning: Interpolation-only expressions are deprecated (terraform_deprecated_interpolation)

Missing Tags

#

With the AWS plugin, you can enforce required tags:

# In .tflint.hcl
rule "aws_resource_missing_tags" {
  enabled = true
  tags = ["Environment", "Team", "ManagedBy"]
}

Now every AWS resource must have these tags or TFLint reports an error.

Provider Plugins

#

AWS Plugin

#
plugin "aws" {
  enabled = true
  version = "0.32.0"
  source  = "github.com/terraform-linters/tflint-ruleset-aws"
}

Checks: invalid instance types, invalid AMIs, invalid IAM policy actions, security group rules, and more.

Azure Plugin

#
plugin "azurerm" {
  enabled = true
  version = "0.27.0"
  source  = "github.com/terraform-linters/tflint-ruleset-azurerm"
}

Google Cloud Plugin

#
plugin "google" {
  enabled = true
  version = "0.30.0"
  source  = "github.com/terraform-linters/tflint-ruleset-google"
}

Built-In Terraform Rules

#

These rules work without any provider plugin:

RuleWhat It Checks
terraform_naming_conventionResource/variable/output naming patterns
terraform_documented_variablesVariables have descriptions
terraform_documented_outputsOutputs have descriptions
terraform_deprecated_interpolation"${var.x}" → var.x
terraform_unused_declarationsUnused variables, data sources, locals
terraform_standard_module_structuremain.tf, variables.tf, outputs.tf exist
terraform_workspace_remoteWarns about terraform.workspace with remote backends
terraform_required_versionrequired_version is declared
terraform_required_providersrequired_providers block exists

Enable them all for strict projects:

rule "terraform_naming_convention" { enabled = true }
rule "terraform_documented_variables" { enabled = true }
rule "terraform_documented_outputs" { enabled = true }
rule "terraform_deprecated_interpolation" { enabled = true }
rule "terraform_unused_declarations" { enabled = true }
rule "terraform_standard_module_structure" { enabled = true }
rule "terraform_required_version" { enabled = true }
rule "terraform_required_providers" { enabled = true }

CI/CD Integration

#

GitHub Actions

#
name: Terraform Lint
on: [pull_request]
 
jobs:
  tflint:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: terraform-linters/setup-tflint@v4
        with:
          tflint_version: v0.53.0
      - run: tflint --init
      - run: tflint --format compact

GitLab CI

#
tflint:
  image: ghcr.io/terraform-linters/tflint:latest
  script:
    - tflint --init
    - tflint --format compact
  rules:
    - if: $CI_PIPELINE_SOURCE == "merge_request_event"

Pre-Commit Hook

#
# .pre-commit-config.yaml
repos:
  - repo: https://github.com/terraform-linters/tflint
    rev: v0.53.0
    hooks:
      - id: tflint

Output Formats

#
tflint                     # Default (human-readable)
tflint --format compact    # One line per issue
tflint --format json       # Machine-readable JSON
tflint --format checkstyle # Checkstyle XML for tools that consume it
tflint --format junit      # JUnit XML for CI
tflint --format sarif      # SARIF for GitHub Code Scanning

For machine-readable output that scripts and CI tools can parse directly, use --format json (generic JSON) or --format sarif (structured findings for code-scanning integrations) instead of the default human-readable text.

TFLint vs Other Tools

#
ToolWhat It DoesWhen to Use
terraform validateSyntax check onlyAlways (fast, built-in)
TFLintSyntax + provider-specific + best practicesAlways (catches real errors)
terraform planFull API check against real infrastructureBefore apply
tfsec / trivySecurity scanningSecurity audits
checkovPolicy complianceCompliance requirements
terraform-docsGenerate documentationModule documentation

Recommended pipeline order: terraform fmt → tflint → terraform validate → terraform plan

Common Configuration Examples

#

Enforce snake_case naming:

#
rule "terraform_naming_convention" {
  enabled = true
  format  = "snake_case"
}

Ignore specific rules for a module:

#
tflint --ignore-rule=terraform_documented_variables

Lint a specific directory:

#
tflint --chdir=modules/vpc/

Recursive lint (all modules):

#
tflint --recursive

Frequently asked questions

#

How do I install TFLint?

#

On macOS run brew install tflint. On Linux, run the official install script: curl -s https://raw.githubusercontent.com/terraform-linters/tflint/master/install_linux.sh | bash. On Windows use choco install tflint. Verify with tflint --version.

How do I install TFLint on Ubuntu?

#

Use the official Linux install script (curl -s https://raw.githubusercontent.com/terraform-linters/tflint/master/install_linux.sh | bash), which works on Ubuntu and other Debian-based distributions. It places the tflint binary on your PATH.

What is the difference between TFLint and terraform validate?

#

terraform validate only checks syntax and internal consistency. TFLint goes further: it catches provider-specific mistakes like invalid instance types, non-existent AMIs, deprecated syntax, and missing required tags — issues that only surface at apply time otherwise.

How do I run TFLint in CI/CD?

#

Install TFLint in your pipeline (the terraform-linters/setup-tflint GitHub Action is the simplest), run tflint --init to load plugins, then tflint --format compact. A non-zero exit code fails the build when lint issues are found.

Hands-On Courses

#

Learn by doing with interactive courses on CopyPasteLearn:

Conclusion

#

TFLint catches real errors that terraform validate misses — invalid instance types, missing tags, deprecated syntax, naming violations. Install it, add a .tflint.hcl with the AWS/Azure/GCP plugin, and integrate it into your CI pipeline. Run tflint before terraform plan to catch mistakes before they reach infrastructure.

#Terraform#DevOps#Infrastructure as Code#Terraform Linting#Troubleshooting

Share this article