linuxlab.io
Tutorials▾
  • Linux & networking
    File system, processes, TCP/IP, BGP and OSPF
    →
  • Terraform & IaC
    HCL, state, plan/apply on a LocalStack sandbox
    →
  • Git & GitHub
    Object model, plumbing, branching, GitHub Actions
    →
All tutorials →
PricingAboutSign inCreate account
/
Intro
Lessons
Footer
linuxlab-TutorialsPricingAboutPrivacy & cookies
Copyright © 2026 LinuxLab. All rights reserved.
linuxlab.io
Tutorials▾
  • Linux & networking
    File system, processes, TCP/IP, BGP and OSPF
    →
  • Terraform & IaC
    HCL, state, plan/apply on a LocalStack sandbox
    →
  • Git & GitHub
    Object model, plumbing, branching, GitHub Actions
    →
All tutorials →
PricingAboutSign inCreate account
/
  • Introduction
  • Lessons
  • How it works
  • Knowledge base
  • Cheat sheet
  • Capstone
  • Interview prep
home/terraform/kb/Providers/tf-provider-block

kb/providers ── Providers ── beginner

The provider block: who Terraform will call

The provider block configures the plugin: which AWS region to talk to, which endpoints to use, which credentials to take. One block per provider is usually enough.

view as markdown

What a provider is in Terraform

A provider is the plugin that sits between Terraform and a cloud. The AWS provider knows how to talk to the AWS API. The Google Cloud provider talks to GCP. There are providers for GitHub (to manage repositories), Cloudflare (DNS), even for a home router.

Every provider needs configuration: where to connect, with which keys, in which region. That is what the provider block does.

Minimal example

hcl
terraform {
  required_providers {
    aws = {
      source  = "hashicorp/aws"
      version = "~> 5.60"
    }
  }
}
provider "aws" {
  region = "us-east-1"
}

There are two blocks here:

  • terraform { required_providers { ... } } is a meta-block. It says "I need the AWS provider at version 5.60 or higher, within major 5." terraform init reads this to know what to download. See tf-init.
  • provider "aws" configures the downloaded plugin. Here it sets only the region.

This example does not list any AWS credentials. Terraform takes them from the standard places (env vars, ~/.aws/credentials). See aws-provider.

Why you need an alias

Sometimes one provider is not enough. The classic case: you need resources in two different AWS regions.

hcl
provider "aws" {
  region = "us-east-1"
}
provider "aws" {
  alias  = "europe"
  region = "eu-central-1"
}
# Resource in the default region us-east-1
resource "aws_s3_bucket" "us" {
  bucket = "my-us-bucket"
}
# Resource in Europe, explicit reference to the alias
resource "aws_s3_bucket" "eu" {
  provider = aws.europe
  bucket   = "my-eu-bucket"
}

One provider without an alias is the default one. Any resource that does not name a provider = goes to it. Everything else goes through aws.alias_name.

default_tags, write it like this

The AWS provider can attach tags to every resource automatically:

hcl
provider "aws" {
  region = "us-east-1"
  default_tags {
    tags = {
      Project     = "my-project"
      Environment = "dev"
      ManagedBy   = "terraform"
    }
  }
}

Now every resource you create gets these tags with no effort on your part. This saves money (tags feed billing analytics), makes cleanup easier (aws s3api list-buckets --query ... --tag-key Environment Value dev), and helps with FinOps.

If a specific resource has its own tags = {...}, they merge with default_tags. Your own tags win over default_tags when a key matches.

Version constraints

In required_providers you can pin the version in several ways:

NotationWhat it means
"5.60.0"Exactly 5.60.0, no deviation.
"= 5.60.0"The same thing, stated explicitly.
">= 5.60.0"Not below 5.60.0. Risky, it can pull in an incompatible 6.x.
"~> 5.60"5.60.x, 5.61.x, and so on. But not 6.x. Pessimistic, a safe default.
"~> 5.60.0"Only 5.60.x. Very strict.
">= 5.60, < 6.0"Equivalent to ~> 5.60, stated explicitly.

The standard in well-run projects is ~> X.Y. This gives you automatic minor updates (bug fixes, new resources) without the risk of a major bump. See tf-version-constraints.

Pitfalls

  • The same provider "aws" {} twice without an alias is an error. You can have either one without an alias or several with different aliases.

  • required_providers is mandatory. If it is missing, Terraform does not know what to download during init. It used to default to hashicorp/aws, but that is now deprecated.

  • A provider block can be empty: provider "aws" {} is valid if all settings come from env vars or credentials files.

  • Set endpoints carefully (see localstack-provider). In production they should disappear, or you might accidentally send a request to the wrong cluster.

  • Do not commit credentials in the provider block. Never write access_key = "AKIA..." in HCL. Use env vars or IAM roles. The one exception: the hardcoded "test" values for LocalStack in training exercises.

§ команды

bash
terraform providers

Shows the tree of every provider your project uses, including the transitive ones pulled in by modules.

bash
terraform providers lock -platform=linux_amd64 -platform=darwin_arm64

Regenerate the lockfile for several platforms, useful when your team is on different operating systems.

§ см. также

  • tf-initterraform init: the first command in any projectterraform init downloads the provider plugins (AWS, GCP, and so on), creates a lockfile that pins their versions, and prepares the working directory. Without it, neither plan nor apply will run.
  • aws-providerAWS provider: configuration and where Terraform finds your keysThe AWS provider looks for credentials in several places in order: env variables, ~/.aws/credentials, the instance IAM role. Usually `aws configure` locally or a role on EC2 is enough, and you configure nothing else.
  • localstack-providerLocalStack: a learning AWS that lives in DockerLocalStack emulates the AWS API locally, inside a Docker container. Terraform thinks it is talking to real AWS, but no real resources are created and no money is spent. Ideal for learning and tests.
  • tf-version-constraintsVersion constraints in Terraform: required_version and providersrequired_version pins which versions of terraform may run this code. required_providers.version does the same for providers. The pessimistic operator ~> 5.60 is the standard: it allows minor updates and blocks major ones.
Footer
linuxlab-
Copyright © 2026 LinuxLab. All rights reserved.
Tutorials
Pricing
About
Privacy & cookies