我正在使用Terraform版本0.12。如果具有相同名称的资源已经存在,我需要跳过资源创建。
我为此做了以下事情:
阅读自定义图像列表,
data "ibm_is_images" "custom_images" {
}
检查图像是否已经存在,
locals {
custom_vsi_image = contains([for x in data.ibm_is_images.custom_images.images: "true" if x.visibility == "private" && x.name == var.vnf_vpc_image_name], "true")
}
output "abc" {
value="${local.custom_vsi_image}"
}
仅当图像存在为false时创建。
resource "ibm_is_image" "custom_image" {
count = "${local.custom_vsi_image == true ? 0 : 1}"
depends_on = ["data.ibm_is_images.custom_images"]
href = "${local.image_url}"
name = "${var.vnf_vpc_image_name}"
operating_system = "centos-7-amd64"
timeouts {
create = "30m"
delete = "10m"
}
}
第一次使用“ terraform apply”可以正常工作。它发现该图像不存在,因此创建了图像。
当我第二次运行“ terraform apply”时。它正在删除上面创建的资源“ custom_image”。知道为什么第二次运行该资源时会删除该资源吗?
此外,如何根据某种条件(例如仅在不存在时)创建资源?
答案 0 :(得分:8)
在Terraform中,您需要明确决定哪个系统负责特定对象的管理,反之,哪些系统只是消耗一个现有对象。无法动态地做出该决定,因为这将使结果不确定,并且-对于Terraform管理的对象-不清楚哪个配置terraform destroy
会破坏该对象。
的确,这种不确定性是为什么您会在尝试创建然后删除资源之间看到Terraform情况的原因:您告诉Terraform仅在该对象不存在时对其进行管理,因此,在Terraform存在后第一次运行Terraform时,它将看到该对象不再受管理,因此将计划销毁它。
如果您的目标是使用Terraform管理所有内容,那么一项重要的设计任务就是确定对象依赖关系如何在Terraform配置内部和之间流动。在您的情况下,似乎在管理图像的系统(可能是或不是Terraform配置)与使用现有图像的一个或多个Terraform配置之间存在生产者/消费者关系。
如果图像由Terraform管理,则表明您的主要Terraform配置应假定图像不存在并无条件地创建它-如果您决定图像是由所有者拥有的与使用它的系统相同-或应假定图像确实已经存在,并使用data
块检索有关它的信息。
这里可能的解决方案是编写一个单独的Terraform配置来管理映像,然后仅在预计该对象不存在的情况下应用该配置。然后,使用现有映像的配置可以假设它存在而无需关心它是否由其他Terraform配置创建。
“地形”文档部分Module Composition,尤其是子部分Conditional Creation of Objects中对此情况有更详细的概述。该指南侧重于单个配置中模块之间的交互,但是相同的基本原理也适用于(通过数据源) 配置之间的依赖性。