ぺーぺーSEのブログ

備忘録・メモ用サイト。

Terraform入門

Terraformとかいうツールが流行っているようだが結局何ができるかよくわからなかったのでここを斜め読みして軽くまとめる。

Terraformはビルド、変更、バージョン管理を安全に効果的に行うツール
low-level(インスタンス、ストレージ、ネットワーク)からhigh-level(DNSエントリ、SaaS)までカバー。
特長は以下の通り。

  • Infrastructure as Code
  • Execution Plans
  • Resource Graph
  • Change Automation

インストール

ここからプラットフォームに合ったバイナリを落とす。 zipなので好きなところに展開する。
たっぷり実行ファイルが出てくるのでPATHを通す。
コマンドで「terraform」をたたいて動くかどうか確認する。

# DOS
C:\tools\terraform_0.5.3>terraform
usage: terraform [--version] [--help] <command> [<args>]

Available commands are:
    apply      Builds or changes infrastructure
    destroy    Destroy Terraform-managed infrastructure
    get        Download and install modules for the configuration
    graph      Create a visual graph of Terraform resources
    init       Initializes Terraform configuration from a module
    output     Read an output from a state file
    plan       Generate and show an execution plan
    push       Upload this Terraform module to Atlas to run
    refresh    Update local state file against real resources
    remote     Configure remote state storage
    show       Inspect Terraform state or plan
    taint      Manually mark a resource for recreation
    version    Prints the Terraform version

Configuration

Terraformは下記のように多くのProviderをコントロールすることができる。
* Atlas
* AWS
* CloudFlare
* CloudStack
* Consul
* DigitalOcean
* DNSMadeEasy
* DNSimple
* Docker
* Google Cloud
* Heroku
* Mailgun
* OpenStack
* Template

Terraformの設定は、.tfファイルにJSON形式で記載する。
詳細はここを参照。

# 例(example.tf)
provider "aws" {
    access_key = "ACCESS_KEY_HERE"
    secret_key = "SECRET_KEY_HERE"
    region = "us-east-1"
}

resource "aws_instance" "example" {
    ami = "ami-408c7f28"
    instance_type = "t1.micro"
}

providerブロックでaws等のプロバイダを指定し、resourceブロックでEC2のような物理コンポーネントやHerokuアプリケーションのような論理リソースを定義する。
resourceブロックには2つの文字列を指定し、それぞれリソースタイプリソース名となる。例ではaws_instanceとexampleとなっている。
resourceブロックのカッコ内にはリソースプロバイダそれぞれの定義を書く。
また、この.tfファイルは変数化して値を外出しできるようだ。

Execution Plan

作成した.tfファイルをカレントディレクトリにしてコマンドで「terraform plan」を実行すると下記のように実行による変更内容が表示される。

# sh
$ terraform plan
...

+ aws_instance.example
    ami:               "" => "ami-408c7f28"
    availability_zone: "" => "<computed>"
    instance_type:     "" => "t1.micro"
    key_name:          "" => "<computed>"
    private_dns:       "" => "<computed>"
    private_ip:        "" => "<computed>"
    public_dns:        "" => "<computed>"
    public_ip:         "" => "<computed>"
    security_groups:   "" => "<computed>"
    subnet_id:         "" => "<computed>"

インスタンス構築・更新の際は「terraform plan」で確認するが、削除の際は「terraform plan -destroy」で確認する。

Apply

terraform apply」を実行すると「terraform plan」で出力された内容が実際に反映される。

# sh
$ terraform apply
aws_instance.example: Creating...
  ami:           "" => "ami-408c7f28"
  instance_type: "" => "t1.micro"

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

...

実行後、Terraformはデフォルトでterraform.tfstateというファイルを出力する。
terraform show」コマンドで確認することができる。

# sh
$ terraform show
aws_instance.example:
  id = i-e60900cd
  ami = ami-408c7f28
  availability_zone = us-east-1c
  instance_type = t1.micro
  key_name =
  private_dns = domU-12-31-39-12-38-AB.compute-1.internal
  private_ip = 10.200.59.89
  public_dns = ec2-54-81-21-192.compute-1.amazonaws.com
  public_ip = 54.81.21.192
  security_groups.# = 1
  security_groups.0 = default
  subnet_id =

インスタンス構築・更新の際は「terraform apply」を実行するが、削除の際は「terraform destroy」を実行する。

Provisioning

Terraformは下記のPorvisionerをコントロールできる。
* chef
* connection
* file
* local-exec
* remote-exec

以下に例を示す。

# 例(example.tf)
resource "aws_instance" "example" {
    ami = "ami-aa7ab6c2"
    instance_type = "t1.micro"

    provisioner "local-exec" {
        command = "echo ${aws_instance.example.public_ip} > file.txt"
    }
}

resourceブロック内にProvisionerを定義することで設定できる。
例ではlocal-execを使用している。これは、対象のインスタンスでコマンドを実行できるProvisioner。
実行はインスタンス作成時と同様「terraform apply」。

Modules

ここまではTerraform自身が何をできるか、という説明だった。
Terraformにはmoduleという機能があって他のツールを実行することができる。
ここではConsulを使用する例を示す。

# 例(example.tf)
provider "aws" {
    access_key = "AWS ACCESS KEY"
    secret_key = "AWS SECRET KEY"
    region = "AWS REGION"
}

module "consul" {
    source = "github.com/hashicorp/consul/terraform/aws"

    key_name = "AWS SSH KEY NAME"
    key_path = "PATH TO ABOVE PRIVATE KEY"
    region = "AWS REGION"
    servers = "3"
}

moduleブロックを使用することでTerraformにmoduleを作成管理することを教える。
sourcemoduleブロックでのみ使用でき、moduleの位置を指定する。
moduleを使用する際は「terraform get」コマンドを実行してmoduleを取得した後、「terraform plan」「terraform apply」を実行する。
実行した結果はmodule経由で実行したツール(ここではConsul)のみぞ知る世界でブラックボックスになる。
ただし、出力結果は取得できるようだ。

最後に

これで一通り何ができるか分かった。
各機能の詳細はここ。 設定ファイルの例はここ