0
votes

Been brushing up using Terraform to manage resources in Azure the past week or so.
Great tool.
I've found there is a distinction between using an AZ user account vs service principal.

The goal is to create resources in Azure using a designated service principal and referencing it's secret that is stored within AZ key vault. Moving away from locally stored secret (file, env var, etc).

I can successfully create resources using an authenticated service principal as long as I have my azurerm provider containing the subid, clientid, clientsecret & tenantid, it works great.

Example of what works when I store service principal secret as a var sp_secret in variables.tf (or even works as env var):

provider "azurerm" {
 version = "=2.48.0"
 features { }
  subscription_id = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
  client_id       = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
  client_secret   = "${var.sp_secret}"
  tenant_id       = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
}

I have been able to successfully pull the service principals secret from the keyvault and 'output' it, but what I want to do is to pull that secret from kv and use, say as a var inside the provider client_secret value. ex. 'client_secret = "${link to secret sitting in kv}"'

Here is what I am doing to retrieve the SP secret from keyvault and output it:

data "azurerm_client_config" "current" {}

variable "keyvault_name" {
  default = "blah-kv"
}

variable "kvrg_name" {
  default = "blah-kv-rg"
}

data "azurerm_key_vault" "keyvault" {
  name                = "${var.keyvault_name}"
  resource_group_name = "${var.kvrg_name}"
}

data "azurerm_key_vault_secret" "kv-sp" {
  name         = "blah-tf-sp-secret"
  key_vault_id = "${data.azurerm_key_vault.keyvault.id}"
}

output "secret_value" {
  value = "${data.azurerm_key_vault_secret.kv-sp.value}"
}

As mentioned, the above snippet successfully retrieves and outputs the secret. I just want to, instead of output the secret, just set that secret as client_secret value in the azurerm provider reference.

I've tried many variations of client_secret = "${data.azurerm_key_vault_secret.kv-sp.value}", and I get the following error:

Error: Cycle: data.azurerm_key_vault.keyvault, provider["registry.terraform.io/hashicorp/azurerm"], data.azurerm_key_vault_secret.kv-sp

I interpret the above error to indicate a circular reference. I've tried a few things i've picked up in my searching for an answer, but no dice.

Any guidance is appreciated.
Thanks!

1
Any updates on this question? Does it solve your problem? If it works for you please accept it.Charles Xu

1 Answers

1
votes

As I know. it's impossible to achieve what you expect. When you use the Terraform to manage Azure resources, then you need to have an Azure account or service principle with enough permissions. If you use the service principle, it means you need to configure the provider azurerm with client id and client secret before running the Terraform code. But when you store the secret in the Azure Key Vault, then you need to run the code, and then you can get the secret. It causes cycle dependency.