diff --git a/docs/wiki/Whats-new.md b/docs/wiki/Whats-new.md index 53ea412b1..000370585 100644 --- a/docs/wiki/Whats-new.md +++ b/docs/wiki/Whats-new.md @@ -52,6 +52,10 @@ Here's what's changed in Enterprise Scale/Azure Landing Zones: ### 🔃 Policy Refresh Q2 FY25 +- [PREVIEW] Added ability to deploy Virtual Network Manager through the portal accelerator with support for Security Admin feature, including default rules blocking high-risk ports [read more](https://learn.microsoft.com/en-us/azure/virtual-network-manager/concept-security-admins). + - [Important] To support the configuration of AVNM, we've had to included a deployment script to configure the Microsoft.Network resource provider on the intermediate root management group. This deployment script and required User-Assigned Managed Identity are created in a resource group in the Management subscription. Please remove the user assigned identity in the resource group hosting the AVNM instance. + - [Important] Due to performance improvements of ARM, we've also had to change the "wait" process in the portal accelerator (waiting for Management Groups to be registered so we can do policy assignments). We are now using the same deployment script with a "Start-Sleep" PowerShell command which is far more reliable. In the management subscription, you will find a resource group `rg-alz-prereqs` that you should remove (with contents) as the identity has Contributor rights on the Intermediate Management Group. + - [Important] A deployment script and User-Assigned Managed Identity is needed in the `rg-alz-avnm` resource group in the Connectivity subscription to register the Security Admin configuration with selected deployment regions. You should delete this identity after deployment. - *Policy Versioning Support* - all initiatives and assignments have been pinned to the current major version of built-in policies or initiatives deployed by ALZ. This ensures that all ALZ deployments will successfully deploy using the currently validated versions of ALZ built-in policies and initiatives. As these get updated the team will validate changes and impact before incrementing the recommended version. - Fixed a Portal Accelerator bug that results in failed deployment when choosing not to deploy policies to the Identity management group. - Updated the display name of the many `Effect` parameters to clearly identify the policy it applies to in the initiative [Enforce recommended guardrails for Azure Key Vault](https://www.azadvertizer.net/azpolicyinitiativesadvertizer/Enforce-Guardrails-KeyVault.html). diff --git a/eslzArm/eslz-portal.json b/eslzArm/eslz-portal.json index 1bc6f1ef7..5da8d2aaf 100644 --- a/eslzArm/eslz-portal.json +++ b/eslzArm/eslz-portal.json @@ -1438,6 +1438,13 @@ }, "visible": true }, + { + "name": "deployAVNM", + "type": "Microsoft.Common.CheckBox", + "label": "Deploy Azure Virtual Network Manager - PREVIEW", + "toolTip": "If selected, Azure Virtual Network Manager will be deployed to manage your virtual networks. Currently, ALZ will only enable Security Admin Rules role by default", + "visible": "[or(equals(steps('connectivity').enableHub, 'vhub'), equals(steps('connectivity').enableHub, 'nva'))]" + }, { "name": "esNwNVANote", "type": "Microsoft.Common.InfoBox", @@ -9499,6 +9506,7 @@ "erRegionalOrAz": "[steps('connectivity').erRegionalOrAz]", "expressRouteScaleUnit": "[steps('connectivity').expressRouteScaleUnit]", "enableHub": "[steps('connectivity').enableHub]", + "deployAVNM": "[steps('connectivity').deployAVNM]", "enableAzFw": "[steps('connectivity').enableAzFw]", "enableAzFwDnsProxy": "[if(equals(steps('connectivity').firewallSku, 'Basic'), 'No', steps('connectivity').enableAzFwDnsProxy)]", "firewallSku": "[steps('connectivity').firewallSku]", diff --git a/eslzArm/eslzArm.json b/eslzArm/eslzArm.json index 0c3ed6760..aa3f2fe4d 100644 --- a/eslzArm/eslzArm.json +++ b/eslzArm/eslzArm.json @@ -380,6 +380,14 @@ "type": "string", "defaultValue": "[deployment().location]" }, + "deployAVNM": { + "type": "bool", + "defaultValue": false, + "allowedValues": [ + true, + false + ] + }, "enableDdoS": { "type": "string", "defaultValue": "No", @@ -1689,6 +1697,9 @@ "roleDefinitions": "[uri(deployment().properties.templateLink.uri, 'managementGroupTemplates/roleDefinitions/customRoleDefinitions.json')]", "policyDefinitions": "[uri(deployment().properties.templateLink.uri, 'managementGroupTemplates/policyDefinitions/policies.json')]", "initiativeDefinitions": "[uri(deployment().properties.templateLink.uri, 'managementGroupTemplates/policyDefinitions/initiatives.json')]", + "preRequisites": "[uri(deployment().properties.templateLink.uri, 'prerequisites/deployPrerequisites.json')]", + "avnmConnectivityHub": "[uri(deployment().properties.templateLink.uri, 'subscriptionTemplates/avnmConfiguration.json')]", + "avnmPolicy": "[uri(deployment().properties.templateLink.uri, 'subscriptionTemplates/avnmPolicy.json')]", "vnetConnectivityHub": "[uri(deployment().properties.templateLink.uri, 'subscriptionTemplates/hubspoke-connectivity.json')]", "vwanConnectivityHub": "[uri(deployment().properties.templateLink.uri, 'subscriptionTemplates/vwan-connectivity.json')]", "nvaConnectivityHub": "[uri(deployment().properties.templateLink.uri, 'subscriptionTemplates/nvahubspoke-connectivity.json')]", @@ -1825,6 +1836,8 @@ "atpOssDbPolicyDeploymentName": "[take(concat('alz-AtpOssDb', variables('deploymentSuffix')), 64)]", "atpSqlDbPolicyDeploymentName": "[take(concat('alz-AtpSqlDb', variables('deploymentSuffix')), 64)]", "ascGovPolicyDeploymentName": "[take(concat('alz-Gov-ASC', variables('deploymentSuffix')), 64)]", + "avnmConnectivityHubDeploymentName": "[take(concat('alz-AVNM', variables('deploymentSuffix')), 64)]", + "avnmPolicyDeploymentName": "[take(concat('alz-AVNMPolicy', variables('deploymentSuffix')), 64)]", "vnetConnectivityHubDeploymentName": "[take(concat('alz-HubSpoke', variables('deploymentSuffix')), 64)]", "vwanConnectivityHubDeploymentName": "[take(concat('alz-VWanHub', variables('deploymentSuffix')), 64)]", "vnetConnectivityHub2DeploymentName": "[take(concat('alz-HubSpoke2', variables('deploymentSuffix')), 64)]", @@ -2222,7 +2235,8 @@ "scope": "[concat('Microsoft.Management/managementGroups/', parameters('enterpriseScaleCompanyPrefix'))]", "dependsOn": [ "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').mgmtGroupDeploymentName)]", - "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').mgmtGroupLiteDeploymentName)]" + "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').mgmtGroupLiteDeploymentName)]", + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -2327,7 +2341,8 @@ "location": "[deployment().location]", "scope": "[concat('Microsoft.Management/managementGroups/', parameters('enterpriseScaleCompanyPrefix'))]", "dependsOn": [ - "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').mgmtGroupLiteDeploymentName)]" + "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').mgmtGroupLiteDeploymentName)]", + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -2418,29 +2433,33 @@ } }, { - // One of Azure's untold stories..... + // ALZ Pre-Requisites and Azure's Untold Story... + "condition": "[not(empty(parameters('managementSubscriptionId')))]", "type": "Microsoft.Resources/deployments", - "apiVersion": "2020-10-01", - "name": "[concat('preparingToLaunch', copyIndex())]", + "apiVersion": "2020-06-01", + "name": "alz-prerequisites", + "scope": "[variables('scopes').eslzRootManagementGroup]", "location": "[deployment().location]", - "scope": "[concat('Microsoft.Management/managementGroups/', parameters('enterpriseScaleCompanyPrefix'))]", "dependsOn": [ - "[variables('deploymentNames').initiativeDeploymentName]" + "[variables('deploymentNames').initiativeDeploymentName]", + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').mgmtSubscriptionPlacement)]" ], - "copy": { - "batchSize": 1, - "count": "[parameters('delayCount')]", - "mode": "Serial", - "name": "policyCompletion" - }, "properties": { "mode": "Incremental", - "template": { - "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#", + "templateLink": { "contentVersion": "1.0.0.0", - "parameters": {}, - "resources": [], - "outputs": {} + "uri": "[variables('deploymentUris').preRequisites]" + }, + "parameters": { + "location": { + "value": "[deployment().location]" + }, + "eslzRootName": { + "value": "[parameters('enterpriseScaleCompanyPrefix')]" + }, + "managementSubscriptionId": { + "value": "[parameters('managementSubscriptionId')]" + } } } }, @@ -2528,6 +2547,7 @@ } } }, + /* The following deployments will optionally configure the governance, security, and monitoring for the Azure platform and landing zones */ @@ -2541,7 +2561,7 @@ "subscriptionId": "[parameters('managementSubscriptionId')]", "dependsOn": [ "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').mgmtSubscriptionPlacement)]", - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -2704,7 +2724,7 @@ "location": "[deployment().location]", "dependsOn": [ "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').mgmtSubscriptionPlacement)]", - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -2809,7 +2829,7 @@ "location": "[deployment().location]", "dependsOn": [ "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').mgmtSubscriptionPlacement)]", - "policyCompletion", + "alz-prerequisites", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').monitoringLiteDeploymentName)]" ], @@ -2846,7 +2866,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -2893,7 +2913,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -2940,7 +2960,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -2987,7 +3007,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3034,7 +3054,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3081,7 +3101,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3128,7 +3148,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3175,7 +3195,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3222,7 +3242,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3269,7 +3289,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3316,7 +3336,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3363,7 +3383,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3410,7 +3430,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3457,7 +3477,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3504,7 +3524,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3551,7 +3571,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3598,7 +3618,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3645,7 +3665,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3692,7 +3712,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3739,7 +3759,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3789,7 +3809,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3836,7 +3856,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3883,7 +3903,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3930,7 +3950,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -3977,7 +3997,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -4024,7 +4044,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -4071,7 +4091,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').vnetConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').nvaConnectivityHubLiteDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').monitoringDeploymentName)]", - "policyCompletion", + "alz-prerequisites", "corpConnectedMoveLzs" ], "copy": { @@ -4309,7 +4329,7 @@ "scope": "[variables('scopes').eslzRootManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -4333,7 +4353,7 @@ "scope": "[variables('scopes').eslzRootManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -4357,7 +4377,7 @@ "scope": "[variables('scopes').eslzRootManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -4381,7 +4401,7 @@ "scope": "[variables('scopes').eslzRootManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -4687,7 +4707,7 @@ "scope": "[variables('scopes').eslzRootManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -4757,7 +4777,7 @@ "scope": "[variables('scopes').platformManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -4982,7 +5002,8 @@ "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').asbPolicyDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').ascPolicyDeploymentName)]", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').ascGovPolicyDeploymentName)]", - "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').ddosDeploymentName)]" + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').ddosDeploymentName)]", + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').vnetConnectivityHubDeploymentName)]" ], "location": "[deployment().location]", "properties": { @@ -5175,6 +5196,73 @@ } } }, + { + // Deploy AVNM + "condition": "[and(parameters('deployAVNM'), or(equals(parameters('enableHub'), 'vhub'), equals(parameters('enableHub'), 'nva')), not(empty(parameters('connectivitySubscriptionId'))))]", + "type": "Microsoft.Resources/deployments", + "apiVersion": "2020-10-01", + "subscriptionId": "[parameters('connectivitySubscriptionId')]", + "name": "[variables('deploymentNames').avnmConnectivityHubDeploymentName]", + "dependsOn": [ + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').connectivitySubscriptionPlacement)]", + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').activityDiagnosticsPolicyDeploymentName)]", + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').resourceDiagnosticsPolicyDeploymentName)]", + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').asbPolicyDeploymentName)]", + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').ascPolicyDeploymentName)]", + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').ascGovPolicyDeploymentName)]", + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').ddosDeploymentName)]", + "alz-prerequisites" + ], + "location": "[deployment().location]", + "properties": { + "mode": "Incremental", + "templateLink": { + "contentVersion": "1.0.0.0", + "uri": "[variables('deploymentUris').avnmConnectivityHub]" + }, + "parameters": { + "location": { + "value": "[parameters('connectivityLocation')]" + }, + "locationSecondary": { + "value": "[parameters('connectivityLocationSecondary')]" + }, + "managementGroupScope": { + "value": "[variables('scopes').eslzRootManagementGroup]" + }, + "connectivitySubscriptionId": { + "value": "[parameters('connectivitySubscriptionId')]" + } + } + } + }, + { + // Deploying AVNM policy + "condition": "[and(parameters('deployAVNM'), or(equals(parameters('enableHub'), 'vhub'), equals(parameters('enableHub'), 'nva')), not(empty(parameters('connectivitySubscriptionId'))))]", + "type": "Microsoft.Resources/deployments", + "apiVersion": "2019-10-01", + "name": "[variables('deploymentNames').avnmPolicyDeploymentName]", + "location": "[deployment().location]", + "scope": "[variables('scopes').eslzRootManagementGroup]", + "dependsOn": [ + "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').avnmConnectivityHubDeploymentName)]" + ], + "properties": { + "mode": "Incremental", + "templateLink": { + "contentVersion": "1.0.0.0", + "uri": "[variables('deploymentUris').avnmPolicy]" + }, + "parameters": { + "topLevelManagementGroupPrefix": { + "value": "[parameters('enterpriseScaleCompanyPrefix')]" + }, + "connectivitySubscriptionId": { + "value": "[parameters('connectivitySubscriptionId')]" + } + } + } + }, { // Creating resource group for Private DNS Zones "condition": "[and(equals(parameters('enablePrivateDnsZones'), 'Yes'), not(empty(parameters('connectivitySubscriptionId'))))]", @@ -5672,7 +5760,7 @@ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').mgmtGroupLiteDeploymentName)]", "dnsZones", "dnsZonesLite", - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -5964,7 +6052,7 @@ "scope": "[variables('scopes').platformManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -5997,7 +6085,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6360,7 +6448,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6417,7 +6505,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6441,7 +6529,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6465,7 +6553,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6489,7 +6577,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6516,7 +6604,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6540,7 +6628,7 @@ "scope": "[variables('scopes').corpManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6567,7 +6655,7 @@ "scope": "[variables('scopes').corpManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6591,7 +6679,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6617,7 +6705,7 @@ "scope": "[variables('scopes').platformManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6643,7 +6731,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6670,7 +6758,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6694,7 +6782,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6721,7 +6809,7 @@ "scope": "[variables('scopes').platformManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6748,7 +6836,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6775,7 +6863,7 @@ "scope": "[variables('scopes').platformManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6802,7 +6890,7 @@ "scope": "[variables('scopes').corpManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6826,7 +6914,7 @@ "scope": "[variables('scopes').corpManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6856,7 +6944,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6880,7 +6968,7 @@ "scope": "[variables('scopes').eslzRootManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -6907,7 +6995,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -7027,7 +7115,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -7054,7 +7142,7 @@ "scope": "[variables('scopes').lzsManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -7081,7 +7169,7 @@ "scope": "[variables('scopes').decommissionedManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -7108,7 +7196,7 @@ "scope": "[variables('scopes').sandboxManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -7138,7 +7226,7 @@ "scope": "[variables('scopes').identityManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -7165,7 +7253,7 @@ "scope": "[variables('scopes').identityManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion", + "alz-prerequisites", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').identitySubscriptionPlacement)]" ], "properties": { @@ -7190,7 +7278,7 @@ "scope": "[variables('scopes').identityManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion", + "alz-prerequisites", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').identitySubscriptionPlacement)]" ], "properties": { @@ -7218,7 +7306,7 @@ "scope": "[variables('scopes').identityManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion", + "alz-prerequisites", "[resourceId('Microsoft.Resources/deployments', variables('deploymentNames').identitySubscriptionPlacement)]" ], "properties": { @@ -7715,7 +7803,7 @@ "subscriptionId": "[parameters('singlePlatformSubscriptionId')]", "dependsOn": [ "[resourceId('Microsoft.Resources/deployments', variables('esliteDeploymentNames').platformLiteSubscriptionPlacement)]", - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -7794,7 +7882,7 @@ "location": "[deployment().location]", "dependsOn": [ "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').monitoringLiteDeploymentName)]", - "policyCompletion" + "alz-prerequisites" ], "properties": { "mode": "Incremental", @@ -8872,7 +8960,7 @@ "scope": "[variables('scopes').platformManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion", + "alz-prerequisites", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').platformLiteSubscriptionPlacement)]" ], "properties": { @@ -8903,7 +8991,7 @@ "scope": "[variables('scopes').platformManagementGroup]", "location": "[deployment().location]", "dependsOn": [ - "policyCompletion", + "alz-prerequisites", "[resourceId('Microsoft.Resources/deployments', variables('esLiteDeploymentNames').platformLiteSubscriptionPlacement)]" ], "properties": { diff --git a/eslzArm/prerequisites/deployPrerequisites.json b/eslzArm/prerequisites/deployPrerequisites.json new file mode 100644 index 000000000..5b397b93a --- /dev/null +++ b/eslzArm/prerequisites/deployPrerequisites.json @@ -0,0 +1,290 @@ +{ + "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "resourceGroupName": { + "type": "string", + "defaultValue": "rg-alz-prereqs", + "metadata": { + "description": "The resource group name where the AVNM resources will be created" + } + }, + "location": { + "type": "string", + "minLength": 6, + "metadata": { + "description": "The location of this AVNM instance. All resources will be deployed to this region." + } + }, + "eslzRootName": { + "type": "string", + "metadata": { + "description": "The name of the Enterprise Scale Landing Zone root resource." + } + }, + "managementSubscriptionId": { + "type": "string", + "metadata": { + "description": "The subscription ID of the management subscription." + } + } + }, + "resources": [ + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2022-09-01", + "name": "alz-prerequisites-001", + "location": "[parameters('location')]", + "subscriptionId": "[parameters('managementSubscriptionId')]", + "properties": { + "expressionEvaluationOptions": { + "scope": "inner" + }, + "mode": "Incremental", + "parameters": { + "location": { + "value": "[parameters('location')]" + }, + "managementSubscriptionId": { + "value": "[parameters('managementSubscriptionId')]" + }, + "resourceGroupName": { + "value": "[parameters('resourceGroupName')]" + } + }, + "template": { + "$schema": "https://schema.management.azure.com/schemas/2018-05-01/subscriptionDeploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string" + }, + "managementSubscriptionId": { + "type": "string" + }, + "resourceGroupName": { + "type": "string" + } + }, + "resources": [ + { + "type": "Microsoft.Resources/resourceGroups", + "apiVersion": "2022-09-01", + "name": "[parameters('resourceGroupName')]", + "location": "[parameters('location')]" + }, + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2022-09-01", + "name": "alz-prerequisites-uai", + "resourceGroup": "[parameters('resourceGroupName')]", + "dependsOn": [ + "[subscriptionResourceId('Microsoft.Resources/resourceGroups', parameters('resourceGroupName'))]" + ], + "properties": { + "expressionEvaluationOptions": { + "scope": "inner" + }, + "mode": "Incremental", + "parameters": { + "location": { + "value": "[parameters('location')]" + }, + "managementSubscriptionId": { + "value": "[parameters('managementSubscriptionId')]" + }, + "resourceGroupName": { + "value": "[parameters('resourceGroupName')]" + } + }, + "template": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string" + }, + "managementSubscriptionId": { + "type": "string" + }, + "resourceGroupName": { + "type": "string" + } + }, + "variables": {}, + "resources": [ + { + "type": "Microsoft.ManagedIdentity/userAssignedIdentities", + "apiVersion": "2023-07-31-preview", + "name": "uai-alz-prereq", + "location": "[parameters('location')]" + } + ], + "outputs": { + "userAssignedIdentityId": { + "type": "string", + "value": "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', 'uai-alz-prereq')]" + }, + "uaiPrincipalId": { + "type": "string", + "value": "[reference(resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', 'uai-alz-prereq'), '2023-07-31-preview').principalId]" + } + } + } + } + } + ], + "outputs": { + "userAssignedIdentityId": { + "type": "string", + "value": "[reference(extensionResourceId(format('/subscriptions/{0}/resourceGroups/{1}', subscription().subscriptionId, parameters('resourceGroupName')), 'Microsoft.Resources/deployments', 'alz-prerequisites-uai'), '2022-09-01').outputs.userAssignedIdentityId.value]" + }, + "uaiPrincipalId": { + "type": "string", + "value": "[reference(extensionResourceId(format('/subscriptions/{0}/resourceGroups/{1}', subscription().subscriptionId, parameters('resourceGroupName')), 'Microsoft.Resources/deployments', 'alz-prerequisites-uai'), '2022-09-01').outputs.uaiPrincipalId.value]" + } + } + + } + } + }, + { + "type": "Microsoft.Authorization/roleAssignments", + "apiVersion": "2022-04-01", + "name": "[guid(format('alz-prerequisites-{0}-{1}', parameters('eslzRootName'), parameters('location')))]", + "location": "[parameters('location')]", + "properties": { + "roleDefinitionId": "/providers/Microsoft.Authorization/roleDefinitions/b24988ac-6180-42a0-ab88-20f7382dd24c", + "principalId": "[reference(subscriptionResourceId(parameters('managementSubscriptionId'), 'Microsoft.Resources/deployments', 'alz-prerequisites-001'), '2022-09-01').outputs.uaiPrincipalId.value]", + "principalType": "ServicePrincipal" + }, + "dependsOn": [ + "[subscriptionResourceId(parameters('managementSubscriptionId'), 'Microsoft.Resources/deployments', 'alz-prerequisites-001')]" + ] + }, + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2022-09-01", + "name": "alz-prerequisites-002", + "location": "[parameters('location')]", + "subscriptionId": "[parameters('managementSubscriptionId')]", + "properties": { + "mode": "Incremental", + "template": { + "$schema": "https://schema.management.azure.com/schemas/2018-05-01/subscriptionDeploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "resources": [ + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2022-09-01", + "name": "alz-prereq-ds", + "resourceGroup": "[parameters('resourceGroupName')]", + "dependsOn": [], + "properties": { + "expressionEvaluationOptions": { + "scope": "inner" + }, + "mode": "Incremental", + "parameters": { + "location": { + "value": "[parameters('location')]" + }, + "eslzRootName": { + "value": "[parameters('eslzRootName')]" + }, + "managementSubscriptionId": { + "value": "[parameters('managementSubscriptionId')]" + }, + "resourceGroupName": { + "value": "[parameters('resourceGroupName')]" + } + }, + "template": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string" + }, + "eslzRootName":{ + "type": "string" + }, + "managementSubscriptionId": { + "type": "string" + }, + "resourceGroupName": { + "type": "string" + } + }, + "resources": [ + { + "type": "Microsoft.Resources/deploymentScripts", + "apiVersion": "2020-10-01", + "name": "alz-prereq-deploymentscript", + "location": "[parameters('location')]", + "kind": "AzurePowerShell", + "identity": { + "type": "UserAssigned", + "userAssignedIdentities": { + "[reference(subscriptionResourceId(parameters('managementSubscriptionId'), 'Microsoft.Resources/deployments', 'alz-prerequisites-001'), '2022-09-01').outputs.userAssignedIdentityId.value]": {} + } + }, + "properties": { + "azPowerShellVersion": "12.3", + "retentionInterval": "PT1H", + "timeout": "PT2H", + "arguments": "[format('-eslzRootName \"{0}\"', parameters('eslzRootName'))]", + "scriptContent": " + param( + [Parameter(Mandatory=$true, HelpMessage=\"Enter the ESLZ root name.\")] + [string] + $eslzRootName + ) + + #API call to register the Microsoft.Network provider against intermediate resource group for AVNM + Invoke-AzRestMethod -Method POST -Uri \"https://management.azure.com/providers/Microsoft.Management/managementGroups/$eslzRootName/providers/Microsoft.Network/register?api-version=2021-04-01\" + + #Register all resource providers required for ALZ + $subs = Search-AzGraph -Query \"ResourceContainers | where type =~ 'microsoft.resources/subscriptions'\" -ManagementGroup $eslzRootName + $rps = @('Microsoft.Insights','Microsoft.AlertsManagement','Microsoft.OperationalInsights','Microsoft.OperationsManagement','Microsoft.Automation','Microsoft.AlertsManagement','Microsoft.Security','Microsoft.Network','Microsoft.EventGrid','Microsoft.ManagedIdentity','Microsoft.GuestConfiguration','Microsoft.Advisor','Microsoft.PolicyInsights') + + foreach ($sub in $subs) { + Write-Host 'Registering resource providers for subscription: ' $sub.subscriptionId + Select-AzSubscription -SubscriptionId $sub.subscriptionId + Get-AzResourceProvider -ProviderNamespace $rps | where {$_.RegistrationState -ne \"Registered\"} | Register-AzResourceProvider + } + + #Sleep for XX minutes to wait for Management Groups to load to cache before assignments + Start-Sleep -Duration (New-TimeSpan -Minutes 10) + + #$result = \"\" + #$count = 0 + + #do { + # $result = Invoke-AzRestMethod -Method POST -Uri \"https://management.azure.com/providers/Microsoft.Management/managementGroups/$eslzRootName/providers/Microsoft.Network/register?api-version=2021-04-01\" + # $count++ + # Start-Sleep -Seconds 30 + # Write-Host 'MG RP Register - Status Code: ' $result.StatusCode ' Count: ' $count + #} while ($result.StatusCode -ne 200 -and $count -lt 10) + " + }, + "metadata": { + "description": "Create a Deployment Script resource to perform the prerequisites." + } + } + ], + "outputs": {} + } + } + } + ] + } + }, + "dependsOn": [ + "alz-prerequisites-001", + "[guid(format('alz-prerequisites-{0}-{1}', parameters('eslzRootName'), parameters('location')))]" + ] + } + ], + "outputs": {} + } \ No newline at end of file diff --git a/eslzArm/prerequisites/deployPrerequisites2.json b/eslzArm/prerequisites/deployPrerequisites2.json new file mode 100644 index 000000000..61435ea80 --- /dev/null +++ b/eslzArm/prerequisites/deployPrerequisites2.json @@ -0,0 +1,204 @@ +{ + "$schema": "https://schema.management.azure.com/schemas/2018-05-01/subscriptionDeploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "resourceGroupName": { + "type": "string", + "defaultValue": "rg-alz-prereqs", + "metadata": { + "description": "The resource group name where the AVNM resources will be created" + } + }, + "location": { + "type": "string", + "minLength": 6, + "metadata": { + "description": "The location of this AVNM instance. All resources will be deployed to this region." + } + }, + "eslzRootName": { + "type": "string", + "metadata": { + "description": "The name of the Enterprise Scale Landing Zone root resource." + } + } + }, + "resources": [ + { + "type": "Microsoft.Resources/resourceGroups", + "apiVersion": "2022-09-01", + "name": "[parameters('resourceGroupName')]", + "location": "[parameters('location')]" + }, + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2022-09-01", + "name": "alz-prerequisites-uai", + "resourceGroup": "[parameters('resourceGroupName')]", + "properties": { + "expressionEvaluationOptions": { + "scope": "inner" + }, + "mode": "Incremental", + "parameters": { + "location": { + "value": "[parameters('location')]" + }, + "eslzRootName": { + "value": "[parameters('eslzRootName')]" + } + }, + "template": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string" + }, + "eslzRootName": { + "type": "string" + } + }, + "variables": {}, + "resources": [ + { + "type": "Microsoft.ManagedIdentity/userAssignedIdentities", + "apiVersion": "2022-01-31-preview", + "name": "[format('uai-prereq-{0}', parameters('location'))]", + "location": "[parameters('location')]", + "metadata": { + "description": "This user assigned identity is used by the Deployment Script resource to interact with Azure resources." + } + }, + { + "type": "Microsoft.Authorization/roleAssignments", + "apiVersion": "2022-04-01", + "name": "[guid(resourceGroup().id, format('uai-prereq-{0}', parameters('location')))]", + "properties": { + "roleDefinitionId": "[subscriptionResourceId('Microsoft.Authorization/roleDefinitions', 'b24988ac-6180-42a0-ab88-20f7382dd24c')]", + "principalId": "[reference(resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', format('uai-prereq-{0}', parameters('location'))), '2022-01-31-preview').principalId]", + "principalType": "ServicePrincipal" + }, + "dependsOn": [ + "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', format('uai-prereq-{0}', parameters('location')))]" + ], + "metadata": { + "description": "This role assignment grants the user assigned identity the Contributor role on the resource group." + } + } + ], + "outputs": { + "userAssignedIdentityId": { + "type": "string", + "value": "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', format('uai-prereq-{0}', parameters('location')))]" + } + } + } + }, + "dependsOn": [ + "[subscriptionResourceId('Microsoft.Resources/resourceGroups', parameters('resourceGroupName'))]" + ] + }, + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2022-09-01", + "name": "[format('ds-{0}-prereqs', parameters('location'))]", + "resourceGroup": "[parameters('resourceGroupName')]", + "properties": { + "expressionEvaluationOptions": { + "scope": "inner" + }, + "mode": "Incremental", + "parameters": { + "location": { + "value": "[parameters('location')]" + }, + "userAssignedIdentityId": { + "value": "[reference(extensionResourceId(format('/subscriptions/{0}/resourceGroups/{1}', subscription().subscriptionId, parameters('resourceGroupName')), 'Microsoft.Resources/deployments', 'alz-prerequisites-uai'), '2022-09-01').outputs.userAssignedIdentityId.value]" + }, + "eslzRootName": { + "value": "[parameters('eslzRootName')]" + } + }, + "template": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string" + }, + "eslzRootName":{ + "type": "string" + }, + "userAssignedIdentityId": { + "type": "string" + } + }, + "resources": [ + { + "type": "Microsoft.Resources/deploymentScripts", + "apiVersion": "2020-10-01", + "name": "alz-prereq-deploymentscript", + "location": "[parameters('location')]", + "kind": "AzurePowerShell", + "identity": { + "type": "UserAssigned", + "userAssignedIdentities": { + "[format('{0}', parameters('userAssignedIdentityId'))]": {} + } + }, + "properties": { + "azPowerShellVersion": "12.3", + "retentionInterval": "PT1H", + "timeout": "PT2H", + "arguments": "[format('-eslzRootName \"{0}\"', parameters('eslzRootName'))]", + "scriptContent": " + param( + [Parameter(Mandatory=$true, HelpMessage=\"Enter the ESLZ root name.\")] + [string] + $eslzRootName + ) + + #API call to register the Microsoft.Network provider against intermediate resource group for AVNM + Invoke-AzRestMethod -Method POST -Uri \"https://management.azure.com/providers/Microsoft.Management/managementGroups/$eslzRootName/providers/Microsoft.Network/register?api-version=2021-04-01\" + + #Sleep for XX minutes to wait for Management Groups to load to cache before assignments + Start-Sleep -Duration (New-TimeSpan -Minutes 10) + + $result = \"\" + $count = 0 + + do { + $result = Invoke-AzRestMethod -Method POST -Uri \"https://management.azure.com/providers/Microsoft.Management/managementGroups/$eslzRootName/providers/Microsoft.Network/register?api-version=2021-04-01\" + $count++ + Start-Sleep -Seconds 30 + Write-Host 'MG RP Register - Status Code: ' $result.StatusCode ' Count: ' $count + } while ($result.StatusCode -ne 200 -and $count -lt 10) + + #Register all resource providers + $subs = Search-AzGraph -Query \"ResourceContainers | where type =~ 'microsoft.resources/subscriptions'\" -ManagementGroup $eslzRootName + $rps = @('Microsoft.Insights','Microsoft.AlertsManagement','Microsoft.OperationalInsights','Microsoft.OperationsManagement','Microsoft.Automation','Microsoft.AlertsManagement','Microsoft.Security','Microsoft.Network','Microsoft.EventGrid','Microsoft.ManagedIdentity','Microsoft.GuestConfiguration','Microsoft.Advisor','Microsoft.PolicyInsights') + + foreach ($sub in $subs) { + Select-AzSubscription -SubscriptionId $sub.id + Write-Host 'Registering resource providers for subscription: ' $sub.id + Get-AzResourceProvider -ProviderNamespace $rps | where {$_.RegistrationState -ne \"Registered\"} | Register-AzResourceProvider + } + " + }, + "metadata": { + "description": "Create a Deployment Script resource to perform the prerequisites." + } + } + ], + "outputs": {} + } + }, + "dependsOn": [ + "[extensionResourceId(format('/subscriptions/{0}/resourceGroups/{1}', subscription().subscriptionId, parameters('resourceGroupName')), 'Microsoft.Resources/deployments', 'alz-prerequisites-uai')]", + "[subscriptionResourceId('Microsoft.Resources/resourceGroups', parameters('resourceGroupName'))]" + ] + } + ], + "outputs": {} +} \ No newline at end of file diff --git a/eslzArm/subscriptionTemplates/avnmConfiguration.json b/eslzArm/subscriptionTemplates/avnmConfiguration.json new file mode 100644 index 000000000..9c901cbbb --- /dev/null +++ b/eslzArm/subscriptionTemplates/avnmConfiguration.json @@ -0,0 +1,459 @@ +{ + "$schema": "https://schema.management.azure.com/schemas/2018-05-01/subscriptionDeploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string", + "metadata": { + "displayName": "location", + "description": "Location of the HUB" + }, + "defaultValue": "[deployment().location]" + }, + "locationSecondary": { + "type": "string", + "metadata": { + "displayName": "locationSecondary", + "description": "Secondary location of the HUB for instances deploying in multiple regions" + }, + "defaultValue": "" + }, + "managementGroupScope": { + "type": "string", + "defaultValue": "", + "metadata": { + "description": "Management group scope for AVNM. Intermediate root management group is the default." + } + }, + "connectivitySubscriptionId": { + "type": "string", + "metadata": { + "description": "SubscriptionId for the connectivity subscription." + }, + "defaultValue": "[subscription().subscriptionId]" + } + }, + "variables": { + "rgName": "rg-alz-avnm", + "resourceDeploymentName": "[take(concat(deployment().name, '-avnm', parameters('location')), 64)]", + "configIds": "[resourceId(parameters('connectivitySubscriptionId'), variables('rgName'), 'Microsoft.Network/networkManagers/securityAdminConfigurations', 'avnm', 'sac-alz')]" + }, + "resources": [ + { + "type": "Microsoft.Resources/resourceGroups", + "apiVersion": "2019-10-01", + "location": "[parameters('location')]", + "name": "[variables('rgName')]", + "properties": {} + }, + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2019-10-01", + "name": "[variables('resourceDeploymentName')]", + "resourceGroup": "[variables('rgName')]", + "dependsOn": [ + "[concat('Microsoft.Resources/resourceGroups/', variables('rgName'))]" + ], + "properties": { + "mode": "Incremental", + "expressionEvaluationOptions": { + "scope": "inner" + }, + "parameters": { + "location": { + "value": "[parameters('location')]" + }, + "managementGroupScope": { + "value": "[parameters('managementGroupScope')]" + } + }, + "template": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string" + }, + "managementGroupScope": { + "type": "string" + } + }, + "resources": [ + { + "type": "Microsoft.Network/networkManagers", + "apiVersion": "2024-03-01", + "name": "avnm", + "location": "[parameters('location')]", + "properties": { + "networkManagerScopeAccesses": [ + "SecurityAdmin" + ], + "networkManagerScopes": { + "managementGroups": [ + "[parameters('managementGroupScope')]" + ] + } + }, + "dependsOn": [ + + ], + "metadata": { + "description": "This is the Azure Virtual Network Manager which will be used to implement the connected group for spoke-to-spoke connectivity." + } + }, + { + "type": "Microsoft.Network/networkManagers/networkGroups", + "apiVersion": "2024-03-01", + "name": "[format('{0}/{1}', 'avnm', 'ng-static')]", + "properties": { + "memberType": "VirtualNetwork", + "description": "Network Group - Static" + }, + "dependsOn": [ + "[resourceId('Microsoft.Network/networkManagers', 'avnm')]" + ], + "metadata": { + "description": "This is the static network group for the spoke VNETs, and hub when topology is mesh." + } + }, + { + "type": "Microsoft.Network/networkManagers/networkGroups", + "apiVersion": "2024-03-01", + "name": "[format('{0}/{1}', 'avnm', 'ng-dynamic')]", + "properties": { + "memberType": "VirtualNetwork", + "description": "Network Group - Dynamic" + }, + "dependsOn": [ + "[resourceId('Microsoft.Network/networkManagers', 'avnm')]" + ], + "metadata": { + "description": "This is the dynamic network group for the spoke VNETs, and hub when topology is mesh." + } + }, + { + "type": "Microsoft.Network/networkManagers/securityAdminConfigurations", + "apiVersion": "2023-11-01", + "name": "[format('{0}/{1}', 'avnm', 'sac-alz')]", + "dependsOn": [ + "[resourceId('Microsoft.Network/networkManagers', 'avnm')]" + ], + "properties": { + "description": "ALZ Security Admin Configuration" + } + }, + { + "type": "Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections", + "apiVersion": "2024-03-01", + "name": "[format('{0}/{1}/{2}', 'avnm', 'sac-alz', 'rc-ALZ')]", + "dependsOn": [ + "[resourceId('Microsoft.Network/networkManagers/securityAdminConfigurations', 'avnm', 'sac-alz')]", + "[resourceId('Microsoft.Network/networkManagers/networkGroups', 'avnm', 'ng-static')]", + "[resourceId('Microsoft.Network/networkManagers/networkGroups', 'avnm', 'ng-dynamic')]" + ], + "properties": { + "appliesToGroups": [ + { + "networkGroupId": "[resourceId('Microsoft.Network/networkManagers/networkGroups', 'avnm', 'ng-static')]" + }, + { + "networkGroupId": "[resourceId('Microsoft.Network/networkManagers/networkGroups', 'avnm', 'ng-dynamic')]" + } + + ] + } + }, + { + "type": "Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections/rules", + "apiVersion": "2024-03-01", + "name": "[format('{0}/{1}/{2}/{3}', 'avnm', 'sac-alz', 'rc-ALZ', 'DenyMgmtInbound')]", + "dependsOn": [ + "[resourceId('Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections', 'avnm', 'sac-alz', 'rc-ALZ')]" + ], + "kind": "Custom", + "properties": { + "description": "Deny VM Management inbound traffic", + "priority": 1000, + "sources": [ + { + "addressPrefixType": "ServiceTag", + "addressPrefix": "Internet" + } + ], + "destinationPortRanges": [ + "22", + "3389" + ], + "protocol": "Any", + "direction": "Inbound", + "access": "Deny" + } + }, + { + "type": "Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections/rules", + "apiVersion": "2024-03-01", + "name": "[format('{0}/{1}/{2}/{3}', 'avnm', 'sac-alz', 'rc-ALZ', 'DenyHighRiskInboundTCP')]", + "dependsOn": [ + "[resourceId('Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections', 'avnm', 'sac-alz', 'rc-ALZ')]" + ], + "kind": "Custom", + "properties": { + "description": "Deny high-risk TCP inbound traffic", + "priority": 1001, + "sources": [ + { + "addressPrefixType": "ServiceTag", + "addressPrefix": "Internet" + } + ], + "destinationPortRanges": [ + "20", + "21", + "23", + "119", + "161", + "445", + "512", + "514", + "873", + "5800", + "5900" + ], + "protocol": "TCP", + "direction": "Inbound", + "access": "Deny" + } + }, + { + "type": "Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections/rules", + "apiVersion": "2024-03-01", + "name": "[format('{0}/{1}/{2}/{3}', 'avnm', 'sac-alz', 'rc-ALZ', 'DenyHighRiskInboundUDP')]", + "dependsOn": [ + "[resourceId('Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections', 'avnm', 'sac-alz', 'rc-ALZ')]" + ], + "kind": "Custom", + "properties": { + "description": "Deny high-risk UDP inbound traffic", + "priority": 1002, + "sources": [ + { + "addressPrefixType": "ServiceTag", + "addressPrefix": "Internet" + } + ], + "destinationPortRanges": [ + "69", + "11211" + ], + "protocol": "UDP", + "direction": "Inbound", + "access": "Deny" + } + }, + { + "type": "Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections/rules", + "apiVersion": "2024-03-01", + "name": "[format('{0}/{1}/{2}/{3}', 'avnm', 'sac-alz', 'rc-ALZ', 'DenyHighRiskInboundANY')]", + "dependsOn": [ + "[resourceId('Microsoft.Network/networkManagers/securityAdminConfigurations/ruleCollections', 'avnm', 'sac-alz', 'rc-ALZ')]" + ], + "kind": "Custom", + "properties": { + "description": "Deny high-risk ANY inbound traffic", + "priority": 1003, + "sources": [ + { + "addressPrefixType": "ServiceTag", + "addressPrefix": "Internet" + } + ], + "destinationPortRanges": [ + "111", + "135", + "162", + "593", + "2049" + ], + "protocol": "Any", + "direction": "Inbound", + "access": "Deny" + } + } + + ] + } + } + }, + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2022-09-01", + "name": "alz-avnm-uai", + "resourceGroup": "[variables('rgName')]", + "properties": { + "expressionEvaluationOptions": { + "scope": "inner" + }, + "mode": "Incremental", + "parameters": { + "location": { + "value": "[parameters('location')]" + } + }, + "template": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string" + } + }, + "variables": {}, + "resources": [ + { + "type": "Microsoft.ManagedIdentity/userAssignedIdentities", + "apiVersion": "2022-01-31-preview", + "name": "[format('uai-avnm-{0}', parameters('location'))]", + "location": "[parameters('location')]", + "metadata": { + "description": "This user assigned identity is used by the Deployment Script resource to interact with Azure resources." + } + }, + { + "type": "Microsoft.Authorization/roleAssignments", + "apiVersion": "2022-04-01", + "name": "[guid(resourceGroup().id, format('uai-avnm-{0}', parameters('location')))]", + "properties": { + "roleDefinitionId": "[subscriptionResourceId('Microsoft.Authorization/roleDefinitions', 'b24988ac-6180-42a0-ab88-20f7382dd24c')]", + "principalId": "[reference(resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', format('uai-avnm-{0}', parameters('location'))), '2022-01-31-preview').principalId]", + "principalType": "ServicePrincipal" + }, + "dependsOn": [ + "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', format('uai-avnm-{0}', parameters('location')))]" + ], + "metadata": { + "description": "This role assignment grants the user assigned identity the Contributor role on the resource group." + } + } + ], + "outputs": { + "userAssignedIdentityId": { + "type": "string", + "value": "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', format('uai-avnm-{0}', parameters('location')))]" + } + } + } + }, + "dependsOn": [ + "[subscriptionResourceId('Microsoft.Resources/resourceGroups', variables('rgName'))]" + ] + }, + { + "type": "Microsoft.Resources/deployments", + "apiVersion": "2022-09-01", + "name": "[format('ds-{0}-prereqs', parameters('location'))]", + "resourceGroup": "[variables('rgName')]", + "properties": { + "expressionEvaluationOptions": { + "scope": "inner" + }, + "mode": "Incremental", + "parameters": { + "location": { + "value": "[parameters('location')]" + }, + "locationSecondary": { + "value": "[parameters('locationSecondary')]" + }, + "userAssignedIdentityId": { + "value": "[reference(extensionResourceId(format('/subscriptions/{0}/resourceGroups/{1}', subscription().subscriptionId, variables('rgName')), 'Microsoft.Resources/deployments', 'alz-avnm-uai'), '2022-09-01').outputs.userAssignedIdentityId.value]" + }, + "rgName": { + "value": "[variables('rgName')]" + }, + "configIds": { + "value": "[variables('configIds')]" + }, + "connectivitySubscriptionId": { + "value": "[parameters('connectivitySubscriptionId')]" + } + }, + "template": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "location": { + "type": "string" + }, + "locationSecondary": { + "type": "string" + }, + "userAssignedIdentityId": { + "type": "string" + }, + "rgName": { + "type": "string" + }, + "configIds": { + "type": "string" + }, + "connectivitySubscriptionId": { + "type": "string" + } + }, + "resources": [ + { + "type": "Microsoft.Resources/deploymentScripts", + "apiVersion": "2020-10-01", + "name": "alz-avnm-deploymentscript", + "location": "[parameters('location')]", + "kind": "AzurePowerShell", + "identity": { + "type": "UserAssigned", + "userAssignedIdentities": { + "[format('{0}', parameters('userAssignedIdentityId'))]": {} + } + }, + "properties": { + "azPowerShellVersion": "12.3", + "retentionInterval": "PT1H", + "timeout": "PT1H", + "arguments": "[format('-location \"{0}\" -locationSecond \"{1}\" -rgName \"{2}\" -configIds \"{3}\" -connSubId \"{4}\"', parameters('location'), parameters('locationSecondary'), parameters('rgName'), parameters('configIds'), parameters('connectivitySubscriptionId'))]", + "scriptContent": " + param( + [string] + $location, + + [string] + $locationSecond, + + [string] + $rgName, + + [string] + $configIds, + + [string] + $connSubId + ) + + $regions = @($location, $locationSecond) + + Select-AzSubscription -SubscriptionId $connSubId + + Deploy-AzNetworkManagerCommit -ResourceGroupName $rgName -Name \"avnm\" -TargetLocation $regions -CommitType \"SecurityAdmin\" -ConfigurationId $configIds + + " + } + } + ], + "outputs": {} + } + }, + "dependsOn": [ + "[extensionResourceId(format('/subscriptions/{0}/resourceGroups/{1}', subscription().subscriptionId, variables('rgName')), 'Microsoft.Resources/deployments', variables('resourceDeploymentName'))]", + "[subscriptionResourceId('Microsoft.Resources/resourceGroups', variables('rgName'))]" + ] + } + ], + "outputs": {} +} \ No newline at end of file diff --git a/eslzArm/subscriptionTemplates/avnmPolicy.json b/eslzArm/subscriptionTemplates/avnmPolicy.json new file mode 100644 index 000000000..c01a3313c --- /dev/null +++ b/eslzArm/subscriptionTemplates/avnmPolicy.json @@ -0,0 +1,82 @@ +{ + "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "topLevelManagementGroupPrefix": { + "type": "string", + "maxLength": 10, + "metadata": { + "description": "Provide a prefix (max 10 characters, unique at tenant-scope) for the Management Group hierarchy and other resources created as part of Enterprise-scale." + } + }, + "location": { + "type": "string", + "metadata": { + "displayName": "location", + "description": "Location for all resources." + }, + "defaultValue": "[deployment().location]" + }, + "connectivitySubscriptionId": { + "type": "string", + "metadata": { + "description": "Provide the subscriptionId you will place into the management group" + } + } + }, + "variables": { + "networkGroupId": "[resourceId(parameters('connectivitySubscriptionId'), 'rg-alz-avnm', 'Microsoft.Network/networkManagers/networkGroups', 'avnm', 'ng-dynamic')]" + }, + "resources": [ + { + "type": "Microsoft.Authorization/policyDefinitions", + "apiVersion": "2023-04-01", + "name": "[uniqueString(variables('networkGroupId'))]", + "properties": { + "description": "AVNM dynamic group membership Policy", + "displayName": "AVNM dynamic group membership Policy", + "mode": "Microsoft.Network.Data", + "policyRule": { + "if": { + "allOf": [ + { + "field": "type", + "equals": "Microsoft.Network/virtualNetworks" + } + ] + }, + "then": { + "effect": "addToNetworkGroup", + "details": { + "networkGroupId": "[variables('networkGroupId')]" + } + } + } + }, + "metadata": { + "description": "This is a Policy definition for dynamic group membership" + } + }, + { + "type": "Microsoft.Authorization/policyAssignments", + "apiVersion": "2023-04-01", + "name": "[uniqueString(variables('networkGroupId'))]", + "location": "[parameters('location')]", + "identity": { + "type": "SystemAssigned" + }, + "properties": { + "description": "AVNM dynamic group membership Policy", + "displayName": "AVNM dynamic group membership Policy", + "enforcementMode": "Default", + "policyDefinitionId": "[managementGroupResourceId('Microsoft.Authorization/policyDefinitions', uniqueString(variables('networkGroupId')))]" + }, + "dependsOn": [ + "[format('Microsoft.Authorization/policyDefinitions/{0}', uniqueString(variables('networkGroupId')))]" + ], + "metadata": { + "description": "Assigns above policy for dynamic group membership" + } + } + ] +} \ No newline at end of file