From 75e13b9b8c1569ca5e9b9ab22d399fb34f094305 Mon Sep 17 00:00:00 2001 From: Gaspar Rajoy Date: Wed, 7 May 2025 16:24:32 -0300 Subject: [PATCH] Added wrappers --- .pre-commit-config.yaml | 1 + wrappers/README.md | 100 ++++++++++++++++++++++++++++++++++++++++ wrappers/main.tf | 14 ++++++ wrappers/outputs.tf | 5 ++ wrappers/variables.tf | 11 +++++ wrappers/versions.tf | 14 ++++++ 6 files changed, 145 insertions(+) create mode 100644 wrappers/README.md create mode 100644 wrappers/main.tf create mode 100644 wrappers/outputs.tf create mode 100644 wrappers/variables.tf create mode 100644 wrappers/versions.tf diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index a6cd369..7e4e7da 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -3,6 +3,7 @@ repos: rev: v1.96.1 hooks: - id: terraform_fmt + - id: terraform_wrapper_module_for_each - id: terraform_docs args: - '--args=--lockfile=false' diff --git a/wrappers/README.md b/wrappers/README.md new file mode 100644 index 0000000..77bf8fa --- /dev/null +++ b/wrappers/README.md @@ -0,0 +1,100 @@ +# Wrapper for the root module + +The configuration in this directory contains an implementation of a single module wrapper pattern, which allows managing several copies of a module in places where using the native Terraform 0.13+ `for_each` feature is not feasible (e.g., with Terragrunt). + +You may want to use a single Terragrunt configuration file to manage multiple resources without duplicating `terragrunt.hcl` files for each copy of the same module. + +This wrapper does not implement any extra functionality. + +## Usage with Terragrunt + +`terragrunt.hcl`: + +```hcl +terraform { + source = "tfr:///terraform-aws-modules/key-pair/aws//wrappers" + # Alternative source: + # source = "git::git@github.com:terraform-aws-modules/terraform-aws-key-pair.git//wrappers?ref=master" +} + +inputs = { + defaults = { # Default values + create = true + tags = { + Terraform = "true" + Environment = "dev" + } + } + + items = { + my-item = { + # omitted... can be any argument supported by the module + } + my-second-item = { + # omitted... can be any argument supported by the module + } + # omitted... + } +} +``` + +## Usage with Terraform + +```hcl +module "wrapper" { + source = "terraform-aws-modules/key-pair/aws//wrappers" + + defaults = { # Default values + create = true + tags = { + Terraform = "true" + Environment = "dev" + } + } + + items = { + my-item = { + # omitted... can be any argument supported by the module + } + my-second-item = { + # omitted... can be any argument supported by the module + } + # omitted... + } +} +``` + +## Example: Manage multiple S3 buckets in one Terragrunt layer + +`eu-west-1/s3-buckets/terragrunt.hcl`: + +```hcl +terraform { + source = "tfr:///terraform-aws-modules/s3-bucket/aws//wrappers" + # Alternative source: + # source = "git::git@github.com:terraform-aws-modules/terraform-aws-s3-bucket.git//wrappers?ref=master" +} + +inputs = { + defaults = { + force_destroy = true + + attach_elb_log_delivery_policy = true + attach_lb_log_delivery_policy = true + attach_deny_insecure_transport_policy = true + attach_require_latest_tls_policy = true + } + + items = { + bucket1 = { + bucket = "my-random-bucket-1" + } + bucket2 = { + bucket = "my-random-bucket-2" + tags = { + Secure = "probably" + } + } + } +} +``` diff --git a/wrappers/main.tf b/wrappers/main.tf new file mode 100644 index 0000000..83110e8 --- /dev/null +++ b/wrappers/main.tf @@ -0,0 +1,14 @@ +module "wrapper" { + source = "../" + + for_each = var.items + + create = try(each.value.create, var.defaults.create, true) + create_private_key = try(each.value.create_private_key, var.defaults.create_private_key, false) + key_name = try(each.value.key_name, var.defaults.key_name, null) + key_name_prefix = try(each.value.key_name_prefix, var.defaults.key_name_prefix, null) + private_key_algorithm = try(each.value.private_key_algorithm, var.defaults.private_key_algorithm, "RSA") + private_key_rsa_bits = try(each.value.private_key_rsa_bits, var.defaults.private_key_rsa_bits, 4096) + public_key = try(each.value.public_key, var.defaults.public_key, "") + tags = try(each.value.tags, var.defaults.tags, {}) +} diff --git a/wrappers/outputs.tf b/wrappers/outputs.tf new file mode 100644 index 0000000..34170d9 --- /dev/null +++ b/wrappers/outputs.tf @@ -0,0 +1,5 @@ +output "wrapper" { + description = "Map of outputs of a wrapper." + value = module.wrapper + sensitive = true # At least one sensitive module output (private_key_openssh) found (requires Terraform 0.14+) +} diff --git a/wrappers/variables.tf b/wrappers/variables.tf new file mode 100644 index 0000000..a6ea096 --- /dev/null +++ b/wrappers/variables.tf @@ -0,0 +1,11 @@ +variable "defaults" { + description = "Map of default values which will be used for each item." + type = any + default = {} +} + +variable "items" { + description = "Maps of items to create a wrapper from. Values are passed through to the module." + type = any + default = {} +} diff --git a/wrappers/versions.tf b/wrappers/versions.tf new file mode 100644 index 0000000..c2da4bc --- /dev/null +++ b/wrappers/versions.tf @@ -0,0 +1,14 @@ +terraform { + required_version = ">= 1.0" + + required_providers { + aws = { + source = "hashicorp/aws" + version = ">= 4.21" + } + tls = { + source = "hashicorp/tls" + version = ">= 3.4" + } + } +}