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

Terraform渲染OpenAPI JSON配置AWS API网关时出现非预期变更

问题根因

出现非预期变更的核心原因有3个:

  1. 模板文件routes.tpl写的是Terraform HCL对象结构,不是合法的OpenAPI JSON格式,templatefile渲染后输出的是HCL语法的普通字符串,根本不符合API网关要求的JSON结构
  2. 资源定义中对已经是字符串的模板渲染结果额外做了一次jsonencode,等于把HCL格式的字符串二次编码成转义的JSON字符串,和云上现存的合法OpenAPI结构完全不匹配
  3. 模板里直接写了var.rest_api_name,templatefile不会自动解析Terraform变量,你也没把这个变量传入模板渲染参数,最终渲染结果里直接保留了字面量var.rest_api_name,不会替换成实际的API名称

从plan输出可以看到,当前云上已存的资源body是包含/path1路径的合法OpenAPI结构,你传入的是未正确渲染的HCL字符串,所以Terraform判定要全量替换body内容。

修复步骤

1. 把routes.tpl改成合法的JSON模板

替换原有HCL结构的内容,所有待替换变量用${}占位,严格遵循JSON语法:

{
  "openapi": "3.0.1",
  "info": {
    "title": "${rest_api_name}",
    "version": "1.0"
  },
  "paths": {
    "/v1/alerts": {
      "get": {
        "x-amazon-apigateway-integration": {
          "httpMethod": "GET",
          "payloadFormatVersion": "1.0",
          "type": "HTTP_PROXY",
          "uri": "${url}"
        }
      }
    }
  }
}

注意:JSON的键和字符串值必须用双引号包裹,不能用HCL的无引号写法

2. 修改main.tf的模块调用,补全模板参数

调用templatefile时把模板用到的rest_api_name变量一并传入:

module "api_gateway_new" {
  source = "../../../modules/api-gateway/new/"
  routes = templatefile("${path.module}/routes.tpl",{
    url = "https://ip-ranges.amazonaws.com/ip-ranges.json"
    rest_api_name = "dev-api-gateway-fargate"
  })
}

3. 修改resource.tf,去掉多余的jsonencode

templatefile渲染后已经是合法的JSON字符串,直接传给body参数即可,不需要二次编码:

resource "aws_api_gateway_rest_api" "default" {
  body = var.routes
  name = "dev-api-gateway-fargate"
  endpoint_configuration {
    types = ["REGIONAL"]
  }
}
验证说明

改完后重新执行terraform plan,body的变更会符合预期:

  • 路径配置从原有/path1更新为你配置的/v1/alerts
  • info.title会显示你传入的实际API名称,不会再出现字面量var.rest_api_name
  • 不会再出现把HCL结构当字符串传入的异常

如果你需要保留原有已部署的/path1路径,要把该路径的配置也加到routes.tpl的paths节点下,否则Terraform会删除这个路径的相关配置。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.30 01:51:45