Intellipaat Back

Explore Courses Blog Tutorials Interview Questions
0 votes
3 views
in AWS by (5.6k points)

I'm trying to create AWS Security Group using Terraform with ingress and engress rules. Rather than creating multiple ingress or egress blocks, I'm using terraform lookup function.

My main.tf file lokks like:

provider "aws" {

  version                 = "~> 2.0"

  region                  = var.region

  profile                 = var.profile

}

resource "aws_security_group" "this" {

  name = "test-sg"

  description = "test security group"

  dynamic "ingress" {

    for_each = var.ingress_rules

    content {

      description      = lookup(ingress.value, "description", null)

      from_port        = lookup(ingress.value, "from_port", null)

      to_port          = lookup(ingress.value, "to_port", null)

      protocol         = lookup(ingress.value, "protocol", null)

      cidr_blocks      = lookup(ingress.value, "cidr_blocks", null)

    }

  }

  egress {

    from_port   = 0

    to_port     = 0

    protocol    = "-1"

    cidr_blocks = ["0.0.0.0/0"]

  }

  tags = {

    Name = "test-sg"

  }

}

and variables.tf file look like:

variable "ingress_rules" {

  default     = {

    "description" = ["For HTTP", "For SSH"]

    "from_port"   = ["80", "22"]

    "to_port"     = ["80", "22"]

    "protocol"    = ["tcp", "tcp"]

    "cidr_blocks" = ["0.0.0.0/0", "0.0.0.0/0"]

  }

  type        = map(list(string))

  description = "Security group rules"

}

When I run terraform plan it gives me the following error:

ingress.value is list of string with 2 elements

 

 Invalid value for "inputMap" parameter: lookup() requires a map as the first

 argument.

What would be the correct way to pass lookup values to variables.tf file.

1 Answer

0 votes
by (12.4k points)

You have constructed the variable's default value a five map with a string key and a list of strings values, you wanted a single map with a series of keys and values associated with various attributes of the ingress rule. So you may update the variable according to your need:

variable "ingress_rules" {

  default     = {

    "my ingress rule" = {

      "description" = "For HTTP"

      "from_port"   = "80"

      "to_port"     = "80"

      "protocol"    = "tcp"

      "cidr_blocks" = ["0.0.0.0/0"]

    },

    "my other ingress rule" = {

      "description" = "For SSH"

      "from_port"   = "22"

      "to_port"     = "22"

      "protocol"    = "tcp"

      "cidr_blocks" = ["0.0.0.0/0"]

    }

  }

  type        = map(any)

  description = "Security group rules"

}

Now you can refine your type further with an object:

default = {

  "my ingress rule" = {

    description = "For HTTP"

    from_port   = 80

    to_port     = 80

    protocol    = "tcp"

    cidr_blocks = ["0.0.0.0/0"]

  },

  "my other ingress rule" = {

    description = "For SSH"

    from_port   = 22

    to_port     = 22

    protocol    = "tcp"

    cidr_blocks = ["0.0.0.0/0"]

  }

}

type = map(object({

  description = string

  from_port   = number

  to_port     = number

  protocol    = string

  cidr_blocks = list(string)

}))

Want to learn more about AWS, then do check out AWS Course offered by Intellipaat.

Related questions

Want to get 50% Hike on your Salary?

Learn how we helped 50,000+ professionals like you !

0 votes
1 answer
0 votes
1 answer
0 votes
1 answer

31k questions

32.8k answers

501 comments

693 users

Browse Categories

...