Architect's Log

I'm a Cloud Architect. I'm highly motivated to reduce toils with driving DevOps.

【Terraform】moduleへの依存を明示する

Terraformはリソースの依存関係を自動的に解決してくれますが、明示的な指定が必要なケースがあります。

シナリオ

次のシナリオを考えます。

  1. リソース
    1. S3バケット (バケット)
    2. セキュリティグループ
    3. EC2インスタンス (インスタンス)
  2. 依存関係
    1. インスタンスにセキュリティグループをアタッチする
    2. インスタンスはバケットに依存する(起動時にバケットからアプリケーションをダウンロードする)

リソースへの依存を明示する

インスタンスのセキュリティグループへの依存はTerraformが解決してくれますが、バケットへの依存はTerraformは検知できません(知りようがありません)。

このようなケースではaws_instance.ec2depends_onでバケットへの依存を指定します。

resource "aws_s3_bucket" "this" {
...
}

resource "aws_security_group" "this" {
...
}

resource "aws_instance" "ec2" {
...
    depends_on = [aws_s3_bucket.this]
}

リソースをmodule化する

では、インスタンスに必要なリソースをmodule化したい場合は、どうすればいいのでしょうか。

こんなケースです。

module "bucket" {
  source = "../modules/storage/s3/private_bucket"
....
}

module "sg" {
  source = "../modules/network/security_group"
....
}

resource "aws_instance" "ec2" {
...
}

検証

depends_on = [module.bucket]でmoduleへの依存を明示できそうな気がします。検証してみました。

depends_onなし

terraform graph | dot -Tpng > graph.pngで依存関係を可視化すると、aws_instance_ec2はmodule.bucketに依存していないことがわかります。

サイズが大きいので、関係する箇所だけ貼ります。

f:id:JHashimoto:20210815172754p:plain

depends_onあり

既出のコードにdepends_onを追加します。

resource "aws_instance" "ec2" {
...
  depends_on = [module.bucket]
}

applyして依存関係を出力すると、aws_instance_ec2にmodule.bucketへの依存が設定されています。

f:id:JHashimoto:20210815172131p:plain

後で確認したら、リファレンスにちゃんと書いてありました。

www.terraform.io

Version note: Module support for depends_on was added in Terraform 0.13, and previous versions can only use it with resources.

depends_onのmoduleサポートはver.0.13のアップデートで入っていました。

medium.com