Terraform入門 ~TerraformでOCIのMySQL DBCS構築~

技術者が語るOracle Cloud

クラウド・コンピューティング市場は日々目まぐるしく変化しています。
また、今日のコロナ禍の影響もあり、世間でもテレワークやクラウド・コンピューティングへの注目が強まり、その需要は飛躍的に高まっています。

今回は、そんなクラウド・コンピューティングでインフラ構築を行う、インフラストラクチャ定義ツールの「Terraform」についてご紹介します。
そして、つい先日、東京リージョンでMySQLのDBCSを作成できるようになりましたので、「Terraform」を用いてOCI上に作成したいと思います。

1.Terraformとは

TerraformはHashiCorp社が開発したインフラストラクチャ定義ツール(Infrastracture as Code)に分類されるツールで、コマンドベースでクラウド上のインフラ構築を行うことができます。
Terraformには下記の利点があります。

  • コマンド実行でGUIでの構築より手軽にインフラ構築可能
  • 第三者によるインフラ構築手順の連携・検証可能
  • 作成したコードの管理・共有・再利用可能
  • オープンソースライセンス(Mozilla Public License 2.0)のため無料で使用可能
  • GUIでの煩雑な操作による人為的ミスを防止

2.Terraform主要コマンド

Terraformには下記の主要なコマンドがあります。

init

Terraform構成ファイルを含んだ作業ディレクトリを初期化する際に使用します。
Terraform構成ファイルを作成・編集した後には必ず必要な手順です。
このコマンド実行でクラウド上の既存の環境が変更されることはありません。

plan

Terraform構成ファイルに記載された変更の実行計画が期待どおりであるか確認します。
実行計画の確認の際にクラウド環境へのアクセスを実施します。
また、-outオプションを指定して、applyの際に使用するリソース作成プランを保存できます。
このコマンド実行でクラウド上の既存の環境が変更されることはありません。

apply

planコマンドで作成した実行計画を基に、クラウド上の環境でインフラ構築を行います。
また、plan -outコマンドで作成したリソース作成プランを指定することで、以前作成したリソース作成プランでインフラ構築を行うことができます。

3.事前準備

1.事前準備

Terraformでインフラ構築を行うにあたり、下記の用意が必要です。

  • Terraformがインストール済みであること
  • OCIのIAMユーザが存在すること
  • 使用するIAMユーザにAPI共有鍵が登録されていること
  • 使用するIAMユーザを対象に、インフラ構築に必要なポリシーが設定されていること
  • API秘密鍵(pem形式)を用意すること
  • API秘密鍵から共有鍵を作成していること
  • SSH秘密鍵(ppk形式)を用意すること
  • SSH秘密鍵(ppk形式)から共有鍵を確認できること

2.構築内容

今回は下図のインフラ構築を行います。

oc11_01.png

  • MySQL・DBシステム
  • 仮想マシン・インスタンス
  • 仮想クラウド・ネットワーク
  • パブリック・サブネット
  • プライベート・サブネット
  • パブリック・サブネット用セキュリティ・リスト
  • プライベート・サブネット用セキュリティ・リスト
  • インターネット・ゲートウェイ
  • ルート表

3.構築環境情報

今回は下記の環境でインフラ構築を行います。

TerraFormバージョン 0.13.3
インストール先OS Windows Server 2016
構築対象クラウド Oracle Cloud Infrastructure

なお、HashiCorp社のTerraform公式サイトからTerraformインストーラを入手できます。

4.TFファイル作成

1.TFファイル記載について

TerraformではTFファイルというファイルを使用してインフラ構築を行います。
TFファイルで記載する各種リソース等の詳細についてはHashiCorp社のTerraformのマニュアルをご確認ください。

2.TFファイル作成

実際にTFファイルを用意していきます。今回は下記の4ファイルを用意します。使用する際に、<>で囲っている部分を編集してください。

  • プロバイダ TFファイル ( exe-terraform-provider.tf )
  • ネットワーク TFファイル ( exe-terraform_network.tf )
  • インスタンス TFファイル ( exe-terraform_instance.tf )
  • MySQL_DBCS TFファイル ( exe-terraform_mysql_dbsystem.tf )

