Search code examples
terraformaws-secrets-manager

Error when trying to pass aws_secretsmanager_secret_version value


Under PASSWORD section of RDS AWS creation, I am trying to pass aws_secretsmanager_secret_version value. I am getting below error.

resource "aws_db_instance" "airflow" {
  allocated_storage                   = "${var.rds_allocated_storage}"
  storage_type                        = "${var.rds_storage_type}"
  storage_encrypted                   = "true"
  engine                              = "mysql"
  engine_version                      = "${var.rds_engine_version}"
  instance_class                      = "${var.rds_instance_class}"
  name                                = "airflow"
  identifier                          = "airflow"
  username                            = "${var.rds_username}"
  password                            = "${jsondecode(aws_secretsmanager_secret_version.secret.secret_string)["rds_password"]}"
  parameter_group_name                = "-airflow-mysql"
  vpc_security_group_ids              = ["${aws_security_group_airflow_sg.id}"]
  db_subnet_group_name                = "${aws_db_subnet_group.airflow_rds.id}"
  kms_key_id                          = "${data.aws_kms_key.rds.arn}"
  license_model                       = "general-public-license"

  depends_on = [
    aws_db_parameter_group.airflow_mysql
  ]

  tags = merge(
    var.common_tags,
    map("Classification", "private"),
    map("Name", "-airflow-rds")
  )
}

secretmanager.tf

resource "aws_secretsmanager_secret" "secret" {
  description         = "airflow"
  kms_key_id          = "${data.aws_kms_key.sm.arn}"
  name                = "airflow"
}
resource "random_string" "rds_password" {
  length = 16
  special = true
  override_special = "/@\" "
}


resource "aws_secretsmanager_secret_version" "secret" {
  secret_id     = "${aws_secretsmanager_secret.secret.id}"
  secret_string = <<EOF
{
  "rds_password": "${random_string.rds_password.result}"
  }
EOF
}

Below is the error logs:-

Error: Error in function call

on ../../modules/airflow/outputs.tf line 27, in output "rds_password": 27: value = jsondecode(aws_secretsmanager_secret_version.secret.secret_string)["rds_password"] |---------------- | aws_secretsmanager_secret_version.secret.secret_string is "{\n \"rds_password\": \"9Y\"@xu3jy@sNGXt/\"\n }\n"

Call to function "jsondecode" failed: invalid character '@' after object key:value pair.

Error: Error in function call

on ../../modules/airflow/rds.tf line 12, in resource "aws_db_instance" "airflow": 12: password = "${jsondecode(aws_secretsmanager_secret_version.secret.secret_string)["rds_password"]}" |---------------- | aws_secretsmanager_secret_version.secret.secret_string is "{\n \"rds_password\": \"9Y\"@xu3jy@sNGXt/\"\n }\n"

Call to function "jsondecode" failed: invalid character '@' after object key:value pair.


Solution

  • As you can see in Terraform documentation the key-val objects in secret_string should be injected with jsonencode().

    Look at the below example (adapted from the doc page):

    # The map here can come from other supported configurations
    # like locals, resource attribute, map() built-in, etc.
    variable "example" {
      default = {
        #HERE YOU DEFINE YOUR MAP
        rds_password= "${random_string.rds_password.result}"
    
      }
    
      type = "map"
    }
    
    resource "aws_secretsmanager_secret_version" "example" {
      secret_id     = "${aws_secretsmanager_secret.example.id}"
      # HERE YOU INJECT THE KEY/VAL
      secret_string = "${jsonencode(var.example)}"
    }