如何在Terraform代码中获取并使用Secret Manager中存储的密钥值
解决方法
场景1:AK/SK和Secret Manager资源都在当前Terraform栈中管理
你可以直接引用已有资源的属性值,无需额外拉取,以AWS云服务为例:
- 你原本创建AK/SK和存储Secret的示例代码如下:
# 创建IAM访问密钥 resource "aws_iam_access_key" "user_ak" { user = "你的IAM用户名" } # 创建Secret Manager密钥实体 resource "aws_secretsmanager_secret" "ak_sk_store" { name = "业务-ak-sk存储" } # 写入AK/SK到Secret Manager resource "aws_secretsmanager_secret_version" "ak_sk_content" { secret_id = aws_secretsmanager_secret.ak_sk_store.id # 这里用JSON格式存储两个密钥字段 secret_string = jsonencode({ access_key = aws_iam_access_key.user_ak.id secret_key = aws_iam_access_key.user_ak.secret }) }
- 直接在需要用到密钥的资源中取值即可,示例:
locals { # 先解析JSON格式的Secret内容,提取两个密钥字段 ak = jsondecode(aws_secretsmanager_secret_version.ak_sk_content.secret_string).access_key sk = jsondecode(aws_secretsmanager_secret_version.ak_sk_content.secret_string).secret_key } # 示例:将密钥写入云服务器的环境变量 resource "aws_instance" "app_server" { ami = "公共镜像ID" instance_type = "t2.micro" user_data = <<EOF export APP_ACCESS_KEY=${local.ak} export APP_SECRET_KEY=${local.sk} EOF }
场景2:Secret Manager中的密钥是预先创建的,不在当前Terraform栈管理
通过Terraform数据源拉取已有Secret的内容即可,示例:
- 声明Secret Manager数据源:
data "aws_secretsmanager_secret" "existing_ak_sk" { name = "你预先存储的Secret名称" } data "aws_secretsmanager_secret_version" "existing_ak_sk_content" { secret_id = data.aws_secretsmanager_secret.existing_ak_sk.id }
- 取值逻辑和场景1完全一致:
locals { ak = jsondecode(data.aws_secretsmanager_secret_version.existing_ak_sk_content.secret_string).access_key sk = jsondecode(data.aws_secretsmanager_secret_version.existing_ak_sk_content.secret_string).secret_key } # 后续任意资源都可以直接引用 local.ak 和 local.sk 使用
注意事项
- 如果你存储Secret时没有使用JSON格式,而是直接将密钥明文存为secret_string,无需执行jsondecode,直接引用secret_string属性即可
- 不要将密钥明文输出到terraform output中,如果必须输出,要给output加上
sensitive = true标记,避免日志泄露 - 运行terraform plan/apply的身份必须持有Secret Manager的Secret读取权限,否则会拉取失败
- 其他云厂商(阿里云、腾讯云、GCP等)的逻辑完全一致,只需替换对应云厂商的Secret Manager资源和数据源即可
内容的提问来源于stack exchange,提问作者abhsihek
相关产品推荐
相关产品推荐

