Search code examples
azureterraformterraform-provider-azure

Migrating Azure Key Vault secrets from one Azure subscription to another


I have multiple Azure subscriptions, and I'm working on getting the key vault from one to another. I've written a terraform program to do this. Here I'm calling the data blocks and using for each loop condition from one subscription and using the output value of those as input values in another subscription. But I'm getting the error please help. Below is the code

data "azurerm_key_vault" "ewo1" {
  provider            = azurerm.demo-eworx-terraform-automation
  name                = "demo-eworx-keyvault"
  resource_group_name = "demo-eworx-rg"
}

output "vault_uri_ewo1" {
  value = data.azurerm_key_vault.ewo1.vault_uri
}

data "azurerm_key_vault_secret" "ewo1" {
  provider     = azurerm.demo-eworx-terraform-automation
  for_each = toset(["demo-eworx-terraform-automation-client-secret", "demo-eworx-terraform-automation-client-id", "demo-eworx-terraform-automation-tenant-id", "demo-eworx-terraform-automation-subscription-id"])
  name         = each.key
  key_vault_id = data.azurerm_key_vault.ewo1.id
}

output "secret_value" {
  value     = [ for secret in data.azurerm_key_vault_secret.ewo1  : secret.name]
}

data "azurerm_key_vault" "ewo11" {
  provider = azurerm.terraform-automation
  name                = "demo-bteb-keyvault"
  resource_group_name = "bteb-demo-work"
}

output "vault_uri_ewo11" {
  value = data.azurerm_key_vault.ewo11.vault_uri
}

resource "azurerm_key_vault_secret" "ewo11" {
  provider = azurerm.terraform-automation
  for_each = toset(["demo-eworx-terraform-automation-client-secret", "demo-eworx-terraform-automation-client-id", "demo-eworx-terraform-automation-tenant-id", "demo-eworx-terraform-automation-subscription-id"])
  name         = each.key
  value        = [ for secret in data.azurerm_key_vault_secret.ewo1  : secret.name]
  key_vault_id = data.azurerm_key_vault.ewo11.id
}

I need to migrate azure key vaults secrets from one subscription to another subscription. I have written the above terraform code, I'm passing the data "azurerm_key_vault" "ewo1" output value as resource "azurerm_key_vault_secret" "ewo11" value input. But getting below error.

Can some check and help me in solving the issue

error message:

Error: Incorrect attribute value type │ │ on demo-keyvault-migration.tf line 38, in resource "azurerm_key_vault_secret" "ewo11": │ 38: value = [ for secret in data.azurerm_key_vault_secret.ewo1 : secret.name] │ ├──────────────── │ │ data.azurerm_key_vault_secret.ewo1 is object with 4 attributes │ │ Inappropriate value for attribute "value": string required. ╵ ╷ │ Error: Incorrect attribute value type │ │ on demo-keyvault-migration.tf line 38, in resource "azurerm_key_vault_secret" "ewo11": │ 38: value = [ for secret in data.azurerm_key_vault_secret.ewo1 : secret.name] │ ├──────────────── │ │ data.azurerm_key_vault_secret.ewo1 is object with 4 attributes │ │ Inappropriate value for attribute "value": string required. ╵ ╷ │ Error: Incorrect attribute value type │ │ on demo-keyvault-migration.tf line 38, in resource "azurerm_key_vault_secret" "ewo11": │ 38: value = [ for secret in data.azurerm_key_vault_secret.ewo1 : secret.name] │ ├──────────────── │ │ data.azurerm_key_vault_secret.ewo1 is object with 4 attributes │ │ Inappropriate value for attribute "value": string required. ╵ ╷ │ Error: Incorrect attribute value type │ │ on demo-keyvault-migration.tf line 38, in resource "azurerm_key_vault_secret" "ewo11": │ 38: value = [ for secret in data.azurerm_key_vault_secret.ewo1 : secret.name] │ ├──────────────── │ │ data.azurerm_key_vault_secret.ewo1 is object with 4 attributes │ ╵


Solution

  • There are a couple of issues here, but the primary one is related to the azurerm_key_vault_secret data source. You are querying the data source while using for_each. That means that the result will be an object with key value pairs. That is why you are getting this in the output:

    data.azurerm_key_vault_secret.ewo1 is object with 4 attributes

    as in for_each you will use four keys:

    for_each = toset(["demo-eworx-terraform-automation-client-secret", "demo-eworx-terraform-automation-client-id", "demo-eworx-terraform-automation-tenant-id", "demo-eworx-terraform-automation-subscription-id"])
    

    The easiest and probably the cleanest way to fix the error is as follows:

    resource "azurerm_key_vault_secret" "ewo11" {
      provider     = azurerm.terraform-automation
      for_each     = data.azurerm_key_vault_secret.ewo1
      name         = each.key
      value        = each.value.value
      key_vault_id = data.azurerm_key_vault.ewo11.id
    }
    

    Here it is a bit unfortunate that each.value.value [1] has to be used due to the attribute naming, but there is not another way. Also, please make sure you understand how the for_each meta-argument [2] works.


    [1] https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/data-sources/key_vault_secret#value

    [2] https://developer.hashicorp.com/terraform/language/meta-arguments/for_each