Search code examples
amazon-web-servicesterraformterraform-provider-awsaws-acm

Merge list with map in terraform


I am writing terraform script to automate the provision of acm for domains, the issue that I am facing is how can I merge the domain and subject_alternative_names like it should pick first domain from domain_name and merge it with first block in subject_alternative_name and go on.

Variable.tf

variable "domain_name" {
  description = "Configuration for alb settings"
  default = [
    "domain.com",
    "helloworld.com",
    "helloworld2.com",
  ]
}
variable "subject_alternative_names" {
  description = "subject_alternative_names"
  default = [ {
    domain.com = {
    "domain.com",
    "domain2.com",
    "domain3.com",
    },
    helloworld.com = {
    "helloworld1.com",
    "helloworld2.com"
    },
    hiworld.com = {
    "hiworld1.com",
    "hiworld2.com"
    }
  }]
}
variable "region" {
  description = "name of the region"
  default     = "us-east-1"
}
variable "validation_method" {
  description = "name of the region"
  default     = "DNS"
}
variable "tags" {
  description = "name of the region"
  default     = "Test"
}

working variable.tf

variable "domain_name" {
  description = "Configuration for alb settings"
  default     = [
    "domain.com",
    "helloworld.com",
    "helloworld2.com",
    "helloworld1.com",
    "helloworld3.com",
  ]
}
variable "subject_alternative_names"{
  description = "subject_alternative_names"
  default     = [
    "domain.com",
    "helloworld.com",
    "helloworld2.com",
    "helloworld1.com",
    "helloworld3.com",
  ]
}
variable "region" {
  description = "name of the region"
  default     = "us-east-1"
}
variable "validation_method" {
  description = "name of the region"
  default     = "DNS"
}
variable "tags" {
  description = "name of the region"
  default     = "Test"
}

main.tf

module "acm" {
  count                     = length(var.domain_name)
  source                    = "./modules/acm"
  domain_name               = var.domain_name[count.index]
  validation_method         = var.validation_method
  tags                      = var.tags
  subject_alternative_names = var.subject_alternative_names
}

resource.tf

variable "domain_name" {
  default     = ""
  description = "Nmae of the domain"
}

variable "validation_method" {
  default     = ""
  description = "Validation method DNS or EMAIL"
}

variable "tags" {
  default     = ""
  description = "tags for the ACM certificate"
}

variable "subject_alternative_names" {
  default     = ""
  description = "subject_alternative_names"
}

resource "aws_acm_certificate" "acm_cert" {
  domain_name               = var.domain_name
  validation_method         = var.validation_method
  subject_alternative_names = var.subject_alternative_names
  lifecycle {
    create_before_destroy = true
  }
  tags = {
    Name = var.tags
  }
}

Solution

  • The easiest way would be to use a single map:

    variable "domain_name_with_alternate_names" {
      default = {
        "domain.com" = [
          "domain.com",
          "domain2.com",
          "domain3.com",
        ],
        "helloworld.com" = [
          "helloworld1.com",
          "helloworld2.com"
        ],
        "hiworld.com" = [
          "hiworld1.com",
          "hiworld2.com"
        ],
        "hiwodd4.com" = []
      }
    }
    
    
    module "acm" {
    
      for_each                  = var.domain_name_with_alternate_names
      
      source                    = "./modules/acm"
      domain_name               = each.key
      validation_method         = var.validation_method
      tags                      = var.tags
      subject_alternative_names = each.value
    }