Exastro IT AutomationのTerraform Driverを使ってみた(ver1.9)

# はじめに
本記事では、ITAのTerraform Driver焦点を当ててその使い方について説明していきたいと思います。

**関連リンク**

* [Exastroコミュニティページ](https://exastro-suite.github.io/docs/index_ja.html)
* [Exastro IT Automation](https://exastro-suite.github.io/it-automation-docs/index_ja.html)
* [Exastro IT Automationをインストールしてみた（v1.9.0）](https://qiita.com/y-masaya3210/items/043395c6a3ca0545014b)
* [【随時更新】Exastroの参考になる記事をまとめてみた](https://qiita.com/ooif/items/79952398fb03ca3ec7fd)

## Exastro IT Automationとは
ITAは、システム設定をIaC(Infrastructure as Code)化して一元管理するためのオープンソースフレームワークです。
機器情報、設定値、作業履歴などシステム構成に関する情報を管理することが可能で、その値をExcelデータとして出力することができます。また、各機器のシステム構築や、運用設定などをワークフローとして管理、または実行する機能を備え、様々なPF構築ツールと連携が可能になっています。

今回はITAを体感できるクイックスタートとして、ITAの標準的な連携機能であるTerraform-Driverを使って、パブリッククラウドのプロビジョニングを行います。また、ポリシーを定義しそれに沿ったVMが作成されているかどうかを確認します。

## Terraformとは
TerraformとはHashiCorp社が提供するオープンソースのツールで、クラウド上のリソースを定義ファイルに沿って生成、破棄、操作してインフラの構築や設定のコード化を実行することができますインフラの構成を宣言的に定義することが特徴で、構築手順をイチから書く必要がなく構成定義のみに集中することができます。

ExastroにおけるTerraform Driverは、ITAシステムのオプションとして機能し、ITAシステムで登録したTerraform EnterpriseまたはTerraform Cloudに対し、Organization の作成、Workspaceの作成、Policyの定義や作業の実行及び作業ログの取得が可能です。



今回はITAにTerraform Enterpriseを登録し作業を行います。


# 作業環境

* Exastro IT Automation ver 1.9.0
* CentOS Linux 7.8(ITAサーバ用)
* Terraform Enterprise
* AWS
* Azure
* Windows 10 (クライアント)
* Google Chrome (Win10側)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1333336/3a81dcf4-5912-c9e0-033f-3639c310fdb7.png)


# 作業概要
今回はTerraform Driverを使って、定義したポリシーに沿ったVMを各パブリッククラウド(AWS,Azure)に作成します。

具体的な手順は以下の通りです。

**【仕込み編】**

1. インターフェース情報の登録
1. Organizationの登録と連携
1. Workspaceの登録と連携
1. 作業パターン(Movement)の登録
1. Module素材の登録
1. Policyの登録
1. policySetの登録
1. PolicySetにPolicyを紐付け
1. PolicySetにWorkspaceを紐付け
1. MovementにModule素材を指定

**【実行編】**

1. オペレーションの登録
1. 変数値の設定
1. Planを確認
1. 作業実行
1. 実行状態確認
1. 変数値を変更して再度実行

上記の【仕込み編】までを一度登録・連携すると、以降の操作は【実行編】を繰り返し行うことで、対象の再設定・再登録を行うことができます。(自動化)


# 仕込み編

## 1.インターフェース情報の登録
Terraform DriverとTerraform Enterpriseを連携させます。

まずはじめに、ブラウザからTerraform Enterpriseにログインし、
[User Settings]→[Tokens]→[Create an API token]の順でクリックして得られる
ユーザトークンを発行しておく必要があります。
発行後、メモしておきます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/c6520b9b-b624-9ae5-d1d3-413000410640.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/525ff4da-28be-c82b-8827-4138a98698ba.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/54848800-5afc-febe-a7b2-19af151673d9.png)





再度ITA画面に戻り、メインメニュー(DASHBOARD)から「Terraform」メニューグループ >> 「インターフェース情報」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/e67fe56c-1b37-d1d7-5bbb-fb42d1c3c9cc.png)

画面が遷移するので、「一覧」欄から「更新」ボタンをクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/77c1f997-40b9-4d8a-83a0-1bf6193e0591.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/0ba88cf7-4d2b-60e3-5474-f8fbaf44fd62.png)

