Azure Terraform Error registering backup protection container for Azure Storage Account

316 views Asked by At

I am using Terraform to create Azure Recovery Services Vault for File Shares. But it keeps reporting error:

Error: registering backup protection container StorageContainer;storage;fer-bpcm-d-rsg-commonsa;xxxbpcmpcgl (Vault fer-bpcm-p-euwe-rvt-golden): backup.ProtectionContainersClient#Register: Failure responding to request: StatusCode=400 -- Original Error: autorest/azure: Service returned an error. Status=400 Code="BMSUserErrorContainerIsAssociatedWithAnotherVault" Message="Container is associated with another vault. Please select the right vault to proceed with the container operation."

  with module.recovery_services_vault.azurerm_backup_container_storage_account.protection_container["fer-bpcm-p-euwe-rvt-golden~xxxbpcmpcgl~data"],
  on ../modules/LandingZone/BPCM/recovery_services_vault/main.tf line 75, in resource "azurerm_backup_container_storage_account" "protection_container":
  75: resource "azurerm_backup_container_storage_account" "protection_container" {

The terraform snippet is as below:

resource "azurerm_recovery_services_vault" "fs_rsv_vaults" {

  for_each                      = { for fs_rsv_vault in var.fileshare_recovery_vaults : fs_rsv_vault.name => fs_rsv_vault }
  name                          = each.value.name
  resource_group_name           = each.value.resource_group_name
  location                      = each.value.location
  # sku, immutability, storage_mode_type, soft_delete_enabled
  # public_network_access_enabled, cross_region_restore_enabled, tags,identity 
}

resource "azurerm_backup_policy_file_share" "rsv_vault_policy" {
  for_each            = { for policy in local.rsv_vault_policy_list : "${policy.vault_name}~${policy.policy_name}" => policy }
  name                = each.value.policy_name
  resource_group_name = azurerm_recovery_services_vault.fs_rsv_vaults[each.value.vault_name].resource_group_name
  recovery_vault_name = azurerm_recovery_services_vault.fs_rsv_vaults[each.value.vault_name].name
  # timezone, backup, retention_daily
}

resource "azurerm_backup_container_storage_account" "protection_container" {
  for_each = { for fileshare in local.fileshare_list : "${fileshare.recovery_vault_name}~${fileshare.storage_account_name}~${fileshare.source_file_share_name}" => fileshare }
  resource_group_name = azurerm_recovery_services_vault.fs_rsv_vaults[each.value.recovery_vault_name].resource_group_name
  recovery_vault_name = each.value.recovery_vault_name
  storage_account_id  = data.azurerm_storage_account.storage_accounts[each.value.storage_account_name].id
}

I checked documetation But how to associate a unique protection container azurerm_backup_container_storage_account to each of the storage account since there is no name argument for protection container ? What is wrong I am doing?

I am passing list of Storage accounts like this:

fileshare_recovery_vaults = [
  {
    name = "myvault"
    resource_group_name = "rsg-backup" 
    ...
    backup_policies = [
      {
        policy_name = "policy-filesh"
        timezone = "UTC"
        backup_frequency = "Daily"
        backup_time = "00:00"
        retention_daily_count = 30
      }
    ]
    fileshares = [
      {
        storage_account_name = "xxxbpcmpcga"
        source_file_share_name = "data"
        resource_group_name = "rsg-commonsa"
        policy_name = "policy-filesh"
      },
      {
        storage_account_name = "xxxbpcmpcgl"
        source_file_share_name = "data"
        resource_group_name = "rsg-commonsa"
        policy_name = "policy-filesh"
      }
    ]
   ..
  }]
1

There are 1 answers

4
Vinay B On BEST ANSWER

I tried registering backup protection container for Azure Storage Account & File Shares I was able to provision the requirement successfully.

The error you're encountering, BMSUserErrorContainerIsAssociatedWithAnotherVault, indicates that the storage container you're trying to register with the Azure Recovery Services Vault is already associated with another vault. This is a common issue when reusing storage accounts or containers that were previously associated with a different vault.

when I tired to link the a new Recovery service vault with a storage container which was already associated with another vault I faced the same Issue which you mentioned.

enter image description here

In Azure, a storage account container can only be associated with one Recovery Services vault at a time. If you try to associate it with a new vault without first disassociating it from the existing one, you'll encounter this error

My Terraform configuration:

provider "azurerm" {
    features {}
}

data "azurerm_resource_group" "example" {
  name     = "demorg-vk"
}

resource "azurerm_recovery_services_vault" "example" {
  name                = "vksb-recovery-vault"
  location            = data.azurerm_resource_group.example.location
  resource_group_name = data.azurerm_resource_group.example.name
  sku                 = "Standard"
}

resource "azurerm_backup_policy_file_share" "example" {
  name                = "vksb-backup-policy"
  resource_group_name = data.azurerm_resource_group.example.name
  recovery_vault_name = azurerm_recovery_services_vault.example.name

  backup {
    frequency = "Daily"
    time      = "23:00"
  }

  retention_daily {
    count = 10
  }
}

# Create storage accounts
resource "azurerm_storage_account" "example" {
  for_each = { for sa in var.storage_accounts : sa.name => sa }

  name                     = each.value.name
  resource_group_name      = data.azurerm_resource_group.example.name
  location                 = data.azurerm_resource_group.example.location
  account_tier             = each.value.tier
  account_replication_type = each.value.replication_type
}

# Create file shares with explicit dependency on storage accounts
resource "azurerm_storage_share" "example" {
  for_each = { for fs in var.file_shares : fs.name => fs }

  name                 = each.value.name
  storage_account_name = azurerm_storage_account.example[each.value.storage_account_name].name
  quota                = each.value.quota

  depends_on = [azurerm_storage_account.example]
}

# Register the storage accounts with the Recovery Services Vault
resource "azurerm_backup_container_storage_account" "example" {
  for_each = { for sa in var.storage_accounts : sa.name => sa }

  resource_group_name = azurerm_recovery_services_vault.example.resource_group_name
  recovery_vault_name = azurerm_recovery_services_vault.example.name
  storage_account_id  = azurerm_storage_account.example[each.key].id
}

# Protect the file shares with explicit dependency on storage shares
resource "azurerm_backup_protected_file_share" "example" {
  for_each = { for fs in var.file_shares : fs.name => fs }

  resource_group_name       = azurerm_recovery_services_vault.example.resource_group_name
  recovery_vault_name       = azurerm_recovery_services_vault.example.name
  source_storage_account_id = azurerm_storage_account.example[each.value.storage_account_name].id
  source_file_share_name    = each.value.name
  backup_policy_id          = azurerm_backup_policy_file_share.example.id

  depends_on = [azurerm_storage_share.example]
}

variable.tf:

variable "storage_accounts" {
  description = "List of storage accounts to create"
  type = list(object({
    name             = string
    tier             = string
    replication_type = string
  }))
}

variable "file_shares" {
  description = "List of file shares to create"
  type = list(object({
    name                = string
    storage_account_name = string
    quota               = number
  }))
}

terraform.tfvars:

storage_accounts = [
  {
    name             = "vksbstgacct1"
    tier             = "Standard"
    replication_type = "LRS"
  },
  {
    name             = "vksbstgacct2"
    tier             = "Standard"
    replication_type = "LRS"
  }
]

file_shares = [
  {
    name                = "vksb-file-share1"
    storage_account_name = "vksbstgacct1"
    quota               = 50
  },
  {
    name                = "vksb-file-share2"
    storage_account_name = "vksbstgacct2"
    quota               = 50
  }
]

Output:

enter image description here

enter image description here

enter image description here