tkak's tech blog

This is my technological memo.

TerraformのGoogle Cloud providerを試してみた。

先日参加したgcp ja night #28 - connpassで、 Google Cloud Platformを$500分無料で使えるクーポンをいただいたので、 Terraform by HashiCorpGoogle Cloud providerを試してみた。

Terraformは、Vagrantとかインフラ便利ツールを作っているHashicoap社の新作。 インフラの状態をDSL形式で定義できて(Infrastructure as Code)、CLIからインフラの状態を変更することができる。

ChefやPuppetとは守備範囲が違って、VM作ったり、バランサの設定したり、DNSを登録したりする作業を自動化する。 守備範囲的には、Chef-metalとかAWS CloudFormationとかとかぶる感じ。

いろんなクラウドサービスを、同じフォーマットのファイルで管理することができるのが大きな強み。 今巷でバズってるMicroservices的な考えで、数多あるクラウドサービスを一元管理できるってなんて夢のツールだろう。

Terraformは、v0.2.2を使用。

すでに試している方がいるので、それも参考に。

Terraform 0.2 で Google Compute Engine を試してみた (初級編) - Qiita

試してみたファイルはGithubに。

tkak/terraform-demo · GitHub

準備

Google Developers Consoleからaccount.jsonとclient_secrets.jsonをダウンロードする。初めて使うので、どこからファイルをダウンロードすればいいかわからなくて少しはまった。古いDashboardに画面遷移する必要があった。

account.json

Google Cloudのアカウント証明書。

"APIs & auth" -> "Credentials"のページ、"OAuth"の"Generate new JSON key"ボタンからダウンロード。もしまだOAuth Client IDを作ってなかったら、"Create new Client ID"ボタンから新しく作成してからJSONファイルを作成する。

client_secrets.json

Google Cloud APIsを利用するためのクライアント情報。

"APIs & auth" -> "APIs"のページ、歯車マークのボタンから別ページに遷移して、"API Access"のページ、"Download JSON"からダウンロードする。

2つのファイルは適当に作業ディレクトリ配下に。

$ ls
account.json client_secrets.json

instanceの作成。

まず試しにinstanceを一つ作ってみる。

作業ディレクトリにtfファイルを作成する。

$ vim google_compute.tf
provider "google" {
    account_file = "./account.json"
    client_secrets_file = "./client_secrets.json"
    project = "tkakfrkw"
    region = "asia-east1-a"
}

resource "google_compute_instance" "default" {
    name = "test"
    machine_type = "f1-micro"
    zone = "asia-east1-b"

    disk {
        image = "debian-7-wheezy-v20140814"
    }

    network {
        source = "default"
    }
}

planでこれから行う作業の確認。

$ terraform plan
Refreshing Terraform state prior to plan...


The Terraform execution plan has been generated and is shown below.
Resources are shown in alphabetical order for quick scanning. Green resources
will be created (or destroyed and then created if an existing resource
exists), yellow resources are being changed in-place, and red resources
will be destroyed.

Note: You didn't specify an "-out" parameter to save this plan, so when
"apply" is called, Terraform can't guarantee this is what will execute.

+ google_compute_instance.default
    disk.#:                     "" => "1"
    disk.0.image:               "" => "debian-7-wheezy-v20140814"
    machine_type:               "" => "f1-micro"
    metadata_fingerprint:       "" => "<computed>"
    name:                       "" => "test"
    network.#:                  "" => "1"
    network.0.internal_address: "" => "<computed>"
    network.0.name:             "" => "<computed>"
    network.0.source:           "" => "default"
    tags_fingerprint:           "" => "<computed>"
    zone:                       "" => "asia-east1-b"

applyで実際の処理を実行。

$ terraform apply
google_compute_instance.default: Creating...
  disk.#:                     "" => "1"
  disk.0.image:               "" => "debian-7-wheezy-v20140814"
  machine_type:               "" => "f1-micro"
  metadata_fingerprint:       "" => "<computed>"
  name:                       "" => "test"
  network.#:                  "" => "1"
  network.0.internal_address: "" => "<computed>"
  network.0.name:             "" => "<computed>"
  network.0.source:           "" => "default"
  tags_fingerprint:           "" => "<computed>"
  zone:                       "" => "asia-east1-b"