下表を参考に記入し、「更新」ボタンをクリックして登録内容を更新します。

|Hostname|User Token|
|-|-|
|(Terraform Enterpriseのドメイン名)|(発行したユーザトークン)|

## 2.Organizationの登録と連携
Terraform EnterpriseのOrganizationを登録します。

左メニューグループから「Organizations管理」を選択します
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/86eb27b1-faee-d68c-cc80-80ab6bb16aa5.png)

画面が遷移するので、登録欄から登録開始を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/e0e9597c-bd71-9020-d111-e88175d628cc.png)

下表を参考に記入し、「登録」ボタンをクリックして登録します。

|Organization Name|Email address|
|-|-|
|ITAlearn_org|(Terraformユーザのメールアドレス)|

また、「フィルタ」ボタンを押下することで先程登録したレコードを確認できます。
登録したレコードの「連携状態チェック」を押下すると、「連携状態チェック」の下にOrganizationの連携状態が表示されます。
Terraform Enterpriseにログインし、Organizationが作成されているか確認します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/625cdb83-d533-e08c-812c-da105b784603.png)




## 3.Workspaceの登録と連携
Terraform EnterpriseのWorkspaceを登録します。

左メニューグループから「Workspaces管理」を選択します
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/af7b7663-52aa-3888-cdf0-63a1040c8af0.png)


画面が遷移するので、登録欄から登録開始を選択します。
ここではAWS実行用とAzure実行用の2つのWorkspaceを登録します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/7e310e43-19c3-bc59-be84-586589ceef7b.png)

下表を参考に記入し、「登録」ボタンをクリックして登録します

|Organization|Workspace Name|
|-|-|
|ITAlearn_org|ITA-demo-AWS|
|ITAlearn_org|ITA-demo-Azure|


また、「フィルタ」ボタンを押下することで先程登録したレコードを確認できます。
登録したレコードの「連携状態チェック」を押下すると、「連携状態チェック」の下にOrganizationの連携状態が表示されます。
Terraform Enterpriseにログインして、Workspaceが作成されているか確認します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/1f0791ef-3453-f83c-820f-79043202eb83.png)



## 4.作業パターン(Movement)の登録
Module素材に関連付けるMovementの設定を行います。

左メニューグループから「Movement一覧」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/be6d55a3-920d-b0c2-3683-30ea1dbd6104.png)


画面が遷移するので、登録欄から登録開始を選択します。
ここではAWS実行用とAzure実行用の2つのMovementを登録します。
また、先程登録したWorkspaceと関連付けます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/3fb5a205-ed78-eef2-8f82-d1fa907b9d0e.png)

下表を参考に記入し、「登録」ボタンをクリックして登録します。

|Movement名|Organization：Workspace|
|-|-|
|VM作成(AWS)|ITAlearn_org:ITA-demo-AWS|
|VM作成(Azure)|ITAlearn_org:ITA-demo-Azure|


## 5.Module素材の登録
実行するModule素材をITAに登録します。

### Module素材
今回ITAに登録するModule素材は以下の4つです。
文字コードは”UTF-8”、改行コードは”LF”、拡張子は”tf”で作成してください。


***AWSインスタンス作成用***

aws_create_instance_variables.tf 
AWSインスタンス作成用の変数定義ファイルです。
変数には具体値変数が代入されます

```tf:aws_create_instance_variables.tf
variable "access_key" {}
variable "secret_key" {}
variable "region" {}
variable "ami" {}
variable "key_name" {}
variable "security_group" {}
variable "tags_name" {}
variable "hello_tf_instance_count" {
    default = 2
}
variable "hello_tf_instance_type" {
    default = "t2.micro"
}
```

aws_create_instance.tf
AWSインスタンス作成用のリソース定義ファイルです。
セキュリティグループ、キーペア事前にAWSで作成・用意します。


