terraform Advent Calendar 202013日目の記事です。
チーム全体でAWSのメンテナンスを行いながらスキルアップを図りたいと思い、IaCとしてTerraformをつい先日取り入れました。
その際にTerraform自体のディレクトリ構造やそこに紐づく設計思想などをどうすべきか、各所にて投稿されているベストプラクティスなど色々と調べながら、チームでモブプロをしながらメンテナンスしやすいかなと思う構成にできた気がするので、そちらを記事にします。
ディレクトリ構成
以下のような形で作りました
.
├── app_modules
│ ├── auto_scaling
│ │ ├── hoge_service
│ │ │ └── main.tf
│ │ ├── ...
│ │ │ └── ...
│ ├── cloudfront
│ │ └── huga_service
│ │ └── main.tf
│ ├── ec2
│ │ ├── hoge_service
│ │ │ └── main.tf
│ │ └── ...
│ │ └── ...
│ └── ...(ワークロードの各サービスに紐づくAWSサービスのモジュール)
│ └── ...
│ └── ...
├── cloud_modules
│ ├── auto_scaling
│ │ ├── group
│ │ │ └── main.tf
│ │ └── lifecycle_hook
│ │ └── main.tf
│ ├── cloudfront
│ │ ├── distribution
│ │ │ └── main.tf
│ │ └── origin_access_identity
│ │ └── main.tf
│ ├── ec2
│ │ ├── eip
│ │ │ └── main.tf
│ │ ├── instance
│ │ │ └── main.tf
│ │ ├── launch_configuration
│ │ │ └── main.tf
│ │ └── placement_group
│ │ └── main.tf
│ └── ...(AWS各サービスの共通設定)
│ └── ...
│ └── ...
├── env_hugahuga
│ ├── config.tf
│ └── main.tf
└── env_hogehoge
├── config.tf
└── main.tf
以下それぞれのディレクトリの内容です。
envディレクトリ
各環境のエントリーポイントです。
app_modulesに定義したモジュール群を呼び出して設定していきます。インスタンスタイプやスケール時の設定、ARNなど、環境によって異なる設定をapp_modules側へ渡せるように変数化して、こちらで設定できるようにしています。
...
# for hoge_service settings
module "elb_hoge_service" {
vpc_id = var.vpc_id
subnets = var.subnets
security_groups = var.security_groups
certificate_arn = var.certificate_arn
source = "../app_modules/elb/hoge_service"
}
module "ec2_hoge_service" {
vpc_security_group_ids = var.vpc_security_group_ids
cluster_name = var.cluster_name
instance_type = var.instance_type
source = "../app_modules/ec2/hoge_service"
}
...
cloud_modulesディレクトリ
プロバイダー内(この場合はAWS)の各サービスの基本実装を入れてます。
cloud_modulesで作ったモジュールをapp_modules側のサービス単位でカスタマイズして利用できるようにします。
cloud_modulesを作る意図としては各サービスにおいての共通設定群を管理するためです。こちらの変更は全app_modulesのサービスに反映されるという想定のため、レビューは特に慎重に実施しています。
...
resource "aws_instance" "example" {
ami = data.aws_ami.default.image_id
vpc_security_group_ids = var.vpc_security_group_ids
subnet_id = var.subnet_id
key_name = var.key_name
instance_type = var.instance_type
iam_instance_profile = var.iam_instance_profile
tags = {
Name = var.name
}
}
...
app_modulesディレクトリ
各AWSサービス単位で切り分けたディレクトリの下にワークロードをサービス単位で切り分けたディレクトリ構成を作りました。cloud_modulesで作った基本実装を読み込んだ上で、各サービス用のカスタマイズを行っています。
...
module "module_ec2_launch_configuration_hoge_service" {
name_prefix = "${var.env}-module-ec2-hoge_service-"
cluster_name = var.cluster_name
security_groups = var.vpc_security_group_ids
instance_type = var.instance_type
key_name = var.key_name
source = "../../../cloud_modules/ec2/launch_configuration"
}
...
それぞれの開発組織・メンバー構成などによってもやりやすい設計があるかと思います。
1つの構成案として誰かの参考になれば幸いです。
それでは良いクリスマスを