TFLint is a Terraform linter for detecting errors that can not be detected by `terraform plan`
Clone or download
wata727 Merge pull request #237 from odinho/patch-1
Add "features" word to docs for people explicitly looking
Latest commit 17a59e2 Sep 15, 2018
Permalink
Failed to load latest commit information.
config Introduce `rule` syntax May 23, 2018
detector Update valid cluster node types Jul 19, 2018
docs Remove aws_instance_not_specified_iam_profile Apr 17, 2018
evaluator Add test case for conditional May 6, 2018
integration/general Remove aws_instance_not_specified_iam_profile Apr 17, 2018
issue Print detector name and link Jul 8, 2017
loader Accept glob pattern as arguments Apr 29, 2018
logger add printer, logger test Nov 23, 2016
mock make mock May 20, 2018
printer Add --quiet option May 6, 2018
schema Handle path delimiter for Windows Apr 29, 2018
state Resource identify check for duplicate resource detector Jul 22, 2017
.gitignore use glide Nov 24, 2016
.travis.yml Remove tip version from TravisCI Nov 12, 2017
CHANGELOG.md Bump up version to 0.7.2 Aug 26, 2018
Dockerfile Merge pull request #155 from VJftw/master Nov 4, 2017
Gopkg.lock dep ensure -update github.com/cristim/ec2-instances-info Aug 26, 2018
Gopkg.toml dep init Jul 2, 2018
LICENSE update README, add document etc. Nov 26, 2016
Makefile Use dep instead of glide Jul 2, 2018
README.md Add "features" word to docs for people explicitly looking Sep 14, 2018
appveyor.yml AppVeyor 🚀 Apr 29, 2018
cli.go Add --quiet option May 6, 2018
cli_test.go Introduce `rule` syntax May 23, 2018
gometalinter.json Disable goconst Jul 8, 2017
integration_test.go Add integration test Apr 23, 2017
main.go Handle color for Windows Apr 29, 2018
sideci.yml gometalinter settings Feb 12, 2017
version.go Bump up version to 0.7.2 Aug 26, 2018

README.md

TFLint

Build Status GitHub release Docker Hub MIT License

TFLint is a Terraform linter for detecting errors that can not be detected by terraform plan

Why TFLint is Required?

Terraform is a great tool for infrastructure as a code. It generates an execution plan, we can rely on this plan to proceed with development. However, this plan does not verify values used in template. For example, following template is invalid configuration (t1.2xlarge is invalid instance type)

resource "aws_instance" "web" {
  ami           = "ami-b73b63a0"
  instance_type = "t1.2xlarge" # invalid type!

  tags {
    Name = "HelloWorld"
  }
}

If you run terraform apply for this template, it will obviously produce an error. However, terraform plan can get an execution plan without causing an error. This is often not a desirable result. In order to solve this problem, TFLint validates values used in template.

Installation

Download binary built for your architecture from latest releases. After downloading, place the binary on the directory on the PATH. The following example is the installation in macOS.

$ wget https://github.com/wata727/tflint/releases/download/v0.7.2/tflint_darwin_amd64.zip
$ unzip tflint_darwin_amd64.zip
Archive:  tflint_darwin_amd64.zip
  inflating: tflint
$ mkdir -p /usr/local/tflint/bin
$ export PATH=/usr/local/tflint/bin:$PATH
$ install tflint /usr/local/tflint/bin
$ tflint -v

Homebrew

macOS users can also use Homebrew to install TFLint:

$ brew tap wata727/tflint
$ brew install tflint

Running in Docker

We provide Docker images for each version on DockerHub. With docker, you can run TFLint without installing it locally.

$ docker run --rm -v $(pwd):/data -t wata727/tflint

Quick Start

Try running TFLint under the directory where Terraform is executed. It detect if there is a issue and output the result. For example, run on the previous invalid template.

$ tflint
template.tf
        ERROR:3 "t1.2xlarge" is invalid instance type. (aws_instance_invalid_type)

Result: 2 issues  (1 errors , 0 warnings , 1 notices)

If you would like to know more about these issues and available features please check the documentation.

Specify Template

If you want to parse only a specific template, not all templates, you can specify a filename as an argument.

$ tflint template.tf

Available Options

Please show tflint --help

Usage:
  tflint [OPTIONS] [FILE]