```tf:aws_create_instance.tf
provider "aws" {
  access_key = var.access_key
  secret_key = var.secret_key
  region = var.region
}

resource "aws_instance" "hello-tf-instance" {
  ami             = var.ami
  key_name        = var.key_name
  security_groups = [var.security_group]
  tags = {
    Name = "${var.tags_name}-${count.index+1}"
  }
  count = var.hello_tf_instance_count
  instance_type = var.hello_tf_instance_type
}
```

***Azureインスタンス作成用***

azure_create_instance_variables.tf
Azureインスタンス作成用の変数定義ファイルです。
変数には具体値変数が代入されます


```tf:azure_create_instance_variables.tf

variable "subscription_id" {}
variable "tenant_id" {}
variable "client_id" {}
variable "client_secret" {}
variable "resource_group_name" {}
variable "security_group" {}
variable "location" {}
variable "Vnet_name" {}
variable "Vnet_address_space" {}
variable "subnet_name" {}
variable "address_prefixes" {}
variable "public_ip_name" {}
variable "allocation_method" {}
variable "domain_name_label" {}
variable "network_interface_name" {}
variable "NIC_name" {}
variable "VM_name" {}
variable "VM_size" {}
variable "publisher" {}
variable "offer" {}
variable "sku" {}
variable "source_image_version" {}
variable "admin_username" {}
variable "ssh_public_key" {}
variable "os_disk_name" {}
variable "caching" {}
variable "storage_account_type" {}
variable "VM_count" {}
```

azure_create_instance.tf　
Azureインスタンス作成用のリソース定義ファイルです。
リソースグループと、そのネットワークセキュリティグループ、仮想ネットワークの作成。
また、作成するVM台数分の仮想マシン本体、ディスク、ネットワークインターフェースの作成を行います。


```tf:azure_create_instance.tf
provider "azurerm" {
  features {}
  subscription_id = var.subscription_id
  client_id       = var.client_id
  client_secret   = var.client_secret
  tenant_id       = var.tenant_id
}

resource "azurerm_resource_group" "hogehoge" {
  name = var.resource_group_name
  location = var.location
}

resource "azurerm_network_security_group" "hogehoge" {
    name =var.security_group
    location = azurerm_resource_group.hogehoge.location
    resource_group_name = azurerm_resource_group.hogehoge.name

    security_rule {
        name                       = "SSH"
        priority                   = 1001
        direction                  = "Inbound"
        access                     = "Allow"
        protocol                   = "Tcp"
        source_port_range          = "*"
        destination_port_range     = "22"
        source_address_prefix      = "*"
        destination_address_prefix = "*"
    }
    security_rule {
        name                       = "HTTP"
        priority                   = 1002
        direction                  = "Inbound"
        access                     = "Allow"
        protocol                   = "Tcp"
        source_port_range          = "*"
        destination_port_range     = "80"
        source_address_prefix      = "*"
        destination_address_prefix = "*"
    }
}

resource "azurerm_virtual_network" "hogehoge" {
  name = var.Vnet_name
  address_space = [var.Vnet_address_space]
  location = azurerm_resource_group.hogehoge.location
  resource_group_name = azurerm_resource_group.hogehoge.name
}

resource "azurerm_subnet" "hogehoge" {
    name                 = var.subnet_name
    resource_group_name  = azurerm_resource_group.hogehoge.name
    virtual_network_name = azurerm_virtual_network.hogehoge.name
    address_prefixes     = [var.address_prefixes]
}

resource "azurerm_public_ip" "hogehoge" {
  count                 = var.VM_count
  name                  = "${var.public_ip_name}-${count.index}"
  location              = azurerm_resource_group.hogehoge.location
  resource_group_name   = azurerm_resource_group.hogehoge.name
  allocation_method     = var.allocation_method
  domain_name_label     = "${var.domain_name_label}-${count.index}"
}

resource "azurerm_network_interface" "hogehoge" {
    count               = var.VM_count
    name                = "${var.network_interface_name}-${count.index}"
    location            = azurerm_resource_group.hogehoge.location
    resource_group_name = azurerm_resource_group.hogehoge.name

    ip_configuration {
        name                          = var.NIC_name
        subnet_id                     = azurerm_subnet.hogehoge.id
        private_ip_address_allocation = var.allocation_method
        public_ip_address_id          = azurerm_public_ip.hogehoge[count.index].id
    }
}

resource "azurerm_network_interface_security_group_association" "hogehoge" {
  count = var.VM_count
  network_interface_id      = azurerm_network_interface.hogehoge[count.index].id
  network_security_group_id = azurerm_network_security_group.hogehoge.id
}

resource "azurerm_linux_virtual_machine" "hogehoge" {
  count                 = var.VM_count
  name                  = "${var.VM_name}-${count.index}"
  resource_group_name   = azurerm_resource_group.hogehoge.name
  location              = azurerm_resource_group.hogehoge.location
  size                  = var.VM_size
  admin_username        = var.admin_username
  network_interface_ids = [azurerm_network_interface.hogehoge[count.index].id]
  
  admin_ssh_key {
  username   = var.admin_username
  public_key = var.ssh_public_key
  }
  
  os_disk {
    name                 = "${var.os_disk_name}-${count.index}"
    caching              = var.caching
    storage_account_type = var.storage_account_type
  }
  
  source_image_reference {
    publisher = var.publisher
    offer     = var.offer
    sku       = var.sku
    version   = var.source_image_version
  }
}
```

