Spec-Zone.ru › OpenTofu 1.9

Входные переменные

Входные переменные позволяют настраивать отдельные аспекты модулей, не изменяя исходный код самого модуля. Благодаря этой возможности модули можно использовать в разных конфигурациях OpenTofu, что делает их компонуемыми и повторно используемыми.

Объявив переменные в корневом модуле конфигурации, вы можете задавать их значения с помощью параметров CLI и переменных окружения. Если вы объявляете их в дочерних модулях, вызывающий модуль должен передавать значения в блоке module.

Если вы знакомы с традиционными языками программирования, будет полезно сравнить модули с определениями функций:

  • Входные переменные похожи на аргументы функции.
  • Выходные значения похожи на возвращаемые функцией значения.
  • Локальные значения похожи на временные локальные переменные функции.
Примечание

Для краткости входные переменные часто называют просто «переменными» или «переменными OpenTofu», если из контекста ясно, о каком типе переменных идёт речь. К другим типам переменных в OpenTofu относятся переменные окружения (задаваемые оболочкой, в которой работает OpenTofu) и переменные выражений (используемые для косвенного представления значения в выражении).

Объявление входной переменной​

Каждую входную переменную, принимаемую модулем, необходимо объявить с помощью блока variable:

Блок кода
variable "image_id" {
  type = string
}

variable "availability_zone_names" {
  type    = list(string)
  default = ["us-west-1a"]
}

variable "docker_ports" {
  type = list(object({
    internal = number
    external = number
    protocol = string
  }))
  default = [
    {
      internal = 8300
      external = 8300
      protocol = "tcp"
    }
  ]
}

Метка после ключевого слова variable задаёт имя переменной, которое должно быть уникальным среди всех переменных одного модуля. Это имя используется для присваивания переменной значения извне и для обращения к её значению внутри модуля.

Имя переменной может быть любым допустимым идентификатором, кроме следующих: source, version, providers, count, for_each, lifecycle, depends_on, locals.

Эти имена зарезервированы для метааргументов в блоках конфигурации модулей и не могут использоваться в качестве имён переменных.

Аргументы​

OpenTofu CLI определяет следующие необязательные аргументы для объявлений переменных:

  • default — значение по умолчанию, которое делает переменную необязательной.
  • type — этот аргумент задаёт типы значений, допустимые для переменной.
  • description — описание входной переменной.
  • validation — блок для определения правил проверки, обычно дополняющих ограничения типов.
  • sensitive — ограничивает вывод OpenTofu в интерфейсе командной строки, когда переменная используется в конфигурации.
  • nullable — задаёт, может ли переменная иметь значение null в модуле.

Значения по умолчанию​

Объявление переменной также может содержать аргумент default. Если он указан, переменная считается необязательной, и значение по умолчанию будет использоваться, если при вызове модуля или запуске OpenTofu значение не задано. Аргумент default требует литерального значения и не может ссылаться на другие объекты конфигурации.

Ограничения типов​

Аргумент type в блоке variable позволяет ограничить тип значения, допустимый для переменной. Если ограничение типа не задано, принимаются значения любого типа.

Хотя ограничения типов необязательны, мы рекомендуем указывать их: они могут служить полезными подсказками для пользователей модуля и позволяют OpenTofu выдавать понятное сообщение об ошибке, если используется значение неправильного типа.

Ограничения типов составляются из ключевых слов и конструкторов типов. Поддерживаются следующие ключевые слова типов:

  • string
  • number
  • bool

Конструкторы типов позволяют задавать сложные типы, например коллекции:

  • list(<TYPE>)
  • set(<TYPE>)
  • map(<TYPE>)
  • object({<ATTR NAME> = <TYPE>, ... })
  • tuple([<TYPE>, ...])

Ключевое слово any можно использовать, чтобы указать, что допустим любой тип. Дополнительные сведения о значении и поведении этих типов, а также подробную информацию об автоматическом преобразовании сложных типов см. в разделе Ограничения типов.

Если указаны аргументы type и default, заданное значение по умолчанию должно быть преобразуемым в указанный тип.

Описание входных переменных​

Поскольку входные переменные модуля являются частью его пользовательского интерфейса, вы можете кратко описать назначение каждой переменной с помощью необязательного аргумента description:

