Terraform 仅当AWS参数存储不存在时,如何在AWS参数存储中创建/覆盖参数?

Terraform 仅当AWS参数存储不存在时,如何在AWS参数存储中创建/覆盖参数?,terraform,aws-cli,terraform-provider-aws,ssm,Terraform,Aws Cli,Terraform Provider Aws,Ssm,我正在使用terraform在AWS参数存储中创建一个参数 resource "aws_ssm_parameter" "username" { name = "username" type = "SecureString" value = "to_be_defined" overwrite = false } provider "aws" { version = "~> 1.53" } 当我第一次运行terraform apply时,如果

我正在使用terraform在AWS参数存储中创建一个参数

resource "aws_ssm_parameter" "username" {
  name      = "username"
  type      = "SecureString"
  value     = "to_be_defined"
  overwrite = false
}

provider "aws" {
  version = "~> 1.53"
}
当我第一次运行
terraform apply
时,如果参数不存在,terraform将创建参数。但是,如果我再次运行它(通常使用不同的值),我会得到错误

ParameterAlreadyExists:参数已存在。覆盖 如果选择此值,请将请求中的覆盖选项设置为true

如果我理解正确,这是由于AWS Cli的行为(并非特定于提供商)

overwrite=false的当前行为是

如果参数不存在,请创建它
如果参数存在,则抛出异常

我想要达到的是

如果参数不存在,请创建它
如果参数存在,则不执行任何操作

我没有找到一种方法来实现期望的行为


我想知道是否有任何方法可以使用terraform(或直接通过AWS CLI)实现所需的行为。

我同意@ydaetskcoR的观点,即您也应该使用terraform state保持该值

但是如果您坚持忽略SSM密钥存在时要更新的值,则可以使用lifecycle
ignore_changes
()

因此,在您的情况下,您可以将代码更新为

resource "aws_ssm_parameter" "username" {
  name      = "username"
  type      = "SecureString"
  value     = "to_be_defined"
  overwrite = false

  lifecycle {
    ignore_changes = [
      value,
  ]
}
覆盖-(可选)覆盖现有参数。如果未指定,则如果资源不是由terraform创建以避免覆盖现有资源,则将默认为false,否则将默认为true(
terraform生命周期规则应用于管理更新行为


顺便说一下,使用terraform管理
SecureString
SSM密钥/值不是一个好的设计,因为它的tfstate文件没有加密

你为什么要它什么都不做?处于Terraform状态的资源的全部意义在于它管理它并将其更新到预期值,从而潜在地纠正漂移。如果你不想这样,那么你就不应该使用Terraform来创建/管理资源。我想我是想在构建过程中破解terraform,因为它不是专门为之设计的。我将看看我是否能使用terraform来做我想要做的事情;商店状态,谢谢。我想我会看看是否可以像@ydaetskcoR建议的那样使用terraform来表示国家。关于国家安全的好观点。然而,我将状态存储在S3中,并使用kms密钥对其进行加密。任何时候我需要使用
ignore\u changes
通常都是一个大的危险信号,表明我做错了什么,或者Terraform不是适合这项工作的工具。事实上,在我相当大的Terraform代码库中,我仅有的两个地方是处理AWS提供程序中的几个错误。任何时候我需要使用
忽略更改
通常都是一个很大的危险信号,表明我做错了什么,或者Terraform不是这项工作的正确工具。事实上,在我相当大的Terraform代码库中,我只有两个地方可以忽略更改,那就是处理AWS提供程序中的几个错误。如果你在autoscaling group中处理
所需容量
,你肯定需要忽略更改。还有其他几个用例。