Deploy Azure like a pro: your first Terraform main.tf made simple

A simple main.tf for an Azure Terraform solution. We will refer to this in later tutorials.

# Configure the Azure Provider 
provider "azurerm" { 
    features {} 
} 

# Create a resource group 
resource "azurerm_resource_group" "example" { 
    name     = "example-resources" 
    location = "East US" 
    tags = { 
        environment = "development" 
    } 
} 

# Create a virtual network 
resource "azurerm_virtual_network" "example" { 
    name                = "example-network" 
    address_space       = ["10.0.0.0/16"] 
    location            = azurerm_resource_group.example.location 
    resource_group_name = azurerm_resource_group.example.name 
} 

# Create a subnet 
resource "azurerm_subnet" "example" { 
    name                 = "internal" 
    resource_group_name  = azurerm_resource_group.example.name 
    virtual_network_name = azurerm_virtual_network.example.name 
    address_prefixes     = ["10.0.2.0/24"] 
} 

# Create a network security group 
resource "azurerm_network_security_group" "example" { 
    name                = "example-nsg" 
    location            = azurerm_resource_group.example.location 
    resource_group_name = azurerm_resource_group.example.name 
    security_rule { 
        name                       = "allow-http" 
        priority                   = 100 
        direction                  = "Inbound" 
        access                     = "Allow" 
        protocol                   = "Tcp" 
        source_port_range          = "*" 
        destination_port_range     = "80" 
        source_address_prefix      = "*" 
        destination_address_prefix = "*" 
    } 
    security_rule { 
        name                       = "allow-https" 
        priority                   = 110 
        direction                  = "Inbound" 
        access                     = "Allow" 
        protocol                   = "Tcp" 
        source_port_range          = "*" 
        destination_port_range     = "443" 
        source_address_prefix      = "*" 
        destination_address_prefix = "*" 
    } 
} 

# Create a public IP 
resource "azurerm_public_ip" "example" { 
    name                = "example-pip" 
    location            = azurerm_resource_group.example.location 
    resource_group_name = azurerm_resource_group.example.name 
    allocation_method   = "Dynamic" 
} 

# Create a network interface 
resource "azurerm_network_interface" "example" { 
    name                = "example-nic" 
    location            = azurerm_resource_group.example.location 
    resource_group_name = azurerm_resource_group.example.name 
    ip_configuration { 
        name                          = "internal" 
        subnet_id                     = azurerm_subnet.example.id 
        private_ip_address_allocation = "Dynamic" 
        public_ip_address_id          = azurerm_public_ip.example.id 
    } 
} 

# Output resource group name 
output "resource_group_name" { 
    value = azurerm_resource_group.example.name 
} 

# Output virtual network name 
output "virtual_network_name" { 
    value = azurerm_virtual_network.example.name 
} 

Let’s walk through each element of the Azure Terraform configuration file in detail:

Provider block

provider "azurerm" { 
features {} 
} 

This configures the Azure Resource Manager (AzureRM) provider which is required to interact with Azure . The features {} block is mandatory in newer versions of the AzureRM provider. This block could also include authentication settings if not using Azure CLI authentication.

Resource group

resource "azurerm_resource_group" "example" { 
name = "example-resources" 
location = "East US" 
tags = { 
    environment = "development" 
    } 
} 

A resource group is a logical container for Azure resources.

Virtual network

resource "azurerm_virtual_network" "example" { 
name = "example-network" 
address_space = ["10.0.0.0/16"] 
location = azurerm_resource_group.example.location 
resource_group_name = azurerm_resource_group.example.name 
} 

This creates an isolated network environment in Azure

Subnet

resource "azurerm_subnet" "example" { 
name = "internal" 
resource_group_name = azurerm_resource_group.example.name 
virtual_network_name = azurerm_virtual_network.example.name 
address_prefixes = ["10.0.2.0/24"] 
} 

This subdivides the virtual network into a smaller network segment.

Network security group

resource "azurerm_network_security_group" "example" { 
    name = "example-nsg" 
    location = azurerm_resource_group.example.location 
    resource_group_name = azurerm_resource_group.example.name 
    security_rule { 
        name = "allow-http" 
        priority = 100 
        direction = "Inbound" 
        access = "Allow" 
        protocol = "Tcp" 
        source_port_range = "*" 
        destination_port_range = "80" 
        source_address_prefix = "*" 
        destination_address_prefix = "*" 
    } 
    security_rule { 
        name = "allow-https" 
        priority = 110 
        direction = "Inbound" 
        access = "Allow" 
        protocol = "Tcp" 
        source_port_range = "*" 
        destination_port_range = "443" 
        source_address_prefix = "*" 
        destination_address_prefix = "*" 
    } 
} 

The security group acts as a virtual firewall to control inbound and outbound traffic. The group contains two security rules that allow HTTP (port 80) and HTTPS (port 443) traffic.

Public IP

resource "azurerm_public_ip" "example" { 
    name = "example-pip" 
    location = azurerm_resource_group.example.location 
    resource_group_name = azurerm_resource_group.example.name 
    allocation_method = "Dynamic" 
} 

Creates a public IP address that can be associated with Azure resources.

Network interface

resource "azurerm_network_interface" "example" { 
    name = "example-nic" 
    location = azurerm_resource_group.example.location 
    resource_group_name = azurerm_resource_group.example.name 
    ip_configuration { 
        name = "internal" 
        subnet_id = azurerm_subnet.example.id 
        private_ip_address_allocation = "Dynamic" 
        public_ip_address_id = azurerm_public_ip.example.id 
    } 
} 

A network interface connects a virtual machine to the virtual network.

Outputs

output "resource_group_name" { 
    value = azurerm_resource_group.example.name 
} 

output "virtual_network_name" { 
    value = azurerm_virtual_network.example.name 
} 

This defines values that will be displayed after terraform applies the configuration. It is useful for referencing created resources in other configurations or for informational purposes. These specific outputs would show the resource group and virtual network names after deployment.

This configuration creates a basic network infrastructure in Azure that could support deploying virtual machines or other services that would need network connectivity.

comments powered by Disqus

Copyright 2025. All rights reserved.