Application Options:
  -v, --version                             Print TFLint version
  -f, --format=[default|json|checkstyle]    Output format (default: default)
  -c, --config=FILE                         Config file name (default: .tflint.hcl)
      --ignore-module=SOURCE1,SOURCE2...    Ignore module sources
      --ignore-rule=RULE1,RULE2...          Ignore rule names
      --var-file=FILE1,FILE2...             Terraform variable file names
      --deep                                Enable deep check mode
      --aws-access-key=ACCESS_KEY           AWS access key used in deep check mode
      --aws-secret-key=SECRET_KEY           AWS secret key used in deep check mode
      --aws-profile=PROFILE                 AWS shared credential profile name used in deep check mode
      --aws-region=REGION                   AWS region used in deep check mode
  -d, --debug                               Enable debug mode
      --error-with-issues                   Return error code when issues exist
      --fast                                Ignore slow rules. Currently, ignore only aws_instance_invalid_ami
  -q, --quiet                               Do not output any message when no issues are found (Format=default only)

Help Options:
  -h, --help                                Show this help message

Configuration

By default, TFLint loads .tflint.hcl according to the following priority:

  • Current directory (./.tflint.hcl)
  • Home directory (~/.tflint.hcl)

The configuration file is described in HCL, and options available on the command line can be described in advance. Following example:

config {
  terraform_version = "0.9.11"
  deep_check = true

  aws_credentials = {
    access_key = "AWS_ACCESS_KEY"
    secret_key = "AWS_SECRET_KEY"
    region     = "us-east-1"
  }

  ignore_module = {
    "github.com/wata727/example-module" = true
  }

  varfile = ["example1.tfvars", "example2.tfvars"]
}

rule "aws_instance_invalid_type" {
  enabled = false
}

rule "aws_instance_previous_type" {
  enabled = false
}

If you want to create a configuration file with a different name, specify the file name with --config option.

$ tflint --config other_config.hcl

Terraform Version

You can set the version of Terraform you are using. If it is set, TFLint will detect issues according to it.

Credentials

TFLint supports various credential providers. It is used with the following priority:

  • Static credentials
  • Shared credentials
  • Environment credentials
  • Default shared credentials

Static Credentials

If you have access key and secret key, you can specify these credentials.

$ tflint --aws-access-key AWS_ACCESS_KEY --aws-secret-key AWS_SECRET_KEY --aws-region us-east-1
config {
  aws_credentials = {
    access_key = "AWS_ACCESS_KEY"
    secret_key = "AWS_SECRET_KEY"
    region     = "us-east-1"
  }
}

Shared Credentials

If you have shared credentials, you can specify credentials profile name. However TFLint supports only ~/.aws/credentials as shared credentials location.

$ tflint --aws-profile AWS_PROFILE --aws-region us-east-1
config {
  aws_credentials = {
    profile = "AWS_PROFILE"
    region  = "us-east-1"
  }
}

Environment Credentials

TFLint looks AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY, AWS_REGION environment values. This is useful when you do not want to explicitly specify credentials.

$ export AWS_ACCESS_KEY_ID=AWS_ACCESS_KEY
$ export AWS_SECRET_ACCESS_KEY=AWS_SECRET_KEY

Rules

You can make settings for each rule in the rule block. Currently, it can set only enabled option. If you set enabled = false, TFLint doesn't check templates by this rule.

rule "aws_instance_previous_type" {
  enabled = false
}

Please see the documentation for a list of rules.

Interpolation Syntax Support

TFLint can interpret part of interpolation syntax. We now support only variables and terraform meta information (e.g. "${terraform.env}"). So you cannot use attributes of resource, outputs of modules and built-in functions. If you are using them, TFLint ignores it. You can check what is ignored by executing it with --debug option.

Variable Files

If you use variable files, Please specify it by arguments or configuration file. TFLint interprets variables as well as Terraform. In other words, when variables are conflicting, It will be overridden or merged correctly.

Deep Check

Deep check is an option that you can actually search resources on AWS and check invalid references and duplicate resources. You can activate it by executing it with --deep option as following:

$ tflint --deep
template.tf
        ERROR:3 "t1.2xlarge" is invalid instance type. (aws_instance_invalid_type)
        ERROR:4 "invalid_profile" is invalid IAM profile name. (aws_instance_invalid_iam_profile)

Result: 2 issues  (2 errors , 0 warnings , 0 notices)

In the above example, an IAM instance profile that does not actually exist is specified, so it is an error. In order to refer to actual resources, AWS credentials are required. You can use command line options, configuration files, environment variables, shared credentials for these specifications.

Developing

If you want to build TFLint at your environment, you can build with the following procedure. Go 1.9 or more is required.

$ make build

Author

Kazuma Watanabe