Key Vault: Why You Should Migrate Off Access Policies This Quarter
Key Vault's access policy model is legacy. RBAC is the path forward. The migration is small, and the security upside is large.
Key Vault has two permission models, and one of them is on its way out. If you're still on access policies, this quarter is the right time to switch.
Access policies (legacy)
- Up to 1,024 entries per vault.
- Permissions are vault-scoped, not Azure-RBAC-aware.
- Cannot be assigned via management groups.
- No conditional access integration.
- No PIM (Privileged Identity Management) eligibility/just-in-time.
Azure RBAC (current model)
- Built-in roles:
Key Vault Reader,Key Vault Secrets User,Key Vault Crypto Officer, etc. - Inheritable from MG → subscription → RG → vault.
- Works with PIM. You can require approval-with-justification to read prod secrets.
- Conditional Access compatible. "Read prod secrets only from compliant devices."
- Audit log entries are richer.
Pick the smallest role you can
| Need | Role |
|---|---|
| App reads secrets at runtime | Key Vault Secrets User |
| Operator manages secret values | Key Vault Secrets Officer |
| Crypto operations on keys | Key Vault Crypto User or Officer |
| Read certs for TLS | Key Vault Certificates Officer |
| Read everything | Key Vault Reader (data plane: names only, not values) |
Granting Owner on the vault to an app identity is the most common
overprovisioning I see. There is almost never a reason for it.
Migration in three steps
az keyvault update --name kv-... --enable-rbac-authorization true- For each existing access-policy entry, find the equivalent RBAC role and assign it at vault scope.
- Remove the old access policy after the app has been validated reading secrets via RBAC.
Network-layer defense (don't skip)
RBAC controls who can ask. Private endpoints + firewall control where they can ask from. A KV with public access enabled is a KV waiting for an incident. Pin to private endpoint + selected VNets + your bastion's IP.