【问题标题】:Terraform for_each + tuple as multi-dimensional arrayTerraform for_each + tuple 作为多维数组
【发布时间】:2021-07-11 07:28:29
【问题描述】:

我有一个本地文件来描述不同的参数,用于不同的环境,例如

parameters.tf:

locals {
  env = {
    dev1 = {
     ...
      natgw_route_table_id           = "rtb-048....."
      transit_gateway_route_table_id = "tgw-rtb-05cc..."
      transit_gateway_id             = "tgw-087..."
      ec2_route_table_id             = "rtb-059..."
      ec2routes_ngw = {
        f1 = {
          destination_cidr = "10.12.13.14/24"\
          nat_gateway_id                = "nat-02a..." 
          transit_gateway_attachment_id = "tgw-attach-0f07..."
        }
        f2 = {
          destination_cidr = "10.12.13.15/32"
          nat_gateway_id   = "nat-0a6c..." 
          transit_gateway_attachment_id = "tgw-attach-028"
        }
     
      }
    }
    ...
    prod = {
       natgw_route_table_id           = "rtb-0be..."
      transit_gateway_route_table_id = "tgw-rtb-0ab7..."
      transit_gateway_id             = "tgw-00dfa..."
      ec2_route_table_id             = ["rtb-0de4...", "rtb-070a9...", "rtb-044a...", "rtb-0c8a..."]
      ec2routes_ngw = {
        f1 = {
            destination_cidr = "10.10.11.12/24"
            nat_gateway_id                = ["nat-09af...", "nat-042b...", "nat-078e...", "nat-0cd2c..."] 
            transit_gateway_attachment_id = "tgw-attach-0ed5025f6fc1731f7"
        }
      }
   }
  }
}

如您所见,对于名为 dev1 的环境,我们有一个子网到一个 nat 网关。 这可以通过以下资源轻松解决:

resource "aws_route" "natgw" {
  for_each               = { for k, v in local.workspace["ec2routes_ngw"] : k => v if(local.workspace["releaseStage"] != "prod")}
  route_table_id         = local.workspace["ec2_route_table_id"]
  destination_cidr_block = each.value.destination_cidr
  nat_gateway_id         = each.value.nat_gateway_id
}

但是,对于 prod 和可能的其他人,我们为每个 AZ 子网及其各自的 NAT 网关提供了一个路由表。

现在,我可以破解它来工作,但我更愿意这样做更优雅一些。

我发现了一些使用for_each 和扁平化本地文件的类似示例。我不介意为那些 prod 类型的环境提供单独的资源,但我不想对其进行硬编码。

感谢任何想法。

【问题讨论】:

  • 你确定这是你的数据结构吗?所以一旦ec2_route_table_idnat_gateway_id 是字符串,那么它们就是一个列表?换句话说,你的数据结构没有一致性?
  • 同意您的数据结构不一致。在 terraform 中展开如此复杂的数据结构需要进行大量重新映射,以便为您想要从中创建的每个资源正确访问该结构。最有可能涉及使用 setproduct() 或 @ 等函数再次重构结构987654332@ 以便稍后使用for_each 创建资源.. 我们在 vpc 模块中做了很多这样的事情:github.com/mineiros-io/terraform-aws-vpc
  • 嗯,它是一个伪数据结构。即使我将nat_gateway_id 格式化为一个包含一个元素的列表以保持一致性,我也不知道如何展开它以创建适当的资源。
  • Flattening nested structures for for_each 中有一个类似情况的工作示例。如果这是您已经看到的示例之一,那么如果您可以展示您尝试过的内容和发生了什么,或者在您的问题中包含您在参考该示例后遇到的任何具体问题,将会有所帮助。

标签: terraform terraform-provider-aws


【解决方案1】:

我最终改变了数据结构,这使得整个问题更容易解决。感谢大家的帮助。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2021-07-09
    • 2021-03-25
    • 2020-08-31
    • 2021-08-02
    • 2020-12-19
    • 1970-01-01
    • 1970-01-01
    • 2021-01-17
    相关资源
    最近更新 更多