Fixing Terraform 'Invalid value for input variable' When Variable Types Don't Match in tfvars

beginner๐Ÿ—๏ธ Terraform2026-05-20| Terraform 1.x, any OS (Linux/macOS/Windows), any cloud provider (AWS/GCP/Azure)

Error Message

Invalid value for input variable: The given value is not suitable for var.instance_count: a number is required.
#terraform#variables#tfvars#type-mismatch

The Error

โ”‚ Error: Invalid value for input variable
โ”‚
โ”‚   on terraform.tfvars line 3:
โ”‚    3: instance_count = "2"
โ”‚
โ”‚ The given value is not suitable for var.instance_count: a number is required.

This blows up during terraform plan or terraform apply. Terraform read your .tfvars file, found the variable, and then rejected the value because its type doesn't match the variable declaration. The plan never starts.

Root Cause

Terraform's type system doesn't coerce silently. Declare a variable as type = number and pass a quoted string like "2"? Rejected. No automatic conversion happens โ€” Terraform expects the exact type. This applies to bool, list, map, and object types too.

The mismatch usually comes from one of these situations:

  • A number or bool wrapped in quotes in the .tfvars file
  • A list variable passed as a plain comma-separated string
  • An object variable missing one or more required attributes
  • The variable type changed in variables.tf but the .tfvars file was never updated to match

Fix 1: Remove Quotes from Number and Bool Values

Ninety percent of the time, this is the culprit. HCL has a straightforward rule: strings get quotes, everything else doesn't.

Wrong:

# terraform.tfvars
instance_count = "2"    # string, not a number
enable_logging = "true" # string, not a bool

Correct:

# terraform.tfvars
instance_count = 2      # number โ€” no quotes
enable_logging = true   # bool โ€” no quotes

Numbers, booleans, lists, and maps all go unquoted. Only string values need the double quotes.

Fix 2: Fix List and Set Variables

Passing a list(string) as a comma-separated string is another common trap. Terraform won't split it for you.

Variable declaration:

# variables.tf
variable "availability_zones" {
  type = list(string)
}

Wrong:

# terraform.tfvars
availability_zones = "us-east-1a,us-east-1b"

Correct:

# terraform.tfvars
availability_zones = ["us-east-1a", "us-east-1b"]

Fix 3: Fix Map and Object Variables

HCL maps use { key = value } syntax โ€” not JSON-style colons. If you copy-paste from a JSON config, the colons will break it.

Variable declaration:

# variables.tf
variable "tags" {
  type = map(string)
}

variable "db_config" {
  type = object({
    engine  = string
    version = string
    port    = number
  })
}

Correct tfvars syntax:

# terraform.tfvars
tags = {
  Environment = "production"
  Team        = "platform"
}

db_config = {
  engine  = "postgres"
  version = "14.5"
  port    = 5432
}

Watch port โ€” it's typed as number, so 5432 has no quotes. Writing "5432" triggers the same error you're trying to fix.

Fix 4: Passing Variables via CLI Flag

Using -var on the command line? Type handling works differently there. Terraform receives the value as a string and converts it based on the declared type โ€” which works fine for simple scalars, but falls apart with lists, maps, and objects.

For anything beyond a basic number or bool, use a .tfvars file:

# Fragile for complex types:
terraform plan -var='instance_count=2'

# More reliable:
terraform plan -var-file="production.tfvars"

Simple number and bool variables generally survive -var fine. The headaches start with list, map, and object.

Fix 5: Check for Type Drift Between Modules

Updated a module recently and changed a variable's type? Your root module's .tfvars might still be using the old format. This one is subtle โ€” the error message points to the tfvars file, not the module where the type actually changed.

# Inspect what type Terraform actually expects:
terraform console
> var.instance_count

Or go straight to the source:

grep -A5 'variable "instance_count"' variables.tf

Quick Diagnostic: Validate Without Applying

Run terraform validate before touching plan:

terraform validate

It won't load your tfvars, so it misses value-level mismatches. But it catches declaration errors fast. For full validation โ€” tfvars included โ€” run plan and pipe the output:

terraform plan -var-file="your.tfvars" 2>&1 | head -30

Verifying the Fix

Once you've corrected the type in your tfvars file, run plan again:

terraform plan

No Invalid value for input variable line means the mismatch is gone. A clean plan looks like this:

Terraform will perform the following actions:

  # aws_instance.web will be created
  + resource "aws_instance" "web" {
      ...
    }

Plan: 1 to add, 0 to change, 0 to destroy.

From there you're dealing with infrastructure logic, not type errors.

Prevention

Three habits that make this class of error rare:

  • Declare types explicitly in variables.tf. Without a type constraint, Terraform accepts anything โ€” and problems surface at runtime instead of plan time, where they're harder to trace.
  • Add validation blocks for stricter checks. They produce clear, human-readable messages rather than the raw type error you're looking at now.
  • Keep a terraform.tfvars.example in git with correct types shown. Anyone updating a variable then has a reference for what format to use.
  • Run terraform plan in CI against your actual tfvars files. Type drift gets caught before it reaches production.
# variables.tf โ€” explicit type + validation
variable "instance_count" {
  type        = number
  description = "Number of EC2 instances to create"
  default     = 1

  validation {
    condition     = var.instance_count >= 1 && var.instance_count <= 20
    error_message = "instance_count must be between 1 and 20."
  }
}

With that validation block in place, a bad value gives you "instance_count must be between 1 and 20" โ€” not the cryptic type error you'd otherwise spend 10 minutes googling at 2am.

Related Error Notes