0.9.7
Output variables
provider "aws" {
region = "us-east-1"
}
variable "topic_arn" {
default = ""
}
resource "aws_sns_topic" "my_topic" {
count = "${var.topic_arn != "" ? 0 : 1}"
name = "my-topic"
}
output "topic_arn" {
value = "${var.topic_arn != "" ? var.topic_arn : aws_sns_topic.my_topic.arn}"
}
When a non-empty value is given for the topic_arn input variable, the output variable topic_arn should be present.
When a non-empty value is given for the topic_arn input variable, the output variable topic_arn is missing:
$ terraform apply -var "topic_arn=arn:aws:sns:us-east-1:000000000000:foobar"
Apply complete! Resources: 0 added, 0 changed, 0 destroyed.
However, when an empty (default) value is given for the topic_arn input variable, the output variable topic_arn is present:
$ terraform apply
aws_sns_topic.my_topic: Creating...
arn: "" => "<computed>"
name: "" => "my-topic"
policy: "" => "<computed>"
aws_sns_topic.my_topic: Creation complete (ID: arn:aws:sns:us-east-1:358315610143:my-topic)
Apply complete! Resources: 1 added, 0 changed, 0 destroyed.
The state of your infrastructure has been saved to the path
below. This state is required to modify and destroy your
infrastructure, so keep it safe. To inspect the complete state
use the `terraform show` command.
State path:
Outputs:
topic_arn = arn:aws:sns:us-east-1:358315610143:my-topic
Run the following command with the HCL file shown above:
$ terraform apply -var "topic_arn=arn:aws:sns:us-east-1:000000000000:foobar"
Hi @jkehres! Sorry for the weird behavior here.
I think what you're actually seeing here is the bug discussed in #9080: errors while evaluating outputs are not shown today, because we want to be able to try to evaluate outputs before all of their inputs are complete.
This is also related to hashicorp/hil#50, which means that right now both "sides" of the conditional need to always be valid, even though only one is ever used.
Were you to try the expression you have there in a resource attribute, I think you'd get an error saying that aws_sns_topic.my_topic.arn doesn't exist, because the count is zero.
Here's a different way to write it that should work:
value = "${element(compact(concat(list(var.topic_arn), aws_sns_topic.my_topic.*.arn)), 0)}"
This should work because in both cases all of the variables can be resolved:
var.topic_arn is empty, the initial list is ["", "(the arn of the resource)"]. compact removes the empty element from the front, so element 0 is "(the arn of the resource)".count = 0, the "splat syntax" expands to an empty list, so the initial list is ["(the value of topic_arn)"], and so element 0 is "(the value of topic_arn)".I totally understand that this convoluted expression creates maintenance headaches, so we're planning to address the limitations here and make this behave in a more intuitive way in future.
Since we already have issues open covering the different aspects of this, I'm going to close it just to keep any further discussion in one place. Thanks for filing this issue!
@apparentlymart I tried to adopt the idea of using "splat syntax" to workaround similar issue. but it does not work:
original:
output test_list {
value = ["${split(" ", var.flag == "true" ? "${aws_instance.example1.id} ${aws_instance.example2.id}" : "${aws_instance.example1.id}")}"]
}
workaround tried with splat syntax:
value = ["${compact(concat(list(aws_instance.example1.id), aws_instance.example2.*.id))}"]
both result in missing output of test_list.
would you please suggest alternative to workaround this? I am using terraform v0.10.0
Thanks
@rchenv did you find a workaround for this? I'm stuck here, too.
@jnoxon I did find a workaround:
value = ["${compact(concat(aws_instance.example1.*.id, aws_instance.example2.*.id))}"]
does the trick.
Sorry I didn't see these responses before... it's hard to keep track of discussions in closed issues. :disappointed: I'm glad to see you found a workaround in spite of my not seeing your question, @rchenv.
For anyone else who finds this here: to work around the current issue that output errors are hidden, one approach is to evaluate the same expression in terraform console to see what error it produces. The errors today unfortunately aren't always the most helpful -- we're planning to work on this in the near future -- but at least it's a better clue about what Terraform was taking issue with.
Note that terraform console behaves as if what you type is automatically wrapped in ${ ... }, so the thing to type into the console would be compact(concat(aws_instance.example1.*.id, aws_instance.example2.*.id)) rather than the full ${compact(concat(aws_instance.example1.*.id, aws_instance.example2.*.id))}.
@apparentlymart Thanks for the info on terraform console. I have not used it before. that is a great time-saving tool!
I tried to boil down what I am doing to something very simple:
variable "use_random" { default = false }
variable "number" { default = 5 }
resource "random_id" "optional" {
count = "${var.use_random}"
byte_length = 1
}
output "result" {
value = "${element(compact(concat(random_id.optional.*.id, list(var.number))),0)}"
}
This works, but if I deploy it with use_random=true and then deploy again with use_random=false, I get no output from the second deploy. If I make no changes and deploy again, it works!
@jnoxon that sounds like you've found a new bug, where perhaps the output isn't getting re-evaluated properly as the number of random id resources goes to zero. Would you mind opening a fresh issue for that?
I'm going to lock this issue because it has been closed for _30 days_ โณ. This helps our maintainers find and focus on the active issues.
If you have found a problem that seems similar to this, please open a new issue and complete the issue template so we can capture all the details necessary to investigate further.
Most helpful comment
I tried to boil down what I am doing to something very simple:
This works, but if I deploy it with use_random=true and then deploy again with use_random=false, I get no output from the second deploy. If I make no changes and deploy again, it works!