●プロバイダTFファイル ( exe-terraform-provider.tf )

terraform {
  required_providers {
    oci = {
      source  = "hashicorp/oci"
      version = "3.94.0"
    }
  }
  required_version = ">= 0.13"
}

provider "oci" {
  tenancy_ocid         = < テナントのOCID >
  region               = < リージョン識別子 >
  user_ocid            = < 使用するユーザのOCID ※1 >
  fingerprint          = < 使用するユーザに設定したAPIキーのフィンガープリント >
  private_key_path     = < 使用するユーザに設定したAPI共有鍵の秘密鍵 ※2 >
  private_key_password = < 使用するユーザに設定したAPI共有鍵の秘密鍵のパスワード >
}

data "oci_identity_availability_domains" "exe_availability_domain" {
  provider       = oci
  compartment_id = < テナントのOCID >
}

※1 使用するユーザはIAMユーザである必要があります。
※2 Windowsで絶対パスを指定する場合、(C:¥¥test¥¥test.pem)の様に「¥」に対してエスケープする必要があります。

●ネットワークTFファイル ( exe-terraform_network.tf )

### Virtual Cloud Network ###

resource "oci_core_vcn" "exe_terraform_vcn" {
    cidr_block = "172.16.0.0/16"
    compartment_id = < コンパートメントのOCID >
    display_name = "exe_terraform_vcn"
}

### Public Subnet ###

resource "oci_core_subnet" "exe_terraform_subnet01" {
    cidr_block = "172.16.1.0/24"
    compartment_id = < コンパートメントのOCID >
    vcn_id = oci_core_vcn.exe_terraform_vcn.id
    display_name = "exe_terraform_subnet01"
    prohibit_public_ip_on_vnic = "false"
    security_list_ids = [oci_core_security_list.exe_terraform_security_list01.id]
    route_table_id = oci_core_route_table.exe_terraform_internet_gateway_route_table.id
}

### Public Subnet Security List Subnet ###

resource "oci_core_security_list" "exe_terraform_security_list01"{
  compartment_id = < コンパートメントのOCID >
  vcn_id = oci_core_vcn.exe_terraform_vcn.id
  display_name = "exe_terraform_security_list01"
  
  egress_security_rules {
    destination = "0.0.0.0/0"
    protocol = "6"
    stateless = "false"
  }

  ingress_security_rules {
    source = "0.0.0.0/0"
    protocol = "6"
    stateless = "false"
    tcp_options {
      max = "22"
      min = "22"
    }
  }
}

### Private Subnet ###

resource "oci_core_subnet" "exe_terraform_subnet02" {
    cidr_block = "172.16.2.0/24"
    compartment_id = < コンパートメントのOCID >
    vcn_id = oci_core_vcn.exe_terraform_vcn.id
    display_name = "exe_terraform_subnet02"
    prohibit_public_ip_on_vnic = "true"
    security_list_ids = [oci_core_security_list.exe_terraform_security_list02.id]
    route_table_id = oci_core_route_table.exe_terraform_internet_gateway_route_table.id
}

### Private Subnet Security List Subnet ###