### Module素材登録
左メニューグループから「Module素材集」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/129aaa01-8832-482d-9d68-7e4ba63adc7d.png)


画面が遷移するので、登録欄から登録開始を選択します。
登録する4つのModule素材と、それに対応したModule素材名を付けて登録します。
Module素材は「事前アップロード」を押下する必要があります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/7793a8b6-078c-4104-3519-4633ae0eb5f2.png)


下表を参考に記入し、「登録」ボタンをクリックして登録します。

|Module素材名|Module素材|
|-|-|
|aws_create_instance_variables|aws_create_instance_variables.tf|
|aws_create_instance_body|aws_create_instance.tf|
|azure_create_instance_variables|azure_create_instance_variables.tf|
|azure_create_instance_body|azure_create_instance.tf|

## 6.Policyの登録
実行するPolicy素材をITAに登録します。

### Policy素材
今回ITAに登録するPolicy素材は以下の4つです。
文字コードは”UTF-8”、改行コードは”LF”、拡張子は”sentinel”で作成してください。

limit-proposed-monthly-cost.sentinel
月額のコストを制限するポリシーです。
月額コストが$50を上回る場合はApplyを行いません。
また、その月額コストの総見積りが出力されます。
AWS,Azureどちらのクラウドにおいても適用可能です。

```sentinel:limit-proposed-monthly-cost.sentinel
import "tfrun"
import "decimal"

limit = decimal.new(50)

cost_limit_by_workspace = func() {
  if tfrun.cost_estimate else null is null {
    print("no cost estimates available")
    return false
    }
	
  workspace_name = tfrun.workspace.name
	
  proposed_cost = decimal.new(tfrun.cost_estimate.proposed_monthly_cost)
	
  if proposed_cost.less_than(limit) {
    print("Proposed monthly cost", proposed_cost.string,
      "of workspace", workspace_name,
      "is under the limit: $", limit)
    return true
  }
	
  if proposed_cost.greater_than(limit) {
    print("Proposed monthly cost", proposed_cost.string,
       "of workspace", workspace_name,
       "is over the limit: $", limit)
    return false
    }
}

cost_validated = cost_limit_by_workspace()

main = rule {
  cost_validated
}
```

### Policy素材登録
左メニューグループから「Policies管理」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/a9ff26db-01d6-5869-fdae-b979f00d409c.png)



画面が遷移するので、登録欄から登録開始を選択します。
登録する4つのModule素材と、それに対応したModule素材名を付けて登録します。
Module素材は「事前アップロード」を押下する必要があります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/80ec5a63-f33b-86f1-23b4-6a5e2f2220a2.png)


