在 Terraform 中使用 Element 和 Split 获取第一项而不是最后一项

Using Element and Split Gets First Item Rather than Last Item in Terraform

我们正在尝试将动态名称应用于防火墙规则,以便根据实例组列表 urls 使用 terraform 在 GCP 中打开 8089 和 8843。它没有获取该结果并给我们 url 中的最后一项,而是给我们 https:

tf:

#This is to resolve an error when deploying to nginx
  resource "google_compute_firewall" "ingress" {
  for_each      = toset(google_container_cluster.standard-cluster.instance_group_urls)
  description   = "Allow traffic on ports 8843, 8089 for  nginx ingress"
  direction     = "INGRESS"
  name          = element(split("/", each.key), length(each.key))
  network       = "https://www.googleapis.com/compute/v1/projects/${local.ws_vars["project-id"]}/global/networks/${local.ws_vars["environment"]}"
  priority      = 1000
  source_ranges = google_container_cluster.standard-cluster.private_cluster_config.*.master_ipv4_cidr_block
  target_tags = [
    element(split("/", each.key), length(each.key))
  ]

  allow {
    ports = [
      "8089",
    ]
    protocol = "tcp"
  }
  allow {
    ports = [
      "8443",
    ]
    protocol = "tcp"
  }
}

结果:

    Error: "name" ("https:") doesn't match regexp "^(?:[a-z](?:[-a-z0-9]{0,61}[a-z0-9])?)$"

  on main.tf line 133, in resource "google_compute_firewall" "ingress":
 133:   name          = element(split("/", each.key), length(each.key))

这里的解决方法是什么?为什么不给出数组中的最后一项?有没有更好的方法?

与许多语言一样,Terraform/HCL 使用基于零的索引,因此如果您想要数组中的最后一个元素,则需要从长度中减去一个元素,如下所示:

locals {
  list = ["foo", "bar", "baz"]
}

output "last_element" {
  value = element(local.list, length(local.list) - 1)
}

element function 引起了这种混乱,因为当您尝试访问超出其环绕的列表长度时并没有得到 bounds/range 错误,因此您得到了第一个元素:

The index is zero-based. This function produces an error if used with an empty list. The index must be a non-negative integer.

Use the built-in index syntax list[index] in most cases. Use this function only for the special additional "wrap-around" behavior described below.

To get the last element from the list use length to find the size of the list (minus 1 as the list is zero-based) and then pick the last element:

> element(["a", "b", "c"], length(["a", "b", "c"])-1)
c

遗憾的是,在撰写本文时,Terraform 目前在内置索引语法中不支持负索引:

locals {
  list = ["foo", "bar", "baz"]
}

output "last_element" {
  value = local.list[-1]
}

抛出以下错误:

Error: Invalid index

  on main.tf line 6, in output "last_element":
   6:   value = local.list[-1]
    |----------------
    | local.list is tuple with 3 elements

The given key does not identify an element in this collection value.