azureのsubnetをimportして使いまわし複数ホストをterraformでたてる

タイトル通りの内容のtfファイルや参考サイトなどを備忘録しておきます。
[以前やってみたとき](https://qiita.com/smallpalace/items/8a2d6046f1892c5797c0)は複数ではなかったのでした。

#### tfファイル

[Azure上の冗長を意味するのは可用性セットの障害ドメインと更新ドメイン](http://azure.sios.jp/archives/4133)らしいのでサブネット分ける意味がどんだけあるのかはアレですがなんとなく分けた感じです。
countで2台たてており、formatで%02dてのは整数2桁って感じの意味合いだと思いますたぶん。なので以下のvarsとtfだとmynode01、mynode02みたいなホスト名がついて上がってきます。

```config:terraform.tf
variable "default_user" {}
variable "default_password" {}
variable "resouce_group_name" {}
variable "location" {}
variable "azurerm_virtual_network_name" {}
variable "azurerm_virtual_network_address_space" {}
variable "azurerm_subnet_name" {}
variable "azurerm_subnet_address_prefix" {}
variable "virtual_machine_name_test" {}
variable "storage_account" {}
variable "account_tier" {}
variable "account_replication_type" {}
variable "vm_size" {}
variable "storage_image_reference_publisher" {}
variable "storage_image_reference_offer" {}
variable "storage_image_reference_sku" {}
variable "storage_image_reference_version" {}
provider "azurerm" {
}
resource "azurerm_resource_group" "test" {
  name = "${var.resouce_group_name}" 
  location = "${var.location}" 
}
resource "azurerm_virtual_network" "test" {
  name = "${var.azurerm_virtual_network_name}" 
  address_space = ["${var.azurerm_virtual_network_address_space}"]
  location = "${azurerm_resource_group.test.location}" 
  resource_group_name = "${azurerm_resource_group.test.name}" 
}
resource "azurerm_subnet" "test" {
  count = 2
  name = "${element(split(",",var.azurerm_subnet_name), count.index%length(split(",", var.azurerm_subnet_name)))}" 
  resource_group_name = "${azurerm_resource_group.test.name}" 
  virtual_network_name = "${azurerm_virtual_network.test.name}" 
  address_prefix = "${element(split(",",var.azurerm_subnet_address_prefix), count.index%length(split(",", var.azurerm_subnet_address_prefix)))}" 
}
resource "azurerm_public_ip" "test" {
  count = 2
  name = "${format("${var.virtual_machine_name_test}%02d", count.index + 1)}-pip" 
  location = "${azurerm_resource_group.test.location}" 
  resource_group_name = "${azurerm_resource_group.test.name}" 
  public_ip_address_allocation = "static" 
  domain_name_label = "${format("${var.virtual_machine_name_test}%02d", count.index + 1)}-pip" 
  tags {
      environment = "test" 
    }
}
resource "azurerm_network_interface" "test" {
  count = 2
  name = "${format("${var.virtual_machine_name_test}%02d", count.index + 1)}-nic1" 
  location = "${azurerm_resource_group.test.location}" 
  resource_group_name = "${azurerm_resource_group.test.name}" 
  ip_configuration {
      name = "${format("${var.virtual_machine_name_test}%02d", count.index + 1)}-ip" 
      subnet_id = "${element(azurerm_subnet.test.*.id, count.index)}" 
      private_ip_address_allocation = "dynamic" 
      public_ip_address_id = "${element(azurerm_public_ip.test.*.id, count.index)}" 
  }
}
resource "azurerm_storage_account" "test" {
    name = "${var.storage_account}" 
    resource_group_name = "${azurerm_resource_group.test.name}" 
    location = "${azurerm_resource_group.test.location}" 
    account_tier = "${var.account_tier}" 
    account_replication_type = "${var.account_replication_type}" 
    tags {
        environment = "staging" 
    }
}
resource "azurerm_storage_container" "test" {
    count = 2
    name = "${format("${var.virtual_machine_name_test}%02d", count.index + 1)}-vhds" 
    resource_group_name = "${azurerm_resource_group.test.name}" 
    storage_account_name = "${azurerm_storage_account.test.name}" 
    container_access_type = "private" 
}
resource "azurerm_virtual_machine" "test" {
  count                 = 2
  name                  = "${format("${var.virtual_machine_name_test}%02d", count.index + 1)}" 
  location              = "${azurerm_resource_group.test.location}" 
  resource_group_name   = "${azurerm_resource_group.test.name}" 
  network_interface_ids = ["${element(azurerm_network_interface.test.*.id, count.index)}"]
  vm_size               = "${var.vm_size}" 
  storage_image_reference {
    publisher = "${var.storage_image_reference_publisher}" 
    offer = "${var.storage_image_reference_offer}" 
    sku = "${var.storage_image_reference_sku}" 
    version = "${var.storage_image_reference_version}" 
  }
  storage_os_disk {
    name              = "${var.virtual_machine_name_test}-osdisk1" 
    vhd_uri = "${azurerm_storage_account.test.primary_blob_endpoint}${element(azurerm_storage_container.test.*.name, count.index)}/myosdisk1.vhd" 
    caching           = "ReadWrite" 
    create_option     = "FromImage" 
    os_type           = "linux" 
  }
  os_profile {
    computer_name  = "${format("${var.virtual_machine_name_test}%02d", count.index + 1)}" 
    admin_username = "${var.default_user}" 
    admin_password = "${var.default_password}" 
  }
  os_profile_linux_config {
    disable_password_authentication = false
  }
  tags {
    environment = "test" 
  }
}
```

#### varsファイル参考

```config:terraform.tfvars.sample
default_user = "ssh-username"
default_password = "ssh-password"
resouce_group_name = "myresource-groupname"
location = "Japan West"
azurerm_virtual_network_name = "my01VNET"
azurerm_virtual_network_address_space = "10.0.0.0/16"
azurerm_subnet_name = "myPub01Subnet,myPub02Subnet"
azurerm_subnet_address_prefix = "10.0.0.0/23,10.0.2.0/23"
virtual_machine_name_test = "mynode"
storage_account = "mystorageaccountname"
account_tier = "Standard"
account_replication_type = "LRS"
vm_size = "Standard_DS1_v2"
storage_image_reference_publisher = "Canonical"
storage_image_reference_offer = "UbuntuServer"
storage_image_reference_sku = "16.04-LTS"
storage_image_reference_version = "latest"

```

#### importサンプル

importしないとなんか消してから作り直そうとしよって既存subnet上にVMあるからsubnet消せないエラーが出て使いまわせなくてガッカリしますがimportするとtfstateに既存リソースの値が書かれて既存のsubnetなどをアッサリつかいまわせるようになります。複数の場合は添え字でいけますしtfファイルで取り出すときには[formatとかcountとかelementとかsplitとか使える](https://www.terraform.io/docs/configuration/interpolation.html)ということらしいのでそんな感じで工夫すると取り出せます。
importのしかたはググってもAWSの例ばっかりですがリソース毎の公式マニュアルのしたのほうにimportコマンドの例が書いてあったりします。
https://www.terraform.io/docs/providers/azurerm/r/subnet.html

```
$ vi main.tf
provider "azurerm" {
}
resource "azurerm_virtual_network" "test" {
}
resource "azurerm_subnet" "test" {
}

$ terraform import azurerm_virtual_network.test /subscriptions/<subscription_id>/resourceGroups/<myresource-groupname>/providers/Microsoft.Network/virtualNetworks/my01VNET
$ terraform import azurerm_subnet.test[0] /subscriptions/<subscription_id>/resourceGroups/<myresource-groupname>/providers/Microsoft.Network/virtualNetworks/my01VNET/subnets/myPub01Subnet
$ terraform import azurerm_subnet.test[1] /subscriptions/<subscription_id>/resourceGroups/<myresource-groupname>/providers/Microsoft.Network/virtualNetworks/my01VNET/subnets/myPub02Subnet
$ mv main.tf{,bkup} 
$ terraform plan
$ terraform apply
$ terraform show
```

NSGを手でNICにくっつける感じなのをどうにかしたいといえばしたい~~けどマニュアルみてもよくわかんなかったです。
どなたか知ってたらおしえてください。~~　コメント欄で教えていただいたので次の機会に善処します。

#### 参考

[Terraformで複数台のEC2インスタンスを構築する場合のTIPS ｜ Developers.IO](https://dev.classmethod.jp/cloud/tips-for-creating-multiple-aws_instance-resources/)
[NSGを作成しようとしているときにリクエストの例外を解析できない・Issue＃788・Azure / azure-sdk-for-python](https://github.com/Azure/azure-sdk-for-python/issues/788)
[Azure Resource Manager: azure_virtual_network - Terraform by HashiCorp](https://www.terraform.io/docs/providers/azurerm/r/virtual_network.html)
[Terraformで複数台のAzure Virtual Machineを構築する方法 - Change the World!](http://changesworlds.com/2016/09/how-to-build-a-plurality-of-azure-virtual-machine-in-the-terraform/)
[azure-examples/computes.tf at master · changeworld/azure-examples](https://github.com/changeworld/azure-examples/blob/master/terraform/computes/computes.tf)
[Interpolation Syntax - Terraform by HashiCorp](https://www.terraform.io/docs/configuration/interpolation.html)
[Terraform職人入門: 日々の運用で学んだ知見を淡々とまとめる - Qiita](https://qiita.com/minamijoyo/items/1f57c62bed781ab8f4d7)