下表を参考に記入し、「登録」ボタンをクリックして登録します。

|Policy名|Policy素材|
|-|-|
|limit-proposed-monthly-cost|limit-proposed-monthly-cost.sentinel|

## 7.PolicySetの登録
PolicySetを登録します。
PolicySetはPolicyおよびWorksoaceと紐づけることで、作業実行時に対象のWorkspaceに対してPolicyを有効にします。

左メニューグループから「Policy Sets管理」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/de697c3d-8e3a-16cd-7e1b-42ff34c4cc38.png)

画面が遷移するので、登録欄から登録開始を選択します。
Policy Setの名前を付け登録します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/372e7339-f033-9816-6f8d-4e30ea4a3132.png)
下表を参考に記入し、「登録」ボタンをクリックして登録します。

|PolicySet名|
|-|
|PolicySet_demo|

## 8.PolicySetにPolicyを紐付け
先ほど登録したPolicyとPolicySetを紐付けます。

左メニューグループから「PolicySet-Policy紐付管理」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/53d1206b-e49e-81db-4b88-cb731eaaf3d4.png)

画面が遷移するので、登録欄から登録開始を選択します。
PolicyとPolicySetを紐付け、登録します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/c78b70a1-2643-508b-7d20-c9e0579c9b9d.png)

下表を参考に記入し、「登録」ボタンをクリックして登録します。

|Policy Set|Policy|
|-|-|
|1:PolicySet_demo|1:limit-proposed-monthly-cost|


## 9.PolicySetにWorkspaceを紐付け
登録したPolicySetとWorkspaceを紐付けます。

画面が遷移するので、登録欄から登録開始を選択します。
PolicySetとWorkspaceを紐付け、登録します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/cf0edd81-4445-6b7c-7673-545cc058963d.png)

下表を参考に記入し、「登録」ボタンをクリックして登録します。

|Policy Set|Organization:Workspace|
|-|-|
|1:PolicySet_demo|ITAlearn_org:ITA-demo-AWS|
|1:PolicySet_demo|ITAlearn_org:ITA-demo-Azure|



## 10.MovementにModule素材を指定
登録したModule素材とMovementを関連付けます。

左メニューグループから「Movement-Module紐付」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/e9e4d29a-d14a-6dd0-a2aa-eb84f39d306f.png)

画面が遷移するので、登録欄から登録開始を選択します。
前節で作成したMovement「VM作成(AWS)」と「VM作成(Azure)」に対応したModule素材を登録します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/61d632b4-c464-2c57-e9d4-08d07ae7ed43.png)

下表を参考に記入し、「登録」ボタンをクリックして登録します。

|Movement|Module素材|
|-|-|
|VM作成(AWS)|aws_create_instance_variables|
|VM作成(AWS)|aws_create_instance_body|
|VM作成(Azure)|azure_create_instance_variables|
|VM作成(Azure)|azure_create_instance_body|

# 実行編

## 1.オペレーションの登録
オペレーションを登録します。
オペレーションとは、作業全体を示すITA内で使用する作業名称のことを指します。

メインメニュー(DASHBOARD)から「基本コンソール」メニューグループ >> 「投入オペレーション一覧」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/45587008-232c-8098-949a-87bf0611d486.png)

画面が遷移するので、登録欄から登録開始を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/92f0746f-8bcc-c52f-ade2-ce8851b18b8d.png)

下表を参考に記入し、「登録」ボタンをクリックして登録します。

|オペレーション名|実施予定日時|
|-|-|
|Terraform_demo|(任意の日時を記入)|

※「実施予定日時」はITA内部で保持するデータであり、実際にオペレーションを実施する時間ではありません

## 2.変数値の設定
Moduleの変数に具体的な数値を代入します。

「Terraform」メニューグループに戻り、左メニューグループから「代入値管理」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/a18517b5-35de-0a6a-faff-a8538dcd3784.png)

画面が遷移するので、登録欄から登録開始を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/c92bfe88-2f71-10f2-6cff-401204e762f8.png)
登録項目は下表を参考にします。