Блок кода
variable "image_id" {
  type        = string
  description = "The id of the machine image (AMI) to use for the server."
}

Описание должно кратко объяснять назначение переменной и ожидаемый тип значения. Эта строка описания может включаться в документацию модуля, поэтому её следует составлять с точки зрения пользователя модуля, а не его сопровождающего. Для комментариев, предназначенных сопровождающим модуля, используйте комментарии.

Пользовательские правила проверки​

Вы можете задать пользовательские правила проверки для конкретной переменной, добавив блок validation в соответствующий блок variable. Пример ниже проверяет, соответствует ли идентификатор AMI правильному синтаксису.

Блок кода
variable "image_id" {
  type        = string
  description = "The id of the machine image (AMI) to use for the server."

  validation {
    condition     = length(var.image_id) > 4 && substr(var.image_id, 0, 4) == "ami-"
    error_message = "The image_id value must be a valid AMI id, starting with \"ami-\"."
  }
}

Дополнительные сведения см. в разделе Пользовательские проверки условий.

Сокрытие значений в выводе CLI​

Если пометить переменную как sensitive, OpenTofu не будет показывать её значение в выводе plan или apply, когда эта переменная используется в другом месте конфигурации.

При этом OpenTofu всё равно записывает конфиденциальные значения в состояние, поэтому любой, у кого есть доступ к данным состояния, сможет просмотреть конфиденциальные значения в открытом виде. Дополнительные сведения см. в разделе Конфиденциальные данные в состоянии.

Объявите переменную конфиденциальной, задав аргумент sensitive в значение true:

Блок кода
variable "user_information" {
  type = object({
    name    = string
    address = string
  })
  sensitive = true
}

resource "some_resource" "a" {
  name    = var.user_information.name
  address = var.user_information.address
}

Любые выражения, результат которых зависит от конфиденциальной переменной, также будут считаться конфиденциальными, поэтому в приведённом выше примере два аргумента resource "some_resource" "a" также будут скрыты в выводе плана:

Блок кода
OpenTofu will perform the following actions:

  # some_resource.a will be created
  + resource "some_resource" "a" {
      + name    = (sensitive value)
      + address = (sensitive value)
    }

Plan: 1 to add, 0 to change, 0 to destroy.

В некоторых случаях, когда конфиденциальная переменная используется во вложенном блоке, OpenTofu может скрыть содержимое всего блока. Это происходит для типов ресурсов, у которых все блоки определённого типа должны быть уникальными, поэтому раскрытие содержимого одного блока может привести к раскрытию содержимого соседнего блока.

Блок кода
  # some_resource.a will be updated in-place
  ~ resource "some_resource" "a" {
      ~ nested_block {
          # At least one attribute in this block is (or was) sensitive,
          # so its contents will not be displayed.
        }
    }

Провайдер также может объявить атрибут конфиденциальным, в результате чего OpenTofu будет скрывать его в обычном выводе независимо от того, какое значение ему присвоено. Дополнительные сведения см. в разделе Конфиденциальные атрибуты ресурсов.

Если вы используете конфиденциальное значение в составе выходного значения, OpenTofu потребует также пометить само выходное значение как конфиденциальное, чтобы подтвердить, что вы намеренно его экспортируете.

Случаи, когда OpenTofu может раскрыть конфиденциальную переменную​

Переменная sensitive — это концепция, относящаяся к конфигурации, и значения передаются провайдерам без маскировки. Ошибка провайдера может раскрыть значение, если оно содержится в сообщении об ошибке. Например, провайдер может вернуть следующую ошибку, даже если "foo" — конфиденциальное значение: "Invalid value 'foo' for field"

Если атрибут ресурса используется в качестве идентификатора ресурса, определяемого провайдером, или его части, то значение будет раскрыто в apply. В примере ниже атрибут prefix задан как конфиденциальная переменная, но затем это значение ("jae") раскрывается в составе идентификатора ресурса:

Блок кода
  # random_pet.animal will be created
  + resource "random_pet" "animal" {
      + id        = (known after apply)
      + length    = 2
      + prefix    = (sensitive value)
      + separator = "-"
    }

Plan: 1 to add, 0 to change, 0 to destroy.

...

