Govern Azure Virtual Network (VNet) CIDR Ranges with Azure Policy

With everything becoming more cloudified, things can get a little more complicated. That is especially so for networking, even more so if you’re using hybrid networking and connecting your cloud networks to your on-premises networks, either through Site-to-Site (S2S) VPN, or ExpressRoute.

If you’re responsible for the network, you want to maintain control.


I had a former colleague present the following scenario to me:

I am trying to prevent VNet Address space creation only to certain scopes. I am trying to write Azure JSON policy but no luck. Do you have by any chance Azure Policy to allow the creation of VNets only on certain Address Spaces?

Let’s dig in!


First, we need to look at what is exposed, and the properties available for a VNet. The easiest way to do this is by looking at an existing VNet and using the ‘Export template’ option in the Azure portal. This allows us to see the ARM code that creates the VNet.

Notice in the code below, that we have a resource called “Microsoft.Network/virtualNetworks” with a property of “addressSpace” and a sub-property of “addressPrefixes”. Also notice that it has the square brackets [ ], this means it’s an array and can accept multiple inputs.

Azure VNet ARM Code

ARG for Aliases

Now that we know what we want to target, we need to confirm that ARM will expose that element’s properties to allow us to write a policy against it. The simplest way I’ve found to do this is by using the Azure Resource Graph (ARG) to query for aliases. You can find some examples in the Azure Policy Aliases documentation.

Using Azure Cloud Shell, and the CLI query example, we can write something like this:

az graph query -q “Resources | where type=~’Microsoft.Network/virtualNetworks’ | limit 1 | project aliases”

In the output we something like the following:

Azure Resource Graph – VNet Aliases

Among all the other aliases that are listed, notice the one that I’ve highlighted. This tells us how to properly reference the properties we want to write the policy against.


Now that we know we need to use the “Microsoft.Network/virtualNetworks/addressSpace.addressPrefixes” reference, we can create our policy against it.

In my policy example, we are filtering against the VirtualNetworks resource type, and then checking the AddressPrefixes against a parameter we’re passing. Notice that we evaluate it with an “in” designation. This is because we know the AddressPrefixes can accept more than one input, and so the parameter is actually an ‘array’ type.

Azure Policy – Deny VNet Address Space


Now that we have our policy created, when we apply it, we need to provide the CIDR to audit (or in this case deny) against.

Azure Policy – Deny VNet Address Space – Parameters

Then, when we try to create a VNet that does not align with the VNet Address Prefix list I’ve defined in the policy assignment, we see that the validation fails, and the error details indicate that the resource was denied by the Policy: ‘Network Policy’.

Create VNet – Validation Failed
Create VNet – Validation Error


And that’s it! We now have an Azure Policy that ensures we maintain control over the network spaces that we allow to be deployed!

About the Author:

I am an experienced Microsoft Azure Cloud Subject Matter Expert (SME). I have a strong passion and drive for learning about technology, and I bring that passion and enthusiasm to everything I do.

I hold several industry certifications, including the Microsoft Certified Solutions Expert (MCSE) in Private Cloud, a charter certification in Cloud Platform and Infrastructure, along with multiple Azure specialty certifications


Ermie, A. (2020). Govern Azure Virtual Network (VNet) CIDR Ranges with Azure Policy. Available at: [Accessed: 20th May 2020].

Check out more great Azure content here

Share this on...

Rate this Post: