简体   繁体   English

如何列出 Terraform 中列表中的所有项目以及此处等效的 for 循环是什么?

[英]How to list all items in a list in Terraform and what's the for loop equivalent here?

I am kind of new to Terraform and could you help me with the lists in terraform.我是 Terraform 的新手,你能帮我看看 terraform 中的列表吗?

This is my code这是我的代码

variable  "ip_bitbucket" {
  type = "list"
}
ip_bitbucket = ["34.199.54.113/32","34.232.25.90/32","34.232.119.183/32","34.236.25.177/32","35.171.175.212/32","52.54.90.98/32","52.202.195.162/32","52.203.14.55/32","52.204.96.37/32","34.218.156.209/32","34.218.168.212/32","52.41.219.63/32","35.155.178.254/32","35.160.177.10/32","34.216.18.129/32","3.216.235.48/32","34.231.96.243/32","44.199.3.254/32","174.129.205.191/32","44.199.127.226/32","44.199.45.64/32","3.221.151.112/32","52.205.184.192/32","52.72.137.240/32"]

and need to access the list as below并且需要访问如下列表

resource "aws_security_group_rule "server_rule" {
  type              = "ingress"
  from_port         = 443
  to_port           = 22
  protocol          = "tcp"
 # for each = var.ip_bitbucket
  cidr_blocks       = 
  security_group_id = data.aws_security_group.server_sg.id
}

How do i access the variable ip_bitbucket in cidr block?如何访问 cidr 块中的变量ip_bitbucket

I was trying with count and element but not getting clear idea我正在尝试使用countelement但没有弄清楚

You can use toset built-in function [1] for that:您可以为此使用toset内置 function [1]:

resource "aws_security_group_rule "server_rule" {
  for_each          = toset(var.ip_bitbucket)
  type              = "ingress"
  from_port         = 443
  to_port           = 22
  protocol          = "tcp"
  cidr_blocks       = [each.value]
  security_group_id = data.aws_security_group.server_sg.id
}

[1] https://developer.hashicorp.com/terraform/language/functions/toset [1] https://developer.hashicorp.com/terraform/language/functions/toset

The for_each argument requires either a map value (with any element type) or a set of strings. for_each参数需要一个 map 值(具有任何元素类型)或一组字符串。 Your input variable is currently declared as being a list, and so it isn't directly compatible with for_each .您的输入变量当前被声明为一个列表,因此它与for_each不直接兼容。

It seems like the order of the elements in ip_bitbucket has no significance and so I think the best answer would be to change the type constraint of that variable to be set(string) , which is a more accurate description of how you will use that value:似乎ip_bitbucket中元素的顺序没有意义,所以我认为最好的答案是将该变量的类型约束更改为set(string) ,这是对如何使用该值的更准确描述:

variable  "ip_bitbucket" {
  type = set(string)
}

However, you can specify more than one CIDR block in a single security group rule so you may not actually need for_each at all here:但是,您可以在单个安全组规则中指定多个 CIDR 块,因此您实际上可能根本不需要for_each

resource "aws_security_group_rule" "server_rule" {
  type              = "ingress"
  from_port         = 443
  to_port           = 22
  protocol          = "tcp"
  cidr_blocks       = var.ip_bitbucket
  security_group_id = data.aws_security_group.server_sg.id
}

The above will declare a single rule which applies to all of the given CIDR ranges.以上将声明适用于所有给定 CIDR 范围的单个规则。

If you do still want to use for_each then you can use var.ip_bitbucket as the for_each value once you've changed its type constraint as described above:如果仍然想使用for_each那么你可以使用var.ip_bitbucket作为for_each值,一旦你改变了它的类型约束,如上所述:

resource "aws_security_group_rule" "server_rule" {
  for_each = var.ip_bitbucket

  type              = "ingress"
  from_port         = 443
  to_port           = 22
  protocol          = "tcp"
  cidr_blocks       = [each.value]
  security_group_id = data.aws_security_group.server_sg.id
}

Noice that each.value needs to be in brackets here because each.value is just a single element from var.ip_bitbucket , and so it's a single string.请注意,这里的each.value需要放在方括号中,因为each.value只是var.ip_bitbucket中的一个元素,因此它是一个字符串。 cidr_blocks expects a set of strings. cidr_blocks需要一组字符串。

If some other part of your module that you've not shown here does rely on the specific ordering of the elements in var.ip_bitbucket then you could leave it declared as a list and then convert it to a set inside the for_each argument.如果此处未显示的模块的某些其他部分确实依赖于var.ip_bitbucket中元素的特定顺序,那么您可以将其声明为列表,然后将其转换为for_each参数中的集合。 However, I would recommend this only if you really do need to preserve the order of these elements, because users or future maintainers of your module may assume that the ordering is important if you declare it as a list.但是,只有当您确实需要保留这些元素的顺序时,我才会推荐这样做,因为如果您将它声明为列表,您的模块的用户或未来的维护者可能会认为顺序很重要。

variable  "ip_bitbucket" {
  type = list(string)
}

resource "aws_security_group_rule" "server_rule" {
  for_each = toset(var.ip_bitbucket)

  type              = "ingress"
  from_port         = 443
  to_port           = 22
  protocol          = "tcp"
  cidr_blocks       = [each.value]
  security_group_id = data.aws_security_group.server_sg.id
}

This is the same as the previous example except that the conversion from list to set happens explicitly with the toset function, rather than automatically as Terraform prepares the value of var.ip_bitbucket .这与前面的示例相同,除了从列表到集合的转换是使用toset function 显式发生的,而不是自动发生的,因为 Terraform 准备了var.ip_bitbucket的值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM