Azure:使用Terraform管理时服务主体的最佳实践及使用困惑
Great question—this is a super common dilemma when scaling Terraform workflows in Azure teams! Let’s break down the pros/cons of each approach, then tackle that Key Vault access problem you’re facing.
Option 1: Shared Single Service Principal
- Pros: Super simple to set up. You create one SP, grant it the necessary Azure RBAC permissions, and share its credentials with the team. No need to manage multiple identities, and permissions are centralized.
- Cons: Big audit blind spot—you can’t trace which team member ran a specific Terraform apply/destroy. If the SP’s secret is compromised, the entire team’s infrastructure is at risk. Rotating the secret also means updating credentials for everyone at once, which is a hassle.
Option 2: Individual Service Principals per User
- Pros: Perfect for accountability—every Terraform action is tied to a specific user’s SP, making audits straightforward. If one user’s SP credentials leak, only their access is affected (not the whole team). You can also grant granular permissions to each SP (e.g., a junior dev only gets read access to production resources).
- Cons: Higher management overhead—you need to create and maintain an SP for every team member. And as you noticed, default Key Vault behavior causes access issues: when an SP creates a Key Vault, Azure automatically grants that SP exclusive access, locking out other team members’ SPs.
Fixing the Key Vault Access Problem
The solution here is to stop relying on the default creator permissions and explicitly define Key Vault access policies in your Terraform code. This way, no matter which SP runs the deployment, the access policy is standardized for the entire team.
Here’s how to do it:
- Create an Azure AD group and add all your team’s Terraform SPs to it (this makes permission management way easier than adding individual SPs).
- In your Terraform Key Vault configuration, use the
access_policyblock (either inline inazurerm_key_vaultor as a separateazurerm_key_vault_access_policyresource) to grant the AD group the necessary permissions. For example:
resource "azurerm_key_vault" "example" { name = "example-keyvault" location = azurerm_resource_group.example.location resource_group_name = azurerm_resource_group.example.name tenant_id = data.azurerm_client_config.current.tenant_id soft_delete_retention_days = 7 purge_protection_enabled = true access_policy { tenant_id = data.azurerm_client_config.current.tenant_id object_id = data.azuread_group.terraform_team.id # ID of your AD group key_permissions = [ "Get", "List", ] secret_permissions = [ "Get", "List", ] } }
This ensures every SP in the group gets consistent access to the Key Vault, regardless of who created it.
Recommended Best Practice
For most teams, individual SPs + Azure AD group-based permissions is the sweet spot:
- You keep the auditability of individual identities.
- You simplify permission management by grouping SPs into an AD group.
- You eliminate Key Vault access issues by codifying access policies in Terraform.
Bonus tips:
- Use certificate-based authentication for SPs instead of secrets—it’s more secure and easier to rotate.
- Follow the principle of least privilege: only grant SPs the minimum permissions they need to run Terraform (e.g., avoid giving Contributor access to all resources; use more granular roles like
Virtual Machine Contributorif that’s all they need). - Automate SP creation/rotation with tools like Azure CLI scripts or Azure DevOps pipelines to reduce manual overhead.
内容的提问来源于stack exchange,提问作者Hafiz

