我有一个 Terraform 配置,它使用在应用阶段从local_file
资源计算的值创建一个aws_api_gateway_usage_plan
资源。
resource "aws_api_gateway_usage_plan" "api_plan" {
name = var.usage_plan_name
api_stages {
api_id = jsondecode(file("dev.json")).resources[1].rest_api_id
stage = "api"
}
# Have to wait for the API to be created before we can create the usage plan
depends_on = [local_file.chalice_config]
}
如您所见,我阅读dev.json
以确定Terraform需求api_id
。问题是,当我运行terraform apply
时,此处描述的新安全检查注意到api_id
评估的先前值已更改!
Provider produced inconsistent final plan: When expanding the plan for aws_api_gateway_usage_plan.api_plan
to include new values learned so far during apply, provider "aws" produced an invalid new value
for .api_stages[0].api_id: was cty.StringVal("****"), but now cty.StringVal("****").
如该文档所述,解决此错误的正确方法是指定在plan
阶段,此api_id
实际上尚未computed
。问题是我不确定如何通过 Terraform 配置执行此操作 - 我引用的文档适用于实际 Terraform 提供程序的编写者。
查看 GitHub 上的问题,似乎将初始值设置为null
并不是执行此操作的合理方法。
有什么想法吗?我正在考虑降级到 Terraform 0.11 以绕过这个新的安全检查,但我希望这在 0.12 中是可能的。
提前感谢!
好吧,在思考了一段时间之后,我想出了一个愚蠢的解决方法,使我能够"欺骗"Terraform,使其相信api_id
的值是在apply
阶段计算的,从而忽略了安全检查。
我所做的是将api_id
表达式替换为以下内容:
api_id = replace("=${aws_security_group.sg.vpc_id}=${jsondecode(file("files/handler/.chalice/deployed/dev.json")).resources[1].rest_api_id}", "=${aws_security_group.sg.vpc_id}=", "")
本质上,我所做的是说api_id
的值取决于一个计算变量 - 即我创建的名为sg
的aws_security_group
的vpc_id
。在这样做时,Terraform 会识别出稍后要计算此值,因此将忽略安全检查。
显然,我实际上不想在这里包含vpc_id
,所以我使用 Terraform 的字符串函数将其从最终表达式中删除。
这是一个非常笨拙的解决方法,我对更好的解决方案持开放态度 - 只是想我会分享我现在拥有的东西,以防其他人遇到同样的问题。
谢谢!
我在创建 lambda 事件源映射时遇到了同样的问题。我克服了它跑步terraform plan
然后terraform apply
在我添加的地方对我的user_data
脚本(使用filebase64
或base64encode
(进行编码时,我遇到了同样的错误,只是简单地使用file
或templatefile
:
user_data = file("${path.module}/provisioning_scripts/init_script.sh")
user_data = templatefile("${path.module}/provisioning_scripts/init_script.tpl", {
USER = "my-user"
GROUP = "my-group"
})
(*( 我无法 100% 重现它,但我正在添加此解决方案作为收到上述错误的另一个可能原因。
也在这里阅读。