Skip to content

claranet/terraform-azurerm-virtual-wan

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Azure Virtual Wan

Changelog Notice Apache V2 License OpenTofu Registry

Azure Virtual Wan module to create a Virtual Wan with one Virtual Hub, an Azure Firewall and an Express Route Circuit with its Private Peering and VPN connections. An infrastructure example referenced in the Azure Cloud Adoption Framework is available here: raw.githubusercontent.com/microsoft/CloudAdoptionFramework/master/ready/enterprise-scale-architecture.pdf

This module use multiple sub-modules:

Naming

Resource naming is based on the Microsoft CAF naming convention best practices. Use the parameter custom_<resource>_name to override names. We rely on the official Terraform Azure CAF naming provider to generate resource names.

Global versioning rule for Claranet Azure modules

Module version Terraform version OpenTofu version AzureRM version
>= 8.x.x Unverified 1.8.x >= 4.0
>= 7.x.x 1.3.x >= 3.0
>= 6.x.x 1.x >= 3.0
>= 5.x.x 0.15.x >= 2.0
>= 4.x.x 0.13.x / 0.14.x >= 2.0
>= 3.x.x 0.12.x >= 2.0
>= 2.x.x 0.12.x < 2.0
< 2.x.x 0.11.x < 2.0

Contributing

If you want to contribute to this repository, feel free to use our pre-commit git hook configuration which will help you automatically update and format some files for you by enforcing our Terraform code module best-practices.

More details are available in the CONTRIBUTING.md file.

Usage

This module is optimized to work with the Claranet terraform-wrapper tool which set some terraform variables in the environment needed by this module. More details about variables set by the terraform-wrapper available in the documentation.

⚠️ Since modules version v8.0.0, we do not maintain/check anymore the compatibility with Hashicorp Terraform. Instead, we recommend to use OpenTofu.

locals {
  vnets = [
    {
      vnet_name                 = "MyVnet1"
      vnet_cidr                 = ["10.10.0.0/16"]
      internet_security_enabled = true
    },
    {
      vnet_name                 = "MyVnet2"
      vnet_cidr                 = ["10.100.0.0/16"]
      internet_security_enabled = false
    }
  ]
  subnets = [
    {
      name      = "MySubnet1OnVnet1"
      cidr      = ["10.10.0.0/24"]
      vnet_name = module.azure_virtual_network["MyVnet1"].virtual_network_name
    },
    {
      name      = "MySubnet2OnVnet1"
      cidr      = ["10.10.1.0/24"]
      vnet_name = module.azure_virtual_network["MyVnet1"].virtual_network_name
    },
    {
      name      = "MySubnet1OnVnet2"
      cidr      = ["10.100.0.0/24"]
      vnet_name = module.azure_virtual_network["MyVnet2"].virtual_network_name
    },
    {
      name      = "MySubnet2OnVnet2"
      cidr      = ["10.100.1.0/24"]
      vnet_name = module.azure_virtual_network["MyVnet2"].virtual_network_name
    }
  ]
}
module "azure_region" {
  source  = "claranet/regions/azurerm"
  version = "x.x.x"

  azure_region = var.azure_region
}

module "rg" {
  source  = "claranet/rg/azurerm"
  version = "x.x.x"

  location    = module.azure_region.location
  client_name = var.client_name
  environment = var.environment
  stack       = var.stack
}

module "virtual_wan" {
  source  = "claranet/virtual-wan/azurerm"
  version = "x.x.x"

  client_name = var.client_name
  environment = var.environment
  stack       = var.stack

  location            = module.azure_region.location
  location_short      = module.azure_region.location_short
  resource_group_name = module.rg.resource_group_name

  virtual_hub_address_prefix = "10.254.0.0/23"

  firewall_enabled                      = true
  express_route_enabled                 = true
  express_route_private_peering_enabled = true
  vpn_gateway_enabled                   = true

  express_route_circuit_service_provider  = "Equinix"
  express_route_circuit_peering_location  = "Paris"
  express_route_circuit_bandwidth_in_mbps = 100

