Terraform v0.12.23
provider.azurerm v2.21.0
azurerm_app_service_certificate
### --- Key Vault section
### Create Key Vault, set access policy to allow service principal to import the certificate and to save secrets
resource "azurerm_key_vault" "kv" {
name = local.kvName
location = data.azurerm_resource_group.rg.location
resource_group_name = data.azurerm_resource_group.rg.name
enabled_for_disk_encryption = false
tenant_id = data.azurerm_client_config.current.tenant_id
tags = var.tags
sku_name = "standard"
lifecycle {
ignore_changes = [
access_policy
]
}
access_policy {
tenant_id = data.azurerm_client_config.current.tenant_id
object_id = data.azurerm_client_config.current.object_id
secret_permissions = [
"get",
"delete",
"set"
]
### Give full control to the sevice principal as it might need to delete a certificate on the next update run
certificate_permissions = [
"create",
"delete",
"deleteissuers",
"get",
"getissuers",
"import",
"list",
"listissuers",
"managecontacts",
"manageissuers",
"setissuers",
"update",
]
}
depends_on = [azurerm_app_service.as]
}
### Upload certificate to Key vault
resource "azurerm_key_vault_certificate" "kvCertificate" {
name = "certificate-name"
key_vault_id = azurerm_key_vault.kv.id
certificate {
contents = filebase64("${var.Config.certificateFilename}")
password = var.ConfigCertificatePassword
}
certificate_policy {
issuer_parameters {
name = var.Config.certificateIssuer
}
key_properties {
exportable = true
key_size = 2048
key_type = "RSA"
reuse_key = false
}
secret_properties {
content_type = "application/x-pkcs12"
}
}
depends_on = [azurerm_key_vault.kv, azurerm_app_service.as]
}
### Assign get certificate permissions to the app service so the app service can access it (real issue here, get permission is not enough)
resource "azurerm_key_vault_access_policy" "kvPolicy" {
key_vault_id = azurerm_key_vault.kv.id
tenant_id = data.azurerm_client_config.current.tenant_id
object_id = azurerm_app_service.as.identity.0.principal_id
secret_permissions = [
"get",
]
certificate_permissions = [
"get",
"list"
]
depends_on = [azurerm_key_vault_certificate.kvCertificate, azurerm_app_service.as]
}
### reference the certificate in the app service (problem here: throws error)
resource "azurerm_app_service_certificate" "asCertificateReference" {
name = "certificate-name"
location = data.azurerm_resource_group.rg.location
resource_group_name = data.azurerm_resource_group.rg.name
key_vault_secret_id = azurerm_key_vault_certificate.kvCertificate.secret_id
depends_on = [azurerm_key_vault_access_policy.kvPolicy, azurerm_app_service.as]
}
The app service certificate is created successfully.
Error: [0m[0m[1mError creating/updating App Service Certificate "certificate-name" (Resource Group "website-dev-we"): web.CertificatesClient#CreateOrUpdate: Failure responding to request: StatusCode=400 -- Original Error: autorest/azure: Service returned an error. Status=400 Code="BadRequest" Message="**The service does not have access to '/subscriptions/4abasa3d-037f-463b-b913-aadf51843526/resourcegroups/website-dev-we/providers/microsoft.keyvault/vaults/kv-dev-we' Key Vault. Please make sure that you have granted necessary permissions to the service to perform the request operation.**" Details=[{"Message":"The service does not have access to '/subscriptions/4abasa3d-037f-463b-b913-aadf51843526/resourcegroups/website-dev-we/providers/microsoft.keyvault/vaults/kv-dev-we' Key Vault. Please make sure that you have granted necessary permissions to the service to perform the request operation."},{"Code":"BadRequest"},{"ErrorEntity":{"Code":"BadRequest","ExtendedCode":"59716","Message":"The service does not have access to '/subscriptions/4abasa3d-037f-463b-b913-aadf51843526/resourcegroups/website-dev-we/providers/microsoft.keyvault/vaults/kv-dev-we' Key Vault. Please make sure that you have granted necessary permissions to the service to perform the request operation.","MessageTemplate":"The service does not have access to '{0}' Key Vault. Please make sure that you have granted necessary permissions to the service to perform the request operation.","Parameters":["/subscriptions/4abasa3d-037f-463b-b913-aadf51843526/resourcegroups/website-dev-we/providers/microsoft.keyvault/vaults/kv-dev-we"]}}][0m
2020-10-05T12:59:37.9602725Z
start by creating a simple app service, then add the rest.
terraform applyNo. standard account and region. Deployment is running on devops using a terraform task.
I've seen a similar complaint here:
https://github.com/terraform-providers/terraform-provider-azurerm/issues/5058
But the reason does not seem to be the same. My access policies are correct. and i have followed the instructions here:
https://www.terraform.io/docs/providers/azurerm/r/app_service_certificate.html
I have browsed a bit and see that this seems to be an issue with the permissions. apparently binding the policy requires a write permission, which does not exist on this resource?
references:
https://stackoverflow.com/questions/60160688/configuring-an-app-service-certificate-seems-to-require-write-access-to-the-key
https://nexxai.dev/using-a-certificate-stored-in-key-vault-in-an-azure-app-service/
hi guys. still waiting on a reply. I don't think this is a question, more of a report on a limitation of the azurerm_app_service_certificate and azurerm_key_vault_access_policy resources. as it is right now, the key vault access policy is not sufficient to work with azurerm_app_service_certificate. it seems to be unusable/doesn't serve its purpose. thank you for your time!
Last comment in #5058 helped me:
https://github.com/terraform-providers/terraform-provider-azurerm/issues/5058#issuecomment-585254067
looks like Azure API creating certificate binding actually uses "Microsoft Azure AppService" built-in ServicePrincipal with Application ID "abfa0a7c-a6b6-4736-8310-5855508787cd" (ObjectID for it is tenant-specific), not under the service principal actually used for core terraform script execution.
so you need to give Get permissions on KV policies both to SP executing the script, and for the built-in "Microsoft Azure AppService" SP
hi @ruifrvaz
Thanks for opening this issue - apologies for the delayed response here!
Taking a look through here this appears to be an issue with the Terraform Configuration - notably Key Vault Access Policies can either be defined inline, or using the separate resource - but can't be through both (as is called out in the documentation) since otherwise these will conflict. As @mkusmiy has mentioned the Service Principal the Azure API is using to retrieve this certificate appears different than the one used by it's Managed Identity - as such I'd recommend updating that as proposed above.
Since this should be fixed by updating the Terraform Configuration being used here, I'm going to close this issue for the moment - but should you have further questions I'd suggest opening an issue in the Community Forums where someone should be able to assist further.
Thanks!
Most helpful comment
hi guys. still waiting on a reply. I don't think this is a question, more of a report on a limitation of the azurerm_app_service_certificate and azurerm_key_vault_access_policy resources. as it is right now, the key vault access policy is not sufficient to work with azurerm_app_service_certificate. it seems to be unusable/doesn't serve its purpose. thank you for your time!