terraform:通过模块传递列表,得到“错误:...应该是一个列表"; [英] terraform: passing list through modules, getting "Error:... should be a list"

查看:14
本文介绍了terraform:通过模块传递列表,得到“错误:...应该是一个列表";的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

ETA:在 terraform github 问题中找到讨论,https://github.com/hashicorp/terraform/issues/13103.已知且非常...特殊"...问题.

<小时>

通过其他两个模块(从 top.tfautoscaling_grouplaunch_configuration)传递一个列表后,这两个模块都将变量定义为type = "list",我收到了来自 terraform plan 的以下投诉:

错误:module.autoscaling_group.aws_launch_configuration.this:security_groups:应该是一个列表"

它似乎将参数识别为列表类型(如果我从变量声明中删除类型规范,它会抱怨).但我发现消除错误的唯一方法是将最终用法包含在列表括号中.这似乎违反直觉(当我这样做时,我还没有看到 apply 会发生什么) - 发生了什么?

<小时>

顺序:

  • top.tf 调用 security_group.
  • top.tf 还调用 autoscaling,传递带有安全组 id 输出的列表.
  • autoscaling 调用 launch_configuration,传递参数.

这是布局,下面是.tf文件的内容.

<代码>.├── autoscaling_group│ └── main.tf├── 启动配置│ └── main.tf├── 安全组│ └── main.tf└── top.tf

top.tf 中的初始调用是:

模块autoscaling_group"{源 =启动配置"security_groups = ["${module.security_group.id}"]}

有问题的用法在 launch_configuration/main.tf:

资源aws_launch_configuration"this"{name_prefix = "foobar"image_id = "this_is_fake"instance_type = "ts.small"security_groups = "${var.security_groups}"}

  • 如果我添加括号:["${var.security_groups}"] 我没有收到错误.
  • 如果我从 launch_configuration/main.tf 的变量定义块中删除 type = "list"terraform plan 会报错:module.autoscaling_group.var.security_groups:模块autoscaling_group中的变量security_groups应该是字符串类型,得到列表
<小时>

top.tf的内容:

提供者aws"{地区=我们-东-1"}模块安全组"{源 =安全组"}模块自动缩放组"{源 =启动配置"security_groups = ["${module.security_group.id}"]}

autoscaling_group/main.tf的内容:

变量security_groups"{类型=列表"description = "附加到已启动实例的安全组."}模块启动配置"{源 =启动配置"security_groups = "${var.security_groups}"}资源aws_autoscaling_group"service_autoscaling_group"{name_prefix = "foobar"min_size = 1最大尺寸 = 1health_check_type = "EC2"启动配置 = "${module.launch_configuration.name}"vpc_zone_identifier = [this_is_fake"]}

launch_configuration/main.tf的内容:

变量security_groups"{类型=列表"description = "附加到已启动实例的安全组."}输出名称"{值 = "${aws_launch_configuration.this.name}"}资源aws_launch_configuration"这个"{name_prefix = "foobar"image_id = "this_is_fake"instance_type = "ts.small"security_groups = "${var.security_groups}"}

再一次,如果我在最后一个赋值 ["${var.security_groups}"] 的 RHS 周围加上括号,我看不到 terraform plan.但是 terraform 将变量识别为列表(因为如果我从声明中删除 type = "list" ,它会抱怨它是列表类型).那么为什么它抱怨它需要一个列表呢?

security_group/main.tf的内容:

输出id"{值 = "${aws_security_group.this.id}"description = "安全组 ID."}资源aws_security_group"这个"{name_prefix = "foobar"vpc_id = "this_is_fake"描述=foobar"出口{从端口 = 0to_port = 0协议 =-1"cidr_blocks = [0.0.0.0/0"]}}

解决方案

我遇到了同样的问题,应该在 v0.12 中解决:https://github.com/hashicorp/terraform/issues/18923#issuecomment-434901762

如果您想将列表作为模块参数传递,这里有一个小技巧.我只是发送一个字符串,然后将其解析为一个列表(AWS Backup 模块的示例):

<块引用>

terraform.tf

模块你的模块"{源 = "./module_path"list_as_string = "${var.element_1};${var.element_1}"}

<块引用>

./module_path/variables.tf

变量list_as_string"{description = "字符串列表"}

<块引用>

./module_path/main.tf