  express_route_circuit_private_peering_primary_peer_address_prefix   = "169.254.254.0/30"
  express_route_circuit_private_peering_secondary_peer_address_prefix = "169.254.254.4/30"
  express_route_circuit_private_peering_vlan_id                       = 1234
  express_route_circuit_private_peering_peer_asn                      = 4321
  express_route_circuit_private_peering_shared_key                    = "MySuperSecretSharedKey"

  logs_destinations_ids = [
    module.logs.log_analytics_workspace_id,
    module.logs.logs_storage_account_id
  ]

  peered_virtual_networks = [
    for vnet in local.vnets : {
      vnet_id                   = module.azure_virtual_network[vnet.vnet_name].virtual_network_id
      internet_security_enabled = vnet.internet_security_enabled
      # routing = {}
    }
  ]

  vpn_gateway_instance_0_bgp_peering_address = ["169.254.21.1"]
  vpn_gateway_instance_1_bgp_peering_address = ["169.254.22.1"]

  vpn_sites = [
    {
      name = "site1"
      links = [
        {
          name       = "site1-primary-endpoint"
          ip_address = "20.20.20.20"
          bgp = [
            {
              asn             = 65530
              peering_address = "169.254.21.2"
            }
          ]
        },
        {
          name       = "site1-secondary-endpoint"
          ip_address = "21.21.21.21"
          bgp = [
            {
              asn             = 65530
              peering_address = "169.254.22.2"
            }
          ]
        }
      ]

    }
  ]

  vpn_connections = [
    {
      name      = "cn-hub-to-site1"
      site_name = "site1"
      links = [
        {
          name           = "site1-primary-link"
          bandwidth_mbps = 200
          bgp_enabled    = true
          ipsec_policy = {
            dh_group                 = "DHGroup14"
            ike_encryption_algorithm = "AES256"
            ike_integrity_algorithm  = "SHA256"
            encryption_algorithm     = "AES256"
            integrity_algorithm      = "SHA256"
            pfs_group                = "PFS14"
            sa_data_size_kb          = 102400000
            sa_lifetime_sec          = 3600
          }
          protocol   = "IKEv2"
          shared_key = "VeryStrongSecretKeyForPrimaryLink"
        },
        {
          name           = "site1-secondary-link"
          bandwidth_mbps = 200
          bgp_enabled    = true
          ipsec_policy = {
            dh_group                 = "DHGroup14"
            ike_encryption_algorithm = "AES256"
            ike_integrity_algorithm  = "SHA256"
            encryption_algorithm     = "AES256"
            integrity_algorithm      = "SHA256"
            pfs_group                = "PFS14"
            sa_data_size_kb          = 102400000
            sa_lifetime_sec          = 3600
          }
          protocol   = "IKEv2"
          shared_key = "VeryStrongSecretKeyForSecondaryLink"
        }
      ]
    }
  ]
}

module "azure_virtual_network" {
  for_each = { for vnet in local.vnets : vnet.vnet_name => vnet }

  source  = "claranet/vnet/azurerm"
  version = "x.x.x"

  environment = var.environment
  client_name = var.client_name
  stack       = var.stack

  location       = module.azure_region.location
  location_short = module.azure_region.location_short

  resource_group_name = module.rg.resource_group_name

  custom_vnet_name = each.value.vnet_name
  vnet_cidr        = each.value.vnet_cidr
}

module "azure_network_subnet" {
  source  = "claranet/subnet/azurerm"
  version = "x.x.x"

  for_each    = { for subnet in local.subnets : subnet.name => subnet }
  environment = var.environment
  client_name = var.client_name
  stack       = var.stack

  location_short = module.azure_region.location_short

  custom_subnet_name = each.key

  resource_group_name  = module.rg.resource_group_name
  virtual_network_name = each.value.vnet_name
  subnet_cidr_list     = each.value.cidr

}

module "logs" {
  source  = "claranet/run/azurerm//modules/logs"
  version = "x.x.x"

  client_name = var.client_name
  environment = var.environment
  stack       = var.stack

