I am trying to associate existing Application Security Group to newly created Virtual Machine - Network Interfaces using the output.tf.
I have infra-asg, app-asg, service-asg and db-asg in the existing pluto-infra resource group. Now I want to associate asg to nics as below
infra-asg & app-asg to pluto-app-1-nic and pluto-app-2-nic
infra-asg & service-asg to pluto-service-1-nic and pluto-service-2-nic
infra-asg & db-asg to pluto-db-1-1-nic, pluto-db-1-2-nic, pluto-db-2-1-nic & pluto-db-2-2-nic
Terraform Module Package structure as below
main.tf
module "virtualmachine" {
source = "./virtualmachine"
existing_resource_group = var.existing_resource_group
virtual_machines = var.virtual_machines
vm_prefix = var.vm_prefix
}
module "associate-asg" {
source = "./application-security-group"
}
variables.tf
variable "resource_group_location" {
type = string
default = "eastus"
}
variable "vm_prefix" {
type = string
default = "pluto"
}
variable "virtual_machines" {
}
variable "existing_resource_group" {
type = string
}
variable.tfvars
existing_resource_group = "pluto"
existing_infra_rg = "pluto-infra"
virtual_machines = {
nodes = {
app1_node1 = {
"vm_name" = "app"
"vm_num" = "1"
networks = {
nic1 = {
"nic_name" = "app-1"
"subnet" = "/subscriptions/****/resourceGroups/pluto/providers/Microsoft.Network/virtualNetworks/pluto-vnet/subnets/app-subnet"
},
}
},
app1_node2 = {
"vm_name" = "app"
"vm_num" = "2"
networks = {
nic1 = {
"nic_name" = "app-2"
"subnet" = "/subscriptions/****/resourceGroups/pluto/providers/Microsoft.Network/virtualNetworks/pluto-vnet/subnets/app-subnet"
},
}
},
service1_node1 = {
"vm_name" = "service"
"vm_num" = "1"
networks = {
nic1 = {
"nic_name" = "service-1"
"subnet" = "/subscriptions/****/resourceGroups/pluto/providers/Microsoft.Network/virtualNetworks/pluto-vnet/subnets/app-subnet"
},
}
},
service2_node2 = {
"vm_name" = "service"
"vm_num" = "2"
networks = {
nic1 = {
"nic_name" = "service-2"
"subnet" = "/subscriptions/****/resourceGroups/pluto/providers/Microsoft.Network/virtualNetworks/pluto-vnet/subnets/app-subnet"
},
}
},
db1_node1 = {
"vm_name" = "db"
"vm_num" = "1"
networks = {
nic1 = {
"nic_name" = "db-1-1"
"subnet" = "/subscriptions/****/resourceGroups/pluto/providers/Microsoft.Network/virtualNetworks/pluto-vnet/subnets/app-subnet"
},
nic2 = {
"nic_name" = "db-1-2"
"subnet" = "/subscriptions/****/resourceGroups/pluto/providers/Microsoft.Network/virtualNetworks/pluto-vnet/subnets/db-subnet"
}
}
},
db2_node2 = {
"vm_name" = "db"
"vm_num" = "2"
networks = {
nic1 = {
"nic_name" = "db-2-1"
"subnet" = "/subscriptions/****/resourceGroups/pluto/providers/Microsoft.Network/virtualNetworks/pluto-vnet/subnets/app-subnet"
},
nic2 = {
"nic_name" = "db-2-2"
"subnet" = "/subscriptions/****/resourceGroups/pluto/providers/Microsoft.Network/virtualNetworks/pluto-vnet/subnets/db-subnet"
},
}
},
}
}
Virtual Machine module details
main.tf
data "azurerm_resource_group" "rg" {
name = var.existing_resource_group
}
resource "azurerm_network_interface" "nic" {
for_each = {
for vm in flatten([
for vm_name, vm in var.virtual_machines.nodes : [
for nic_name, nic in vm.networks : {
vm_number = vm.vm_num,
vm_name = vm_name,
nic_name = nic_name,
subnet_value = nic.subnet
nic_name_value = nic.nic_name
}
]
]
) : "${vm.vm_name}-${vm.nic_name}" => vm
}
name = "${var.vm_prefix}-${each.value.nic_name_value}-nic"
location = "eastus"
resource_group_name = var.existing_resource_group
ip_configuration {
name = "${var.vm_prefix}-${each.value.nic_name_value}-ipconfig"
subnet_id = each.value.subnet_value
private_ip_address_allocation = "Dynamic"
}
}
resource "azurerm_linux_virtual_machine" "vm" {
depends_on = [azurerm_network_interface.nic]
for_each = var.virtual_machines.nodes
name = "${var.vm_prefix}-${each.value.vm_name}-${each.value.vm_num}"
admin_username = "plutoadmin"
admin_password = "pluto@1234522"
disable_password_authentication = false
location = "eastus"
resource_group_name = var.existing_resource_group
network_interface_ids = [for nic_key, nic in azurerm_network_interface.nic : nic.id if startswith(nic_key, "${each.key}-")]
size = "Standard_B2ms"
os_disk {
name = "${var.vm_prefix}-${each.value.vm_name}-${each.value.vm_num}-OSdisk"
caching = "ReadWrite"
storage_account_type = "Standard_LRS"
}
source_image_reference {
publisher = "RedHat"
offer = "RHEL"
sku = "82gen2"
version = "latest"
}
}
variable.tf
variable "vm_prefix" {
type = string
default = "pluto"
}
variable "virtual_machines" {
}
variable "existing_resource_group" {
type = string
}
output.tf
output "vm_nics_ids" {
value = [for nic_key, nic in azurerm_network_interface.nic : nic.id]
}
Application Security Group module details
data "azurerm_application_security_group" "infra-asg" {
name = "infra-asg"
resource_group_name = "pluto-infra"
}
data "azurerm_application_security_group" "app-asg" {
name = "app-asg"
resource_group_name = "pluto-infra"
}
data "azurerm_application_security_group" "service-asg" {
name = "service-asg"
resource_group_name = "pluto-infra"
}
data "azurerm_application_security_group" "db-asg" {
name = "db-asg"
resource_group_name = "pluto-infra"
}
data "azurerm_network_interface" "app-nic-1" {
name = "pluto-app-1-nic"
resource_group_name = "pluto"
}
resource "azurerm_network_interface_application_security_group_association" "infra-app-asg-1" {
network_interface_id = data.azurerm_network_interface.app-nic-1.id
application_security_group_id = data.azurerm_application_security_group.infra-asg.id
}
resource "azurerm_network_interface_application_security_group_association" "app-asg-1" {
network_interface_id = data.azurerm_network_interface.app-nic-1.id
application_security_group_id = data.azurerm_application_security_group.app-asg.id
}
# App Node 2
data "azurerm_network_interface" "app-nic-2" {
name = "pluto-app-2-nic"
resource_group_name = "pluto"
}
resource "azurerm_network_interface_application_security_group_association" "infra-app-asg-2" {
network_interface_id = data.azurerm_network_interface.app-nic-2.id
application_security_group_id = data.azurerm_application_security_group.infra-asg.id
}
resource "azurerm_network_interface_application_security_group_association" "app-asg-2" {
network_interface_id = data.azurerm_network_interface.app-nic-2.id
application_security_group_id = data.azurerm_application_security_group.app-asg.id
}
# service Node 1
data "azurerm_network_interface" "service-nic-1" {
name = "pluto-service-1-nic"
resource_group_name = "pluto"
}
resource "azurerm_network_interface_application_security_group_association" "infra-service-asg-1" {
network_interface_id = data.azurerm_network_interface.service-nic-1.id
application_security_group_id = data.azurerm_application_security_group.infra-asg.id
}
resource "azurerm_network_interface_application_security_group_association" "service-asg-1" {
network_interface_id = data.azurerm_network_interface.service-nic-1.id
application_security_group_id = data.azurerm_application_security_group.service-asg.id
}
# service Node 2
data "azurerm_network_interface" "service-nic-2" {
name = "pluto-service-2-nic"
resource_group_name = "pluto"
}
resource "azurerm_network_interface_application_security_group_association" "infra-service-asg-2" {
network_interface_id = data.azurerm_network_interface.service-nic-2.id
application_security_group_id = data.azurerm_application_security_group.infra-asg.id
}
resource "azurerm_network_interface_application_security_group_association" "service-asg-2" {
network_interface_id = data.azurerm_network_interface.service-nic-2.id
application_security_group_id = data.azurerm_application_security_group.service-asg.id
}
# DB -1-1
data "azurerm_network_interface" "db-nic-1-1" {
name = "pluto-db-1-1-nic"
resource_group_name = "pluto"
}
resource "azurerm_network_interface_application_security_group_association" "infra-db-asg-1-1" {
network_interface_id = data.azurerm_network_interface.db-nic-1-1.id
application_security_group_id = data.azurerm_application_security_group.infra-asg.id
}
resource "azurerm_network_interface_application_security_group_association" "db-asg-1-1" {
network_interface_id = data.azurerm_network_interface.db-nic-1-1.id
application_security_group_id = data.azurerm_application_security_group.db-asg.id
}
# DB -1-2
data "azurerm_network_interface" "db-nic-1-2" {
name = "pluto-db-1-2-nic"
resource_group_name = "pluto"
}
resource "azurerm_network_interface_application_security_group_association" "infra-db-asg-1-2" {
network_interface_id = data.azurerm_network_interface.db-nic-1-2.id
application_security_group_id = data.azurerm_application_security_group.infra-asg.id
}
resource "azurerm_network_interface_application_security_group_association" "db-asg-1-2" {
network_interface_id = data.azurerm_network_interface.db-nic-1-2.id
application_security_group_id = data.azurerm_application_security_group.db-asg.id
}
# DB -2-1
data "azurerm_network_interface" "db-nic-2-1" {
name = "pluto-db-2-1-nic"
resource_group_name = "pluto"
}
resource "azurerm_network_interface_application_security_group_association" "infra-db-asg-2-1" {
network_interface_id = data.azurerm_network_interface.db-nic-2-1.id
application_security_group_id = data.azurerm_application_security_group.db-asg.id
}
resource "azurerm_network_interface_application_security_group_association" "db-asg-2-1" {
network_interface_id = data.azurerm_network_interface.db-nic-2-1.id
application_security_group_id = data.azurerm_application_security_group.infra-asg.id
}
# DB -2-2
data "azurerm_network_interface" "db-nic-2-2" {
name = "pluto-db-2-2-nic"
resource_group_name = "pluto"
}
resource "azurerm_network_interface_application_security_group_association" "infra-db-asg-2-2" {
network_interface_id = data.azurerm_network_interface.db-nic-2-2.id
application_security_group_id = data.azurerm_application_security_group.infra-asg.id
}
resource "azurerm_network_interface_application_security_group_association" "db-asg-2-2" {
network_interface_id = data.azurerm_network_interface.db-nic-2-2.id
application_security_group_id = data.azurerm_application_security_group.db-asg.id
}
could you guide me how to pass the nic ids from virtual machine module to Application security group module and loop them ?
You can use outputs to pass data from one module to another. You are already on the right path as you have an output block that has the map of your nic ID's. To retrieve, on your root main.tf (the one that references both your vm and asg module) pass them is by accessing the attributes as you would normally do on any other resource block with the keyword "module". Then only thing missing is a variable on your asg module that allows you to pass in the collection
main.tf
module "virtualmachine" {
source = "./virtualmachine"
existing_resource_group =
var.existing_resource_group
virtual_machines = var.virtual_machines
vm_prefix = var.vm_prefix
}
module "associate-asg" {
source = "./application-security-group"
nic_ids = module.virtualmachine.vm_nics_ids //passing in via the variable declared on asg module
}
variable.tf (on your asg module)
variable "nic_ids" {
type = list(string)
}
main.tf (asg module)
resource "azurerm_network_interface_application_security_group_association" "infra-db-asg-2-2" {
count = length(var.nic_ids)
network_interface_id =
var.nic_ids[count.index]
application_security_group_id =
data.azurerm_application_security_group.infra-asg.id
}
You already have your output done on your vm module so this will work. Dont forget to do a terraform init after the changes so your root will get the latest changes from modules. Hope this helps