since I'm very new in terraform :
I'm trying to deploy a K8s cluster on vsphere
.... terraform.tfvars
vms = {
master_vm1 = { name = "master01", vm_disk_size = 50, vm_vcpu = 2, vm_memory = 2048, vm_ip = "192.168.50.66"},
master_vm2= { name = "master02", vm_disk_size = 50, vm_vcpu = 4, vm_memory = 4096, vm_ip = "192.168.50.77"},
master_vm3 = { name = "master03", vm_disk_size = 50, vm_vcpu = 4, vm_memory = 4096, vm_ip = "192.168.50.88"},
worker_vm1 = { name = "worker101", vm_disk_size = 80, vm_vcpu = 2, vm_memory = 2048, vm_ip = "192.168.50.166"},
worker_vm2= { name = "worker102", vm_disk_size = 80, vm_vcpu = 4, vm_memory = 4096, vm_ip = "192.168.50.177"},
worker_vm3 = { name = "worker103", vm_disk_size = 80, vm_vcpu = 4, vm_memory = 4096, vm_ip = "192.168.50.188"},
main.tf
resource "vsphere_virtual_machine" "vm" {
for_each = var.vms
..
..
name = format("${each.value.name}.${var.vm_domain}")
num_cpus = var.vm_vcpu == false ? var.vm_vcpu : each.value.vm_vcpu
memory = var.vm_memory == false ? var.vm_memory : each.value.vm_memory
firmware = var.vm_firmware
folder = var.vm_folder
cpu_hot_add_enabled = "true"
memory_hot_add_enabled = "true"
disk {
label = var.vm_disk_label
size = each.value.vm_disk_size
thin_provisioned = var.vm_disk_thin
}
Using this approach the deployment works flawless
However, if I try to simply the terraform.tfvars...
nodes = {
master_nodes ={
master_vm1 ={ name = "master101", vm_ip = "192.168.50.66"}
master_vm2 ={ name = "master102", vm_ip = "192.168.50.77"}
master_vm3 ={ name = "master103", vm_ip = "192.168.50.88"}
}
worker_nodes ={
worker_vm1 ={ name = "worker101", vm_ip = "192.168.50.166"}
worker_vm2 ={ name = "worker102", vm_ip = "192.168.50.177"}
worker_vm3 ={ name = "worker103", vm_ip = "192.168.50.188"}
}
}
I failed to understand how to iterate over nodes ....
You have to flatten your nodes
variable, e.g.:
locals {
nodes_flat = merge(flatten([
for node_key, node_values in var.nodes: {
for sub_node_key, node_details in node_values:
"${node_key}-${sub_node_key}" => {
"node_key" = node_key
"sub_node_key" = sub_node_key
"name" = node_details.name
"vm_ip" = node_details.vm_ip
}
}
])...) # do NOT remove the dots
}
then
resource "vsphere_virtual_machine" "vm" {
for_each = local.nodes_flat
..
..
name = format("${each.value.name}.${var.vm_domain}")
#num_cpus = var.vm_vcpu == false ? var.vm_vcpu : each.value.vm_vcpu # # your `nodes` does not contain vm_vcpu, so don't know what you want to do here.
#memory = var.vm_memory == false ? var.vm_memory : each.value.vm_memory # your `nodes` does not contain vm_memory, so don't know what you want to do here.
firmware = var.vm_firmware
folder = var.vm_folder
cpu_hot_add_enabled = "true"
memory_hot_add_enabled = "true"
disk {
label = var.vm_disk_label
#size = each.value.vm_disk_size # your `nodes` does not contain vm_disk_size, so don't know what you want to do here.
thin_provisioned = var.vm_disk_thin
}
}
That's should give you idea. You are not defining vm_disk_size
in nodes
nor even use vm_ip
that you actually have (same for vm_vcpu
and vm_memory
). But regardless, flattening is the way to solve your problem.