Azure Policy
Azure Policy evaluates every resource against rules and can deny, audit, change or deploy in response. The Azure Enterprise Baseline assigns its preventive guardrails and its compliance initiatives at mg-acme, the top of its management-group tree, so they hold in all 14 subscriptions and no subscription Owner can remove them.
What it does
A policy definition is a rule (an if condition on resource properties) with an effect: Deny refuses the request, Audit and AuditIfNotExists record non-compliance, DenyAction blocks one action such as delete, Modify adds or changes properties such as tags, and DeployIfNotExists deploys a missing companion resource. An initiative (policy set) groups definitions and passes them parameters. An assignment applies a definition or initiative at a scope; its enforce setting can be DoNotEnforce, in which effects are evaluated and reported but never applied. An exemption waives a scope from an assignment, and assignments that modify or deploy need a managed identity for remediation. Evaluation is free.
How BuiltForProd uses it
Guardrails. The organizations unit defines four custom initiatives at mg-acme and assigns them there with enforce = true. Built-in definitions are looked up by display name, so no definition GUID appears in code, and assignment names stay within the 24 characters a management-group assignment allows.
| Assignment | Initiative | Contents |
|---|---|---|
acme-sec-guard | acme-security-guardrails | Deny: storage shared-key access, public blob access, insecure transfer, Transport Layer Security (TLS) below 1.2, public IPs on network interfaces, Key Vault without soft delete or purge protection. Audit: open virtual machine management ports, Key Vault public network access, Azure Kubernetes Service clusters without HTTPS. Custom deny of role assignments to individual users |
acme-regions | acme-region-restriction | Deny resources and resource groups outside the allowed locations; audit a resource whose location differs from its group |
acme-audit-prot | acme-audit-protection | DenyAction on deleting diagnostic settings, and on deleting the audit workspace and audit storage (tag Purpose = audit), including through a resource-group delete |
acme-tags | acme-tag-policy | Namespace, Environment, Stage, ManagedBy and Repository must carry an allowed value (Audit; enforce_tag_policy = true makes it Deny); Modify copies each tag from the resource group when a resource lacks it |
The allowed locations are derived, not typed: the home region, every region folder under environments/, and global. acme-core-public holds the one exemption, acme-allow-public-blobs, from the public-blob rule only. The audit-protection effect is a parameter whose only other value is Disabled.
Compliance initiatives. The policy-compliance unit assigns the frameworks switched in security.hcl:
# Azure Policy compliance initiatives assigned at mg-<ns> (Audit mode). mcsb and soc2_baseline are on.
compliance_initiatives = { # @optional: one switch per built-in initiative (free)
mcsb = true # Microsoft cloud security benchmark
soc2_baseline = true # BuiltForProd-soc2-baseline (custom, 13 controls)
cis_azure_v3 = false # CIS Microsoft Azure Foundations Benchmark v3.0.0
nist_800_53_r5 = false # NIST SP 800-53 Rev. 5
nist_800_171_r2 = false # NIST SP 800-171 Rev. 2
pci_dss_v4 = false # PCI DSS v4.0
hipaa_hitrust = false # HIPAA HITRUST 9.2
soc2_type2 = false # SOC 2 Type 2 (built-in)
iso_27001 = false # ISO 27001:2013
cmmc_l2 = false # CMMC Level 2
fedramp_moderate = false # FedRAMP Moderate
}
BuiltForProd-soc2-baseline is a custom initiative of 13 SOC 2 controls built from built-in definitions and two custom ones (no role assignments to users, and acme-audit-storage-cmk, which requires a customer-managed key on storage tagged Purpose = audit). It is assigned as acme-soc2-base; every control's effect is a parameter, Audit by default, and soc2_control_effects can switch one to Deny or Disabled. The built-in frameworks, the Microsoft cloud security benchmark among them, are assigned in DoNotEnforce, so their DeployIfNotExists and Modify policies report without acting. acme-plat-sandbox is waived from every compliance assignment.
Backstop. acme-actlog-dine assigns the built-in DeployIfNotExists policy that streams a subscription's Activity Log to the audit workspace, in DoNotEnforce: it flags any subscription that lacks the setting the subscription baseline creates.
Results appear under Policy compliance and in Microsoft Defender for Cloud regulatory compliance. Under CODEOWNERS, a change to security.hcl needs the infra admins and the security team, and a change to the modules the infra admins and the platform leads.
Terms you will see
| Term | Meaning |
|---|---|
| Initiative | A set of policy definitions assigned and reported together. |
| Effect | What a policy does on a match: Deny, Audit, DenyAction, Modify, DeployIfNotExists. |
| DenyAction | An effect that blocks one action, here delete, on matching resources. |
| DoNotEnforce | An assignment mode that evaluates and reports but applies no effect. |
| Exemption | A waiver of one scope from an assignment or from one of its definitions. |
| Remediation | Applying a Modify or DeployIfNotExists effect to existing resources, with the assignment's identity. |
Where to read more
- Azure Enterprise Baseline overview for the guardrails in context.
- Management groups for the scope every assignment uses.
- Policy as code for why guardrails live in the repository.