Utilizing Bicep to Deploy Azure Virtual Machines with the Next Available Static IP

Deploy Azure Virtual Machines (VMs) with static IPs. Specifically, we’ll explore the methodology of dynamically allocating a static IP without explicitly designating what that IP is. Put differently, the objective here is to select the next available IP in a virtual network subnet and fix it as a static address for the VM, all within the same template.

Certainly, there are alternative routes to achieve this, such as utilizing Azure Command-Line Interface (CLI) or Azure PowerShell. But what caught my intellectual curiosity was the question of whether this could be accomplished solely using Azure Bicep. The pursuit of this possibility led me to the following approach, which I believe fellow enthusiasts and technical experts will find both challenging and rewarding.

High-Level Steps.

  1. Create a separate module for VM Nic
  2. Called the VM NIC module twice inside the VM Module
    • First step is to create a NIC using dynamic IP
    • Output the IP from the first module run and use it as an input for the second time to make it static.

hopefully below diagram may help you.

Deploy Azure Virtual Machines

Bicep templates

NIC Module

@description('Virtual machine name. Do not include numerical identifier.')
@maxLength(14)
param virtualMachineNameSuffix string

@description('Virtual machine location.')
param location string = resourceGroup().location

@description('Resource Id of Subnet to place VM into.')
param subnetId string

@description('Private IP address')
param privateIpAddress string = ''

@description('Private IP Allocation Method')
param privateIPAllocationMethod string = 'dynamic'

@description('Object containing resource tags.')
param tags object = {}


resource staticNic 'Microsoft.Network/networkInterfaces@2021-02-01' =  {
  name: '${virtualMachineNameSuffix}-nic01'
  location: location
  tags: !empty(tags) ? tags : json('null')
  properties: {
    ipConfigurations: [
      {
        name: 'ipconfig1'
        properties: {
          subnet: {
            id: subnetId
          }
          privateIPAllocationMethod: privateIPAllocationMethod
          privateIPAddress:(privateIPAllocationMethod =='Dynamic') ? null: privateIpAddress
        }
      }
    ]
  }
}

output nicId string = staticNic.id
output nicName string = staticNic.name
output ipAddress string = staticNic.properties.ipConfigurations[0].properties.privateIPAddress

Note – Following output line is the critical part of exporting the assigned IP.

output ipAddress string = staticNic.properties.ipConfigurations[0].properties.privateIPAddress

VM Module (NIC Part)

If you look at the first module call, we are basically deploying the NIC using dynamic allocation method to get the next available IP for us. And in the second call we are using the output from first call. (Highlighted)

module nic 'virtual-machine-nic.bicep' = {
  name: '${virtualMachineNameSuffix}-nic01-deployment'
  params: {
    location: location
    subnetId: subnetId
    virtualMachineNameSuffix: virtualMachineNameSuffix
    privateIPAllocationMethod:'Dynamic'
  }
}

module nicStaticIp 'virtual-machine-nic.bicep' = {
  name: '${virtualMachineNameSuffix}-nic01-deployment-static'
  params: {
    location: location
    subnetId: subnetId
    virtualMachineNameSuffix: virtualMachineNameSuffix
    privateIPAllocationMethod:'Static'
    privateIpAddress:nic.outputs.ipAddress
  }
}

you can get the full code in my GitHub below. Link

In conclusion, the exploration into deploying Azure virtual machines with static IPs using Azure Bicep has proven to be a fascinating and rewarding endeavor. Although the solution might not be the only approach, it represents a well-crafted method that leverages the power of Azure Bicep as a sole language. By orchestrating the dynamic allocation of IPs and transforming them into static assignments, we’ve managed to streamline a critical aspect of VM management. This method not only simplifies the process but also aligns with the evolving landscape of cloud infrastructure management. It is a testament to the flexibility and robustness of Azure Bicep and underscores the possibilities that await those eager to delve into the intricacies of cloud automation. For enthusiasts and professionals alike, it opens a new avenue to explore, refine, and innovate.

As always reach out to me if you have any questions or suggestions. 🙂

Learn More –

Arinco Blog – Blogs – Arinco

MS Docs – Bicep language for deploying Azure resources – Azure Resource Manager | Microsoft Learn

Read more recent blogs

Get started on the right path to cloud success today. Our Crew are standing by to answer your questions and get you up and running.