Microsoft Defender for Cloud · Azure App Service
Managed identity should be used in web apps
Written and reviewed by Emnode · Last reviewed
What does the recommendation "Managed identity should be used in web apps" check?
Audits each App Service web app (resource type Microsoft.Web/sites) and flags any that has no managed identity configured, meaning the 'identity' block is absent or set to None. A system-assigned or user-assigned identity both satisfy the check. It looks only at whether an identity exists on the app, not at what that identity can access: it does not verify that the identity holds sensible role assignments, and it does not check that your code actually authenticates with it. Function apps are covered by a separate recommendation, so this control is scoped to web apps alone.
Why does "Managed identity should be used in web apps" matter?
Without a managed identity, a web app reaches Key Vault, Storage, SQL or any other Azure service using a secret you put there yourself: a connection string, an access key or a client secret sitting in app settings or, worse, in source control. Those secrets get copied into logs, shared in tickets and forgotten at rotation time, and a single leaked key hands an attacker the same reach as the app. A managed identity replaces the secret with a token Azure issues and rotates automatically, so there is no credential to steal, expire or rotate by hand. The business consequence of skipping it is a wider breach radius and a slow, error-prone credential rotation every time someone leaves or a key is exposed.
How do I fix "Managed identity should be used in web apps"?
- Enable a system-assigned identity on the app: in the portal open the web app, go to Settings then Identity, and on the System assigned tab switch Status to On and Save. Or run: az webapp identity assign --resource-group <rg> --name <app-name>
- Grant that identity only the access it needs, for example a single Key Vault: az role assignment create --assignee-object-id <identity-principal-id> --assignee-principal-type ServicePrincipal --role 'Key Vault Secrets User' --scope <key-vault-resource-id>. Then rewrite the app to fetch secrets with the identity (DefaultAzureCredential) and delete the old keys from app settings.
- Bake it into infrastructure by setting identity: { type: 'SystemAssigned' } on the Microsoft.Web/sites resource in Bicep so new apps ship with an identity by default. To enforce it across the estate, assign the built-in policy by display name rather than a hardcoded GUID: pid=$(az policy definition list --query "[?displayName=='App Service apps should use managed identity'].name" -o tsv); az policy assignment create --name require-webapp-mi --policy "$pid" --scope <subscription-or-mg-scope>
Remediation script · bash
# 1. Give the app its own identity and capture the principal ID.
principalId=$(az webapp identity assign \
--resource-group payments-rg \
--name payments-api-prod \
--query principalId -o tsv)
# 2. Grant least privilege on the exact resource it uses (not the subscription).
az role assignment create \
--assignee-object-id "$principalId" \
--assignee-principal-type ServicePrincipal \
--role "Storage Blob Data Contributor" \
--scope "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/payments-rg/providers/Microsoft.Storage/storageAccounts/paymentsdata"
# 3. Only after the code uses DefaultAzureCredential and the new path is verified,
# delete the stored secret so there is nothing left to leak.
az webapp config appsettings delete \
--resource-group payments-rg --name payments-api-prod \
--setting-names StorageConnectionString
# 4. Ratchet it shut: audit any future app created without a managed identity.
az policy assignment create \
--name audit-webapp-managed-identity \
--policy 2b9ad585-36bc-4615-b300-fd4435808332 \
--scope "/subscriptions/00000000-0000-0000-0000-000000000000" Full walkthrough (console steps, edge cases and verification) in the lesson Use managed identities instead of stored secrets.
Is "Managed identity should be used in web apps" a false positive?
A web app that holds no secrets and never calls another Azure service, for example a purely static marketing site or a self-contained demo, has nothing for an identity to authenticate to, so enabling one adds an unused principal without reducing any real risk. Suppress the finding for those apps with a documented exemption rather than provisioning an identity that grants access to nothing.
More Azure App Service controls
- API App should only be accessible over HTTPS
- CORS should not allow every resource to access API Apps
- CORS should not allow every resource to access Web Applications
- Ensure API app has Client Certificates Incoming client certificates set to On
- FTPS should be required in API apps
- FTPS should be required in web apps
- Java should be updated to the latest version for API apps
- Managed identity should be used in API apps
- Microsoft Defender for App Service should be enabled
- PHP should be updated to the latest version for API apps
- Python should be updated to the latest version for API apps
- Remote debugging should be turned off for API App