├── LICENSE ├── README.md ├── azuredeploy.json ├── dsc ├── windowsdevvm.ps1 └── windowsdevvm.zip ├── exercises ├── README.md ├── exercise1.md ├── exercise2.md ├── exercise3.md ├── exercise4.md ├── exercise5.md ├── exercise6.md └── exercise7.md ├── images ├── exercise1-image1.png ├── exercise1-image2.png ├── exercise1-image3.png ├── exercise2-image1.png ├── exercise2-image2.png ├── exercise2-image3.png ├── exercise2-image4.png ├── exercise2-image5.png ├── exercise2-image6.png ├── exercise2-image7.png ├── exercise2-image8.png ├── exercise3-image1.png ├── exercise3-image2.png ├── exercise3-image3.png ├── exercise3-image4.png ├── exercise3-image5.png ├── exercise3-image6.png ├── exercise3-image7.png ├── exercise4-image1.png ├── exercise4-image2.png ├── exercise4-image3.png ├── exercise4-image4.png ├── exercise4-image5.png ├── exercise5-image1.png ├── exercise5-image2.png ├── exercise5-image3.png ├── exercise6-image1.png ├── exercise6-image2.png ├── exercise6-image3.png ├── exercise6-image4.png ├── exercise6-image5.png ├── exercise6-image6.png ├── exercise7-image1.png ├── exercise7-image2.png ├── exercise7-image3.png ├── exercise7-image4.png ├── exercise7-image5.png └── lab_image.svg ├── presentation └── Azure Backup.pptx ├── scripts ├── prepare-linux-vm.sh └── prepare-windows-vm.ps1 └── templates ├── deploy-buv-backup-policies.json ├── deploy-buv-vault.json ├── deploy-infra.json ├── deploy-law.json ├── deploy-linux-vm.json ├── deploy-rsv-backup-policies.json ├── deploy-rsv-vault.json └── deploy-windows-vm.json /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2022 Matt Felton 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Azure Backup Demonstration 2 | 3 | ## Overview 4 | This repository includes a variety of artifacts that can be used to learn and demonstrate a subset of capabilities for [Azure Backup](https://docs.microsoft.com/en-us/azure/backup/backup-overview). Azure Backup is the native backup solution in the Microsoft Azure cloud. It provides backup functionality for workloads running in Azure or on-premises. A detailed listing of which workloads are supported are documented in the [public documentation](https://docs.microsoft.com/en-us/azure/backup/backup-support-matrix). The artifacts in this repository cover **only** the following use cases: 5 | 6 | * Azure Virtual Machines 7 | * Azure Managed Disks 8 | * Azure Storage - Blobs 9 | * Azure Storage - File Shares 10 | 11 | 12 | ## Artifacts 13 | The artifacts include a PowerPoint overview deck, deployable lab to learn and demonstrate features and capabilities, and a series of exercises to demonstrate and experiment with key features. 14 | 15 | ## Lab Deployment 16 | The deployable lab included in this repository is coded using [ARM resource templates](https://docs.microsoft.com/en-us/azure/azure-resource-manager/templates/syntax) and uses a combination of PowerShell and Bash scripts and DSC to pre-configure resources deployed. 17 | 18 | The resources in this lab are spread across three resource groups spread across the paired regions. The two resource groups deployed in the primary region include the Recovery Services Vault, Backup Vault, VMs, storage accounts, and virtual networks. The third resource group is deployed in the paired secondary region and deploys an empty virtual network that will be used to demonstrate the [cross region restore functionality](https://azure.microsoft.com/en-us/blog/cross-region-restore-crr-for-azure-virtual-machines-using-azure-backup/). 19 | 20 | Both the Recovery Services Vault and Backup Vault include custom backup policies including a basic VM policy, advanced VM policy, Azure Files policy, Azure Managed Disk policy, and Azure Blob policy. The Linux VM (vml-pri-1-cf) is associated with the basic VM backup policy and the Windows VM (vmw-pri-1-cf) is configured with the advanced VM backup policy and also comes with the [MARS agent preinstalled](https://docs.microsoft.com/en-us/azure/backup/install-mars-agent). The third windows VM (vmw-pri-2-ncf) is not configured for any backup policy and is present to allow you to demonstrate association of a backup policy through the Portal. 21 | 22 | Two storage accounts are deployed, one used for Azure Files and one used for Azure Blobs. An empty file share named sampleshare is precreated on one storage account and an empty blob container named sampleblobs is configured on the second storage account. You must populate the file share and blob container with your own sample data. You can then associate the file share and blob container with the relevant custom policies in the Recovery Services Vault and Backup Vault. 23 | 24 | The MARS agent on the Windows VM (vmw-pri-1-cf) can be setup and integrated with the Recovery Services Vault to demonstrate individual backup and restoration of system state, files, and folders from a Windows VM. 25 | 26 | ![lab image](images/lab_image.svg) 27 | 28 | ### Prerequisites 29 | 1. You must hold at least the [Contributor RBAC role](https://docs.microsoft.com/en-us/azure/role-based-access-control/built-in-roles#contributor) at the subscription scope in the subscription the resources will be deployed to. 30 | 31 | 2. You must be capable of deploying resources to a set of paired regions. The templates are configured to allow deployment to regions within the US geopolitical region and that have regional pairs. If you wish to deploy to another geopolitical region, you will need to modify the azuredeploy.json template. 32 | 33 | 3. The virtual machines created in this deployment are deployed into availability zones. The region(s) you deploy the resources to [must support availability zones](https://docs.microsoft.com/en-us/azure/availability-zones/az-region). 34 | 35 | ### Installation with Azure Portal 36 | 37 | Click the Deploy To Azure button below. 38 | 39 | [![Deploy to Azure](https://aka.ms/deploytoazurebutton)](https://portal.azure.com/#create/Microsoft.Template/uri/https%3A%2F%2Fraw.githubusercontent.com%2Fmattfeltonma%2Fazure-backup-demo%2Fmain%2Fazuredeploy.json) 40 | 41 | ### Installation with Azure CLI 42 | 1. Set the following variables: 43 | * DEPLOYMENT_NAME - The name of the location 44 | * DEPLOYMENT_LOCATION - The location to create the deployment 45 | * LOCATION - The primary region to deploy resources to 46 | * SEC_LOCATION - The secondary paired region to deploy resources to. This is used to demonstrate the cross region restore feature. 47 | * ADMIN_USER_NAME - The name to set for the VM administrator username 48 | * SUBSCRIPTION- The name or id of the subscription you wish to deploy the resources to 49 | 50 | 2. Set the CLI to the subscription you wish to deploy the resources to: 51 | 52 | * **az account set --subscription SUBSCRIPTION** 53 | 54 | 3. Deploy the lab using the command (tags parameter is optional): 55 | 56 | * **az deployment sub create --name $DEPLOYMENT_NAME --location $DEPLOYMENT_LOCATION --template-uri https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/main/azuredeploy.json --parameters location=$LOCATION secLocation=$SEC_LOCATION vmAdminUsername=$ADMIN_USER_NAME tags='{"mytag":"value"}'** 57 | 58 | 4. You will be prompted to provide a password for the local administrator of the virtual machine. 59 | 60 | ### Post Installation 61 | Once the lab is deployed, you should wait at least 24 hours for restore points to be generated for the virtual machines. You can remotely access the virtual machines using the deployed Azure Bastion instance. 62 | 63 | ### Exercises 64 | This repository contains a collection of exercises you can perform with the lab to learn or demonstrate the core features of Azure Backup. You can find [the exercises here](/exercises/README.md). 65 | 66 | ### Removal of Resources 67 | It is very important you follow the instructions below when you are done with the lab. If you do not follow these instructions, it could result in shadow resources which will require you to work with support to remove. 68 | 69 | 1. Follow the [instructions here](https://docs.microsoft.com/en-us/azure/backup/backup-azure-delete-vault?tabs=portal) to delete the Recovery Services Vault. 70 | 71 | 2. Follow the [instructions here](https://docs.microsoft.com/en-us/azure/backup/backup-vault-overview#delete-a-backup-vault) to delete the Backup Vault. 72 | 73 | 3. DO NOT proceed to this step until you have done steps 1 and 2. Once those steps are complete and both vaults are deleted, you can delete the resource groups containing the resources created as part of this lab. 74 | 75 | -------------------------------------------------------------------------------- /azuredeploy.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2018-05-01/subscriptionDeploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "location": { 6 | "type": "string", 7 | "metadata": { 8 | "description": "The location to deploy the resources. Modify template to allow additional regions" 9 | }, 10 | "allowedValues": [ 11 | "centralus", 12 | "eastus", 13 | "eastus2", 14 | "northcentralus", 15 | "southcentralus", 16 | "westcentralus", 17 | "westus", 18 | "westus2" 19 | ] 20 | }, 21 | "secLocation": { 22 | "type": "string", 23 | "metadata": { 24 | "description": "The secondary region region to deploy resources to. This should be the paired region of the primary region to support the cross region restore functionality" 25 | }, 26 | "allowedValues": [ 27 | "centralus", 28 | "eastus", 29 | "eastus2", 30 | "northcentralus", 31 | "southcentralus", 32 | "westcentralus", 33 | "westus", 34 | "westus2" 35 | ] 36 | }, 37 | "vmAdminUsername": { 38 | "type": "string", 39 | "metadata": { 40 | "description": "Administrator name for VMs that are created" 41 | } 42 | }, 43 | "vmAdminPassword": { 44 | "type": "securestring", 45 | "metadata": { 46 | "description": "Password for the VMs that are created" 47 | } 48 | }, 49 | "tags": { 50 | "type": "object", 51 | "metadata": { 52 | "description": "The tags that wil be associated to the resources" 53 | }, 54 | "defaultValue": { 55 | "environment": "demo" 56 | } 57 | }, 58 | "uniqueData": { 59 | "type": "string", 60 | "metadata": { 61 | "description": "Creates a new GUID to create uniqueness for resources" 62 | }, 63 | "defaultValue": "[substring(newGuid(),0,8)]" 64 | } 65 | }, 66 | "variables": { 67 | "resourcesApiVersion": "2020-06-01", 68 | "deployBuVlt": "deploy-bu-vault", 69 | "deployBuVltBackupPolicies": "deploy-bu-backup-policies", 70 | "deployLaw": "deploy-law", 71 | "deployRgs": "deploy-demo-rgs", 72 | "deployInfRes": "deploy-inf-res", 73 | "deployRsVlt": "deploy-rs-vault", 74 | "deployRsVltBackupPolicies": "deploy-rs-backup-policies", 75 | "rgNamePriVlt": "[concat('rgbckvltpri', parameters('uniqueData'))]", 76 | "rgNamePriWl": "[concat('rgbckwlpri', parameters('uniqueData'))]", 77 | "rgNameSecWl": "[concat('rgbckwlsec', parameters('uniqueData'))]", 78 | "templateUriLaw": "[concat(uri(deployment().properties.templateLink.uri,'templates/deploy-law.json'))]", 79 | "templateUriRsVlt": "[concat(uri(deployment().properties.templateLink.uri,'templates/deploy-rsv-vault.json'))]", 80 | "templateUriRsVltBackupPolicies": "[concat(uri(deployment().properties.templateLink.uri,'templates/deploy-rsv-backup-policies.json'))]", 81 | "templateUriBuVlt": "[concat(uri(deployment().properties.templateLink.uri,'templates/deploy-buv-vault.json'))]", 82 | "templateUriBuVltBackupPolicies": "[concat(uri(deployment().properties.templateLink.uri,'templates/deploy-buv-backup-policies.json'))]", 83 | "templateUriInfRes": "[concat(uri(deployment().properties.templateLink.uri,'templates/deploy-infra.json'))]" 84 | }, 85 | "resources": [ 86 | { 87 | "name": "[variables('deployRgs')]", 88 | "type": "Microsoft.Resources/deployments", 89 | "apiVersion": "[variables('resourcesApiVersion')]", 90 | "location": "[parameters('location')]", 91 | "subscriptionId": "[subscription().subscriptionId]", 92 | "properties": { 93 | "mode": "Incremental", 94 | "template": { 95 | "$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#", 96 | "contentVersion": "1.0.0.0", 97 | "resources": [ 98 | { 99 | "name": "[variables('rgNamePriVlt')]", 100 | "type": "Microsoft.Resources/resourceGroups", 101 | "apiVersion": "[variables('resourcesApiVersion')]", 102 | "location": "[parameters('location')]", 103 | "tags": "[parameters('tags')]", 104 | "properties": { 105 | } 106 | }, 107 | { 108 | "name": "[variables('rgNamePriWl')]", 109 | "type": "Microsoft.Resources/resourceGroups", 110 | "apiVersion": "[variables('resourcesApiVersion')]", 111 | "location": "[parameters('location')]", 112 | "tags": "[parameters('tags')]", 113 | "properties": { 114 | } 115 | }, 116 | { 117 | "name": "[variables('rgNameSecWl')]", 118 | "type": "Microsoft.Resources/resourceGroups", 119 | "apiVersion": "[variables('resourcesApiVersion')]", 120 | "location": "[parameters('secLocation')]", 121 | "tags": "[parameters('tags')]", 122 | "properties": { 123 | } 124 | } 125 | ] 126 | } 127 | } 128 | }, 129 | { 130 | "name": "[variables('deployLaw')]", 131 | "type": "Microsoft.Resources/deployments", 132 | "apiVersion": "[variables('resourcesApiVersion')]", 133 | "subscriptionId": "[subscription().subscriptionId]", 134 | "resourceGroup": "[variables('rgNamePriWl')]", 135 | "dependsOn": [ 136 | "[concat('Microsoft.Resources/deployments/', variables('deployRgs'))]" 137 | ], 138 | "properties": { 139 | "mode": "Incremental", 140 | "parameters": { 141 | "tags": { 142 | "value": "[parameters('tags')]" 143 | }, 144 | "uniqueData": { 145 | "value": "[parameters('uniqueData')]" 146 | } 147 | }, 148 | "templateLink": { 149 | "uri": "[variables('templateUriLaw')]", 150 | "contentVersion": "1.0.0.0" 151 | } 152 | } 153 | }, 154 | { 155 | "name": "[variables('deployRsVlt')]", 156 | "type": "Microsoft.Resources/deployments", 157 | "apiVersion": "[variables('resourcesApiVersion')]", 158 | "subscriptionId": "[subscription().subscriptionId]", 159 | "resourceGroup": "[variables('rgNamePriVlt')]", 160 | "dependsOn": [ 161 | "[concat('Microsoft.Resources/deployments/', variables('deployLaw'))]" 162 | ], 163 | "properties": { 164 | "mode": "Incremental", 165 | "parameters": { 166 | "lawResourceId": { 167 | "value": "[reference(variables('deployLaw')).outputs.logAnalyticsResourceId.value]" 168 | }, 169 | "tags": { 170 | "value": "[parameters('tags')]" 171 | }, 172 | "uniqueData": { 173 | "value": "[parameters('uniqueData')]" 174 | } 175 | }, 176 | "templateLink": { 177 | "uri": "[variables('templateUriRsVlt')]", 178 | "contentVersion": "1.0.0.0" 179 | } 180 | } 181 | }, 182 | { 183 | "name": "[variables('deployRsVltBackupPolicies')]", 184 | "type": "Microsoft.Resources/deployments", 185 | "apiVersion": "[variables('resourcesApiVersion')]", 186 | "subscriptionId": "[subscription().subscriptionId]", 187 | "resourceGroup": "[variables('rgNamePriVlt')]", 188 | "dependsOn": [ 189 | "[concat('Microsoft.Resources/deployments/', variables('deployRsVlt'))]" 190 | ], 191 | "properties": { 192 | "mode": "Incremental", 193 | "parameters": { 194 | "recSvcVaultName": { 195 | "value": "[reference(variables('deployRsVlt')).outputs.rsVaultName.value]" 196 | }, 197 | "tags": { 198 | "value": "[parameters('tags')]" 199 | }, 200 | "uniqueData": { 201 | "value": "[parameters('uniqueData')]" 202 | } 203 | }, 204 | "templateLink": { 205 | "uri": "[variables('templateUriRsVltBackupPolicies')]", 206 | "contentVersion": "1.0.0.0" 207 | } 208 | } 209 | }, 210 | { 211 | "name": "[variables('deployBuVlt')]", 212 | "type": "Microsoft.Resources/deployments", 213 | "apiVersion": "[variables('resourcesApiVersion')]", 214 | "subscriptionId": "[subscription().subscriptionId]", 215 | "resourceGroup": "[variables('rgNamePriVlt')]", 216 | "dependsOn": [ 217 | "[concat('Microsoft.Resources/deployments/', variables('deployRsVltBackupPolicies'))]" 218 | ], 219 | "properties": { 220 | "mode": "Incremental", 221 | "parameters": { 222 | "tags": { 223 | "value": "[parameters('tags')]" 224 | }, 225 | "uniqueData": { 226 | "value": "[parameters('uniqueData')]" 227 | } 228 | }, 229 | "templateLink": { 230 | "uri": "[variables('templateUriBuVlt')]", 231 | "contentVersion": "1.0.0.0" 232 | } 233 | } 234 | }, 235 | { 236 | "name": "[variables('deployBuVltBackupPolicies')]", 237 | "type": "Microsoft.Resources/deployments", 238 | "apiVersion": "[variables('resourcesApiVersion')]", 239 | "subscriptionId": "[subscription().subscriptionId]", 240 | "resourceGroup": "[variables('rgNamePriVlt')]", 241 | "dependsOn": [ 242 | "[concat('Microsoft.Resources/deployments/', variables('deployBuVlt'))]" 243 | ], 244 | "properties": { 245 | "mode": "Incremental", 246 | "parameters": { 247 | "buVaultName": { 248 | "value": "[reference(variables('deployBuVlt')).outputs.buVaultName.value]" 249 | }, 250 | "uniqueData": { 251 | "value": "[parameters('uniqueData')]" 252 | } 253 | }, 254 | "templateLink": { 255 | "uri": "[variables('templateUriBuVltBackupPolicies')]", 256 | "contentVersion": "1.0.0.0" 257 | } 258 | } 259 | }, 260 | { 261 | "name": "[variables('deployInfRes')]", 262 | "type": "Microsoft.Resources/deployments", 263 | "apiVersion": "[variables('resourcesApiVersion')]", 264 | "subscriptionId": "[subscription().subscriptionId]", 265 | "resourceGroup": "[variables('rgNamePriWl')]", 266 | "dependsOn": [ 267 | "[concat('Microsoft.Resources/deployments/', variables('deployBuVltBackupPolicies'))]" 268 | ], 269 | "properties": { 270 | "mode": "Incremental", 271 | "parameters": { 272 | "lawResourceId": { 273 | "value": "[reference(variables('deployLaw')).outputs.logAnalyticsResourceId.value]" 274 | }, 275 | "rsVaultAdvBuPolicyResId": { 276 | "value": "[reference(variables('deployRsVltBackupPolicies')).outputs.cstVmAdvPolResId.value]" 277 | }, 278 | "rsVaultBscBuPolicyResId": { 279 | "value": "[reference(variables('deployRsVltBackupPolicies')).outputs.cstVmBscPolResId.value]" 280 | }, 281 | "rsVaultName": { 282 | "value": "[reference(variables('deployRsVlt')).outputs.rsVaultName.value]" 283 | }, 284 | "rsVaultRg": { 285 | "value": "[variables('rgNamePriVlt')]" 286 | }, 287 | "secLocation": { 288 | "value": "[parameters('secLocation')]" 289 | }, 290 | "secResourceGroupName": { 291 | "value": "[variables('rgNameSecWl')]" 292 | }, 293 | "tags": { 294 | "value": "[parameters('tags')]" 295 | }, 296 | "uniqueData": { 297 | "value": "[parameters('uniqueData')]" 298 | }, 299 | "vmAdminPassword": { 300 | "value": "[parameters('vmAdminPassword')]" 301 | }, 302 | "vmAdminUsername": { 303 | "value": "[parameters('vmAdminUsername')]" 304 | } 305 | }, 306 | "templateLink": { 307 | "uri": "[variables('templateUriInfRes')]", 308 | "contentVersion": "1.0.0.0" 309 | } 310 | } 311 | } 312 | ], 313 | "outputs": { 314 | } 315 | } -------------------------------------------------------------------------------- /dsc/windowsdevvm.ps1: -------------------------------------------------------------------------------- 1 | configuration WindowsDevVM { 2 | param 3 | ( 4 | [Parameter(Mandatory)] 5 | [String]$MachineName, 6 | 7 | [Parameter(Mandatory)] 8 | [System.Management.Automation.PSCredential]$Admincreds, 9 | 10 | [Parameter(Mandatory=$false)] 11 | [string]$SystemTimeZone = "Eastern Standard Time", 12 | 13 | [Int]$RetryCount = 20, 14 | [Int]$RetryIntervalSec = 30 15 | ) 16 | 17 | Import-DscResource -ModuleName xStorage, xNetworking, ComputerManagementDsc, PSDesiredStateConfiguration 18 | $Interface = Get-NetAdapter | Where-Object Name -Like "Ethernet*" | Select-Object -First 1 19 | $InterfaceAlias = $($Interface.Name) 20 | 21 | Node localhost 22 | { 23 | LocalConfigurationManager 24 | { 25 | RebootNodeIfNeeded = $true 26 | } 27 | 28 | TimeZone TimeZoneSet 29 | { 30 | IsSingleinstance = 'Yes' 31 | TimeZone = $SystemTimeZone 32 | } 33 | 34 | IEEnhancedSecurityConfiguration 'DisableForAdministrators' 35 | { 36 | Role = 'Administrators' 37 | Enabled = $false 38 | } 39 | 40 | IEEnhancedSecurityConfiguration 'DisableForUsers' 41 | { 42 | Role = 'Users' 43 | Enabled = $false 44 | } 45 | 46 | xWaitforDisk Disk1 47 | { 48 | DiskId = 1 49 | DiskIdType = "Number" 50 | RetryIntervalSec = $RetryIntervalSec 51 | RetryCount = $RetryCount 52 | } 53 | 54 | xDisk DataDisk 55 | { 56 | DiskId = 1 57 | DiskIdType = "Number" 58 | DriveLetter= "F" 59 | DependsOn = "[xWaitForDisk]Disk1" 60 | } 61 | } 62 | } -------------------------------------------------------------------------------- /dsc/windowsdevvm.zip: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/dsc/windowsdevvm.zip -------------------------------------------------------------------------------- /exercises/README.md: -------------------------------------------------------------------------------- 1 | # Azure Backup Exercises 2 | 3 | The exercises in this repository demonstrate the core capabilities of Azure Backup. Ensure you have deployed the lab and followed the pre and post-configuration steps outlined [here](../README.md) prior to attempting these exercises. 4 | 5 | * [Exercise 1 - Azure Backup Overview](/exercises/exercise1.md) 6 | * [Exercise 2 - Azure Backup Policies](/exercises/exercise2.md) 7 | * [Exercise 3 - Azure Backup Center](/exercises/exercise3.md) 8 | * [Exercise 4 - Restoring a Virtual Machine](/exercises/exercise4.md) 9 | * [Exercise 5 - Backup a Virtual Machine](/exercises/exercise5.md) 10 | * [Exercise 6 - Backup and Restore Azure Files](/exercises/exercise6.md) 11 | * [Exercise 7 - Backup and Restore Azure Blobs](/exercises/exercise7.md) 12 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /exercises/exercise1.md: -------------------------------------------------------------------------------- 1 | ## Exercise 1 - Azure Backup Overview 2 | 3 | **NOTE: You should let this lab run for 24 hours before proceeding with these exercises to allow for restore points to be created** 4 | 5 | In this exercise you will open the Azure Portal to look at the resources deployed with the lab. You will learn about [Azure Backup Architecture](https://learn.microsoft.com/en-us/azure/backup/backup-architecture) and its resources such as the [Recovery Services Vault](https://docs.microsoft.com/en-us/azure/backup/backup-azure-recovery-services-vault-overview) and [Backup Vault](https://learn.microsoft.com/en-us/azure/backup/backup-vault-overview). 6 | 7 | Open the Azure Portal and select the resource group that begins with rgbckvltpri. The resource group contains two resources, a Recovery Services Vault and a Backup Vault. 8 | 9 | ![recovery services vault resource group](../images/exercise1-image1.png) 10 | 11 | The [Recovery Services Vault](https://learn.microsoft.com/en-us/azure/backup/backup-azure-recovery-services-vault-overview) is used by the Azure Backup service to store data that is backed up for Azure Virtual Machines, Azure Files, files and folders on a Windows Server using the [MARS (Microsoft Azure Recovery Services) agent](https://learn.microsoft.com/en-us/azure/backup/install-mars-agent), and other resources. It also stores backup policies which control how these items are backup up. 12 | 13 | You will notice the Recovery Services Vault has been deployed to the same region as the workload. When used for backup, Recovery Services Vault must be created in the same region and subscription as the workloads that are being backed up. 14 | 15 | 16 | The [Backup Vault](https://learn.microsoft.com/en-us/azure/backup/backup-vault-overview) is another resource used by the Azure Backup service. Backup Vaults are used to backup blobs in Azure Storage, Managed Disks, and Azure Database for PostgreSQL. It also holds the backup policies which control how the data is backed up. An interesting thing to note about Backup Vaults is that for blobs and managed disks, the data is never transferred to the Backup Vault and the vault is instead used as an orchestration model which activites built-in features of the services such as blob point-in-time restore or the snapshot capability of managed disks. 17 | 18 | Unlike Recovery Services Vaults, Backup Vaults do not need to be within the same subscription as the workloads that are being backed up when backing up Managed Disks or blobs. 19 | 20 | Select the resource group that begins with rgasrwlpri. This resource group is used to hold the resources that represent the workload in its normal state. 21 | 22 | ![primary workload resource group](../images/exercise1-image2.png) 23 | 24 | The resource group contains three virtual machines. The VM named vmw-pri-1-cf is a Windows Server that has been configured for backup. The VM named vml-pri-1-cf is a Linux server that has been configured for backup. The third VM named vmw-pri-2-ncf is not yet configured for backup and will be used in a later exercise. 25 | 26 | An Azure Bastion instance is provided to allow for remote access to the VMs in both the primary region and VMs failed over to the secondary region. 27 | 28 | The Log Analytics Workspace is used to capture Recovery Services logs and metrics. The vault has been configured to send its diagnostics data to the workspace. 29 | 30 | Select the resource group that begins with rgbackirpri1. This resource group contains the restore point collections. 31 | 32 | ![secondary resources group](../images/exercise1-image3.png) 33 | 34 | [Restore point collections include one or more restore points](https://learn.microsoft.com/en-us/azure/virtual-machines/virtual-machines-create-restore-points) which are resources that contain the virtual machine configuration and snapshots of the attached managed disks. Snapshots can be [application-consistent or file-consistent](https://learn.microsoft.com/en-us/azure/backup/backup-azure-vms-introduction#snapshot-consistency). A single restore point collection can include multiple restore points which the retention is maintained through the backup policy. 35 | 36 | *Take note that the lab environment needs to be left running for a period of time to generate the restore point collections and restore points.* 37 | 38 | When backing up virtual machines with the Azure Backup service, a restore point collection and restore point is first created for the virtual machine. The contents of this restore point are stored in a resource group within the customer's subscription. This is referred to as the opational tier. Once per day, a recovery point is written to the Recovery Services Vault. This is referred to as the standard or vault tier. Restore points can optionally be moved to the [archive tier](https://learn.microsoft.com/en-us/azure/backup/archive-tier-support). This tier [can sometimes result in lower costs](https://learn.microsoft.com/en-us/azure/backup/archive-tier-support#archive-recommendations-only-for-azure-virtual-machines) for storage of the backups. [This video](https://learn.microsoft.com/en-us/azure/backup/archive-tier-support#how-azure-backup-moves-recovery-points-to-the-vault-archive-tier) provides an excellent overview of how restore points traverse storage tiers. 39 | 40 | Restore points in the operational tier are used with the [instant restore feature](https://learn.microsoft.com/en-us/azure/backup/backup-instant-restore-capability) which can restore a virtual machine to a prior state in a faster than restoring from a restore point in the standard/vault tier. A backup policy determines how long restore points are retained in the operational tier. The next exercise will explore backup policies. 41 | 42 | This completes exercise 1. You can now proceed to [exercise 2](/exercises/exercise2.md). -------------------------------------------------------------------------------- /exercises/exercise2.md: -------------------------------------------------------------------------------- 1 | ## Exercise 2 - Azure Backup Policies 2 | 3 | In this exercise you will explore the [backup policies](https://learn.microsoft.com/en-us/azure/backup/azure-backup-glossary#backup-rule--backup-policy) used by the Azure Backup service to control the frequency and retention of backups. Both Recovery Services Vaults and Backup Vaults use backup policies. 4 | 5 | Open the Azure Portal and select the resource group that begins with rgbckvltpri. This resource group contains the Recovery Services Vault and Backup Vault used in the lab. Select the Recovery Services Vault which will begin with vlt. Once within the blade for the Recovery Services Vault, select the Backup policies menu item seen in the screenshot below. 6 | 7 | ![Recovery Services Vault](../images/exercise2-image1.png) 8 | 9 | Backup policies for virtual machines are either [standard (sometimes referred to as basic) policies](https://learn.microsoft.com/en-us/azure/backup/backup-azure-arm-vms-prepare) or [enhanced policies](https://learn.microsoft.com/en-us/azure/backup/backup-azure-vms-enhanced-policy). Standard policies are capable of creating one backup a day and retaining restore points for up to 5 days, while enhanced policies can create multiple backups a day (taking multiple backups a day is in public preview as of 1/2023) and retain restore points for up to 30 days. 10 | 11 | ![Backup Policies](../images/exercise2-image2.png) 12 | 13 | The Recovery Service Vault in this lab is created with three backup policies. The policy beginning with cstBscVmPolicy configures protected items assigned this policy to backup once a day at midnight based on Eastern Standard Time. Restore Points are retained for 5 days in the operational tier to allow for instant restore. Daily backups stored in the standard/vault tier are retained for 7 days, weekly backups for 12 weeks, monthly backups for 12 months, and yearly backups for 3 years. This policy is associated with the Linux VM named vml-pri-1-cf. 14 | 15 | There are two options not pictured in the screenshot below. The first is to automatically send backups in the standard/vault tier to the [archive tier](https://learn.microsoft.com/en-us/azure/backup/archive-tier-support). The other option configures the policy to use a custom resource group to store restore point collections. By default, the service will create a resource group with a generic name to store restore point collections. 16 | 17 | ![Standard Policy](../images/exercise2-image3.png) 18 | 19 | The backup policy beginning with cstAdvVmPolicy is an example of an enhanced policy. The policy is configured to create a backup every 4 hours starting at midnight and creating these backups for all 24 hours of the day. This effectively creates 6 restore points a day. Restore Points are retained for 5 days in the operational tier to allow for instant restore. Daily backups stored in the standard/vault tier are retained for 7 days, weekly backups for 12 weeks, monthly backups for 12 months, and yearly backups for 3 years. This policy is associated with the Windows VM named vmw-pri-1-cf. 20 | 21 | ![Enhanced Policy](../images/exercise2-image4.png) 22 | 23 | The third backup policy beginning with cstFilePolicy is an example of a backup policy for Azure Files. Each resource type that can be backed up to a Recovery Services Vault or Backup Vault has its own schema for the backup policy. This policy is configured to backup the Azure Files share every 4 hours starting at midnight and creating these backs for 23 hours of the day (for some reason it does not allow for 24). Daily backups stored in the standard/vault tier are retained for 7 days, weekly backups for 12 weeks, monthly backups for 12 months, and yearly backups for 3 years. 24 | 25 | With Azure File shares snapshots are created of the share using the [snapshot feature of Azure Files](https://learn.microsoft.com/en-us/azure/storage/files/storage-snapshots-files). You have the option of restoring the entire share or individual files. Metadata about the backup is stored in the Recovery Services Vault, not the snapshots themselves. These are stored with the storage account the file share lives in. 26 | 27 | ![Azure Files Share](../images/exercise2-image5.png) 28 | 29 | Backup Vaults also use backup policies. Open the Azure Portal and select the resource group that begins with rgbckvltpri. Select the Backup Vault which will begin with buvlt. Once within the blade for the Backup Vault, select the Backup policies menu item seen in the screenshot below. 30 | 31 | Take note that when using a Backup Vault filters are enabled to filter to specific types of resources. In the Backup Policies blade, you will need to set the Datasource to the appropriate resource to see policies and resources that are being backed up. 32 | 33 | ![Backup Vault](../images/exercise2-image6.png) 34 | 35 | The Backup Vault in this lab is created with two custom policies. One policy is created for Azure Disks and one for Azure Blobs. 36 | 37 | The policy for Azure Disks begins with cstDiskPolicy. This policy is configured to backup the managed disk every hour. The first backup taken each week is retained for 7 days. The weekly backup is retained for 12 weeks. 38 | 39 | A virtual machine backed up through Recovery Services Vault backups up the entire machine and all of the disks attached to it. Azure Disk backup is useful when you need more frequent backups of a specific managed disk, such as a data disk. 40 | 41 | ![Disk Policy](../images/exercise2-image7.png) 42 | 43 | The second policy in the Backup Vault is for Azure Blobs stored in an Azure Storage Account. This policy's name begins with cstBlobPolicy. It is configured to retain backups for 30 days. Notice that within the policy the backup frequency is set to non-applicable. This is because the [blob versioning](https://learn.microsoft.com/en-us/azure/storage/blobs/versioning-overview) feature of Azure Storage is enabled on the Azure Storage account by the backup. This feature automatically retains previous versions of the blob. 44 | 45 | Like the Azure Disks backup feature, the Azure Blob backup feature does not transfer data to the Backup Vault. The prior blob versions are retained within the same Azure Storage Account. If you'd prefer to have the blobs stored in another Azure Storage Account in a different resource group or subscription, you should look at [object replication](https://learn.microsoft.com/en-us/azure/storage/blobs/object-replication-overview) instead. 46 | 47 | ![Blob Policy](../images/exercise2-image8.png) 48 | 49 | This completes exercise 2. You can now proceed to [exercise 3](/exercises/exercise3.md). -------------------------------------------------------------------------------- /exercises/exercise3.md: -------------------------------------------------------------------------------- 1 | ## Exercise 3 - Azure Backup Center 2 | 3 | In this exercise you will open the Azure Portal and explore the Azure Backup Center. 4 | 5 | While you could maintain your backups by interacting with the Recovery Services Vaults and Backup Vaults individually, that methodology breaks down at scale. [Azure Backup Center](https://learn.microsoft.com/en-us/azure/backup/backup-center-overview) provides a central location to administer all of the Recovery Services Vaults and Backup Vaults across subscriptions associated with the Azure AD tenant. 6 | 7 | Open the Azure Portal and use the search bar to find and access the Backup Center blade. Once the blade opens, a summary of the state of backups configured across the platform is presented. Simliar to the Backup Vault, the overview provides is filtered by datasource type. In the screenshot below, the datasource type is set to Azure Virtual Machines. 8 | 9 | ![Backup Center](../images/exercise3-image1.png) 10 | 11 | Selecting the Backup instances menu item under the Manage section displays all of the resources of the filtered datasource type that are being backed up. In the screenshot below, the two virtual machines configured for backup are displayed along with the vault the machine is configured to backup to and the latest restore point available. 12 | 13 | ![Backup Instances](../images/exercise3-image2.png) 14 | 15 | Selecting a specific virtual machine displays a detailed status of the backups for the virtual machine. In the screenshot below, the vml-pri-1-cf virtual machine is shown. The status of the prior backup, associated Backup Policy, and restore points are listed as well as the storage tier each backup is in. Operations such as the creation of an on-demand backup, restore of the VM, [recovering a specific file](https://learn.microsoft.com/en-us/azure/backup/tutorial-restore-files), or even restoring the virtual machine to another region via the [cross-region restore feature](https://azure.microsoft.com/en-us/blog/cross-region-restore-crr-for-azure-virtual-machines-using-azure-backup/). 16 | 17 | Note how the restore points for this machine are file-system consistent (often referred to as crash consistent). While Azure Backup can perform application-consistent backups, Linux machines require a [framework (collection of scripts)](https://learn.microsoft.com/en-us/azure/backup/backup-azure-linux-app-consistent) be implemented to support this. Windows machines do not require this extra configuration and application-consistent backups are provided by default. 18 | 19 | ![Linux VM Backup](../images/exercise3-image3.png) 20 | 21 | Selecting the Backup Policies menu item under Manage displays all of the Backup Policies across the both Recovery Services Vaults and Backup Vaults across all subscriptions in the tenant. The Vaults menu item does the same to display all of the Recovery Services Vaults and Backup Vaults. 22 | 23 | The Backup jobs menu item under Monitoring and Reporting displays the status of the backup jobs performed by the service. You can select a specific backup job to get useful information such as information on failed backups or the duration of successful backups. 24 | 25 | ![Backup Job Status](../images/exercise3-image4.png) 26 | 27 | The Alerts menu item under Monitoring and Reporting. This section of Backup Center will display [Azure Monitor alerts](https://learn.microsoft.com/en-us/azure/backup/backup-azure-monitoring-built-in-monitor?tabs=recovery-services-vaults#azure-monitor-alerts-for-azure-backup) and [metric alerts](https://learn.microsoft.com/en-us/azure/backup/metrics-overview) for Azure Backup. These alerts include security alerts such as the deletion of data or a failed backup job. Setting up the alerting is beyond the scope of these exercises, but is [outlined in detail within the public documentation](https://learn.microsoft.com/en-us/azure/backup/backup-azure-monitoring-built-in-monitor?tabs=recovery-services-vaults#azure-monitor-alerts-for-azure-backup). 28 | 29 | ![Azure Backup Alerts](../images/exercise3-image5.png) 30 | 31 | The Backup Reports menu item provides an [Azure Workbook](https://learn.microsoft.com/en-us/azure/azure-monitor/visualize/workbooks-overview) that can be used to monitor the the state of backups across the customer's Azure platform such as information on the data amount of space used for backups. 32 | 33 | ![Azure Backup Workbook](../images/exercise3-image6.png) 34 | 35 | Under the Policy and Compliance sections, compliance with custom or [built-in policies for Azure Backup](https://learn.microsoft.com/en-us/azure/backup/policy-reference) applied to a scope containing the resource group can be viewed. Additionally, a summary of resources not configured for backup can be displayed using the Protectable datasources menu item. 36 | 37 | ![Protectable Items](../images/exercise3-image7.png) 38 | 39 | This completes exercise 3. You can now proceed to [exercise 4](/exercises/exercise4.md). -------------------------------------------------------------------------------- /exercises/exercise4.md: -------------------------------------------------------------------------------- 1 | ## Exercise 4 - Restoring a Virtual Machine with Azure Backup Center 2 | 3 | In this exercise you will restore a virtual machine using Azure Backup Center. 4 | 5 | When restoring a virtual machine using Azure Backup a new machine can be created from the restore point, a managed disk can be restored which can then be attached to a virtual machine, or existing managed disks can be replaced on the virtual machine. In this exercise you will create a new machine from a restore point. 6 | 7 | Open the Azure Portal and use the search bar to find and access the Backup Center blade. Once the blade opens navigate to the Backup instances menu item under the Manage section. Select the machine named vmw-pri-1-cf. 8 | 9 | ![Select Azure VM](../images/exercise4-image1.png) 10 | 11 | On backup item screen, select the option to Restore the virtual machine. 12 | 13 | ![Restore VM](../images/exercise4-image2.png) 14 | 15 | On the Restore Virtual Machine screen you are prompted to select a restore point. The consistency and storage tier is included in the description of the restore point. Restore points in the snapshot tier are eligible for instant restore for a quick restore while vault-standard are stored within the vault and will take longer to restore. 16 | 17 | ![Restore Points](../images/exercise4-image3.png) 18 | 19 | After selecting the restore point you are prompted with how you would like the restore point restored. For this exercise, you will create a new virtual machine from the backup. 20 | 21 | You are then prompted to set the name, subscription, resource group, virtual network, subnet, [staging location](https://learn.microsoft.com/en-us/answers/questions/933909/explain-me-the-concept-of-staging-location), and optionally attaching managed item to the restore virtual machine. Choose the storage account beginning with stfile for the staging location and then select the Restore button. 22 | 23 | ![Restore Points](../images/exercise4-image4.png) 24 | 25 | The status of the restore job can be monitored by navigating to the Backup jobs menu item in the monitoring and reporting seciton. Once complete the virtual machine will be available to access 26 | 27 | ![Restore Job Status](../images/exercise4-image5.png) 28 | 29 | Once complete, the virtual machine will be available to access. 30 | 31 | This completes exercise 4. You can now proceed to [exercise 5](/exercises/exercise5.md). -------------------------------------------------------------------------------- /exercises/exercise5.md: -------------------------------------------------------------------------------- 1 | ## Exercise 5 - Backup a Virtual Machine with Azure Backup Center 2 | 3 | In this exercise you will configure a virtual machine for backup using Azure Backup Center. 4 | 5 | Open the Azure Portal and use the search bar to find and access the Backup Center blade. Once the blade opens select the Backup button in the overview section. 6 | 7 | On the Start: Configure Backup screen select the Azure Virtual machine as the datasource type and select the Recovery Services Vault with the name beginning with vlt. Select the Continue button. 8 | 9 | ![Start: Configure Backup](../images/exercise5-image1.png) 10 | 11 | On the Configure Backup screen you are prompted to select a backup policy. You can filter the policies to either Standard or Enhanced. For this exercise select enhanced policies and choose the policy that begins with cstAdvVmPolicy. You must then add the virtual machine named vmw-pri-2-ncf. 12 | 13 | Select the Enable Backup button. This will configure the machine for Azure Backup. 14 | 15 | ![Configure Backup](../images/exercise5-image2.png) 16 | 17 | Once the deployment is complete, the machine will be listed as a backup instance in Azure Backup Center. 18 | 19 | ![Backup instance](../images/exercise5-image3.png) 20 | 21 | This completes exercise 5. You can now proceed to [exercise 6](/exercises/exercise6.md). -------------------------------------------------------------------------------- /exercises/exercise6.md: -------------------------------------------------------------------------------- 1 | ## Exercise 6 - Backup and Restore Azure File Shares 2 | 3 | In this exercise you will an Azure File share. 4 | 5 | Open the Azure Portal and [upload a sample file](https://learn.microsoft.com/en-us/azure/storage/files/storage-how-to-use-files-portal?tabs=azure-portal) to the samplefiles share in the storage account beginning with stfile. 6 | 7 | Once the file is uploaded, open up Azure Backup Center, navigate to the Oveview page and select the Backup option. Select the Azure Files (Azure Storage) as the datasource type and select the Recovery Services Vault with the name beginning with vlt. 8 | 9 | ![Start: Configure Backup](../images/exercise6-image1.png) 10 | 11 | On the Configure Backup screen select the Azure Storage account with the name beginning with stfile. The storage account will register with the Recovery Services Vault. 12 | 13 | ![Register with vault](../images/exercise6-image2.png) 14 | 15 | Add the sampleshare file share and select the backup policy with the name beginning with cstFilePolicy. Select the Enable backup button. 16 | 17 | It will take a few minutes to enable the backup. 18 | 19 | ![Enable Backup](../images/exercise6-image3.png) 20 | 21 | You will now create an on-demand backup. 22 | 23 | Navigate back to Backup Center when the deployment is complete. Select the Backup instances and choose Azure Files (Azure Storage) as the datasource type. Choose the stfile storage account and select the Backup now option. 24 | 25 | The backup will be very quick. 26 | 27 | ![On-Demand Backup](../images/exercise6-image4.png) 28 | 29 | Once the backup is complete, navigate to the file share and delete the sample file that you uploaded and then navigate back to Backup Center. 30 | 31 | You will now restore the file you deleted. 32 | 33 | Open the backup instance for the stfile storage account. Notice that you can restore either the entire share or an individual file. Select the option for File Recovery. 34 | 35 | ![File Recovery](../images/exercise6-image5.png) 36 | 37 | Choose the newly created restore point, select the original location, and add the file you wish to restore. Select the Restore button when complete. 38 | 39 | The restore will be very quick. 40 | 41 | ![Restore file](../images/exercise6-image6.png) 42 | 43 | Navigate back to the stfile storage account and open the file share. You will see the file you restored is back. 44 | 45 | This completes exercise 6. You can now proceed to [exercise 7](/exercises/exercise7.md). -------------------------------------------------------------------------------- /exercises/exercise7.md: -------------------------------------------------------------------------------- 1 | ## Exercise 7 - Backup and Restore Azure Blobs 2 | 3 | In this exercise you will backup an Azure Blob container for backup. 4 | 5 | Open the Azure Portal and [upload the file to sampleblobs container](https://learn.microsoft.com/en-us/azure/storage/blobs/storage-quickstart-blobs-portal) in the storage account beginning with stblob. 6 | 7 | Once the file is uploaded, open up Azure Backup Center, navigate to the Oveview page and select the Backup option. Select the Azure Blobs (Azure Storage) as the datasource type and select the Recovery Services Vault with the name beginning with vlt. Select the Continue button. 8 | 9 | ![Start: Configure Backup](../images/exercise7-image1.png) 10 | 11 | On the basic page of the Configure Backup select the Azure Blobs (Azure Storage) as the datasource type and select the Backup Vault with the name beginning with buvlt. 12 | 13 | ![Configure Backup - Basic](../images/exercise7-image2.png) 14 | 15 | On the Backup policy page of the Configure Backup select the backup policy with the name beginning with cstBlobPolicy. Select the next button. 16 | 17 | On the Datasources page of the Configure backup select the stblob storage account as a datasource. 18 | 19 | The vault will attempt to configure the storage account for backup. This will fail due to the missing role assignment. When backing up Azure Blobs, the Backup Vault places a delete lock on the storage account. It requires that the system-assigned managed identity for the vault has the Storage Account Backup Contributor role on the storage account. 20 | 21 | Select the Assign missing roles option to automatically create the role assignment. It can take up to ten minutes for the roles to propagate across the Azure environment. 22 | 23 | Once complete, select the option to complete the backup. 24 | 25 | ![Configure Backup - Datasources](../images/exercise7-image3.png) 26 | 27 | Navigate to the blob container on the stblob storage account and delete the file you uploaded. Note the time you delete the blob, you will need this when selecting a restore point. 28 | 29 | Navigate back to Backup Center and open the backup instance for the stblob storage account and select the restore option. Select the restore point and select the Next: Restore parameters button. 30 | 31 | ![Select Restore Point](../images/exercise7-image4.png) 32 | 33 | On the Restore parameters page you can choose to restore all blobs, a specific container or containers, or restore blobs based on a prefix match. For this exercise you will chose the restore all blobs option. Select the Validate button, then the Next: Review + restore option, and finally the Restore button. 34 | 35 | ![Select Restore Option](../images/exercise7-image5.png) 36 | 37 | While the restore process is underway, the containers will be unavailable to read or write to. Once complete, the blob you deleted will be restored. 38 | 39 | This completes exercise 7. -------------------------------------------------------------------------------- /images/exercise1-image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise1-image1.png -------------------------------------------------------------------------------- /images/exercise1-image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise1-image2.png -------------------------------------------------------------------------------- /images/exercise1-image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise1-image3.png -------------------------------------------------------------------------------- /images/exercise2-image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise2-image1.png -------------------------------------------------------------------------------- /images/exercise2-image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise2-image2.png -------------------------------------------------------------------------------- /images/exercise2-image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise2-image3.png -------------------------------------------------------------------------------- /images/exercise2-image4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise2-image4.png -------------------------------------------------------------------------------- /images/exercise2-image5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise2-image5.png -------------------------------------------------------------------------------- /images/exercise2-image6.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise2-image6.png -------------------------------------------------------------------------------- /images/exercise2-image7.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise2-image7.png -------------------------------------------------------------------------------- /images/exercise2-image8.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise2-image8.png -------------------------------------------------------------------------------- /images/exercise3-image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise3-image1.png -------------------------------------------------------------------------------- /images/exercise3-image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise3-image2.png -------------------------------------------------------------------------------- /images/exercise3-image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise3-image3.png -------------------------------------------------------------------------------- /images/exercise3-image4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise3-image4.png -------------------------------------------------------------------------------- /images/exercise3-image5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise3-image5.png -------------------------------------------------------------------------------- /images/exercise3-image6.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise3-image6.png -------------------------------------------------------------------------------- /images/exercise3-image7.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise3-image7.png -------------------------------------------------------------------------------- /images/exercise4-image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise4-image1.png -------------------------------------------------------------------------------- /images/exercise4-image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise4-image2.png -------------------------------------------------------------------------------- /images/exercise4-image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise4-image3.png -------------------------------------------------------------------------------- /images/exercise4-image4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise4-image4.png -------------------------------------------------------------------------------- /images/exercise4-image5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise4-image5.png -------------------------------------------------------------------------------- /images/exercise5-image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise5-image1.png -------------------------------------------------------------------------------- /images/exercise5-image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise5-image2.png -------------------------------------------------------------------------------- /images/exercise5-image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise5-image3.png -------------------------------------------------------------------------------- /images/exercise6-image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise6-image1.png -------------------------------------------------------------------------------- /images/exercise6-image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise6-image2.png -------------------------------------------------------------------------------- /images/exercise6-image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise6-image3.png -------------------------------------------------------------------------------- /images/exercise6-image4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise6-image4.png -------------------------------------------------------------------------------- /images/exercise6-image5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise6-image5.png -------------------------------------------------------------------------------- /images/exercise6-image6.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise6-image6.png -------------------------------------------------------------------------------- /images/exercise7-image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise7-image1.png -------------------------------------------------------------------------------- /images/exercise7-image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise7-image2.png -------------------------------------------------------------------------------- /images/exercise7-image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise7-image3.png -------------------------------------------------------------------------------- /images/exercise7-image4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise7-image4.png -------------------------------------------------------------------------------- /images/exercise7-image5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/images/exercise7-image5.png -------------------------------------------------------------------------------- /presentation/Azure Backup.pptx: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mattfeltonma/azure-backup-demo/8c956b1773eafb4ed51cd4e57585a0bd24e682d6/presentation/Azure Backup.pptx -------------------------------------------------------------------------------- /scripts/prepare-linux-vm.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | # Add repositories 4 | curl -sL https://packages.microsoft.com/keys/microsoft.asc | 5 | gpg --dearmor | 6 | sudo tee /etc/apt/trusted.gpg.d/microsoft.gpg > /dev/null 7 | AZ_REPO=$(lsb_release -cs) 8 | echo "deb [arch=amd64] https://packages.microsoft.com/repos/azure-cli/ $AZ_REPO main" | 9 | sudo tee /etc/apt/sources.list.d/azure-cli.list 10 | 11 | # Install Azure CLI 12 | sudo apt-get update 13 | sudo apt-get -y install ca-certificates curl apt-transport-https lsb-release gnupg 14 | sudo apt-get -y install azure-cli 15 | 16 | # Create test files and folders 17 | sudo mkdir /var/sample-files 18 | cat < samplefile1.txt 19 | This is sample file 1 20 | EOF 21 | 22 | cat < samplefile2.txt 23 | This is sample file 2 24 | EOF 25 | 26 | cat < samplefile3.txt 27 | This is sample file 3 28 | EOF 29 | 30 | sudo chmod -R 644 /var/sample-files -------------------------------------------------------------------------------- /scripts/prepare-windows-vm.ps1: -------------------------------------------------------------------------------- 1 | # Setup logging 2 | Start-Transcript -path "C:\MachinePrep\logs\log.txt" 3 | 4 | # Create directory to store installation files 5 | New-Item -ItemType directory -Path C:\MachinePrep\files 6 | 7 | try { 8 | # Install RSAT Tools 9 | Write-Host "Installing RSAT Tools..." 10 | Install-WindowsFeature -IncludeAllSubFeature RSAT 11 | } 12 | catch { 13 | Write-Host "Unable to install RSAT Tools" 14 | } 15 | 16 | try { 17 | 18 | # Install nuget package manager 19 | Write-Host "Installing nuget..." 20 | Install-PackageProvider -Name Nuget -Force 21 | 22 | # Install Azure CLI 23 | Write-Host "Downloading Azure CLI..." 24 | $cliUri = "https://aka.ms/installazurecliwindows" 25 | Invoke-WebRequest -Uri $cliUri -OutFile .\AzureCLI.msi; Start-Process msiexec.exe -Wait -ArgumentList '/I AzureCLI.msi /quiet'; rm .\AzureCLI.msi 26 | 27 | # Install Azure PowerShell 28 | Write-Host "Installing Azure CLI..." 29 | Install-Module -Name Az -Scope CurrentUser -Repository PSGallery -Force 30 | } 31 | 32 | catch { 33 | Write-Host "Unable to install Azure CLI" 34 | } 35 | 36 | try { 37 | # Create test files 38 | Write-Host "Creating test files" 39 | 40 | New-Item 'F:\sample-files' -ItemType directory 41 | "This is sample file 1" | Out-File F:\sample-files\samplefile1.txt 42 | "This is sample file 2" | Out-File F:\sample-files\samplefile2.txt 43 | "This is sample file 3 and its original content" | Out-File F:\sample-files\samplefile3.txt 44 | } 45 | catch { 46 | Write-Host "Unable to create test files" 47 | } 48 | 49 | try { 50 | # Download MARS agent 51 | $marsUri = "https://aka.ms/azurebackup_agent" 52 | $marsDest = "C:\MachinePrep\files\mars-agent.exe" 53 | Invoke-WebRequest -Uri $marsUri -OutFile $marsDest 54 | 55 | # Install MARS agent 56 | Start-Process $marsDest -ArgumentList '/q' 57 | 58 | } 59 | 60 | catch { 61 | Write-Host "Unable to install MARS agent" 62 | } 63 | Stop-Transcript -------------------------------------------------------------------------------- /templates/deploy-buv-backup-policies.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "buVaultName": { 6 | "type": "string", 7 | "metadata": { 8 | "description": "The name of the Backup Vault" 9 | } 10 | }, 11 | "uniqueData": { 12 | "type": "string", 13 | "metadata": { 14 | "description": "Data used to append to resources to ensure uniqueness" 15 | }, 16 | "defaultValue": "[substring(newGuid(),0,8)]" 17 | } 18 | }, 19 | "variables": { 20 | "buVltApiVersion": "2022-05-01", 21 | "backupDiskPolicyName": "[concat('cstDiskPolicy',parameters('uniqueData'))]", 22 | "backupBlobPolicyName": "[concat('cstBlobPolicy',parameters('uniqueData'))]", 23 | "backupRunTime": "R/2022-08-09T04:00:00+00:00/PT1H", 24 | "retentionDailyDuration": "P7D", 25 | "retentionWeeklyDuration": "P12W", 26 | "retentionBlob": "P30D" 27 | }, 28 | "resources": [ 29 | { 30 | "name": "[concat(parameters('buVaultName'), '/', variables('backupDiskPolicyName'))]", 31 | "type": "Microsoft.DataProtection/backupVaults/backupPolicies", 32 | "apiVersion": "[variables('buVltApiVersion')]", 33 | "properties": { 34 | "objectType": "BackupPolicy", 35 | "datasourceTypes": [ 36 | "Microsoft.Compute/disks" 37 | ], 38 | "policyRules": [ 39 | { 40 | "backupParameters": { 41 | "backupType": "Incremental", 42 | "objectType": "AzureBackupParams" 43 | }, 44 | "trigger": { 45 | "schedule": { 46 | "repeatingTimeIntervals": [ 47 | "[variables('backupRunTime')]" 48 | ], 49 | "timeZone": "UTC" 50 | }, 51 | "taggingCriteria": [ 52 | { 53 | "criteria": [ 54 | { 55 | "absoluteCriteria": [ 56 | "FirstOfWeek" 57 | ], 58 | "objectType": "ScheduleBasedBackupCriteria" 59 | } 60 | ], 61 | "tagInfo": { 62 | "tagName": "Weekly", 63 | "id": "Weekly_" 64 | }, 65 | "taggingPriority": 20, 66 | "isDefault": false 67 | }, 68 | { 69 | 70 | "tagInfo": { 71 | "tagName": "Default", 72 | "id": "Default_" 73 | }, 74 | "taggingPriority": 99, 75 | "isDefault": true 76 | } 77 | ], 78 | "objectType": "ScheduleBasedTriggerContext" 79 | }, 80 | "dataStore": { 81 | "dataStoreType": "OperationalStore", 82 | "objectType": "DataStoreInfoBase" 83 | }, 84 | "name": "BackupHourly", 85 | "objectType": "AzureBackupRule" 86 | }, 87 | { 88 | "name": "Default", 89 | "isDefault": true, 90 | "objectType": "AzureRetentionRule", 91 | "ruleType": "Retention", 92 | "lifecycles": [ 93 | { 94 | "sourceDataStore": { 95 | "dataStoreType": "OperationalStore", 96 | "objectType": "DataStoreInfoBase" 97 | }, 98 | "deleteAfter": { 99 | "objectType": "AbsoluteDeleteOption", 100 | "duration": "[variables('retentionDailyDuration')]" 101 | } 102 | } 103 | ] 104 | }, 105 | { 106 | "name": "Weekly", 107 | "isDefault": false, 108 | "objectType": "AzureRetentionRule", 109 | "ruleType": "Retention", 110 | "lifecycles": [ 111 | { 112 | "sourceDataStore": { 113 | "dataStoreType": "OperationalStore", 114 | "objectType": "DataStoreInfoBase" 115 | }, 116 | "deleteAfter": { 117 | "objectType": "AbsoluteDeleteOption", 118 | "duration": "[variables('retentionWeeklyDuration')]" 119 | } 120 | } 121 | ] 122 | } 123 | ] 124 | } 125 | }, 126 | { 127 | "name": "[concat(parameters('buVaultName'), '/', variables('backupBlobPolicyName'))]", 128 | "type": "Microsoft.DataProtection/backupVaults/backupPolicies", 129 | "apiVersion": "[variables('buVltApiVersion')]", 130 | "properties": { 131 | "objectType": "BackupPolicy", 132 | "datasourceTypes": [ 133 | "Microsoft.Storage/storageAccounts/blobServices" 134 | ], 135 | "policyRules": [ 136 | { 137 | "isDefault": true, 138 | "name": "Default", 139 | "objectType": "AzureRetentionRule", 140 | "lifecycles": [ 141 | { 142 | "sourceDataStore": { 143 | "dataStoreType": "OperationalStore", 144 | "objectType": "DataStoreInfoBase" 145 | }, 146 | "deleteAfter": { 147 | "objectType": "AbsoluteDeleteOption", 148 | "duration": "[variables('retentionBlob')]" 149 | } 150 | } 151 | ] 152 | } 153 | ] 154 | } 155 | } 156 | ], 157 | "outputs": { 158 | "cstDiskPolicyName": { 159 | "type": "string", 160 | "value": "[variables('backupDiskPolicyName')]" 161 | }, 162 | "cstDiskPolResId": { 163 | "type": "string", 164 | "value": "[resourceId('Microsoft.DataProtection/backupVaults/backupPolicies', parameters('buVaultName'), variables('backupDiskPolicyName'))]" 165 | }, 166 | "cstBlobPolicyName": { 167 | "type": "string", 168 | "value": "[variables('backupBlobPolicyName')]" 169 | }, 170 | "cstBlobPolResId": { 171 | "type": "string", 172 | "value": "[resourceId('Microsoft.DataProtection/backupVaults/backupPolicies', parameters('buVaultName'), variables('backupBlobPolicyName'))]" 173 | } 174 | } 175 | } -------------------------------------------------------------------------------- /templates/deploy-buv-vault.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "tags": { 6 | "type": "object", 7 | "metadata": { 8 | "description": "The tags that will be associated to the resources" 9 | }, 10 | "defaultValue": { 11 | "environment": "lab" 12 | } 13 | }, 14 | "uniqueData": { 15 | "type": "string", 16 | "metadata": { 17 | "description": "Data used to append to resources to ensure uniqueness" 18 | }, 19 | "defaultValue": "[substring(newGuid(),0,8)]" 20 | } 21 | }, 22 | "variables": { 23 | "buVltApiVersion": "2022-05-01", 24 | "location": "[resourceGroup().location]", 25 | "storageType": "GeoRedundant", 26 | "vaultName": "[concat('buvlt',parameters('uniqueData'))]" 27 | }, 28 | "resources": [ 29 | { 30 | "name": "[variables('vaultName')]", 31 | "type": "Microsoft.DataProtection/BackupVaults", 32 | "apiVersion": "[variables('buVltApiVersion')]", 33 | "location": "[variables('location')]", 34 | "tags": "[parameters('tags')]", 35 | "sku": { 36 | "name": "RS0", 37 | "tier": "Standard" 38 | }, 39 | "identity": { 40 | "type": "SystemAssigned" 41 | }, 42 | "properties": { 43 | "monitoringSettings": { 44 | "azureMonitorAlertSettings": { 45 | "alertsForAllJobFailures": "Enabled" 46 | } 47 | }, 48 | "storageSettings": [ 49 | { 50 | "datastoreType": "VaultStore", 51 | "type": "[variables('storageType')]" 52 | } 53 | ] 54 | } 55 | } 56 | ], 57 | "outputs": { 58 | "buVaultName": { 59 | "type": "string", 60 | "value": "[variables('vaultName')]" 61 | }, 62 | "buVaultResourceId": { 63 | "type": "string", 64 | "value": "[resourceId('Microsoft.DataProtection/BackupVaults',variables('vaultName'))]" 65 | } 66 | } 67 | } -------------------------------------------------------------------------------- /templates/deploy-infra.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "lawResourceId": { 6 | "type": "string", 7 | "metadata": { 8 | "description": "The resource id of the Log Analytics Workspace" 9 | } 10 | }, 11 | "rsVaultAdvBuPolicyResId": { 12 | "type": "string", 13 | "metadata": { 14 | "description": "The resource id of the advanced backup policy" 15 | } 16 | }, 17 | "rsVaultBscBuPolicyResId": { 18 | "type": "string", 19 | "metadata": { 20 | "description": "The resource id of the basic backup policy" 21 | } 22 | }, 23 | "rsVaultName": { 24 | "type": "string", 25 | "metadata": { 26 | "description": "The name of the secondary region (must be the paired region)" 27 | } 28 | }, 29 | "rsVaultRg": { 30 | "type": "string", 31 | "metadata": { 32 | "description": "The name of the resource group the Recovery Services Vault is in" 33 | } 34 | }, 35 | "secLocation": { 36 | "type": "string", 37 | "metadata": { 38 | "description": "The name of the secondary region (must be the paired region)" 39 | } 40 | }, 41 | "secResourceGroupName": { 42 | "type": "string", 43 | "metadata": { 44 | "description": "The name of the resource group in the secondary region" 45 | } 46 | }, 47 | "tags": { 48 | "type": "object", 49 | "metadata": { 50 | "description": "The tags that will be associated to the resources" 51 | }, 52 | "defaultValue": { 53 | "environment": "lab" 54 | } 55 | }, 56 | "uniqueData": { 57 | "type": "string", 58 | "metadata": { 59 | "description": "Data used to append to resources to ensure uniqueness" 60 | }, 61 | "defaultValue": "[substring(newGuid(),0,8)]" 62 | }, 63 | "vmAdminPassword": { 64 | "type": "securestring", 65 | "metadata": { 66 | "description": "Password for the VMs that are created" 67 | } 68 | }, 69 | "vmAdminUsername": { 70 | "type": "string", 71 | "metadata": { 72 | "description": "Administrator name for VMs that are created" 73 | } 74 | } 75 | }, 76 | "variables": { 77 | 78 | "diagnosticApiVersion": "2017-05-01-preview", 79 | "networkApiVersion": "2020-07-01", 80 | "rcvSvcVltApiVersion": "2022-04-01", 81 | "resourcesApiVersion": "2020-06-01", 82 | "storageApiVersion": "2021-09-01", 83 | "availabilityZone": "1", 84 | "location": "[resourceGroup().location]", 85 | "bastionName": "[concat('bst', parameters('uniqueData'))]", 86 | "bastionPublicIpName": "[concat('pip-bst', parameters('uniqueData'))]", 87 | "bastionSubnetName": "AzureBastionSubnet", 88 | "deployVmBackup": "deploy-vm-backup", 89 | "deploySecInfRes": "deploy-sec-reg-inf", 90 | "deploySecVnetPeering": "deploy-sec-vnet-peering", 91 | "deployVmLinPriServer1": "deploy-vm-lin-pri-1-cf", 92 | "deployVmWinPriServer1": "deploy-vm-win-pri-1-cf", 93 | "deployVmWinPriServer2": "deploy-vm-win-pri-2-ncf", 94 | "storageBlobAccountName": "[concat('stblob', parameters('uniqueData'))]", 95 | "storageFileAccountName": "[concat('stfile', parameters('uniqueData'))]", 96 | "templateUriLin": "[concat(uri(deployment().properties.templateLink.uri,'deploy-linux-vm.json'))]", 97 | "templateUriWin": "[concat(uri(deployment().properties.templateLink.uri,'deploy-windows-vm.json'))]", 98 | "vmLinPriServer1Name": "vml-pri-1-cf", 99 | "vmLinPriServer1Ip": "10.0.2.4", 100 | "vmSku": "Standard_D4s_v5", 101 | "vmWinPriServer1Name": "vmw-pri-1-cf", 102 | "vmWinPriServer1Ip": "10.0.2.5", 103 | "vmWinPriServer2Name": "vmw-pri-2-ncf", 104 | "vmWinPriServer2Ip": "10.0.2.6", 105 | "workloadSubnetName": "snet-wl", 106 | "wlPriNsgName": "nsg-wl-pri", 107 | "wlPriPeerName": "peertosec", 108 | "wlPriResourceGroupName": "[resourceGroup().name]", 109 | "wlPriVnetBastionSubnetCidr": "10.0.1.0/24", 110 | "wlPriVnetCidr": "10.0.0.0/16", 111 | "wlPriVnetName": "[concat('vnet-wl-pri', parameters('uniqueData'))]", 112 | "wlPriVnetWlSubnetCidr": "10.0.2.0/24", 113 | "wlSecNsgName": "nsg-wl-sec", 114 | "wlSecPeerName": "peertopri", 115 | "wlSecVnetCidr": "10.1.0.0/16", 116 | "wlSecVnetName": "[concat('vnet-wl-sec', parameters('uniqueData'))]", 117 | "wlSecVnetWlSubnetCidr": "10.1.2.0/24" 118 | }, 119 | "resources": [ 120 | { 121 | "type": "Microsoft.Storage/storageAccounts", 122 | "apiVersion": "[variables('storageApiVersion')]", 123 | "name": "[variables('storageFileAccountName')]", 124 | "location": "[variables('location')]", 125 | "tags": "[parameters('tags')]", 126 | "kind": "StorageV2", 127 | "sku": { 128 | "name": "Standard_GRS" 129 | }, 130 | "properties": { 131 | }, 132 | "resources": [ 133 | ] 134 | }, 135 | { 136 | "type": "Microsoft.Storage/storageAccounts/fileServices/shares", 137 | "apiVersion": "[variables('storageApiVersion')]", 138 | "name": "[concat(variables('storageFileAccountName'), '/default/', 'sampleshare')]", 139 | "dependsOn": [ 140 | "[resourceId('Microsoft.Storage/storageAccounts', variables('storageFileAccountName'))]" 141 | ] 142 | }, 143 | { 144 | "type": "Microsoft.Storage/storageAccounts", 145 | "apiVersion": "[variables('storageApiVersion')]", 146 | "name": "[variables('storageBlobAccountName')]", 147 | "location": "[variables('location')]", 148 | "tags": "[parameters('tags')]", 149 | "kind": "StorageV2", 150 | "sku": { 151 | "name": "Standard_GRS" 152 | }, 153 | "properties": { 154 | }, 155 | "resources": [ 156 | ] 157 | }, 158 | { 159 | "type": "Microsoft.Storage/storageAccounts/blobServices/containers", 160 | "apiVersion": "[variables('storageApiVersion')]", 161 | "name": "[concat(variables('storageBlobAccountName'),'/default/','sampleblobs')]", 162 | "dependsOn": [ 163 | "[resourceId('Microsoft.Storage/storageAccounts', variables('storageBlobAccountName'))]" 164 | ] 165 | }, 166 | { 167 | "name": "[variables('bastionPublicIpName')]", 168 | "type": "Microsoft.Network/publicIpAddresses", 169 | "apiVersion": "[variables('networkApiVersion')]", 170 | "location": "[variables('location')]", 171 | "tags": "[parameters('tags')]", 172 | "properties": { 173 | "publicIpAllocationMethod": "Static" 174 | }, 175 | "sku": { 176 | "name": "Standard" 177 | } 178 | }, 179 | { 180 | "type": "Microsoft.Network/networkSecurityGroups", 181 | "name": "[variables('wlPriNsgName')]", 182 | "apiVersion": "[variables('networkApiVersion')]", 183 | "location": "[variables('location')]", 184 | "tags": "[parameters('tags')]", 185 | "properties": { 186 | "securityRules": [] 187 | } 188 | }, 189 | { 190 | "name": "[variables('deploySecInfRes')]", 191 | "type": "Microsoft.Resources/deployments", 192 | "apiVersion": "[variables('resourcesApiVersion')]", 193 | "resourceGroup": "[parameters('secResourceGroupName')]", 194 | "properties": { 195 | "mode": "Incremental", 196 | "template": { 197 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 198 | "contentVersion": "1.0.0.0", 199 | "parameters": {}, 200 | "variables": {}, 201 | "resources": [ 202 | { 203 | "type": "Microsoft.Network/networkSecurityGroups", 204 | "name": "[variables('wlSecNsgName')]", 205 | "apiVersion": "[variables('networkApiVersion')]", 206 | "location": "[parameters('secLocation')]", 207 | "tags": "[parameters('tags')]", 208 | "properties": { 209 | "securityRules": [] 210 | } 211 | }, 212 | { 213 | "type": "Microsoft.Network/virtualNetworks", 214 | "name": "[variables('wlSecVnetName')]", 215 | "apiVersion": "[variables('networkApiVersion')]", 216 | "location": "[parameters('secLocation')]", 217 | "tags": "[parameters('tags')]", 218 | "dependsOn": [ 219 | "[resourceId(parameters('secResourceGroupName'),'Microsoft.Network/networkSecurityGroups', variables('wlSecNsgName'))]" 220 | ], 221 | "properties": { 222 | "addressSpace": { 223 | "addressPrefixes": [ 224 | "[variables('wlSecVnetCidr')]" 225 | ] 226 | }, 227 | "subnets": [ 228 | { 229 | "name": "[variables('workloadSubnetName')]", 230 | "properties": { 231 | "addressPrefix": "[variables('wlSecVnetWlSubnetCidr')]", 232 | "networkSecurityGroup": { 233 | "id": "[resourceId(parameters('secResourceGroupName'),'Microsoft.Network/networkSecurityGroups',variables('wlSecNsgName'))]" 234 | } 235 | } 236 | } 237 | ], 238 | "enableDdosProtection": false 239 | }, 240 | "resources": [ 241 | ] 242 | } 243 | ] 244 | } 245 | } 246 | }, 247 | { 248 | "type": "Microsoft.Network/virtualNetworks", 249 | "name": "[variables('wlPriVnetName')]", 250 | "apiVersion": "[variables('networkApiVersion')]", 251 | "location": "[variables('location')]", 252 | "tags": "[parameters('tags')]", 253 | "dependsOn": [ 254 | "[resourceId('Microsoft.Network/publicIpAddresses', variables('bastionPublicIpName'))]", 255 | "[resourceId('Microsoft.Network/networkSecurityGroups', variables('wlPriNsgName'))]", 256 | "[concat('Microsoft.Resources/deployments/', variables('deploySecInfRes'))]" 257 | ], 258 | "properties": { 259 | "addressSpace": { 260 | "addressPrefixes": [ 261 | "[variables('wlPriVnetCidr')]" 262 | ] 263 | }, 264 | "subnets": [ 265 | { 266 | "name": "[variables('bastionSubnetName')]", 267 | "properties": { 268 | "addressPrefix": "[variables('wlPriVnetBastionSubnetCidr')]" 269 | } 270 | }, 271 | { 272 | "name": "[variables('workloadSubnetName')]", 273 | "properties": { 274 | "addressPrefix": "[variables('wlPriVnetWlSubnetCidr')]", 275 | "networkSecurityGroup": { 276 | "id": "[resourceId('Microsoft.Network/networkSecurityGroups', variables('wlPriNsgName'))]" 277 | } 278 | } 279 | } 280 | ], 281 | "enableDdosProtection": false 282 | }, 283 | "resources": [ 284 | { 285 | "name": "[variables('wlPriPeerName')]", 286 | "type": "virtualNetworkPeerings", 287 | "apiVersion": "[variables('networkApiVersion')]", 288 | "location": "[resourceGroup().location]", 289 | "dependsOn": [ 290 | "[concat('Microsoft.Network/virtualNetworks/', variables('wlPriVnetName'))]" 291 | ], 292 | "properties": { 293 | "allowVirtualNetworkAccess": "true", 294 | "allowForwardedTraffic": "true", 295 | "allowGatewayTransit": "false", 296 | "useRemoteGateways": "false", 297 | "remoteVirtualNetwork": { 298 | "id": "[resourceId(parameters('secResourceGroupName'),'Microsoft.Network/virtualNetworks',variables('wlSecVnetName'))]" 299 | } 300 | } 301 | } 302 | ] 303 | }, 304 | { 305 | "name": "[variables('deploySecVnetPeering')]", 306 | "type": "Microsoft.Resources/deployments", 307 | "apiVersion": "[variables('resourcesApiVersion')]", 308 | "resourceGroup": "[parameters('secResourceGroupName')]", 309 | "dependsOn": [ 310 | "[resourceId('Microsoft.Network/virtualNetworks/virtualNetworkPeerings', variables('wlPriVnetName'), variables('wlPriPeerName'))]" 311 | ], 312 | "properties": { 313 | "mode": "Incremental", 314 | "template": { 315 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 316 | "contentVersion": "1.0.0.0", 317 | "parameters": {}, 318 | "variables": {}, 319 | "resources": [ 320 | { 321 | "name": "[concat(variables('wlSecVnetName'),'/',variables('wlSecPeerName'))]", 322 | "type": "Microsoft.Network/virtualNetworks/virtualNetworkPeerings", 323 | "apiVersion": "[variables('networkApiVersion')]", 324 | "location": "[resourceGroup().location]", 325 | "properties": { 326 | "allowVirtualNetworkAccess": "true", 327 | "allowForwardedTraffic": "true", 328 | "allowGatewayTransit": "true", 329 | "useRemoteGateways": "false", 330 | "remoteVirtualNetwork": { 331 | "id": "[resourceId(variables('wlPriResourceGroupName'), 'Microsoft.Network/virtualNetworks', variables('wlPriVnetName'))]" 332 | } 333 | } 334 | } 335 | ] 336 | } 337 | } 338 | }, 339 | { 340 | "name": "[variables('bastionName')]", 341 | "type": "Microsoft.Network/bastionHosts", 342 | "apiVersion": "[variables('networkApiVersion')]", 343 | "location": "[variables('location')]", 344 | "dependsOn": [ 345 | "[resourceId('Microsoft.Network/publicIpAddresses', variables('bastionPublicIpName'))]", 346 | "[resourceId('Microsoft.Network/virtualNetworks', variables('wlPriVnetName'))]", 347 | "[concat('Microsoft.Resources/deployments/',variables('deploySecVnetPeering'))]" 348 | ], 349 | "tags": "[parameters('tags')]", 350 | "properties": { 351 | "ipConfigurations": [ 352 | { 353 | "name": "bastionConfig", 354 | "properties": { 355 | "subnet": { 356 | "id": "[resourceId('Microsoft.Network/virtualNetworks/subnets', variables('wlPriVnetName'), variables('bastionSubnetName'))]" 357 | }, 358 | "publicIPAddress": { 359 | "id": "[resourceId('Microsoft.Network/publicIpAddresses', variables('bastionPublicIpName'))]" 360 | }, 361 | "privateIPAllocationMethod": "Dynamic" 362 | } 363 | } 364 | ] 365 | } 366 | }, 367 | { 368 | "name": "[concat(variables('bastionName'),'/microsoft.insights/diag')]", 369 | "type": "Microsoft.Network/bastionHosts/providers/diagnosticSettings", 370 | "apiVersion": "[variables('diagnosticApiVersion')]", 371 | "location": "[variables('location')]", 372 | "tags": "[parameters('tags')]", 373 | "dependsOn": [ 374 | "[resourceId('Microsoft.Network/bastionHosts',variables('bastionName'))]" 375 | ], 376 | "properties": { 377 | "name": "SendToWorkspace", 378 | "workspaceId": "[parameters('lawResourceId')]", 379 | "logs": [ 380 | { 381 | "category": "BastionAuditLogs", 382 | "enabled": true 383 | } 384 | ], 385 | "metrics": [ 386 | ] 387 | }, 388 | "resources": [ 389 | ] 390 | }, 391 | { 392 | "name": "[variables('deployVmLinPriServer1')]", 393 | "type": "Microsoft.Resources/deployments", 394 | "apiVersion": "[variables('resourcesApiVersion')]", 395 | "dependsOn": [ 396 | "[resourceId('Microsoft.Network/bastionHosts',variables('bastionName'))]" 397 | ], 398 | "properties": { 399 | "mode": "Incremental", 400 | "parameters": { 401 | "adminPassword": { 402 | "value": "[parameters('vmAdminPassword')]" 403 | }, 404 | "adminUserName": { 405 | "value": "[parameters('vmAdminUsername')]" 406 | }, 407 | "availabilityZone": { 408 | "value": "[variables('availabilityZone')]" 409 | }, 410 | "serverIpAddress": { 411 | "value": "[variables('vmLinPriServer1Ip')]" 412 | }, 413 | "myWorkspaceId": { 414 | "value": "[reference(parameters('lawResourceId'), '2015-03-20').customerId]" 415 | }, 416 | "myWorkspaceKey": { 417 | "value": "[listKeys(parameters('lawResourceId'), '2015-03-20').primarySharedKey]" 418 | }, 419 | "subnetName": { 420 | "value": "[variables('workloadSubnetName')]" 421 | }, 422 | "tags": { 423 | "value": "[parameters('tags')]" 424 | }, 425 | "uniqueData": { 426 | "value": "[parameters('uniqueData')]" 427 | }, 428 | "virtualMachineSize": { 429 | "value": "[variables('vmSku')]" 430 | }, 431 | "vmName": { 432 | "value": "[variables('vmLinPriServer1Name')]" 433 | }, 434 | "vnetName": { 435 | "value": "[variables('wlPriVnetName')]" 436 | } 437 | }, 438 | "templateLink": { 439 | "uri": "[variables('templateUriLin')]", 440 | "contentVersion": "1.0.0.0" 441 | } 442 | } 443 | }, 444 | { 445 | "name": "[variables('deployVmWinPriServer1')]", 446 | "type": "Microsoft.Resources/deployments", 447 | "apiVersion": "[variables('resourcesApiVersion')]", 448 | "dependsOn": [ 449 | "[concat('Microsoft.Resources/deployments/',variables('deployVmLinPriServer1'))]" 450 | ], 451 | "properties": { 452 | "mode": "Incremental", 453 | "parameters": { 454 | "adminPassword": { 455 | "value": "[parameters('vmAdminPassword')]" 456 | }, 457 | "adminUserName": { 458 | "value": "[parameters('vmAdminUsername')]" 459 | }, 460 | "availabilityZone": { 461 | "value": "[variables('availabilityZone')]" 462 | }, 463 | "serverIpAddress": { 464 | "value": "[variables('vmWinPriServer1Ip')]" 465 | }, 466 | "myWorkspaceId": { 467 | "value": "[reference(parameters('lawResourceId'), '2015-03-20').customerId]" 468 | }, 469 | "myWorkspaceKey": { 470 | "value": "[listKeys(parameters('lawResourceId'), '2015-03-20').primarySharedKey]" 471 | }, 472 | "subnetName": { 473 | "value": "[variables('workloadSubnetName')]" 474 | }, 475 | "tags": { 476 | "value": "[parameters('tags')]" 477 | }, 478 | "uniqueData": { 479 | "value": "[parameters('uniqueData')]" 480 | }, 481 | "virtualMachineSize": { 482 | "value": "[variables('vmSku')]" 483 | }, 484 | "vmName": { 485 | "value": "[variables('vmWinPriServer1Name')]" 486 | }, 487 | "vnetName": { 488 | "value": "[variables('wlPriVnetName')]" 489 | } 490 | }, 491 | "templateLink": { 492 | "uri": "[variables('templateUriWin')]", 493 | "contentVersion": "1.0.0.0" 494 | } 495 | } 496 | }, 497 | { 498 | "name": "[variables('deployVmWinPriServer2')]", 499 | "type": "Microsoft.Resources/deployments", 500 | "apiVersion": "[variables('resourcesApiVersion')]", 501 | "dependsOn": [ 502 | "[concat('Microsoft.Resources/deployments/',variables('deployVmWinPriServer1'))]" 503 | ], 504 | "properties": { 505 | "mode": "Incremental", 506 | "parameters": { 507 | "adminPassword": { 508 | "value": "[parameters('vmAdminPassword')]" 509 | }, 510 | "adminUserName": { 511 | "value": "[parameters('vmAdminUsername')]" 512 | }, 513 | "availabilityZone": { 514 | "value": "[variables('availabilityZone')]" 515 | }, 516 | "serverIpAddress": { 517 | "value": "[variables('vmWinPriServer2Ip')]" 518 | }, 519 | "myWorkspaceId": { 520 | "value": "[reference(parameters('lawResourceId'), '2015-03-20').customerId]" 521 | }, 522 | "myWorkspaceKey": { 523 | "value": "[listKeys(parameters('lawResourceId'), '2015-03-20').primarySharedKey]" 524 | }, 525 | "subnetName": { 526 | "value": "[variables('workloadSubnetName')]" 527 | }, 528 | "tags": { 529 | "value": "[parameters('tags')]" 530 | }, 531 | "uniqueData": { 532 | "value": "[parameters('uniqueData')]" 533 | }, 534 | "virtualMachineSize": { 535 | "value": "[variables('vmSku')]" 536 | }, 537 | "vmName": { 538 | "value": "[variables('vmWinPriServer2Name')]" 539 | }, 540 | "vnetName": { 541 | "value": "[variables('wlPriVnetName')]" 542 | } 543 | }, 544 | "templateLink": { 545 | "uri": "[variables('templateUriWin')]", 546 | "contentVersion": "1.0.0.0" 547 | } 548 | } 549 | }, 550 | { 551 | "name": "[variables('deployVmBackup')]", 552 | "type": "Microsoft.Resources/deployments", 553 | "apiVersion": "[variables('resourcesApiVersion')]", 554 | "dependsOn": [ 555 | "[concat('Microsoft.Resources/deployments/',variables('deployVmWinPriServer2'))]" 556 | ], 557 | "resourceGroup": "[parameters('rsVaultRg')]", 558 | "properties": { 559 | "mode": "Incremental", 560 | "template": { 561 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 562 | "contentVersion": "1.0.0.0", 563 | "parameters": {}, 564 | "variables": {}, 565 | "resources": [ 566 | { 567 | "name": "[concat(parameters('rsVaultName'),'/Azure/IaasVMContainer;iaasvmcontainerv2;',resourceGroup().name,';',variables('vmLinPriServer1Name'),'/VM;iaasvmcontainerv2;',resourceGroup().name,';',variables('vmLinPriServer1Name'))]", 568 | 569 | "type": "Microsoft.RecoveryServices/vaults/backupFabrics/protectionContainers/protectedItems", 570 | "apiVersion": "[variables('rcvSvcVltApiVersion')]", 571 | "location": "[variables('location')]", 572 | "properties": { 573 | "protectedItemType": "Microsoft.Compute/virtualMachines", 574 | "policyId": "[parameters('rsVaultBscBuPolicyResId')]", 575 | "sourceResourceId": "[resourceId('Microsoft.Compute/virtualMachines', variables('vmLinPriServer1Name'))]" 576 | } 577 | }, 578 | { 579 | "name": "[concat(parameters('rsVaultName'),'/Azure/IaasVMContainer;iaasvmcontainerv2;',resourceGroup().name,';',variables('vmWinPriServer1Name'),'/VM;iaasvmcontainerv2;',resourceGroup().name,';',variables('vmWinPriServer1Name'))]", 580 | "type": "Microsoft.RecoveryServices/vaults/backupFabrics/protectionContainers/protectedItems", 581 | "apiVersion": "[variables('rcvSvcVltApiVersion')]", 582 | "location": "[variables('location')]", 583 | "dependsOn": [ 584 | "[concat('Microsoft.RecoveryServices/vaults/',parameters('rsVaultName'),'/backupFabrics/Azure/protectionContainers/IaasVMContainer;iaasvmcontainerv2;',resourceGroup().name,';',variables('vmLinPriServer1Name'),'/protectedItems/','VM;iaasvmcontainerv2;',resourceGroup().name,';',variables('vmLinPriServer1Name'))]" 585 | ], 586 | "properties": { 587 | "protectedItemType": "Microsoft.Compute/virtualMachines", 588 | "policyId": "[parameters('rsVaultAdvBuPolicyResId')]", 589 | "sourceResourceId": "[resourceId('Microsoft.Compute/virtualMachines', variables('vmWinPriServer1Name'))]" 590 | } 591 | } 592 | ] 593 | } 594 | } 595 | } 596 | ], 597 | "outputs": { 598 | } 599 | } -------------------------------------------------------------------------------- /templates/deploy-law.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "tags": { 6 | "type": "object", 7 | "metadata": { 8 | "description": "The tags that will be associated to the resources" 9 | }, 10 | "defaultValue": { 11 | "environment": "lab" 12 | } 13 | }, 14 | "uniqueData": { 15 | "type": "string", 16 | "metadata": { 17 | "description": "Data used to append to resources to ensure uniqueness" 18 | }, 19 | "defaultValue": "[substring(newGuid(),0,8)]" 20 | } 21 | }, 22 | "variables": { 23 | "laApiVersion": "2015-11-01-preview", 24 | "laWorkspaceName": "[concat('la', parameters('uniqueData'))]", 25 | "location": "[resourceGroup().location]" 26 | }, 27 | "resources": [ 28 | { 29 | "name": "[variables('laWorkspaceName')]", 30 | "type": "Microsoft.OperationalInsights/workspaces", 31 | "apiVersion": "[variables('laApiVersion')]", 32 | "location": "[variables('location')]", 33 | "tags": "[parameters('tags')]", 34 | "properties": { 35 | "sku": { 36 | "name": "PerGB2018" 37 | }, 38 | "publicNetworkAccessForIngestion": "Enabled", 39 | "publicNetworkAccessForQuery": "Enabled", 40 | "retentionInDays": 30 41 | }, 42 | "resources": [] 43 | } 44 | ], 45 | "outputs": { 46 | "logAnalyticsName": { 47 | "type": "string", 48 | "value": "[variables('laWorkspaceName')]" 49 | }, 50 | "logAnalyticsResourceId": { 51 | "type": "string", 52 | "value": "[resourceId('Microsoft.OperationalInsights/workspaces', variables('laWorkspaceName'))]" 53 | }, 54 | "logAnalyticsWorkspaceId": { 55 | "type": "string", 56 | "value": "[reference(resourceId('Microsoft.OperationalInsights/workspaces',variables('laWorkspaceName')),'2015-03-20').customerId]" 57 | }, 58 | "logAnalyticsWorkspaceKey": { 59 | "type": "string", 60 | "value": "[listKeys(resourceId('Microsoft.OperationalInsights/workspaces', variables('laWorkspaceName')), '2015-03-20').primarySharedKey]" 61 | } 62 | } 63 | } -------------------------------------------------------------------------------- /templates/deploy-linux-vm.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "adminPassword": { 6 | "type": "securestring", 7 | "metadata": { 8 | "description": "The password for the administrator account created on the VM" 9 | } 10 | }, 11 | "adminUsername": { 12 | "type": "string", 13 | "metadata": { 14 | "description": "Name of the administrator account created on the VM" 15 | } 16 | }, 17 | "availabilityZone": { 18 | "type": "string", 19 | "metadata": { 20 | "description": "The number of the availability zone to deploy to" 21 | } 22 | }, 23 | "linkedTemplateLocation": { 24 | "type": "string", 25 | "metadata": { 26 | "description": "The location of linked templates and scripts" 27 | }, 28 | "defaultValue": "[deployment().properties.templateLink.uri]" 29 | }, 30 | "myWorkspaceId": { 31 | "type": "string", 32 | "metadata": { 33 | "description": "The Log and Analytics workspace ID that the Microsoft Monitoring Agent will deliver metrics and logs to" 34 | } 35 | }, 36 | "myWorkspaceKey": { 37 | "type": "string", 38 | "metadata": { 39 | "description": "The Log and Analytics workspace secret" 40 | } 41 | }, 42 | "serverIpAddress": { 43 | "type": "string", 44 | "metadata": { 45 | "description": "The static IP address assigned to the server's network interface" 46 | } 47 | }, 48 | "subnetName": { 49 | "type": "string", 50 | "metadata": { 51 | "description": "The subnet within the Virtual Network the network interface for the VM is to be placed in" 52 | } 53 | }, 54 | "tags": { 55 | "type": "object", 56 | "metadata": { 57 | "description": "The tags that will be associated to the VM" 58 | } 59 | }, 60 | "uniqueData": { 61 | "type": "string", 62 | "metadata": { 63 | "description": "Data used to append to resources to ensure uniqueness" 64 | }, 65 | "defaultValue": "[substring(newGuid(),0,8)]" 66 | }, 67 | "virtualMachineSize": { 68 | "type": "string", 69 | "metadata": { 70 | "description": "VM Size" 71 | } 72 | }, 73 | "vmName": { 74 | "type": "string", 75 | "metadata": { 76 | "description": "VM Name" 77 | } 78 | }, 79 | "vnetName": { 80 | "type": "string", 81 | "metadata": { 82 | "description": "The Virtual Network the VM is to be placed in" 83 | } 84 | }, 85 | "vnetResourceGroup": { 86 | "type": "string", 87 | "defaultValue": "[resourceGroup().name]", 88 | "metadata": { 89 | "description": "The resource group of the Virtual Network the VM will use" 90 | } 91 | }, 92 | "vnetSubscriptionId": { 93 | "type": "string", 94 | "defaultValue": "[subscription().subscriptionId]", 95 | "metadata": { 96 | "description": "The subscription of the Virtual Network the VM will use" 97 | } 98 | } 99 | }, 100 | "variables": { 101 | "networkApiVersion": "2021-08-01", 102 | "vmApiVersion": "2021-11-01", 103 | "location": "[resourceGroup().location]", 104 | "nicName": "[concat(parameters('vmName'),parameters('uniqueData'))]", 105 | "osDiskType": "StandardSSD_LRS", 106 | "scriptName": "prepare-linux-vm.sh", 107 | "scriptUrl": "[uri(parameters('linkedTemplateLocation'), concat('../scripts/', variables('scriptName')))]", 108 | "subnetRef": "[resourceId(parameters('vnetSubscriptionId'),parameters('vnetResourceGroup'),'Microsoft.Network/virtualNetworks/subnets',parameters('vnetName'),parameters('subnetName'))]" 109 | }, 110 | "resources": [ 111 | { 112 | "name": "[variables('nicName')]", 113 | "type": "Microsoft.Network/networkInterfaces", 114 | "apiVersion": "[variables('networkApiVersion')]", 115 | "location": "[variables('location')]", 116 | "tags": "[parameters('tags')]", 117 | "properties": { 118 | "ipConfigurations": [ 119 | { 120 | "name": "ipconfig1", 121 | "properties": { 122 | "privateIPAllocationMethod": "Static", 123 | "privateIPAddress": "[parameters('serverIpAddress')]", 124 | "subnet": { 125 | "id": "[variables('subnetRef')]" 126 | } 127 | } 128 | } 129 | ] 130 | } 131 | }, 132 | { 133 | "name": "[parameters('vmName')]", 134 | "type": "Microsoft.Compute/virtualMachines", 135 | "apiVersion": "[variables('vmApiVersion')]", 136 | "location": "[variables('location')]", 137 | "tags": "[parameters('tags')]", 138 | "dependsOn": [ 139 | "[concat('Microsoft.Network/networkInterfaces/', variables('nicName'))]" 140 | ], 141 | "properties": { 142 | "diagnosticsProfile": { 143 | "bootDiagnostics": { 144 | "enabled": true 145 | } 146 | }, 147 | "hardwareProfile": { 148 | "vmSize": "[parameters('virtualMachineSize')]" 149 | }, 150 | "networkProfile": { 151 | "networkInterfaces": [ 152 | { 153 | "id": "[resourceId('Microsoft.Network/networkInterfaces', variables('nicName'))]" 154 | } 155 | ] 156 | }, 157 | "osProfile": { 158 | "computerName": "[parameters('vmName')]", 159 | "adminUsername": "[parameters('adminUsername')]", 160 | "adminPassword": "[parameters('adminPassword')]", 161 | "linuxConfiguration": { 162 | "disablePasswordAuthentication": false, 163 | "provisionVmAgent": true 164 | } 165 | }, 166 | "storageProfile": { 167 | "osDisk": { 168 | "createOption": "fromImage", 169 | "managedDisk": { 170 | "storageAccountType": "[variables('osDiskType')]" 171 | } 172 | }, 173 | "imageReference": { 174 | "publisher": "Canonical", 175 | "offer": "UbuntuServer", 176 | "sku": "18.04-LTS", 177 | "version": "latest" 178 | } 179 | } 180 | }, 181 | "zones": [ 182 | "[parameters('availabilityZone')]" 183 | ], 184 | "resources": [ 185 | { 186 | "name": "[concat(parameters('vmName'),'/CustomScriptExtension')]", 187 | "type": "Microsoft.Compute/virtualMachines/extensions", 188 | "apiVersion": "[variables('vmApiVersion')]", 189 | "location": "[variables('location')]", 190 | "tags": "[parameters('tags')]", 191 | "dependsOn": [ 192 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]" 193 | ], 194 | "properties": { 195 | "publisher": "Microsoft.Azure.Extensions", 196 | "type": "CustomScript", 197 | "typeHandlerVersion": "2.1", 198 | "autoUpgradeMinorVersion": true, 199 | "settings": { 200 | }, 201 | "protectedSettings": { 202 | "fileUris": [ 203 | "[variables('scriptUrl')]" 204 | ], 205 | "commandToExecute": "[concat('sh ', variables('scriptName'), ' ', parameters('adminUsername'))]" 206 | } 207 | } 208 | }, 209 | { 210 | "type": "extensions", 211 | "name": "Microsoft.Azure.NetworkWatcher", 212 | "apiVersion": "[variables('vmApiVersion')]", 213 | "location": "[variables('location')]", 214 | "dependsOn": [ 215 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]", 216 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/CustomScriptExtension')]" 217 | ], 218 | "properties": { 219 | "publisher": "Microsoft.Azure.NetworkWatcher", 220 | "type": "NetworkWatcherAgentLinux", 221 | "typeHandlerVersion": "1.4", 222 | "autoUpgradeMinorVersion": true 223 | } 224 | }, 225 | { 226 | "type": "extensions", 227 | "name": "OMSExtension", 228 | "apiVersion": "[variables('vmApiVersion')]", 229 | "location": "[variables('location')]", 230 | "dependsOn": [ 231 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]", 232 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/Microsoft.Azure.NetworkWatcher')]" 233 | ], 234 | "properties": { 235 | "publisher": "Microsoft.EnterpriseCloud.Monitoring", 236 | "type": "OmsAgentForLinux", 237 | "typeHandlerVersion": "1.13", 238 | "autoUpgradeMinorVersion": true, 239 | "settings": { 240 | "workspaceId": "[parameters('myWorkspaceId')]", 241 | "stopOnMultipleConnections": true 242 | }, 243 | "protectedSettings": { 244 | "workspaceKey": "[parameters('myWorkspaceKey')]" 245 | } 246 | } 247 | }, 248 | { 249 | "type": "extensions", 250 | "name": "DependencyAgentLinux", 251 | "apiVersion": "[variables('vmApiVersion')]", 252 | "location": "[variables('location')]", 253 | "dependsOn": [ 254 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]", 255 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/OMSExtension')]" 256 | ], 257 | "properties": { 258 | "publisher": "Microsoft.Azure.Monitoring.DependencyAgent", 259 | "type": "DependencyAgentLinux", 260 | "typeHandlerVersion": "9.5", 261 | "autoUpgradeMinorVersion": true 262 | } 263 | }, 264 | { 265 | "type": "extensions", 266 | "name": "AzureMonitorLinuxAgent", 267 | "apiVersion": "[variables('vmApiVersion')]", 268 | "location": "[variables('location')]", 269 | "dependsOn": [ 270 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]", 271 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/DependencyAgentLinux')]" 272 | ], 273 | "properties": { 274 | "publisher": "Microsoft.Azure.Monitor", 275 | "type": "AzureMonitorLinuxAgent", 276 | "typeHandlerVersion": "1.5", 277 | "autoUpgradeMinorVersion": true, 278 | "enableAutomaticUpgrade": true 279 | } 280 | } 281 | ] 282 | } 283 | ] 284 | } -------------------------------------------------------------------------------- /templates/deploy-rsv-backup-policies.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "recSvcVaultName": { 6 | "type": "string", 7 | "metadata": { 8 | "description": "The name of the Recovery Services Vault" 9 | } 10 | }, 11 | "tags": { 12 | "type": "object", 13 | "metadata": { 14 | "description": "The tags that will be associated to the resources" 15 | }, 16 | "defaultValue": { 17 | "environment": "lab" 18 | } 19 | }, 20 | "uniqueData": { 21 | "type": "string", 22 | "metadata": { 23 | "description": "Data used to append to resources to ensure uniqueness" 24 | }, 25 | "defaultValue": "[substring(newGuid(),0,8)]" 26 | } 27 | }, 28 | "variables": { 29 | "rcvSvcVltApiVersion": "2022-04-01", 30 | "location": "[resourceGroup().location]", 31 | "backupFilePolicyName": "[concat('cstFilePolicy',parameters('uniqueData'))]", 32 | "backupRunTime": "00:00:00", 33 | "backupVmBscPolicyName": "[concat('cstBscVmPolicy',parameters('uniqueData'))]", 34 | "backupVmAdvPolicyName": "[concat('cstAdvVmPolicy',parameters('uniqueData'))]" 35 | }, 36 | "resources": [ 37 | { 38 | "name": "[concat(parameters('recSvcVaultName'), '/', variables('backupVmBscPolicyName'))]", 39 | "type": "Microsoft.RecoveryServices/vaults/backupPolicies", 40 | "apiVersion": "[variables('rcvSvcVltApiVersion')]", 41 | "location": "[variables('location')]", 42 | "tags": "[parameters('tags')]", 43 | "properties": { 44 | "backupManagementType": "AzureIaasVM", 45 | "instantRPDetails": { 46 | "azureBackupRGNamePrefix": "rgbckirpri", 47 | "azureBackupRGNameSuffix": "[parameters('uniqueData')]" 48 | }, 49 | "instantRpRetentionRangeInDays": 5, 50 | "policyType": "V1", 51 | "schedulePolicy": { 52 | "schedulePolicyType": "SimpleSchedulePolicy", 53 | "scheduleRunFrequency": "Daily", 54 | "scheduleRunTimes": [ 55 | "[variables('backupRunTime')]" 56 | ] 57 | }, 58 | "retentionPolicy": { 59 | "retentionPolicyType": "LongTermRetentionPolicy", 60 | "dailySchedule": { 61 | "retentionDuration": { 62 | "count": 7, 63 | "durationType": "Days" 64 | }, 65 | "retentionTimes": [ 66 | "[variables('backupRunTime')]" 67 | ] 68 | }, 69 | "weeklySchedule": { 70 | "daysOfTheWeek": [ 71 | "Sunday" 72 | ], 73 | "retentionDuration": { 74 | "count": 12, 75 | "durationType": "Weeks" 76 | }, 77 | "retentionTimes": [ 78 | "[variables('backupRunTime')]" 79 | ] 80 | }, 81 | "monthlySchedule": { 82 | "retentionScheduleFormatType": "Weekly", 83 | "retentionDuration": { 84 | "count": 12, 85 | "durationType": "Months" 86 | }, 87 | "retentionScheduleWeekly": { 88 | "daysOfTheWeek": [ 89 | "Sunday" 90 | ], 91 | "weeksOfTheMonth": [ 92 | "Last" 93 | ] 94 | }, 95 | "retentionTimes": [ 96 | "[variables('backupRunTime')]" 97 | ] 98 | }, 99 | "yearlySchedule": { 100 | "retentionScheduleFormatType": "Weekly", 101 | "monthsOfYear": [ 102 | "December" 103 | ], 104 | "retentionDuration": { 105 | "count": 3, 106 | "durationType": "Years" 107 | }, 108 | "retentionScheduleWeekly": { 109 | "daysOfTheWeek": [ 110 | "Sunday" 111 | ], 112 | "weeksOfTheMonth": [ 113 | "Last" 114 | ] 115 | }, 116 | "retentionTimes": [ 117 | "[variables('backupRunTime')]" 118 | ] 119 | } 120 | }, 121 | "timeZone": "Eastern Standard Time" 122 | } 123 | }, 124 | { 125 | "name": "[concat(parameters('recSvcVaultName'), '/', variables('backupVmAdvPolicyName'))]", 126 | "type": "Microsoft.RecoveryServices/vaults/backupPolicies", 127 | "apiVersion": "[variables('rcvSvcVltApiVersion')]", 128 | "location": "[variables('location')]", 129 | "dependsOn": [ 130 | "[resourceId('Microsoft.RecoveryServices/vaults/backupPolicies', parameters('recSvcVaultName'), variables('backupVmBscPolicyName'))]" 131 | ], 132 | "tags": "[parameters('tags')]", 133 | "properties": { 134 | "backupManagementType": "AzureIaasVM", 135 | "instantRPDetails": { 136 | "azureBackupRGNamePrefix": "rgbckirpri", 137 | "azureBackupRGNameSuffix": "[parameters('uniqueData')]" 138 | }, 139 | "instantRpRetentionRangeInDays": 5, 140 | "policyType": "V2", 141 | "schedulePolicy": { 142 | "schedulePolicyType": "SimpleSchedulePolicyV2", 143 | "scheduleRunFrequency": "Hourly", 144 | "hourlySchedule": { 145 | "interval": 4, 146 | "scheduleWindowDuration": 24, 147 | "scheduleWindowStartTime": "[variables('backupRunTime')]" 148 | } 149 | }, 150 | "retentionPolicy": { 151 | "retentionPolicyType": "LongTermRetentionPolicy", 152 | "dailySchedule": { 153 | "retentionDuration": { 154 | "count": 7, 155 | "durationType": "Days" 156 | }, 157 | "retentionTimes": [ 158 | "[variables('backupRunTime')]" 159 | ] 160 | }, 161 | "weeklySchedule": { 162 | "daysOfTheWeek": [ 163 | "Sunday" 164 | ], 165 | "retentionDuration": { 166 | "count": 12, 167 | "durationType": "Weeks" 168 | }, 169 | "retentionTimes": [ 170 | "[variables('backupRunTime')]" 171 | ] 172 | }, 173 | "monthlySchedule": { 174 | "retentionScheduleFormatType": "Weekly", 175 | "retentionDuration": { 176 | "count": 12, 177 | "durationType": "Months" 178 | }, 179 | "retentionScheduleWeekly": { 180 | "daysOfTheWeek": [ 181 | "Sunday" 182 | ], 183 | "weeksOfTheMonth": [ 184 | "Last" 185 | ] 186 | }, 187 | "retentionTimes": [ 188 | "[variables('backupRunTime')]" 189 | ] 190 | }, 191 | "yearlySchedule": { 192 | "retentionScheduleFormatType": "Weekly", 193 | "monthsOfYear": [ 194 | "December" 195 | ], 196 | "retentionDuration": { 197 | "count": 3, 198 | "durationType": "Years" 199 | }, 200 | "retentionScheduleWeekly": { 201 | "daysOfTheWeek": [ 202 | "Sunday" 203 | ], 204 | "weeksOfTheMonth": [ 205 | "Last" 206 | ] 207 | }, 208 | "retentionTimes": [ 209 | "[variables('backupRunTime')]" 210 | ] 211 | } 212 | }, 213 | "timeZone": "Eastern Standard Time" 214 | } 215 | }, 216 | { 217 | "name": "[concat(parameters('recSvcVaultName'), '/', variables('backupFilePolicyName'))]", 218 | "type": "Microsoft.RecoveryServices/vaults/backupPolicies", 219 | "apiVersion": "[variables('rcvSvcVltApiVersion')]", 220 | "location": "[variables('location')]", 221 | "dependsOn": [ 222 | "[resourceId('Microsoft.RecoveryServices/vaults/backupPolicies', parameters('recSvcVaultName'), variables('backupVmAdvPolicyName'))]" 223 | ], 224 | "tags": "[parameters('tags')]", 225 | "properties": { 226 | "backupManagementType": "AzureStorage", 227 | "schedulePolicy": { 228 | "schedulePolicyType": "SimpleSchedulePolicy", 229 | "scheduleRunFrequency": "Hourly", 230 | "hourlySchedule": { 231 | "interval": 4, 232 | "scheduleWindowDuration": 23, 233 | "scheduleWindowStartTime": "[variables('backupRunTime')]" 234 | } 235 | }, 236 | "retentionPolicy": { 237 | "retentionPolicyType": "LongTermRetentionPolicy", 238 | "dailySchedule": { 239 | "retentionDuration": { 240 | "count": 7, 241 | "durationType": "Days" 242 | }, 243 | "retentionTimes": [ 244 | "[variables('backupRunTime')]" 245 | ] 246 | }, 247 | "weeklySchedule": { 248 | "daysOfTheWeek": [ 249 | "Sunday" 250 | ], 251 | "retentionDuration": { 252 | "count": 12, 253 | "durationType": "Weeks" 254 | }, 255 | "retentionTimes": [ 256 | "[variables('backupRunTime')]" 257 | ] 258 | }, 259 | "monthlySchedule": { 260 | "retentionScheduleFormatType": "Weekly", 261 | "retentionDuration": { 262 | "count": 12, 263 | "durationType": "Months" 264 | }, 265 | "retentionScheduleWeekly": { 266 | "daysOfTheWeek": [ 267 | "Sunday" 268 | ], 269 | "weeksOfTheMonth": [ 270 | "Last" 271 | ] 272 | }, 273 | "retentionTimes": [ 274 | "[variables('backupRunTime')]" 275 | ] 276 | }, 277 | "yearlySchedule": { 278 | "retentionScheduleFormatType": "Weekly", 279 | "monthsOfYear": [ 280 | "December" 281 | ], 282 | "retentionDuration": { 283 | "count": 3, 284 | "durationType": "Years" 285 | }, 286 | "retentionScheduleWeekly": { 287 | "daysOfTheWeek": [ 288 | "Sunday" 289 | ], 290 | "weeksOfTheMonth": [ 291 | "Last" 292 | ] 293 | }, 294 | "retentionTimes": [ 295 | "[variables('backupRunTime')]" 296 | ] 297 | } 298 | }, 299 | "timeZone": "Eastern Standard Time", 300 | "workLoadType": "AzureFileShare" 301 | } 302 | } 303 | ], 304 | "outputs": { 305 | "cstVmBscPolName": { 306 | "type": "string", 307 | "value": "[variables('backupVmBscPolicyName')]" 308 | }, 309 | "cstVmBscPolResId": { 310 | "type": "string", 311 | "value": "[resourceId('Microsoft.RecoveryServices/vaults/backupPolicies', parameters('recSvcVaultName'), variables('backupVmBscPolicyName'))]" 312 | }, 313 | "cstVmAdvPolName": { 314 | "type": "string", 315 | "value": "[variables('backupVmAdvPolicyName')]" 316 | }, 317 | "cstVmAdvPolResId": { 318 | "type": "string", 319 | "value": "[resourceId('Microsoft.RecoveryServices/vaults/backupPolicies', parameters('recSvcVaultName'), variables('backupVmAdvPolicyName'))]" 320 | }, 321 | "cstFilePolName": { 322 | "type": "string", 323 | "value": "[variables('backupFilePolicyName')]" 324 | }, 325 | "cstFilePolResId": { 326 | "type": "string", 327 | "value": "[resourceId('Microsoft.RecoveryServices/vaults/backupPolicies', parameters('recSvcVaultName'), variables('backupFilePolicyName'))]" 328 | } 329 | } 330 | } -------------------------------------------------------------------------------- /templates/deploy-rsv-vault.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "lawResourceId": { 6 | "type": "string", 7 | "metadata": { 8 | "description": "The resource id of the Log Analytics Workspace" 9 | } 10 | }, 11 | "tags": { 12 | "type": "object", 13 | "metadata": { 14 | "description": "The tags that will be associated to the resources" 15 | }, 16 | "defaultValue": { 17 | "environment": "lab" 18 | } 19 | }, 20 | "uniqueData": { 21 | "type": "string", 22 | "metadata": { 23 | "description": "Data used to append to resources to ensure uniqueness" 24 | }, 25 | "defaultValue": "[substring(newGuid(),0,8)]" 26 | } 27 | }, 28 | "variables": { 29 | "diagnosticApiVersion": "2017-05-01-preview", 30 | "rcvSvcVltApiVersion": "2022-04-01", 31 | "location": "[resourceGroup().location]", 32 | "vaultName": "[concat('vlt',parameters('uniqueData'))]" 33 | }, 34 | "resources": [ 35 | { 36 | "name": "[variables('vaultName')]", 37 | "type": "Microsoft.RecoveryServices/vaults", 38 | "apiVersion": "[variables('rcvSvcVltApiVersion')]", 39 | "location": "[variables('location')]", 40 | "tags": "[parameters('tags')]", 41 | "sku": { 42 | "name": "RS0", 43 | "tier": "Standard" 44 | }, 45 | "identity": { 46 | "type": "SystemAssigned" 47 | }, 48 | "properties": { 49 | "monitoringSettings": { 50 | "azureMonitorAlertSettings": { 51 | "alertsForAllJobFailures": "Enabled" 52 | }, 53 | "classicAlertSettings": { 54 | "alertsForCriticalOperations": "Disabled" 55 | } 56 | } 57 | } 58 | }, 59 | { 60 | "name": "[concat(variables('vaultName'),'/','vaultconfig')]", 61 | "type": "Microsoft.RecoveryServices/vaults/backupconfig", 62 | "dependsOn": [ 63 | "[resourceId('Microsoft.RecoveryServices/vaults', variables('vaultName'))]" 64 | ], 65 | "apiVersion": "[variables('rcvSvcVltApiVersion')]", 66 | "location": "[variables('location')]", 67 | "tags": "[parameters('tags')]", 68 | "properties": { 69 | "enhancedSecurityState": "Disabled", 70 | "isSoftDeleteFeatureStateEditable": true, 71 | "softDeleteFeatureState": "Disabled" 72 | } 73 | }, 74 | { 75 | "name": "[concat(variables('vaultName'),'/','vaultstorageconfig')]", 76 | "type": "Microsoft.RecoveryServices/vaults/backupstorageconfig", 77 | "dependsOn": [ 78 | "[resourceId('Microsoft.RecoveryServices/vaults', variables('vaultName'))]", 79 | "[resourceId('Microsoft.RecoveryServices/vaults/backupconfig',variables('vaultName'),'vaultconfig')]" 80 | ], 81 | "apiVersion": "[variables('rcvSvcVltApiVersion')]", 82 | "location": "[variables('location')]", 83 | "tags": "[parameters('tags')]", 84 | "properties": { 85 | "storageModelType": "GeoRedundant", 86 | "crossRegionRestoreFlag": true 87 | } 88 | }, 89 | { 90 | "name": "[concat(variables('vaultName'),'/microsoft.insights/diag')]", 91 | "type": "Microsoft.RecoveryServices/vaults/providers/diagnosticSettings", 92 | "apiVersion": "[variables('diagnosticApiVersion')]", 93 | "location": "[variables('location')]", 94 | "tags": "[parameters('tags')]", 95 | "dependsOn": [ 96 | "[resourceId('Microsoft.RecoveryServices/vaults/backupstorageconfig', variables('vaultName'), 'vaultstorageconfig')]" 97 | ], 98 | "properties": { 99 | "name": "sendToWorkspace", 100 | "workspaceId": "[parameters('lawResourceId')]", 101 | "logAnalyticsDestinationType": "Dedicated", 102 | "logs": [ 103 | { 104 | "category": "CoreAzureBackup", 105 | "enabled": true 106 | }, 107 | { 108 | "category": "AddonAzureBackupJobs", 109 | "enabled": true 110 | }, 111 | { 112 | "category": "AddonAzureBackupAlerts", 113 | "enabled": true 114 | }, 115 | { 116 | "category": "AddonAzureBackupPolicy", 117 | "enabled": true 118 | }, 119 | { 120 | "category": "AddonAzureBackupStorage", 121 | "enabled": true 122 | }, 123 | { 124 | "category": "AddonAzureBackupProtectedInstance", 125 | "enabled": true 126 | } 127 | ], 128 | "metrics": [ 129 | { 130 | "category": "Health", 131 | "enabled": true 132 | } 133 | ] 134 | }, 135 | "resources": [ 136 | ] 137 | } 138 | ], 139 | "outputs": { 140 | "rsVaultName": { 141 | "type": "string", 142 | "value": "[variables('vaultName')]" 143 | }, 144 | "rsVaultResourceId": { 145 | "type": "string", 146 | "value": "[resourceId('Microsoft.RecoveryServices/vaults', variables('vaultName'))]" 147 | } 148 | } 149 | } -------------------------------------------------------------------------------- /templates/deploy-windows-vm.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", 3 | "contentVersion": "1.0.0.0", 4 | "parameters": { 5 | "adminPassword": { 6 | "type": "securestring", 7 | "metadata": { 8 | "description": "The password for the administrator account created on the VM" 9 | } 10 | }, 11 | "adminUsername": { 12 | "type": "string", 13 | "metadata": { 14 | "description": "Name of the administrator account created on the VM" 15 | } 16 | }, 17 | "availabilityZone": { 18 | "type": "string", 19 | "metadata": { 20 | "description": "The number of the availability zone to deploy to" 21 | } 22 | }, 23 | "linkedTemplateLocation": { 24 | "type": "string", 25 | "metadata": { 26 | "description": "The location of linked templates and scripts" 27 | }, 28 | "defaultValue": "[deployment().properties.templateLink.uri]" 29 | }, 30 | "myWorkspaceId": { 31 | "type": "string", 32 | "metadata": { 33 | "description": "The Log and Analytics workspace ID that the Microsoft Monitoring Agent will deliver metrics and logs to" 34 | } 35 | }, 36 | "myWorkspaceKey": { 37 | "type": "string", 38 | "metadata": { 39 | "description": "The Log and Analytics workspace secret" 40 | } 41 | }, 42 | "subnetName": { 43 | "type": "string", 44 | "metadata": { 45 | "description": "The subnet within the Virtual Network the network interface for the VM is to be placed in" 46 | } 47 | }, 48 | "serverIpAddress": { 49 | "type": "string", 50 | "metadata": { 51 | "description": "The static IP address assigned to the server's network interface" 52 | } 53 | }, 54 | "tags": { 55 | "type": "object", 56 | "metadata": { 57 | "description": "The tags that will be associated to the VM" 58 | } 59 | }, 60 | "uniqueData": { 61 | "type": "string", 62 | "metadata": { 63 | "description": "Data used to append to resources to ensure uniqueness" 64 | }, 65 | "defaultValue": "[substring(newGuid(),0,8)]" 66 | }, 67 | "virtualMachineSize": { 68 | "type": "string", 69 | "metadata": { 70 | "description": "VM Size" 71 | } 72 | }, 73 | "vmName": { 74 | "type": "string", 75 | "metadata": { 76 | "description": "VM Name" 77 | } 78 | }, 79 | "vnetName": { 80 | "type": "string", 81 | "metadata": { 82 | "description": "The Virtual Network the VM is to be placed in" 83 | } 84 | }, 85 | "vnetResourceGroup": { 86 | "type": "string", 87 | "defaultValue": "[resourceGroup().name]", 88 | "metadata": { 89 | "description": "The resource group of the Virtual Network the VM will use" 90 | } 91 | }, 92 | "vnetSubscriptionId": { 93 | "type": "string", 94 | "defaultValue": "[subscription().subscriptionId]", 95 | "metadata": { 96 | "description": "The subscription of the Virtual Network the VM will use" 97 | } 98 | } 99 | }, 100 | "variables": { 101 | "networkApiVersion": "2021-08-01", 102 | "vmApiVersion": "2021-11-01", 103 | "modulesUrl": "[uri(parameters('linkedTemplateLocation'), concat('../dsc/windowsdevvm.zip'))]", 104 | "configurationFunction": "windowsdevvm.ps1\\WindowsDevVM", 105 | "location": "[resourceGroup().location]", 106 | "nicName": "[concat(parameters('vmName'),parameters('uniqueData'))]", 107 | "osDiskType": "StandardSSD_LRS", 108 | "scriptName": "prepare-windows-vm.ps1", 109 | "scriptUrl": "[uri(parameters('linkedTemplateLocation'), concat('../scripts/', variables('scriptName')))]", 110 | "subnetRef": "[resourceId(parameters('vnetSubscriptionId'),parameters('vnetResourceGroup'),'Microsoft.Network/virtualNetworks/subnets',parameters('vnetName'),parameters('subnetName'))]" 111 | }, 112 | "resources": [ 113 | { 114 | "name": "[variables('nicName')]", 115 | "type": "Microsoft.Network/networkInterfaces", 116 | "apiVersion": "[variables('networkApiVersion')]", 117 | "location": "[variables('location')]", 118 | "tags": "[parameters('tags')]", 119 | "properties": { 120 | "ipConfigurations": [ 121 | { 122 | "name": "ipconfig1", 123 | "properties": { 124 | "privateIPAllocationMethod": "Static", 125 | "privateIPAddress": "[parameters('serverIpAddress')]", 126 | "subnet": { 127 | "id": "[variables('subnetRef')]" 128 | } 129 | } 130 | } 131 | ] 132 | } 133 | }, 134 | { 135 | "name": "[parameters('vmName')]", 136 | "type": "Microsoft.Compute/virtualMachines", 137 | "apiVersion": "[variables('vmApiVersion')]", 138 | "location": "[variables('location')]", 139 | "tags": "[parameters('tags')]", 140 | "dependsOn": [ 141 | "[concat('Microsoft.Network/networkInterfaces/', variables('nicName'))]" 142 | ], 143 | "properties": { 144 | "diagnosticsProfile": { 145 | "bootDiagnostics": { 146 | "enabled": true 147 | } 148 | }, 149 | "hardwareProfile": { 150 | "vmSize": "[parameters('virtualMachineSize')]" 151 | }, 152 | "networkProfile": { 153 | "networkInterfaces": [ 154 | { 155 | "id": "[resourceId('Microsoft.Network/networkInterfaces', variables('nicName'))]" 156 | } 157 | ] 158 | }, 159 | "osProfile": { 160 | "computerName": "[parameters('vmName')]", 161 | "adminUsername": "[parameters('adminUsername')]", 162 | "adminPassword": "[parameters('adminPassword')]", 163 | "windowsConfiguration": { 164 | "enableAutomaticUpdates": true, 165 | "provisionVmAgent": true 166 | } 167 | }, 168 | "storageProfile": { 169 | "dataDisks": [ 170 | { 171 | "name": "[concat(parameters('vmName'),'_data-disk1')]", 172 | "caching": "None", 173 | "diskSizeGB": "1", 174 | "lun": 0, 175 | "createOption": "Empty", 176 | "managedDisk": { 177 | "storageAccountType": "StandardSSD_LRS" 178 | } 179 | } 180 | ], 181 | "osDisk": { 182 | "createOption": "fromImage", 183 | "managedDisk": { 184 | "storageAccountType": "[variables('osDiskType')]" 185 | } 186 | }, 187 | "imageReference": { 188 | "publisher": "MicrosoftWindowsServer", 189 | "offer": "WindowsServer", 190 | "sku": "2019-Datacenter", 191 | "version": "latest" 192 | } 193 | } 194 | }, 195 | "zones": [ 196 | "[parameters('availabilityZone')]" 197 | ], 198 | "resources": [ 199 | { 200 | "type": "extensions", 201 | "name": "DependencyAgentWindows", 202 | "apiVersion": "[variables('vmApiVersion')]", 203 | "location": "[variables('location')]", 204 | "dependsOn": [ 205 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]" 206 | ], 207 | "properties": { 208 | "publisher": "Microsoft.Azure.Monitoring.DependencyAgent", 209 | "type": "DependencyAgentWindows", 210 | "typeHandlerVersion": "9.5", 211 | "autoUpgradeMinorVersion": true 212 | } 213 | }, 214 | { 215 | "type": "extensions", 216 | "name": "MMAExtension", 217 | "apiVersion": "[variables('vmApiVersion')]", 218 | "location": "[variables('location')]", 219 | "dependsOn": [ 220 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]", 221 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/DependencyAgentWindows')]" 222 | ], 223 | "properties": { 224 | "publisher": "Microsoft.EnterpriseCloud.Monitoring", 225 | "type": "MicrosoftMonitoringAgent", 226 | "typeHandlerVersion": "1.0", 227 | "autoUpgradeMinorVersion": true, 228 | "settings": { 229 | "workspaceId": "[parameters('myWorkspaceId')]", 230 | "stopOnMultipleConnections": true 231 | }, 232 | "protectedSettings": { 233 | "workspaceKey": "[parameters('myWorkspaceKey')]" 234 | } 235 | } 236 | }, 237 | { 238 | "type": "extensions", 239 | "name": "AzureMonitorWindowsAgent", 240 | "apiVersion": "[variables('vmApiVersion')]", 241 | "location": "[variables('location')]", 242 | "dependsOn": [ 243 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]", 244 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/MMAExtension')]" 245 | ], 246 | "properties": { 247 | "publisher": "Microsoft.Azure.Monitor", 248 | "type": "AzureMonitorWindowsAgent", 249 | "typeHandlerVersion": "1.0", 250 | "autoUpgradeMinorVersion": true, 251 | "enableAutomaticUpgrade": true 252 | } 253 | }, 254 | { 255 | "type": "extensions", 256 | "name": "Microsoft.Azure.NetworkWatcher", 257 | "apiVersion": "[variables('vmApiVersion')]", 258 | "location": "[variables('location')]", 259 | "dependsOn": [ 260 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]", 261 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/AzureMonitorWindowsAgent')]" 262 | ], 263 | "properties": { 264 | "publisher": "Microsoft.Azure.NetworkWatcher", 265 | "type": "NetworkWatcherAgentWindows", 266 | "typeHandlerVersion": "1.4", 267 | "autoUpgradeMinorVersion": true 268 | } 269 | }, 270 | { 271 | "type": "extensions", 272 | "name": "WindowsDevVM", 273 | "apiVersion": "[variables('vmApiVersion')]", 274 | "location": "[variables('location')]", 275 | "dependsOn": [ 276 | "[resourceId('Microsoft.Compute/virtualMachines', parameters('vmName'))]", 277 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/Microsoft.Azure.NetworkWatcher')]" 278 | ], 279 | "properties": { 280 | "publisher": "Microsoft.Powershell", 281 | "type": "DSC", 282 | "typeHandlerVersion": "2.77", 283 | "autoUpgradeMinorVersion": true, 284 | "settings": { 285 | "ModulesUrl": "[variables('modulesUrl')]", 286 | "ConfigurationFunction": "[variables('configurationFunction')]", 287 | "Properties": { 288 | "MachineName": "[parameters('vmName')]", 289 | "AdminCreds": { 290 | "UserName": "[parameters('adminUsername')]", 291 | "Password": "PrivateSettingsRef:AdminPassword" 292 | } 293 | } 294 | }, 295 | "protectedSettings": { 296 | "Items": { 297 | "AdminPassword": "[parameters('adminPassword')]" 298 | } 299 | } 300 | } 301 | }, 302 | { 303 | "type": "extensions", 304 | "name": "CustomScriptExtension", 305 | "apiVersion": "[variables('vmApiVersion')]", 306 | "location": "[variables('location')]", 307 | "dependsOn": [ 308 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'))]", 309 | "[concat('Microsoft.Compute/virtualMachines/', parameters('vmName'), '/extensions/WindowsDevVM')]" 310 | ], 311 | "properties": { 312 | "publisher": "Microsoft.Compute", 313 | "type": "CustomScriptExtension", 314 | "typeHandlerVersion": "1.10", 315 | "autoUpgradeMinorVersion": true, 316 | "settings": { 317 | "fileUris": [ 318 | "[variables('scriptUrl')]" 319 | ] 320 | }, 321 | "protectedSettings": { 322 | "commandToExecute": "[concat('powershell.exe -Command \"./', variables('scriptName'), '; exit 0;\"')]" 323 | } 324 | } 325 | } 326 | ] 327 | } 328 | ] 329 | } --------------------------------------------------------------------------------