【Terraform】【AWS】Map型でOutputして別Moduleに値を渡す

もくじ

はじめに

やること

本日もTerraformのお話です。

やることは、Map型の変数でOutputして、別のModuleから参照することです。

前回の記事で、VPCとサブネットを作成しました。

サブネットの情報を別のModuleから参照して、EC2インスタンスを作成してみようと思います。

得られるメリット

モジュールを分けると、どこにどのようなリソースを定義しているかわかりやすくなります。

そしてモジュールで作成したリソースをMap型でOutputできると、別モジュールからKeyで値を取得できます。(あたりまえですが)

また、変数に階層構造をもたせて視覚的にもわかりやすく記述できます。さらに、別モジュールで変数をインポートしてfor_eachなどで繰り返し、たとえばマルチAZ構成のEC2をひとつのリソース定義で記述できます。

やってみる

ディレクトリ構成

ディレクトリ構成は以下のようになっています。ハイライトしているところは、今回追加したところです。

{root}/
|
|---[environment]
|    |---[dev]
|          |---main.tf
|          |---provider.tf
|
|---[module]
     |---[Computing]
     |     |---ec2.tf
     |     |---variable.tf
     |
     |---[Network]
           |---vpc.tf
           |---subnet.tf
           |---variable.tf
           |---output.tf

コード内容

  • environment/dev/main.tf
## Networkモジュール
module "network" {
  source     = "../../module/Network"
  sysname    = var.param.sysname
  env        = var.param.env
  cidr_block = var.param.cidr_block
  zone       = var.param.zone
}

## Computingモジュール
module "computing" {
  source  = "../../module/Computing"
  subnets = module.network.subnets
  depends_on = [
    module.network
  ]
}

computingモジュールを追加しています。この中にEC2の定義を書いています。

networkモジュールからsubnetsという名前でサブネットの情報をOutputしているので、computingモジュールで使えるように変数に格納しています。(subnets = module.network.subnets


  • module/Network/output.tf
output "subnets" {
  value = (tomap({
    "01" = {
      "public_subnet"  = aws_subnet.public_subnet["01"]
      "private_subnet" = aws_subnet.private_subnet["01"]
    },
    "02" = {
      "public_subnet"  = aws_subnet.public_subnet["02"]
      "private_subnet" = aws_subnet.private_subnet["02"]
    }
  }))
}

今回のテーマとなるコードです。Map型でOutputするコードとなります。

まず、Output変数(別Moduleから参照されるときに使用する変数)はsubnetsとなります。

値(value)をMap型にするため、Terraformのtomap関数を使用しています。

Keyは"01""02"として、それぞれにus-east-1aus-east-1cのパブリックサブネットとプライベートサブネットを変数として組み込んでいます。


  • module/Computing/variable.tf
variable "subnets" {}

computingモジュールのvariable.tfでは、networkモジュールがOutputしたsubnetsというMap変数を扱えるようにするため、subnets変数を宣言しているのみです。


  • module/Computing/ec2.tf
resource "aws_instance" "ec2" {
  ami           = "ami-09d3b3274b6c5d4aa"
  subnet_id     = var.subnets["02"].public_subnet.id
  instance_type = "t2.micro"
}

最低限の設定値のみ記載しています。

注目してほしいところはサブネットの指定です。

Map型であるsubnets変数のKey"02"のパブリックサブネットを指定しています。

このように、Keyの指定でどちらのAZに配置するか決めることができます。

実行結果

Map変数のKey"02"の方である、us-east-1cのパブリックサブネットにEC2がデプロイされました。

番外編(EC2を各AZにfor_eachでデプロイする)

コード内容

  • (番外編)module/Computing/ec2.tf (両方のAZに配置する場合)
resource "aws_instance" "ec2_01_and_02" {
  for_each      = var.subnets
  ami           = "ami-09d3b3274b6c5d4aa"
  subnet_id     = each.value.public_subnet.id
  instance_type = "t2.micro"
}

Map型の変数がcomputingモジュールで扱えるため、for_eachを使用して両方のAZにEC2をデプロイしてみます。

上のコードの場合、両方のパブリックサブネットに同じEC2がデプロイされます。

実行結果(番外編)

ひとつのresourceブロックで、2つのEC2が各AZに配置されました。

この記事が気に入ったら
フォローしてね!

よかったらシェアしてね!

コメント

コメントする

コメントは日本語で入力してください。(スパム対策)

CAPTCHA

もくじ
閉じる