Terraform: Referencing attribute on resource created with count

Created on 15 Feb 2017  ยท  10Comments  ยท  Source: hashicorp/terraform

I've created four RDS instances (one master and three slaves in the three AZs) and am now trying to setup a ELB in front of the RDS instances.

I've used aws_elb to setup the ELB and am now trying to attach the RDS instances to that using aws_elb_attachment.

But I'm not sure how to do that using count.

# Attach all the RDS instances to the ELB.
resource "aws_elb_attachment" "main-rds-fc2" {
  count                         = 3 # !! _MUST_ be the same as 'aws_db_instance.main_fc2.count'  !!

  elb                           = "${aws_elb.main-rds-fc2.id}"
  instance                      = "${aws_db_instance.main_fc2.${count.index}.id}"
#  instance                      = "${format("aws_db_instance.main_fc2.%d.id", count.index)}"
}

The first example of instances gives me the error:

Error reading config for aws_elb_attachment[main-rds-fc2]: parse error at 1:28: expected "}" but found invalid sequence "$"

(I had expected that one to work!)

The second (commented out) looks like it would work:

module.core-main.aws_elb_attachment.main-rds-fc2.0
  elb:      "core-main-rds-fc2"
  instance: "aws_db_instance.main_fc2.0.id"

but gives me:

* aws_elb_attachment.main-rds-fc2.2: Failure registering instances with ELB: InvalidInstance: InvalidInstance found in [aws_db_instance.main_fc2.2.id]. Invalid id: "aws_db_instance.main_fc2.2.id" (Service: AmazonEC2; Status Code: 400; Error Code: InvalidInstanceID.Malformed; Request ID: 06cabc95-8f0c-484b-8f32-5451fa0c9ef7)

which is kind'a obvious - it's not a variable/reference, but a string.

Trying instance = "${format("${aws_db_instance.main_fc2.%d.id}", count.index)}" or instance = "${${format("aws_db_instance.main_fc2.%d.id", count.index)}}" both give me errors

Error downloading modules: module core-main: Error loading .terraform/modules/ce3ac1d445a47c76df64ef224dfadb09/loadbalancer-rds.tf: Error reading config for aws_elb_attachment[main-rds-fc2]: d.id: resource variables must be three parts: TYPE.NAME.ATTR in:

and

Error downloading modules: module core-main: Error loading .terraform/modules/ce3ac1d445a47c76df64ef224dfadb09/loadbalancer-rds.tf: Error reading config for aws_elb_attachment[main-rds-fc2]: parse error at 1:3: expected expression but found invalid sequence "$"

respectively.

Trying to create three separate resources:

resource "aws_elb_attachment" "main-rds-fc2.0" {
  elb                           = "${aws_elb.main-rds-fc2.id}"
  instance                      = "${aws_db_instance.main_fc2.0.id}"
}

instead gives me:

Error configuring: Unexpected value for InstanceType field: "0"

which, I guess is obvious because it thinks the third option/part is the attribute to get. But that's what's stated in the state file.

documentation

Most helpful comment

@FransUrbo Have you tried this?
instance: "${aws_db_instance.mainfc2.*.id[0]}"

it returns first element from the 'id' list.
works for me.

All 10 comments

Some more tries, I came up with:

  instance = "${format("$${aws_db_instance.main_fc2.%d.id}", count.index)}"

which seems to be the closest, but that also gave me

Error configuring: Unexpected value for InstanceType field: "0"

So I'm guessing it's more a question on how to retrieve an attribute from a counted resource.

The last example of instance gives the plan:

+ module.core-main.aws_elb_attachment.main-rds-fc2.0
    elb:      "core-main-rds-fc2"
    instance: "${aws_db_instance.main_fc2.0.id}"

but again, there's FOUR parts, where the fourth is actually the attribute I want.

@FransUrbo Have you tried this?
instance: "${aws_db_instance.mainfc2.*.id[0]}"

it returns first element from the 'id' list.
works for me.

Ah, no never tried that! I'll try to remember that next time. I've scratched the ELB. Apparently, it's not possible to put a ELB in front of a RDS anyway (according to the AWS docs), so I'll have to resort to using round-robin with Route53.

But if that example should work, then how about changing the labels of this issue to documentation and update the docs about interpolation at https://www.terraform.io/docs/configuration/interpolation.html ?

I have come cross the similar issue when I am attaching my ASG EC2 instances to Internal ELB.

resource "aws_elb_attachment" "internal_elb_attach_to_proxy_asg" {
elb = "${aws_elb.proxy_elb.id}" // ELB ID
instance = "${aws_autoscaling_group.proxy_asg.id}" // Attaching ASG to the ELB
}

Error

Failure registering instances with ELB: InvalidInstance: InvalidInstance found in xxxxxx-ASG. Status Code: 400; Error Code: InvalidInstanceID.Malformed; Request ID:

Does anyone know how we fix this ?

Agreed that we should have better docs for this.

The _Using Templates with Count_ section covers this pattern, but it makes it sounds like it's something unique to templates when in fact it's a general pattern that can be applied to any set of inter-related resources.

I have managed to fix this by using asg_attachment data source where we have to pass elb details to an ASG.

@FransUrbo Use the below syntax.
instance = "${aws_db_instance.main_fc2.*.id[count.index]}"

I am going to close this issue due to inactivity. Our documentation has had many updates since this was opened!

If there is still a question, I recommend the the community forum, where there are far more people available to help. If there is a bug or you would like to make a feature request, please open a new issue and fill out the template.
Thanks!

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.

Was this page helpful?
0 / 5 - 0 ratings