google_compute_instance.default: Creation complete

Apply complete! Resources: 1 added, 0 changed, 0 destroyed.

The state of your infrastructure has been saved to the path
below. This state is required to modify and destroy your
infrastructure, so keep it safe. To inspect the complete state
use the `terraform show` command.

State path: terraform.tfstate

showでインフラの状態を確認。

$ terraform show terraform.tfstate
google_compute_instance.default:
  id = test
  disk.# = 1
  disk.0.image = debian-7-wheezy-v20140814
  machine_type = f1-micro
  metadata_fingerprint = iyTlDGmC25M=
  name = test
  network.# = 1
  network.0.internal_address = 10.240.150.255
  network.0.name = nic0
  network.0.source = default
  tags_fingerprint = 42WmSpB8rSM=
  zone = asia-east1-b

f:id:keepkeptkept:20141005150747p:plain

できてる、できてる。

ちなみに、terraform.tfstateファイルはバイナリファイル。v0.3.0からはjsonになるっぽい。

$ file terraform.tfstate
terraform.tfstate: data

instanceの削除

instanceを削除してみる。

instanceの部分をコメントアウト

$ vim google_compute.tf
provider "google" {
    account_file = "./account.json"
    client_secrets_file = "./client_secrets.json"
    project = "tkakfrkw"
    region = "asia-east1-a"
}

/*
resource "google_compute_instance" "default" {
    name = "test"
    machine_type = "f1-micro"
    zone = "asia-east1-b"

    disk {
        image = "debian-7-wheezy-v20140814"
    }

    network {
        source = "default"
    }
}
*/

plan, apply, show。

$ terraform plan
efreshing Terraform state prior to plan...

google_compute_instance.default: Refreshing state... (ID: test)

The Terraform execution plan has been generated and is shown below.
Resources are shown in alphabetical order for quick scanning. Green resources
will be created (or destroyed and then created if an existing resource
exists), yellow resources are being changed in-place, and red resources
will be destroyed.

Note: You didn't specify an "-out" parameter to save this plan, so when
"apply" is called, Terraform can't guarantee this is what will execute.

- google_compute_instance.default

$ terraform apply
google_compute_instance.default: Refreshing state... (ID: test)
google_compute_instance.default: Destroying...
google_compute_instance.default: Destruction complete

Apply complete! Resources: 0 added, 0 changed, 1 destroyed.

$ terraform show
The state file is empty. No resources are represented.

JSON形式で試す

tfファイルはJSON形式でも定義できるので、拡張子.tf.jsonのファイルを用意する。上のtfファイルと同じ処理をするJSONは以下の通り。

$ vim google_compute.tf.json
{
    "provider": {
        "google": {
            "account_file": "./account.json",
            "client_secrets_file": "./client_secrets.json",
            "project": "tkakfrkw",
            "region": "asia-east1-a"
        }
    },

    "resource": {
        "google_compute_instance": {
            "default": {
                "name": "test",
                "machine_type": "f1-micro",
                "zone": "asia-east1-b",

                "disk": {
                    "image": "debian-7-wheezy-v20140814"
                },

                "network": {
                    "source": "default"
                }
            }
        }
    }
}

plan, apply, showしてみたが特に問題なく実行できた。JSON形式対応してくれるのはかなりいい機能だと思う。 他のサービスからJSON出力させて、botにterraformを実行させるみたいなこともできそう。

まとめ

ここ最近Terraformっぽいツールが欲しいと思っていて自作しようとしてたところに、彗星のごとくMichell Hashimoto先生の新作が降ってきた。最近ではAWS以外にもGoogleMicrosoft、Degital Oceanなどのクラウドサービスがよくなってきていて、ハイブリッドにクラウドを利用する時代がきているのかもしれない。そんな時代にあった良いツールを出してくるHashimoto先生はさすがだと思った。