Terraform Version: 0.11.8
OS: Mac OS 10.14 (18A391)
variable "functions" {
type = "list"
default = ["function0", "function1"]
}
variable "function0_vars" {
type = "map"
default = {
"URL" = "https://google.com"
"ONE" = "TWO"
}
}
variable "function1_vars" {
type = "map"
default = {
"URL" = "https://yahoo.com"
"THREE" = "FOUR"
}
}
resource "aws_lambda_function" "test" {
count = "${length(var.functions)}"
function_name = "${element(var.functions, count.index)}"
handler = "some_handler"
runtime = "python2.7"
role = "some_role"
environment = {
# works
variables = "${var.function0_vars}"
# does not works
variables = "${var.${element(var.functions, count.index)}_vars}"
}
}
I am trying to use a variable inside a variable in aws_lambda_function but this problem is generic I think.
I know what I am trying to achieve can be done through locals (#17229) but unfortunately, you cannot use count in locals.
The code I have posted here is just a _short_ version of what I actually have. I have a long list of lambda functions, which I want to iterate over.
How about creating a two-level map?
variable "function_vars" {
type = "map"
default = {
"function0" = {
"URL" = "https://google.com"
"ONE" = "TWO"
},
"function1" = {
"URL" = "https://yahoo.com"
"THREE" = "FOUR"
}
}
}
And then index that:
variables = "${lookup(var.function_vars, element(var.functions, count.index))}"
Does that solve your problem?
hey @jeremywadsack ,
Thanks for your response. I did try that earlier but got this error.
~/vikas terraform plan
Error: aws_lambda_function.test: 2 error(s) occurred:
* aws_lambda_function.test[1]: lookup: lookup() may only be used with flat maps, this map contains elements of type map in:
${lookup(var.function_vars, element(var.functions, count.index))}
* aws_lambda_function.test[0]: lookup: lookup() may only be used with flat maps, this map contains elements of type map in:
${lookup(var.function_vars, element(var.functions, count.index))}
~/vikas
I know what I am trying to achieve can be done through locals (#17229) but unfortunately, you cannot use count in locals.
I was initially attempting to accomplish a similar goal to yours, and ran into the same problems. What worked for me was simplifying the data structure altogether. Try this:
locals {
function_vars = [
{
name = "function_1"
foo = "tree"
baz = "plant"
},
{
name = "function_2"
foo = "apple"
baz = "orange"
},
]
}
resource "aws_lambda_function" "test" {
function_name = "${lookup(local.function_vars[count.index], "name")}"
handler = "some_handler"
runtime = "python2.7"
role = "some_role"
environment = {
variables = "${local.function_vars[count.index]}"
}
count = "${length(local.function_vars)}"
}
If these values need to be configurable by the parent sourcing this, then simply use variables for initializing the values:
variable "func1" {
type = "map"
default = {
name = "function_1"
foo = "tree"
baz = "plant"
}
}
variable "func2" {
type = "map"
default = {
name = "function_2"
foo = "apple"
baz = "orange"
}
}
locals {
function_vars = [
"${var.func1}",
"${var.func2}",
]
}
The key here is that the item you're iterating over is locals.function_vars,
Thanks much @sudoforge !!! That worked perfectly.
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 was initially attempting to accomplish a similar goal to yours, and ran into the same problems. What worked for me was simplifying the data structure altogether. Try this:
If these values need to be configurable by the parent sourcing this, then simply use variables for initializing the values:
The key here is that the item you're iterating over is
locals.function_vars,