跳过至主要内容

数据源

数据源 允许 OpenTofu 使用在 OpenTofu 之外定义的信息,由另一个单独的 OpenTofu 配置定义,或者由函数修改。

每个 提供商 可能会在其一组 资源 类型旁边提供数据源。

使用数据源

通过一种称为数据资源的特殊类型的资源访问数据源,使用 data 块声明

代码块
data "aws_ami" "example" {
most_recent = true

owners = ["self"]
tags = {
Name = "app-server"
Tested = "true"
}
}

data 块请求 OpenTofu 从给定的数据源 ("aws_ami") 读取数据并将结果导出到给定的本地名称 ("example") 下。该名称用于在同一个 OpenTofu 模块中的其他地方引用此资源,但在模块范围之外没有意义。

数据源和名称共同充当给定资源的标识符,因此必须在模块内是唯一的。

在块体({} 之间)中是由数据源定义的查询约束。此部分中的大多数参数取决于数据源,实际上,在本例中,most_recentownerstags 都是专门为 aws_ami 数据源 定义的参数。

当与数据资源区分时,主要类型的资源(如由 resource 块声明)被称为管理资源。这两种类型的资源都接受参数并导出属性以供配置使用,但是管理资源会导致 OpenTofu 创建、更新和删除基础设施对象,而数据资源只会导致 OpenTofu 读取对象。为了简洁起见,当含义从上下文中明确时,管理资源通常简称为“资源”。

数据源参数

每个数据资源都与一个数据源相关联,该数据源决定它读取的对象(或对象)的类型以及哪些查询约束参数可用。

每个数据源又属于一个 提供商,它是 OpenTofu 的插件,提供了一组资源类型和数据源,这些资源类型和数据源通常属于单个云或本地基础设施平台。

data 块主体内的多数项目是由所选数据源定义的,并特定于所选数据源,这些参数可以充分利用 表达式 和其他动态 OpenTofu 语言功能。

但是,有一些“元参数”是由 OpenTofu 本身定义的,并且适用于所有数据源。这些参数通常对可以与它们一起使用的语言功能有额外的限制,并在以下部分中进行了更详细的描述。

数据资源行为

OpenTofu 在规划阶段尽可能读取数据资源,但在计划中宣布它必须推迟到应用阶段读取资源以保留操作顺序。

  • 给定的参数中至少有一个是管理资源属性或 OpenTofu 无法在应用步骤之前预测的其他值。
  • 数据资源直接依赖于管理资源,而管理资源本身在当前计划中具有计划的更改。
  • 数据资源具有 自定义条件,并且直接或间接依赖于管理资源,而管理资源本身在当前计划中具有计划的更改。

有关数据资源依赖于其他对象的含义的详细信息,请参阅 数据资源依赖项。此类数据资源的任何生成的属性在规划期间将是未知的,因此它不能在必须完全了解值的场景中使用。

仅限本地数据源

虽然许多数据源对应于通过远程网络 API 访问的基础设施对象类型,但一些专门的数据源仅在 OpenTofu 本身内运行,计算一些结果并将它们公开以供其他地方使用。

例如,仅限本地数据源存在于 渲染模板读取本地文件渲染 AWS IAM 策略 中。

仅限本地数据源的行为与所有其他数据源的行为相同,但它们的结果数据仅在 OpenTofu 操作期间暂时存在,并且每次创建新计划时都会重新计算。

数据资源依赖项

数据资源具有与 管理资源定义的相同依赖关系解析行为。在 data 块中设置 depends_on 元参数会推迟读取数据源,直到所有对依赖项的更改都已应用。

为了确保数据源在各种情况下访问尽可能最新的信息,直接引用管理资源的参数的处理方式与将资源列在 depends_on 中相同。可以通过间接地通过 local 值引用管理资源值来避免这种行为,除非数据资源本身具有 自定义条件

自定义条件检查

您可以使用preconditionpostcondition块来指定有关数据源运行方式的假设和保证。以下示例创建一个检查 AMI 是否具有正确标签的后置条件。

代码块
data "aws_ami" "example" {
id = var.aws_ami_id

lifecycle {
# The AMI ID must refer to an existing AMI that has the tag "nomad-server".
postcondition {
condition = self.tags["Component"] == "nomad-server"
error_message = "tags[\"Component\"] must be \"nomad-server\"."
}
}
}

自定义条件可以帮助捕获假设,帮助未来的维护人员了解配置设计和意图。它们还返回有关错误的有用信息,更早地并在上下文中返回,帮助消费者更轻松地诊断其配置中的问题。

有关更多详细信息,请参阅自定义条件检查

多个资源实例

数据资源支持countfor_each元参数,如为托管资源定义的那样,具有相同的语法和行为。

与托管资源一样,当存在countfor_each时,重要的是将资源本身与其创建的多个资源实例区分开来。每个实例都将使用约束参数的自身变体从其数据源中单独读取,从而产生一个索引结果。

选择非默认提供程序配置

数据资源支持provider元参数,如为托管资源定义的那样,具有相同的语法和行为。

生命周期自定义

数据资源没有为其生命周期提供任何自定义设置。但是,lifecycle块为将来版本保留。

示例

数据源配置如下所示

代码块
# Find the latest available AMI that is tagged with Component = web
data "aws_ami" "web" {
filter {
name = "state"
values = ["available"]
}

filter {
name = "tag:Component"
values = ["web"]
}

most_recent = true
}

描述

data块创建给定类型(第一个块标签)和名称(第二个块标签)的数据实例。类型和名称的组合必须是唯一的。

在块内({ })是数据实例的配置。配置取决于类型;与资源一样,公共 OpenTofu 注册表上的每个提供程序都有自己的文档,用于配置和使用其提供的数据类型。

每个数据实例都将导出一个或多个属性,这些属性可以在其他资源中用作data.<TYPE>.<NAME>.<ATTRIBUTE>形式的引用表达式。例如

代码块
resource "aws_instance" "web" {
ami = data.aws_ami.web.id
instance_type = "t1.micro"
}

元参数

由于数据源本质上是资源的只读子集,因此它们还支持资源的相同元参数,但lifecycle配置块除外。

非默认提供程序配置

资源类似,当模块对同一提供程序具有多个配置时,您可以使用provider元参数指定要使用的配置

代码块
data "aws_ami" "web" {
provider = aws.west

# ...
}

有关更多信息,请参阅资源provider元参数

数据源生命周期

如果数据实例的参数不包含对计算值的任何引用,例如尚未创建的资源的属性,那么数据实例将在 OpenTofu 的“刷新”阶段读取并更新其状态,默认情况下,该阶段在创建计划之前运行。这确保在计划期间检索到的数据可用,并且差异将显示获得的实际值。

数据实例参数可能引用计算值,在这种情况下,实例本身的属性直到其所有参数都定义后才能解析。在这种情况下,刷新数据实例将推迟到“应用”阶段,并且数据实例属性的所有插值将在计划中显示为“计算”,因为这些值尚未知。