资源资源"示例"{real_list = ["${split(";", var.list_as_string)}"]}

ETA: Found discussion in terraform github issues, https://github.com/hashicorp/terraform/issues/13103. Known and very... "idiosyncratic"... issue.


After passing a list through two other modules (from top.tf through autoscaling_group to launch_configuration), both of which define the variable as type = "list", I'm getting the following complaint from terraform plan:

"Error: module.autoscaling_group.aws_launch_configuration.this: 
security_groups: should be a list"

It seems to recognize the parameter as a list type (if I remove the type specification from the variable declaration, it complains). But the only way I find to silence the error is to wrap the final usage in list brackets. This seems counterintuitive (and I haven't seen what happens with apply when I do so) - what's going on?


The sequence:

  • top.tf calls security_group.
  • top.tf also calls autoscaling, passing a list with the security group id output.
  • autoscaling calls launch_configuration, passing the parameter through.

Here's the layout, contents of .tf files is below.

.
├── autoscaling_group
│   └── main.tf
├── launch_configuration
│   └── main.tf
├── security_group
│   └── main.tf
└── top.tf

The initiating call in top.tf is:

module "autoscaling_group" {
  source = "launch_configuration"
  security_groups = ["${module.security_group.id}"]
  }

The offending usage is in launch_configuration/main.tf:

resource "aws_launch_configuration" "this" {
  name_prefix = "foobar"
  image_id = "this_is_fake"
  instance_type = "ts.small"
  security_groups = "${var.security_groups}"
  }

  • If I add brackets: ["${var.security_groups}"] I don't get the error.
  • If I remove the type = "list" from the variable definition block in launch_configuration/main.tf, terraform plan complains: module.autoscaling_group.var.security_groups: variable security_groups in module autoscaling_group should be type string, got list

The content of top.tf:

provider "aws" {
  region = "us-east-1"
  }

module "security_group" {
  source = "security_group"
  }

module "autoscaling_group" {
  source = "launch_configuration"
  security_groups = ["${module.security_group.id}"]
  }

The content of autoscaling_group/main.tf:

variable "security_groups" {
  type = "list"
  description = "The security groups to attach to launched instances."
  }

module "launch_configuration" {
  source = "launch_configuration"
  security_groups = "${var.security_groups}"
  }

resource "aws_autoscaling_group" "service_autoscaling_group" {

  name_prefix = "foobar"

  min_size = 1
  max_size = 1
  health_check_type = "EC2"
  launch_configuration = "${module.launch_configuration.name}"
  vpc_zone_identifier = ["this_is_fake"]
  }

The content of launch_configuration/main.tf:

variable "security_groups" {
  type = "list"
  description = "The security groups to attach to launched instances."
  }

output "name" {
  value = "${aws_launch_configuration.this.name}"
  }

resource "aws_launch_configuration" "this" {
  name_prefix = "foobar"
  image_id = "this_is_fake"
  instance_type = "ts.small"
  security_groups = "${var.security_groups}"
  }

Again, if I wrap brackets around the RHS of the last assignment ["${var.security_groups}"], I don't see the error from terraform plan. But terraform recognizes the variable as a list (since it complains about it being a list type if I remove the type = "list" from the declaration). So why does it complain that it expects a list here?

The content of security_group/main.tf:

output "id" {
  value = "${aws_security_group.this.id}"
  description = "The security group ID."
  }

resource "aws_security_group" "this" {

  name_prefix = "foobar"
  vpc_id      = "this_is_fake"
  description = "foobar"

  egress {
    from_port       = 0
    to_port         = 0
    protocol        = "-1"
    cidr_blocks     = ["0.0.0.0/0"]
    }
  }

解决方案

I had the same issue, it should be resolved in the v0.12 : https://github.com/hashicorp/terraform/issues/18923#issuecomment-434901762

If you want to pass a list as module parameter here is a small hack to do it. I just send a string and then parse it to a list (Example with AWS Backup module) :

terraform.tf

module "your_module" {
  source = "./module_path"

  list_as_string = "${var.element_1};${var.element_1}"
}

./module_path/variables.tf

variable "list_as_string" {
  description = "List in string"
}

./module_path/main.tf

resource "resource" "exemple" {
  real_list = ["${split(";", var.list_as_string)}"]
}

这篇关于terraform:通过模块传递列表,得到“错误:...应该是一个列表";的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