Somewhere in your subscription there is a storage account with anonymous blob access still enabled, or shared-key auth on, or no SAS expiration policy, or a firewall that allows every network. You just do not know which one. Storage misconfigurations like these are a top source of Azure data exposure, and the settings that matter are scattered across seven different blades on each individual account. There is no simple recurring "how are my storage accounts configured?" report, so the misconfigured account sits there until someone stumbles on it (or someone outside your organization does first).
Why Azure cannot tell you this out of the box
- The portal shows one account at a time. Anonymous access, TLS version, shared-key auth, SAS policy, and network rules each live on their own blade, per account. Reviewing fifty accounts by hand means hundreds of clicks, and the answer is stale the moment you finish.
- Azure Policy can audit individual settings, but you assemble it yourself. You have to pick and assign the right policy definitions one by one, and the result is a compliance blade you must remember to go look at. Nothing arrives in your team channel on a schedule.
- There is no score. Native tooling gives you per-setting pass/fail lists, not a single graded view that says "these three accounts are your worst offenders, and here is the systemic gap across the whole estate."
The DIY approach: query the config, score it, schedule it
Every setting that matters is management-plane configuration, readable with nothing more than the Reader role. Azure Resource Graph exposes them all in one query:
- Query
microsoft.storage/storageaccountsand projectallowBlobPublicAccess,supportsHttpsTrafficOnly,minimumTlsVersion,allowSharedKeyAccess,sasPolicy,networkAcls.defaultAction, andpublicNetworkAccess. - Watch the nulls: on several of these properties a missing value means the default applies (for example, shared-key auth is enabled unless explicitly disabled), so treat null as the insecure setting where the default is permissive.
- Weight the checks (anonymous blob access enabled should hurt the score far more than a missing SAS policy) and compute a per-account grade.
- Run it on a scheduled Function or Automation runbook and post the result to Teams: in Teams, create a webhook via Workflows → "Post to a channel when a webhook request is received" and send the report there.
The pieces are all standard; the work is in maintaining the check list, the weighting, the null-handling, and the report format as your estate grows.
A ready-made option: Storage Hygiene Scorecard
Storage Hygiene Scorecard is that pattern packaged. Every day it reads each storage account's configuration and grades it against seven weighted checks: anonymous blob access disabled, HTTPS-only traffic, minimum TLS 1.2, shared-key auth disabled (Entra-only), SAS expiration policy set, network default action Deny, and public network access restricted. The scorecard lands in your Teams channel as an Adaptive Card with the average hygiene score, the accounts below your threshold with their specific gaps, and the most common systemic gaps across the estate. It reads management-plane configuration only (never account keys, never your data) and needs just the Reader role at subscription scope.
Key facts
- Native recurring storage-config report: none; the portal is per-account, Azure Policy is assemble-it-yourself and pull, not push.
- The seven settings that matter: anonymous blob access, HTTPS-only, minimum TLS version, shared-key auth, SAS expiration policy, network default action, public network access.
- All management-plane: readable with the Reader role alone; no keys, no data access needed.
- Null means default: several properties are permissive when unset, so a naive query that skips nulls will miss real exposure.
Related reading: time-boxed Azure role elevation without paying for PIM.
Written by the team at Katabarwa Labs. We build small, single-purpose Azure tools that run entirely inside your own tenant. Questions: abaho@llmgraph.ai.