***AWS代入値登録内容***

|オペレーション|Movement|変数名|具体値|
|-|-|-|-|
|Terraform_demo|VM作成(AWS)|security_group|ita-demo-sg※|
|Terraform_demo|VM作成(AWS)|key_name|ita-demo-key※|
|Terraform_demo|VM作成(AWS)|access_key|(AWSアクセスキー)|
|Terraform_demo|VM作成(AWS)|secret_key|(AWSシークレットキー)|
|Terraform_demo|VM作成(AWS)|region|(任意のリージョン)|
|Terraform_demo|VM作成(AWS)|tags_name|ita-demo-instance|
|Terraform_demo|VM作成(AWS)|hello_tf_instance_type|t2.large|
|Terraform_demo|VM作成(AWS)|hello_tf_instance_count|3|
|Terraform_demo|VM作成(AWS)|ami|(任意のAMI)|

※セキュリティーグループとキーペアは事前に作成しておく必要があります。


***Azure代入値登録内容***

|オペレーション|Movement|変数名|具体値|
|-|-|-|-|
|Terraform_demo|VM作成(Azure)|subscription_id|(Azure認証情報)|
|Terraform_demo|VM作成(Azure)|tenant_id|(Azure認証情報)|
|Terraform_demo|VM作成(Azure)|client_id|(Azure認証情報)|
|Terraform_demo|VM作成(Azure)|client_secret|(Azure認証情報)|
|Terraform_demo|VM作成(Azure)|resource_group_name|ita-demo-rg|
|Terraform_demo|VM作成(Azure)|location |japaneast|
|Terraform_demo|VM作成(Azure)|security_group|ita-demo-security-group|
|Terraform_demo|VM作成(Azure)|Vnet_name|ita-demo-vnet|
|Terraform_demo|VM作成(Azure)|Vnet_address_space|10.0.0.0/16|
|Terraform_demo|VM作成(Azure)|subnet_name|ita-demo-subnet|
|Terraform_demo|VM作成(Azure)|address_prefixes|10.0.2.0/24|
|Terraform_demo|VM作成(Azure)|public_ip_name|public_ip_name|
|Terraform_demo|VM作成(Azure)|allocation_method|Dynamic|
|Terraform_demo|VM作成(Azure)|domain_name_label |(任意のグローバルなドメイン名)|
|Terraform_demo|VM作成(Azure)|network_interface_name|ita-demo-nwif|
|Terraform_demo|VM作成(Azure)|NIC_name|ita-demo-NIC|
|Terraform_demo|VM作成(Azure)|VM_name |ta-demo-web-azure|
|Terraform_demo|VM作成(Azure)|publisher|OpenLogic|
|Terraform_demo|VM作成(Azure)|offer|CentOS|
|Terraform_demo|VM作成(Azure)|sku|8_2|
|Terraform_demo|VM作成(Azure)|source_image_version |latest|
|Terraform_demo|VM作成(Azure)|os_disk_name|os_disk_name|
|Terraform_demo|VM作成(Azure)|storage_account_type |Standard_LRS|
|Terraform_demo|VM作成(Azure)|caching |ReadWrite|
|Terraform_demo|VM作成(Azure)|admin_username|ita-demo|
|Terraform_demo|VM作成(Azure)|ssh_public_key| (任意のSSH公開鍵)※|
|Terraform_demo|VM作成(Azure)|VM_size |Standard_B2MS|
|Terraform_demo|VM作成(Azure)|VM_count |3|

※事前に用意したSSH公開鍵を利用してください。
入力する具体値はSSH公開鍵のテキスト「ssh-rsa xxxxxxxx～」となります。

## 3.Planを確認
ここまでの作業で、実行するMovementの作成と代入値の登録が完了しました。
次に、作成したModuleが定義したポリシーに沿っているのか確かめましょう。

左メニューグループから「作業実行」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/235e3d19-d655-c52d-f65a-49af561fedcf.png)

画面が遷移するので、作成したMovementとオペレーションを選択し、「Plan確認」を押下します。
[Plan確認]はPlan/PolicyCheckまでを行い、処理を停止します。(Applyは実行しません。)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/e469f71f-9043-680e-2212-388577cc3fd5.png)