  location       = module.azure_region.location
  location_short = module.azure_region.location_short

  resource_group_name = module.rg.resource_group_name
}

Providers

Name Version
azurecaf ~> 1.2, >= 1.2.22
azurerm ~> 3.73
null ~> 3.0

Modules

Name Source Version
express_route ./modules/express-route n/a
firewall ./modules/firewall n/a
routing ./modules/routing-intent n/a
vhub ./modules/virtual-hub n/a
vpn ./modules/vpn n/a

Resources

Name Type
azurerm_virtual_wan.vwan resource
null_resource.routing_precondition resource
azurecaf_name.virtual_wan_caf data source

Inputs

Name Description Type Default Required
azure_firewall_as_next_hop_enabled Whether use Azure Firewall as next hop or a NVA. bool true no
branch_to_branch_traffic_allowed Boolean flag to specify whether branch to branch traffic is allowed bool true no
client_name Name of client. string n/a yes
custom_express_route_circuit_name Custom ExpressRoute Circuit name string null no
custom_express_route_gateway_name Custom ExpressRoute Gateway name string null no
custom_firewall_name Custom Firewall's name string null no
custom_virtual_hub_name Custom Virtual Hub's name string null no
custom_vpn_gateway_name Custom name for the VPN Gateway string null no
custom_vwan_name Custom Virtual Wan's name. string null no
default_tags_enabled Option to enabled or disable default tags bool true no
environment Name of application's environment. string n/a yes
express_route_circuit_bandwidth_in_mbps The bandwith in Mbps of the ExpressRoute Circuit being created on the Service Provider number null no
express_route_circuit_peering_location ExpressRoute Circuit peering location. string null no
express_route_circuit_private_peering_peer_asn Peer BGP ASN for ExpressRoute Circuit Private Peering number null no
express_route_circuit_private_peering_primary_peer_address_prefix Primary peer address prefix for ExpressRoute Circuit private peering string null no
express_route_circuit_private_peering_secondary_peer_address_prefix Secondary peer address prefix for ExpressRoute Circuit private peering string null no
express_route_circuit_private_peering_shared_key Shared secret key for ExpressRoute Circuit Private Peering string null no
express_route_circuit_private_peering_vlan_id VLAN Id for ExpressRoute Circuit number null no
express_route_circuit_service_provider The name of the ExpressRoute Circuit Service Provider. string null no
express_route_custom_diagnostic_settings_name Custom name of the diagnostics settings, name will be 'default' if not set. string "default" no
express_route_enabled Enable or not ExpressRoute configuration bool false no
express_route_gateway_allow_non_virtual_wan_traffic Whether the gateway accept traffic from non-Virtual WAN networks. bool false no
express_route_gateway_extra_tags Extra tags for Express Route Gateway map(string) {} no
express_route_gateway_scale_unit The number of scale unit with which to provision the ExpressRoute Gateway. number 1 no
express_route_logs_categories Log categories to send to destinations. list(string) null no
express_route_logs_destinations_ids List of destination resources IDs for logs diagnostic destination for Express Route resource.
Can be Storage Account, Log Analytics Workspace and Event Hub. No more than one of each can be set.
If you want to specify an Azure EventHub to send logs and metrics to, you need to provide a formated string with both the EventHub Namespace authorization send ID and the EventHub name (name of the queue to use in the Namespace) separated by the `
` character. list(string) null
express_route_logs_metrics_categories Metrics categories to send to destinations. list(string) null no
express_route_private_peering_enabled Enable ExpressRoute Circuit Private Peering bool false no
express_route_sku ExpressRoute SKU
object({
tier = string,
family = string
})
{
"family": "MeteredData",
"tier": "Premium"
}
no
extra_tags Map of additional tags. map(string) {} no
firewall_availibility_zones Availability zones in which the Azure Firewall should be created. list(number)
[
1,
2,
3
]
no
firewall_custom_diagnostic_settings_name Custom name of the diagnostics settings, name will be 'default' if not set. string "default" no
firewall_dns_servers List of DNS servers that the Azure Firewall will direct DNS traffic to for the name resolution list(string) null no
firewall_enabled Enable or not Azure Firewall in the Virtual Hub bool true no
firewall_extra_tags Extra tags for Firewall resource map(string) {} no
firewall_logs_categories Log categories to send to destinations. list(string) null no
firewall_logs_destinations_ids List of destination resources IDs for logs diagnostic destination for Azure Firewall resource.
Can be Storage Account, Log Analytics Workspace and Event Hub. No more than one of each can be set.
If you want to specify an Azure EventHub to send logs and metrics to, you need to provide a formated string with both the EventHub Namespace authorization send ID and the EventHub name (name of the queue to use in the Namespace) separated by the `
` character. list(string) null
firewall_logs_metrics_categories Metrics categories to send to destinations. list(string) null no
firewall_policy_id ID of the Firewall Policy applied to this Firewall. string null no
firewall_private_ip_ranges List of SNAT private CIDR IP ranges, or the special string IANAPrivateRanges, which indicates Azure Firewall does not SNAT when the destination IP address is a private range per IANA RFC 1918 list(string) null no
firewall_public_ip_count Number of public IPs to assign to the Firewall. number 1 no
firewall_sku_tier SKU tier of the Firewall. Possible values are Premium and Standard. string "Standard" no
internet_routing_enabled Whether force the internet routing through Azure Firewall or the NVA. bool true no
internet_security_enabled Define internet security parameter in both VPN Connections and Virtual Hub Connections if set bool null no
location Azure location. string n/a yes
location_short Short string for Azure location. string n/a yes
logs_destinations_ids List of destination resources IDs for logs diagnostic destination.
Can be Storage Account, Log Analytics Workspace and Event Hub. No more than one of each can be set.
If you want to specify an Azure EventHub to send logs and metrics to, you need to provide a formated string with both the EventHub Namespace authorization send ID and the EventHub name (name of the queue to use in the Namespace) separated by the `
` character. list(string) n/a
name_prefix Prefix for generated resources names. string "" no
name_slug Slug to use with the generated resources names. string "" no
name_suffix Suffix for the generated resources names. string "" no
next_hop_nva_id ID of the NVA used as next hop. string null no
office365_local_breakout_category Specifies the Office365 local breakout category. Possible values include: Optimize, OptimizeAndAllow, All, None string "None" no
peered_virtual_networks Virtual Networks to peer with the Virtual Hub.
list(object({
vnet_id = string
peering_name = optional(string)
internet_security_enabled = optional(bool, true)

routing = optional(object({
associated_route_table_id = optional(string)

propagated_route_table = optional(object({
labels = optional(list(string))
route_table_ids = optional(list(string))
}))

static_vnet_route = optional(object({
name = optional(string)
address_prefixes = optional(list(string))
next_hop_ip_address = optional(string)
}))
}))
}))
[] no
private_routing_enabled Whether force the private routing through Azure Firewall or the NVA. bool true no
resource_group_name Name of the application's resource group. string n/a yes
routing_intent_enabled Whether enable or not the routing intent. bool false no
stack Name of application's stack. string n/a yes
virtual_hub_address_prefix The address prefix which should be used for this Virtual Hub. Cannot be smaller than a /24. A /23 is recommended by Azure string n/a yes
virtual_hub_extra_tags Extra tags for this Virtual Hub map(string) {} no
virtual_hub_routes List of route blocks. next_hop_ip_address values can be azure_firewall or an IP address.
list(object({
address_prefixes = list(string),
next_hop_ip_address = string
}))
[] no
virtual_hub_sku The SKU of the Virtual Hub. Possible values are Basic and Standard string "Standard" no
virtual_wan_extra_tags Extra tags for this Virtual Wan map(string) {} no
virtual_wan_type Specifies the Virtual Wan type. Possible Values include: Basic and Standard string "Standard" no
vpn_connections VPN Connections configuration
list(object({
name = string
site_name = optional(string)
site_id = optional(string)
internet_security_enabled = optional(bool, false)
links = list(object({
name = string
egress_nat_rule_ids = optional(list(string), [])
ingress_nat_rule_ids = optional(list(string), [])
bandwidth_mbps = optional(number, 10)
bgp_enabled = optional(bool, false)
connection_mode = optional(string, "Default")
ipsec_policy = optional(object({
dh_group = string
ike_encryption_algorithm = string
ike_integrity_algorithm = string
encryption_algorithm = string
integrity_algorithm = string
pfs_group = string
sa_data_size_kb = number
sa_lifetime_sec = number
}))
protocol = optional(string, "IKEv2")
ratelimit_enabled = optional(bool, false)
route_weight = optional(number, 0)
shared_key = optional(string, null)
local_azure_ip_address_enabled = optional(bool, false)
policy_based_traffic_selector_enabled = optional(bool, false)
}))
traffic_selector_policy = optional(list(object({
local_address_ranges = list(string)
remote_address_ranges = list(string)
})), [])
}))
[] no
vpn_encryption_enabled Boolean flag to specify whether VPN encryption is enabled bool true no
vpn_gateway_custom_diagnostic_settings_name Custom name of the diagnostics settings, name will be 'default' if not set. string "default" no
vpn_gateway_enabled Enable or not the deployment of a VPN Gateway and its Connections bool false no
vpn_gateway_extra_tags Extra tags for the VPN Gateway map(string) null no
vpn_gateway_instance_0_bgp_peering_address List of custom BGP IP Addresses to assign to the first instance list(string) [] no
vpn_gateway_instance_1_bgp_peering_address List of custom BGP IP Addresses to assign to the second instance list(string) [] no
vpn_gateway_logs_categories Log categories to send to destinations. list(string) null no
vpn_gateway_logs_destinations_ids List of destination resources IDs for logs diagnostic destination for VPN Gateway resource.
Can be Storage Account, Log Analytics Workspace and Event Hub. No more than one of each can be set.
If you want to specify an Azure EventHub to send logs and metrics to, you need to provide a formated string with both the EventHub Namespace authorization send ID and the EventHub name (name of the queue to use in the Namespace) separated by the `
` character. list(string) null
vpn_gateway_logs_metrics_categories Metrics categories to send to destinations. list(string) null no
vpn_gateway_routing_preference Azure routing preference. Tou can choose to route traffic either via Microsoft network or via the ISP network through public Internet string "Microsoft Network" no
vpn_gateway_scale_unit The scale unit for this VPN Gateway number 1 no
vpn_sites VPN Site configuration
list(object({
name = string,
address_cidrs = optional(list(string), [])
links = list(object({
name = string
fqdn = optional(string)
ip_address = optional(string)
bgp = optional(list(object({
asn = string
peering_address = string
})), [])
provider_name = optional(string)
speed_in_mbps = optional(string)
}))
device_model = optional(string)
device_vendor = optional(string)
}))
[] no

Outputs

Name Description
express_route_circuit_id The ID of the ExpressRoute circuit
express_route_circuit_service_key The string needed by the service provider to provision the ExpressRoute circuit
express_route_circuit_service_provider_provisioning_state The ExpressRoute circuit provisioning state from your chosen service provider
express_route_gateway_id ID of the ExpressRoute gateway
express_route_peering_azure_asn ASN (Autonomous System Number) Used by Azure for BGP Peering
firewall_id ID of the firewall
firewall_ip_configuration IP configuration of the created firewall
firewall_management_ip_configuration Management IP configuration of the created firewall
firewall_private_ip_address Private IP address of the firewall
firewall_public_ip Public IP address of the Firewall
virtual_hub_default_route_table_id ID of the default route table in the Virtual Hub
virtual_hub_id ID of the virtual hub
virtual_wan_id ID of the Virtual Wan
vpn_gateway_bgp_settings BGP Settings of the VPN Gateway
vpn_gateway_connections_ids List of name and IDs of VPN gateway connections
vpn_gateway_id ID of the VPN Gateway

Related documentation