random_pet.animal: Creating...
random_pet.animal: Creation complete after 0s [id=jae-known-mongoose]

Запрет нулевых входных значений​

Аргумент nullable в блоке переменной определяет, может ли вызывающий модуль присвоить переменной значение null.

Блок кода
variable "example" {
  type     = string
  nullable = false
}

Значение по умолчанию для nullable — true. Когда nullable имеет значение true, null является допустимым значением переменной, и конфигурация модуля всегда должна учитывать возможность того, что значение переменной равно null. Передача значения null в качестве входного аргумента модуля переопределит любое значение default.

Если задать для nullable значение false, значение переменной никогда не будет null внутри модуля. Если nullable имеет значение false, а у переменной есть значение default, OpenTofu использует значение по умолчанию, если входной аргумент модуля имеет значение null.

Аргумент nullable управляет только тем, где прямое значение переменной может быть null. Для переменных с типами коллекций или структур, например списков и объектов, вызывающий модуль по-прежнему может использовать null во вложенных элементах или атрибутах, если сама коллекция или структура не равна null.

Использование значений входных переменных​

Внутри модуля, в котором объявлена переменная, к её значению можно обращаться в выражениях как к var.<NAME>, где <NAME> соответствует метке, указанной в блоке объявления:

Примечание

Входные переменные создаются блоком variable, но обращаются к ним как к атрибутам объекта с именем var.

Блок кода
resource "aws_instance" "example" {
  instance_type = "t2.micro"
  ami           = var.image_id
}

Присвоенное переменной значение можно использовать только в выражениях внутри модуля, где она объявлена.

Присваивание значений переменным корневого модуля​

Переменным, объявленным в корневом модуле конфигурации, можно задавать значения несколькими способами:

  • По отдельности, с помощью параметра командной строки -var.
  • В файлах определений переменных (.tfvars), указанных в командной строке или загружаемых автоматически.
  • В качестве переменных окружения.

В следующих разделах эти параметры описаны подробнее. Этот раздел не относится к дочерним модулям, где значения входных переменных задаются в конфигурации родительского модуля, как описано в разделе Модули.

Переменные в командной строке​

Чтобы указать отдельные переменные в командной строке, используйте параметр -var при запуске команд tofu plan и tofu apply:

Блок кода
tofu apply -var="image_id=ami-abc123"
tofu apply -var='image_id_list=["ami-abc123","ami-def456"]' -var="instance_type=t2.micro"
tofu apply -var='image_id_map={"us-east-1":"ami-abc123","us-east-2":"ami-def456"}'

В приведённых выше примерах используется синтаксис, подходящий для оболочек Unix, например в Linux или macOS. Дополнительные сведения о кавычках в командной оболочке, в том числе примеры для командной строки Windows, см. в разделе Входные переменные в командной строке.

Вы можете использовать параметр -var несколько раз в одной команде, чтобы задать значения нескольких переменных.

Файлы определений переменных (.tfvars)​

Чтобы задать много переменных, удобнее указать их значения в файле определений переменных (имя файла должно заканчиваться на .tfvars или .tfvars.json), а затем указать этот файл в командной строке с помощью -var-file:

Блок кода
tofu apply -var-file="testing.tfvars"

В файлах определений переменных используется тот же базовый синтаксис, что и в файлах языка OpenTofu, но они содержат только присваивания значений переменным:

Блок кода
image_id = "ami-abc123"
availability_zone_names = [
  "us-east-1a",
  "us-west-1c",
]

OpenTofu также автоматически загружает несколько файлов определений переменных, если они существуют:

  • Файлы с точными именами terraform.tfvars или terraform.tfvars.json.
  • Любые файлы, имена которых заканчиваются на .auto.tfvars или .auto.tfvars.json.

Файлы, имена которых заканчиваются на .json, вместо этого обрабатываются как объекты JSON, где свойства корневого объекта соответствуют именам переменных:

Блок кода
{
  "image_id": "ami-abc123",
  "availability_zone_names": ["us-west-1a", "us-west-1c"]
}

Переменные окружения​

В качестве запасного способа задания переменных OpenTofu ищет в окружении собственного процесса переменные окружения, имена которых начинаются с TF_VAR_, за которым следует имя объявленной переменной.