### PolicyCheckログを確認する
押下後の画面遷移先で、ステータスが「完了(異常)」となっていることが確認できます。
画面下に移動し、PolicyCheckログを確認しましょう。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/c2e5eb39-8846-f182-6533-49e93c679e78.png)

### 代入値を変更して再度実行
前項で代入値がポリシーを違反していることがわかりました。
なので、代入値を変更して再度実行しましょう。

***Terraform >> 代入値管理***から下表を参考に代入値を変更します

|オペレーション|Movement|変数名|具体値(変更前)|具体値(変更後)|
|-|-|-|-|-|
|Terraform_demo|VM作成(AWS)|hello_tf_instance_type|t2.large|t2.micro|
|Terraform_demo|VM作成(Azure)|VM_size |Standard_B2MS|Standard_B1LS|

変更完了後、再度同様に実行しましょう。

押下後の画面遷移先で、ステータスが「完了」となっていることが確認できます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/a15eafc7-527d-cf7a-c33d-7d33bec68e20.png)



## 4.作業実行
実行するModuleが定義したポリシーを適用していることが確認できました。最後にMovementを実行し、結果を対象ホストで確認しましょう。

左メニューグループから再度「作業実行」を選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/47ff5a54-4f0a-d691-d522-aea5b06255c1.png)
画面が遷移するので、作成したMovementとオペレーションを選択し、「Plan確認」を押下します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/42ffcd1a-34e7-5199-6afc-fd7c14db693e.png)


## 5.実行状態を確認
実行後の画面遷移先で、実行ステータスやログを確認することができます。
投入データや出力データを確認することも可能です。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/11a7f7d0-b396-ccb0-b667-7dc00bc98262.png)

画面遷移先で実行ステータスが「***完了***」を確認出来たら、
実際にAWS,Azureにブラウザからアクセスし、インスタンスが作成できているか確認しましょう。

実行後のAWSにインスタンスが追加されているか確認します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/40cfbc18-1041-dd0a-6038-5dea490df357.png)

「ita-demo-instance」という名前のインスタンスが3つ作成されていることがわかります。
また、設定通りインスタンスタイプもすべて「t2.micro」です。

一方Azureはどうでしょうか
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/1a9b01aa-3a7c-2514-897d-793e355e78b1.png)

「ita-demo-rg」という名前のリソースグループが作成され、
その中に「ita-demo-web-azure」という仮想マシン3つが建ちました。


## 6.変数値を変更して再度実行
最後に、作成するインスタンス数の具体値を変更して再度同じMovementを実行してみます。
***Terraform >> 代入値管理***から下表を参考に具体値を変更します。

|オペレーション|Movement|変数名|具体値(変更前)|具体値(変更後)|
|-|-|-|-|-|
|Terraform_demo|VM作成(AWS)|hello_tf_instance_count|3|5|
|Terraform_demo|VM作成(Azure)|VM_count |3|1|

変更完了後、再度同様に実行しましょう。

AWS・Azureにブラウザから接続し、VMインスタンスの数が変更した通りに増減しているか確認します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/652376/7cc2616b-def9-035a-743f-4cd1395cd909.png)

変更した通り、AWS上のインスタンスは３台から５台に
Azure上のインスタンスは３台から１台に変更することができました。

# おわりに
今回はITAのTerraform-Driverを使って、パブリッククラウドのプロビジョニングを行いました。
ここから建てたVMに対してITAのAnsible-Driverを使ってサーバの設定などを行えそうですね。
また、Conductorを使って楽にマルチクラウドのプロビジョニングが行えそうです。

### 索引
+ [ExastroSuite コミュニティページ](https://exastro-suite.github.io/docs/index_ja.html)
+ [Exastro IT Automation](https://exastro-suite.github.io/it-automation-docs/index_ja.html)
+ [【随時更新】Exastroの参考になる記事をまとめてみた](https://qiita.com/ooif/items/79952398fb03ca3ec7fd)