Symptoms
- A key or SAS URL was found in a Git repository, a ticket, a public paste or a log.
- Unexpected egress, listing or deletes in storage logs from unknown IPs.
- Defender for Storage alerts such as access from a suspicious IP or unusual data extraction.
1. Identify what leaked
| Leaked | Signed by | How to revoke |
|---|---|---|
| Account key | — | Rotate that key |
| Account or service SAS | An account key | Rotate the key that signed it |
| Service SAS with stored access policy | Account key + policy | Delete or change the policy |
| User delegation SAS | Entra ID user delegation key | Revoke user delegation keys |
| Connection string | Contains an account key | Rotate that key |
2. Find who uses each key before rotating
Rotating a key in use breaks those apps. Check Key Vault references, app settings and pipeline variables for the key or connection string. Prefer to switch consumers to the other key first, then rotate the leaked one.
az storage account keys list -g rg-data -n stproddata -o table
3. Rotate
# Leaked key1: move apps to key2 first, then
az storage account keys renew -g rg-data -n stproddata --key primary
# If you can't tell which key signed a SAS, rotate both — one at a time, updating apps in between
az storage account keys renew -g rg-data -n stproddata --key secondary
User delegation SAS:
az storage account revoke-delegation-keys -g rg-data -n stproddata
Stored access policy:
az storage container policy delete --account-name stproddata -c exports -n partner-read --auth-mode key
Caution
In a confirmed compromise, availability comes second. If you cannot find all consumers quickly, rotate both keys and fix the apps that break.
4. Check what was accessed
StorageBlobLogs
| where TimeGenerated > ago(7d)
| where AuthenticationType in ("AccountKey", "SAS")
| summarize ops = count(), bytes = sum(ResponseBodySize) by CallerIpAddress, OperationName, AuthenticationType
| order by bytes desc
Compare caller IPs with your known app egress. Large GetBlob volume from an unknown IP means data was taken; involve your security and data protection teams.
5. Lock it down
az storage account update -g rg-data -n stproddata --allow-shared-key-access false
az storage account update -g rg-data -n stproddata --public-network-access Disabled
Disabling shared key access breaks anything still using keys or account SAS. Do it after apps move to managed identity with Storage Blob Data Reader/Contributor roles.
Prevent it next time
- Use managed identities and user delegation SAS; disable shared key access.
- Set a SAS expiration policy on the account and a key rotation reminder.
- Run secret scanning on repositories and pipelines.
- Turn on Defender for Storage on accounts that hold sensitive data.