Error: Duplicate output definition: "was already defined at outputs.tf"
Fixes Terraform's "Error: Duplicate output definition ... was already defined", where two output blocks share a name in one module. Use when validate fails after refactoring outputs or merging branches. Not for duplicate resources (same fix, different block).
TL;DR
Two output blocks share the same name. Outputs must be unique per module, just like resources. Delete or rename one of them, then terraform validate.
The error
Error: Duplicate output definition
An output named "lambda_execution_role_arn" was already defined at outputs.tf:3,1-35.Steps to fix
Find all definitions:
grep -n 'output "lambda_execution_role_arn"' outputs.tf(use your output name).- Expected: two or more
outputblocks with the same name, often a leftover single-line version plus a new block-style one.
- Expected: two or more
Keep one definition and delete the other. If both carry different values, decide which one callers should see and merge.
- Expected: exactly one
output "[name]"block remains.
- Expected: exactly one
Run
terraform validate.- Expected:
Success! The configuration is valid.
- Expected:
When to use this
terraform validateorplanfails withDuplicate output definitionafter merging branches, refactoring outputs.tf, or converting output styles.
When NOT to use this
Duplicate resource configurationis the same idea for resources (fix the same way).Unsupported attributeonmodule.[name].[output]means the caller wants an output the module never defined.
Compatibility
- All Terraform versions; outputs have always required unique names per module.
Root cause
Output names form the module's public interface, so each name must map to exactly one value. Duplicates usually come from refactoring (adding a block-style output without removing the old single-line one) or bad merges that concatenate two versions of outputs.tf.
Edge cases
- Outputs in different modules may share names freely; only duplicates within one module error.
override.tffiles can intentionally redefine outputs; that is the one sanctioned exception, and it still requires the_override.tffilename.