3

we are trying to modify our Terraform infrastructure which we have not built ourselves. The current code does support multiple disks but only one NIC. We tried to modify the NIC part accordingly but failed. Unfortunately we did not save the code we tried or the error messages. I hope someone can tell me what these changes have to be.

This is what we have:

the relevant code snippets

module "tf_file_1_module" {
[...]
vm_ipnet = "1.2.3."
vm_ipstart = "4"
network = "staging"
[...]
}

shall be changed to

module "tf_file_1_module" {
[...]
vm_ipnet = ["5.6.7", "1.2.3"]
vm_ipstart = ["8", "10"]
network = ["foo-network", "bar-network"]
[...]
}

For the main disk we have no explicit configuration in the module. Additional disks are configured with the optional parameters

thin_provisioned       = ["true", "true"]
data_disk_size_gb      = ["100", "5"]

Those are handled by this code:

  dynamic "disk" {
     for_each = var.data_disk_size_gb
     content {
       label            = "disk${disk.key + 1}"
       size             = var.data_disk_size_gb[disk.key]
       unit_number      = disk.key + 1
       thin_provisioned = var.thin_provisioned != null ? var.thin_provisioned[disk.key] : true
       eagerly_scrub    = var.eagerly_scrub != null ? var.eagerly_scrub[disk.key] : false
     }
   }

That is what we tried to reproduce for the NICs.

the (more or less) complete code

We have the following structure defined in our Terraform workflow:

├── config
│   ├── backend.conf
│   └── backend.tfvars
├── tf_file_1.tf

Inside the .tf files we have this definition:

module "tf_file_1_module" {
source = "git@local.repo.server.git?ref=master"
datacenter = "DC"
cluster = "Linux-Cluster"
network = "staging"
datastore_cluster = "Netapp"
vm_template = "packer-template"
vm_setname = "tf_file_1"
vm_setcount = 1
vm_folder = "Linuxhosts/staging"
vm_cpu = 2
cpu_hot_add_enabled = "true"
cpu_hot_remove_enabled = "true"
vm_memory = 4096
memory_hot_add_enabled = "true"
vm_domain = "my.fancy.domain"
vm_ipnet = "1.2.3."
vm_ipstart = "4"
logging_enabled = "true"
anti_affinity = "false"
}

The network is mapped internally to the name within the vCenter so we don't have to type out the long network name that no one can memorize.

So each file uses its own module which is sourced from the Git repository and then modified to the needs. The structure looks like this:

.
├── main.tf
├── output.tf
├── provider.tf
├── README.md
├── variables.tf
└── versions.tf

Inside the module's main.tf there are some definitions, among them the one for the network:

data "vsphere_network" "network" {
  name = "/${var.datacenter}/network/${var.network_map[var.network]}"
  datacenter_id = data.vsphere_datacenter.dc.id
}
(→ Here you can also see the mapping for the network name)
 
resource "vsphere_virtual_machine" "vm" {
  count = var.vm_setcount
  name = "${var.vm_setname}${format("%02d", count.index + 1)}${var.append_fqdn == true ? ".my.fancy.domain" : ""}"
  resource_pool_id = data.vsphere_compute_cluster.cluster.resource_pool_id
  datastore_cluster_id = data.vsphere_datastore_cluster.datastore_cluster.id
  annotation = "Deployed via Terraform"
  num_cpus = var.vm_cpu
  cpu_hot_add_enabled = var.cpu_hot_add_enabled
  cpu_hot_remove_enabled = var.cpu_hot_remove_enabled
  memory = var.vm_memory
  memory_hot_add_enabled = var.memory_hot_add_enabled
  folder = var.vm_folder
  guest_id = data.vsphere_virtual_machine.small.guest_id
  scsi_type = data.vsphere_virtual_machine.small.scsi_type
  enable_logging = var.logging_enabled
 
  network_interface {
    network_id = data.vsphere_network.network.id
    adapter_type = data.vsphere_virtual_machine.small.network_interface_types[0]
  }
 
  clone {
    template_uuid = data.vsphere_virtual_machine.small.id
    customize {
      linux_options {
        host_name = "${var.vm_setname}${format("%02d", count.index + 1)}"
        domain = var.vm_domain
      }
 
      network_interface {
        ipv4_address = "${var.vm_ipnet}.${count.index + var.vm_ipstart}"
        ipv4_netmask = 24
      }
 
      ipv4_gateway = "${var.vm_ipnet}.1"
      dns_server_list = ["8.8.8.8"]
      dns_suffix_list = ["my.fancy.domain"]
    }
  }
}

The important variables are defined as follows:

variable "network" {
  description = "Network in which the VM will be created."
  type        = string
}
 
variable "vm_ipnet" {
  description = "Host VM IP address network part prefix."
  type        = string
}
 
variable "vm_ipstart" {
  description = "VM host part IP address configuration/start address. Will automatially increase when more than one vm are to be created."
  type        = string
}
Hauke Laging
  • 5,157
  • 2
  • 23
  • 40

0 Answers0