You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何引用for_each创建的K8s Service模块资源配置Azure应用网关?

dynamic "backend_address_pool" {
for_each = toset(var.backends[*].name)
content {
name = "backend-pool-${backend_address_pool.value}"
ip_addresses = flatten([
for s in module.k8s_services["${backend_address_pool.value}"].kubernetes_service.internal_lb.status : [
for lb in s.load_balancer : [
for ingress in lb.ingress : ingress.ip if ingress.ip != null
]
]
])
}
}
...
}

错误信息:

╷
│ Error: Invalid index
│
│ on appgw.tf line 49, in resource "azurerm_application_gateway" "ag":
│ 49: for s in module.k8s_services["${backend_address_pool.value}"].kubernetes_service.internal_lb.status : [
│ ├────────────────
│ │ backend_address_pool.value is "application"
│ │ module.k8s_services is object with no attributes
│
│ The given key does not identify an element in this collection value.

## 解决方案

### 1. 调整模块调用方式
使用`for_each`遍历`var.backends`实例化模块,让`module.k8s_services`成为以backend名称为键的对象集合:

```hcl
module "k8s_services" {
  source = "./modules/k8s_services"
  for_each = { for b in var.backends : b.name => b }
  
  name = each.value.name
  k8s_namespace = each.value.k8s_namespace
  selector = ... # 替换为你的实际selector配置
}

2. 为模块添加输出

在modules/k8s_services目录下创建outputs.tf,显式暴露Service的状态信息(Terraform模块不会自动暴露内部资源属性):

output "service_status" {
  description = "Status details of the internal LoadBalancer Service"
  type = object({
    load_balancer = object({
      ingress = list(object({
        ip = string
      }))
    })
  })
  value = kubernetes_service.internal_lb.status
}

3. 修改应用网关配置

调整dynamic块的for_each逻辑,直接遍历模块实例集合,通过输出简化IP提取:

resource "azurerm_application_gateway" "ag" {
...
  dynamic "backend_address_pool" {
    for_each = module.k8s_services
    content {
      name = "backend-pool-${backend_address_pool.key}"
      ip_addresses = [
        for ingress in backend_address_pool.value.service_status.load_balancer.ingress : ingress.ip
        if ingress.ip != null
      ]
    }
  }
...
}

关键说明

  • 原始错误核心是未用for_each批量实例化模块,导致module.k8s_services不是可索引的多实例集合。
  • 模块必须显式输出需要引用的属性,不能直接跨模块访问内部资源的属性。
  • 简化IP提取逻辑:service_status.load_balancer.ingress本身是列表,直接过滤非空IP即可,无需多层嵌套flatten。

内容的提问来源于stack exchange,提问作者virdz

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.10 21:09:54