如何在Terraform中使用条件属性

时间:2019-05-04 17:53:19

标签: terraform terraform-provider-azure

我写了一个脚本来使用terraform创建Azure VM。脚本很灵活,可以将OS作为输入。现在,azurerm_virtual_machine资源块中有一些特定于OS的属性。 如何使用诸如Windows使用os_profile_windows_config{}或OS是Linux使用os_profile_linux_config{}之类的条件。

正常条件语句不起作用,因为此属性没有直接使用=取任何值。

resource "azurerm_virtual_machine" "vmdeploy" {
  count = "${var.count_of_VMs}"
  name = "${var.vm_name}-${count.index}"
  resource_group_name = "${azurerm_resource_group.deployrg.name}"
  availability_set_id = "${azurerm_availability_set.avset.id}"
  location = "${azurerm_resource_group.deployrg.location}"
  network_interface_ids = ["${element(azurerm_network_interface.nic.*.id, count.index)}"]
  vm_size = "Standard_DS1_v2"

  storage_image_reference{
    publisher = "${var.OS_Image_Publisher}"
    offer = "${var.OS_Image_Offer}"
    sku = "${var.OS_Image_Sku}"
    version = "latest"
  }
  storage_os_disk{
    name = "${var.vm_name}-${count.index}-osdisk"
    caching = "ReadWrite"
    managed_disk_type = "Standard_LRS"
    create_option = "FromImage"
  }

  storage_data_disk {
    name = "${element(azurerm_managed_disk.mdisk.*.name, count.index)}"
    managed_disk_id = "${element(azurerm_managed_disk.mdisk.*.id, count.index)}"
    create_option = "Attach"
    lun = 1
    disk_size_gb = "${element(azurerm_managed_disk.mdisk.*.disk_size_gb, count.index)}"
  }

  os_profile {
    computer_name = "${var.vm_name}-${count.index}"
    admin_username = "XXXXXXXXXXXX"
    admin_password = "XXXXXXXXXXXX"
  }

  os_profile_windows_config {

  }
}

我试图在这里找到一种使用条件的方法,以根据作为输入提供的OS版本使用相应的config属性。

1 个答案:

答案 0 :(得分:0)

在terraform-0.12之前这是不可能的。使用dynamic blocks版本0.12可以做到这一点。

provider "azurerm" {
  version = "~>2.19.0"
  features {}
}

variable "image" {
  type = map
  default = {
    publisher = "Canonical"
    offer     = "UbuntuServer"
    sku       = "16.04-LTS"
    version   = "latest"
  }
}

locals {
  _is_microsoft = substr(lookup(var.image, "publisher", "value_not_declared"), 0, 9) == "Microsoft" ? true : false
  is_linux      = ! local._is_microsoft ? { empty = true } : {}
  is_windows    = local._is_microsoft ? { empty = true } : {}
}

resource "azurerm_resource_group" "rg" {
  name     = "rg"
  location = "east us"
}

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

resource "azurerm_subnet" "subnet" {
  name                 = "subnet"
  resource_group_name  = azurerm_resource_group.rg.name
  virtual_network_name = azurerm_virtual_network.rg.name
  address_prefixes     = ["10.10.10.0/24"]
}

resource "azurerm_network_interface" "rg" {
  name                = "nic"
  location            = azurerm_resource_group.rg.location
  resource_group_name = azurerm_resource_group.rg.name

  ip_configuration {
    name                          = "ipconfig"
    subnet_id                     = azurerm_subnet.subnet.id
    private_ip_address_allocation = "Dynamic"
  }
}

resource "azurerm_virtual_machine" "rg" {
  name                  = "-vm"
  location              = azurerm_resource_group.rg.location
  resource_group_name   = azurerm_resource_group.rg.name
  network_interface_ids = [azurerm_network_interface.rg.id]
  vm_size               = "Standard_D2_v3"

  storage_image_reference {
    publisher = lookup(var.image, "publisher")
    offer     = lookup(var.image, "offer")
    sku       = lookup(var.image, "sku")
    version   = lookup(var.image, "version")
  }
  storage_os_disk {
    name              = "disk1"
    caching           = "ReadWrite"
    create_option     = "FromImage"
    managed_disk_type = "Standard_LRS"
  }
  os_profile {
    computer_name  = "computer"
    admin_username = "localadmin"
    admin_password = "donotuserthispassword123!"
  }

  dynamic "os_profile_linux_config" {
    for_each = local.is_linux

    content {
      disable_password_authentication = false
    }
  }

  dynamic "os_profile_windows_config" {
    for_each = local.is_windows

    content {
      provision_vm_agent = true
    }
  }
}

请注意,天青石团队认为这是not a good 想法,并将资源分为两种不同的类型。采用 azurerm_linux_virtual_machine或azurerm_windows_virtual_machine。 使用单个接口构建模块,然后使用计数选择 构建Windows或Linux的资源。