Это может быть полезно при запуске OpenTofu в автоматизированной среде или при последовательном выполнении нескольких команд OpenTofu с одними и теми же переменными. Например, в приглашении bash в системе Unix:

Блок кода
$ export TF_VAR_image_id=ami-abc123
$ tofu plan
...

В операционных системах, где имена переменных окружения чувствительны к регистру, OpenTofu ищет имя переменной в точном соответствии с конфигурацией, поэтому имя нужной переменной окружения обычно содержит прописные и строчные буквы, как в примере выше.

Значения сложных типов​

Если значения переменных задаются в файле определений переменных, для присваивания значений сложных типов, например списков и отображений, можно использовать обычный синтаксис литеральных выражений OpenTofu.

Для параметра командной строки -var и переменных окружения действуют особые правила. Для удобства OpenTofu по умолчанию интерпретирует значения -var и переменных окружения как буквальные строки, для которых достаточно кавычек командной оболочки и не нужны специальные кавычки OpenTofu. Например, в оболочке Unix:

Блок кода
$ export TF_VAR_image_id='ami-abc123'

Однако если для переменной корневого модуля задано ограничение типа, требующее сложного значения (списка, множества, отображения, объекта или кортежа), OpenTofu попытается обработать его с помощью того же синтаксиса, что используется в файлах определений переменных. При этом необходимо внимательно соблюдать правила экранирования строк в командной оболочке:

Блок кода
$ export TF_VAR_availability_zone_names='["us-west-1b","us-west-1d"]'

Для удобства чтения и чтобы не беспокоиться об экранировании в командной оболочке, мы рекомендуем всегда задавать сложные значения переменных через файлы определений переменных. Дополнительные сведения о кавычках и экранировании аргументов -var см. в разделе Входные переменные в командной строке.

Значения необъявленных переменных​

Если вы задали значение переменной, но не объявили соответствующую ей variable {}, в зависимости от способа задания значения может появиться ошибка или предупреждение.

Если вы задаёте значения необъявленных переменных с помощью переменных окружения, ошибка или предупреждение не появятся. Это связано с тем, что переменные окружения могут быть объявлены, но не использоваться во всех запускаемых конфигурациях.

Если вы задаёте значения необъявленных переменных в файле, появится предупреждение. Это помогает выявить случаи, когда вы задали значение переменной, предназначенное для объявления переменной, но, возможно, допустили ошибку в определении значения. Например, для следующей конфигурации:

Блок кода
variable "moose" {
  type = string
}

и следующего файла .tfvars:

Блок кода
mosse = "Moose"

OpenTofu предупредит, что переменная "mosse" не объявлена, что поможет обнаружить эту ошибку.

Если вы используете файлы .tfvars для нескольких конфигураций и ожидаете, что это предупреждение будет появляться и дальше, можно использовать параметр -compact-warnings, чтобы сократить вывод.

Если вы задаёте значения необъявленных переменных в командной строке, OpenTofu вернёт ошибку. Чтобы избежать этой ошибки, объявите блок переменной для этого значения или удалите значение переменной из вызова OpenTofu.

Приоритет определения переменных​

Описанные выше способы задания переменных можно использовать в любых сочетаниях. Если одной переменной присвоено несколько значений, OpenTofu использует последнее найденное значение, заменяя все предыдущие. Обратите внимание: одной переменной нельзя присвоить несколько значений в рамках одного источника.

OpenTofu загружает переменные в следующем порядке; более поздние источники имеют приоритет над предыдущими:

  • Переменные окружения
  • Файл terraform.tfvars, если он существует.
  • Файл terraform.tfvars.json, если он существует.
  • Все файлы *.auto.tfvars или *.auto.tfvars.json, обработанные в лексикографическом порядке имён файлов.
  • Все параметры -var и -var-file командной строки в порядке их указания.
Важно

Переменные со значениями типа map и object ведут себя так же, как и другие переменные: последнее найденное значение заменяет предыдущие. Это изменение по сравнению с предыдущими версиями OpenTofu, в которых значения map объединялись, а не заменялись.

Copyright (c) The OpenTofu Authors
Copyright (c) 2014 HashiCorp, Inc.
Mozilla Public License, version 2.0
https://opentofu.org/docs/v1.9/language/values/variables/

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API