resource "oci_core_security_list" "exe_terraform_security_list02"{
  compartment_id = < コンパートメントのOCID >
  vcn_id = oci_core_vcn.exe_terraform_vcn.id
  display_name = "exe_terraform_security_list02"
  
  egress_security_rules {
    destination = "0.0.0.0/0"
    protocol = "6"
    stateless = "false"
  }

  ingress_security_rules {
    source = "0.0.0.0/0"
    protocol = "6"
    stateless = "false"
    tcp_options {
      max = "3306"
      min = "3306"
    }
  }

  ingress_security_rules {
    source = "0.0.0.0/0"
    protocol = "6"
    stateless = "false"
    tcp_options {
      max = "33060"
      min = "33060"
    }
  }

### Internet Gateway ###

resource "oci_core_internet_gateway" "exe_terraform_internet_gateway" {
  compartment_id = < コンパートメントのOCID >
  vcn_id = oci_core_vcn.exe_terraform_vcn.id
  display_name = "exe_terraform_internet_gateway"
}

### Route Table ###

resource "oci_core_route_table" "exe_terraform_internet_gateway_route_table" {
  compartment_id = < コンパートメントのOCID >
  vcn_id = oci_core_vcn.exe_terraform_vcn.id
  display_name = "exe_terraform_internet_gateway_route_table"  
  route_rules {
    network_entity_id = oci_core_internet_gateway.exe_terraform_internet_gateway.id
    destination = "0.0.0.0/0"
  }
}

●インスタンスTFファイル ( exe-terraform_instance.tf )

resource "oci_core_instance" "exe-terraform-instance01" {
  availability_domain = lookup(data.oci_identity_availability_domains.exe_availability_domain.availability_domains[0],"name")
  fault_domain = "FAULT-DOMAIN-1"
  compartment_id = < コンパートメントのOCID >
  shape = "VM.Standard.E2.1.Micro"
  display_name = "exe-terraform-instance01"
  create_vnic_details {
        subnet_id = oci_core_subnet.exe_terraform_subnet01.id
        private_ip = "172.16.1.10"
        assign_public_ip = "true"
    }
    source_details {
        source_id = < OSイメージのOCID ※3 >
        source_type = "image"
    }
     metadata = {
        ssh_authorized_keys = < SSH共有鍵の内容 >
    }
}

※3 OCI提供のOSイメージのOCIDはリリースノートから確認できます。

●MySQL DBCS TFファイル ( exe-terraform_mysql_dbsystem.tf )

resource "oci_mysql_mysql_db_system" "exe_terraform_mysql_db_system01" {
  admin_password = < 管理者ユーザのパスワード ※4 >
  admin_username = "root"
  availability_domain = lookup(data.oci_identity_availability_domains.exe_availability_domain.availability_domains[0],"name")
  fault_domain = "FAULT-DOMAIN-2"
  compartment_id = < コンパートメントのOCID >
  display_name = "exe_terraform_mysql_db_system01"
  configuration_id = < MySQL構成のOCID ※5 >
  shape_name = "VM.Standard.E2.1"
  subnet_id = oci_core_subnet.exe_terraform_subnet02.id
  ip_address = "172.16.2.10"
  data_storage_size_in_gb = "50"
  port = "3306"
  port_x = "33060"
}

※4 管理者パスワードは8文字から32文字までの長さで、大文字、小文字、数字および 特殊文字をそれぞれ1つ以上含める必要があります。


※5 MySQL DBCSで使用する構成のOCIDは、OCIの画面左側のメニューから MySQL >> 構成 を 選択することで確認できます。今回は、VM.Standard.E2.1 シェイプのデフォルト構成の VM.Standard.E2.1.Built-in を使用します。

oc11_02.png

5.実行

1.TFファイルとAPI秘密鍵配置

TFファイルとAPI秘密鍵(exe-terraform_mysql_dbsystem.tf)を配置されているディレクトリに移動します。
下記では C:¥work¥ にTFファイルとAPI秘密鍵が配置されています。

PS C:\Users\Administrator> cd C:\work\
PS C:\work> dir


    ディレクトリ: C:\work


Mode                LastWriteTime         Length Name
----                -------------         ------ ----
-a----       2020/09/29     16:39           1766 exe-terraform-ipa.pem
-a----       2020/09/30     11:06            438 exe-terraform-provider.tf
-a----       2020/09/30     11:08           1107 exe-terraform_instance.tf
-a----       2020/09/30     11:11            628 exe-terraform_mysql_dbsystem.tf
-a----       2020/09/30     11:17           3932 exe-terraform_network.tf
-a----       2020/09/30     11:16            698 exe-terraform_variable.tf


PS C:\work> 

2.terraform init

terraform initを実行し、作業ディレクトリを初期化する際に使用します。

PS C:\work> terraform init

Initializing the backend...

Initializing provider plugins...
=- Using previously-installed hashicorp/oci v3.94.0

Terraform has been successfully initialized!

You may now begin working with Terraform. Try running "terraform plan" to see
any changes that are required for your infrastructure. All Terraform commands
should now work.

If you ever set or change modules or backend configuration for Terraform,
rerun this command to reinitialize your working directory. If you forget, other
commands will detect it and remind you to do so if necessary.
PS C:\work>

3.terraform plan

terraform planを実行し、TFファイルに記載した内容の任意の名前のリソース作成プランを作成します。
今回は exe-terraform-plan というリソース作成プラン名にします。

PS C:\work> terraform plan -out exe-terraform-plan
Refreshing Terraform state in-memory prior to plan...
The refreshed state will be used to calculate this plan, but will not be
persisted to local or remote state storage.

data.oci_identity_availability_domains.exe_availability_domain: Refreshing state...

------------------------------------------------------------------------

An execution plan has been generated and is shown below.
Resource actions are indicated with the following symbols:
  + create

Terraform will perform the following actions:

< 中略 >

Plan: 9 to add, 0 to change, 0 to destroy.

------------------------------------------------------------------------

This plan was saved to: exe-terraform-plan

To perform exactly these actions, run the following command to apply:
    terraform apply "exe-terraform-plan"

PS C:\work>

4.terraform apply

terraform planで作成したリソース作成プランを指定してterraform applyを実行し、OCI上でインフラ構築を実施します。今回は先程作成したexe-terraform-planを使用します。
各リソースのOCIDは自動で割り当てられます。

PS C:\work> terraform apply exe-terraform-plan
oci_core_vcn.exe_terraform_vcn: Creating...
oci_core_vcn.exe_terraform_vcn: Creation complete after 0s [id=< VCNのOCID >]
oci_core_security_list.exe_terraform_security_list01: Creating...
oci_core_security_list.exe_terraform_security_list02: Creating...
oci_core_internet_gateway.exe_terraform_internet_gateway: Creating...
oci_core_security_list.exe_terraform_security_list01: Creation complete after 0s 
[id=< Publicサブネット用セキュリティリストのOCID> ]
oci_core_internet_gateway.exe_terraform_internet_gateway: Creation complete after 0s 
[id=< インターネットゲートウェイのOCID >]
oci_core_security_list.exe_terraform_security_list02: Creation complete after 0s 
[id=< Privateサブネット用セキュリティリストのOCID >]
oci_core_route_table.exe_terraform_internet_gateway_route_table: Creating…

< 中略 >

Apply complete! Resources: 9 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
PS C:\work>

6.確認

1.リソース作成確認

Terraformで作成したリソースについて確認します。

・MySQL・DBシステム

oc11_03.png

・仮想マシン・インスタンス

oc11_04.png

・仮想クラウド・ネットワーク

oc11_05.png

・パブリック・サブネット

oc11_06.png

・プライベート・サブネット

oc11_07.png

・パブリック・サブネット用セキュリティ・リスト(イングレス・ルール)

oc11_08.png

・パブリック・サブネット用セキュリティ・リスト(エグレス・ルール)

oc11_09.png

・プライベート・サブネット用セキュリティ・リスト(イングレス・ルール)

oc11_10.png

・プライベート・サブネット用セキュリティ・リスト(エグレス・ルール)

oc11_11.png

・インターネット・ゲートウェイ

oc11_12.png

・ルート表

oc11_13.png

2.MySQL接続

Terraformで作成したインスタンスからMySQL DBCSに接続します。

1.MySQL Community Downloadsから作成したインスタンスのOSにあったYumリポジトリを入手します。

2.Tera Term等を用いて作成したインスタンスにSSH接続します。

oc11_14.png

3.接続したインスタンスにYumリポジトリを転送します。

oc11_15.png

4.rootユーザに切替えます。

$ sudo su

5.rpmでYumリポジトリインストールします。

# rpm -ivh <MySQLのYumリポジトリファイル>

6.Yumで mysql-community-client をインストールします。

#  yum install mysql-community-client

7.MySQL DBCSのIPアドレスを指定して接続し、パスワードを入力します。

# mysql -u root -p -h 172.16.2.10
Enter password:

接続に成功したら確認完了です。

7.まとめ

今回、Terraformについてご紹介させていただきましたがいかがでしたでしょうか。
Terraformは奥が深く、今回ご紹介しきれなかった機能もまだまだあります。もし当記事を見て興味をお持ちいただけましたらぜひご活用ください。