5 — Outputs¶
Folder: 01-basics/4-dependencies/explicit/
has the simple case; the structured examples below need a scratch root.
An output exposes a value from a root module — to your terminal, to a parent module, or
to another config reading this one's state.
The simple case¶
4-dependencies/explicit/main.tf ends with:
output "pet_output" {
description = "Record the value of pet ID generated by the random_pet resource"
value = random_pet.my_pet.id
}
Primitive vs structured¶
output "pet_id" {
description = "The generated random pet name/id."
value = random_pet.my_pet.id
}
output "all_named_pet_files" {
description = "Map of pet name to file path."
value = { for k, f in local_file.named_pets : k => f.filename }
}
The second uses a for expression to build a map from a for_each'd resource — see
count and for_each for where local_file.named_pets comes
from.
terraform apply
terraform output pet_id
terraform output -raw pet_id
terraform output -json all_named_pet_files
terraform output -json all_named_pet_files | jq -r '.fido'
-raw works on pet_id but errors on all_named_pet_files. -raw prints a bare
string with no quotes or JSON wrapping, which only makes sense for a primitive. For maps,
lists and objects you need -json. This is the distinction you hit the moment you try to
pipe an output into a shell variable.
Outputs are the module interface¶
Inside a child module, output blocks are how the caller reads values back:
module.<name>.<output>. That's the mechanism behind
Lab 9, and the
for-expression-over-module-instances pattern in
Lab 13 is exactly the
all_named_pet_files shape above applied to modules instead of resources.
Outputs land in state in plaintext¶
Anything you output is written to the state file as-is, including values you marked
sensitive. sensitive = true suppresses the value in CLI output only — see
Validation and sensitive values.
Convention¶
Outputs belong in outputs.tf. Terraform doesn't care — it concatenates every .tf file
in the directory — but scattering them makes them hard to find. The core GCP root
breaks this rule in two places, which is
worth seeing precisely so you don't inherit the habit.
Key takeaway¶
An output is a published interface and a plaintext state entry at the same time. Declare
one because something outside this config needs the value — a parent module, another
root, a human running terraform output. Declaring one just to look at a value yourself is
what terraform state show already does, without widening the contract.
Theory: §10 Outputs · Next: Data sources