- OpenTofu言語
- 変数と出力
- 入力変数
入力変数
入力変数を使用すると、モジュールのソースコードを変更することなく、モジュールの側面をカスタマイズできます。この機能により、異なる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 UIの出力を制限します。
- `nullable` - モジュール内で変数が `null` にできるかどうかを指定します。
デフォルト値
変数宣言には、 `default` 引数を含めることもできます。存在する場合、変数は *オプション* と見なされ、モジュールを呼び出したりOpenTofuを実行したりするときに値が設定されていない場合、デフォルト値が使用されます。 `default` 引数にはリテラル値が必要であり、構成内の他のオブジェクトを参照することはできません。
型制約
`variable` ブロックの `type` 引数を使用すると、変数の値として受け入れられる値の型を制限できます。型制約が設定されていない場合、任意の型の値が受け入れられます。
型制約はオプションですが、指定することをお勧めします。モジュールのユーザーにとって役立つリマインダーとなり、間違った型が使用された場合に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."
}
説明は、変数の目的と期待される値の種類を簡潔に説明する必要があります。この説明文字列は、モジュールに関するドキュメントに含まれる場合があるため、モジュールの保守者ではなく、ユーザーの視点から記述する必要があります。モジュール保守者向けのコメントには、コメントを使用してください。
カスタム検証ルール
対応する variable
ブロック内に validation
ブロックを追加することで、特定の変数にカスタム検証ルールを指定できます。以下の例では、AMI ID の構文が正しいかどうかを確認しています。
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"
の2つの引数もプラン出力に表示されません。
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 はブロック全体を編集済みとして扱う場合があります。これは、特定のタイプのすべてのブロックが一意である必要があるリソースタイプで発生し、1つのブロックの内容を開示すると、兄弟ブロックの内容が暗示される可能性があるためです。
# 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" が機密値であっても、プロバイダーは次のエラーを返す場合があります。"フィールド 'foo' の値が無効です"
リソース属性がプロバイダー定義のリソースIDとして、またはその一部として使用されている場合、apply
は値を公開します。以下の例では、prefix
属性は機密変数に設定されていますが、その値("jae")は後でリソースIDの一部として公開されます。
# 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]
Null入力値の許可しない
変数ブロックの nullable
引数は、モジュール呼び出し元が変数に値 null
を割り当てることができるかどうかを制御します。
variable "example" {
type = string
nullable = false
}
nullable
のデフォルト値は true
です。 nullable
が true
の場合、null
は変数の有効な値であり、モジュール構成は常に変数値が null
である可能性を考慮する必要があります。 null
値をモジュール入力引数として渡すと、default
値がオーバーライドされます。
nullable
を false
に設定すると、変数値がモジュール内で null
にならないことが保証されます。 nullable
が false
で、変数に default
値がある場合、モジュール入力引数が null
の場合、OpenTofu はデフォルト値を使用します。
nullable
引数は、変数の直接値が null
であるかどうかのみを制御します。リストやオブジェクトなどのコレクション型または構造体型の変数の場合は、コレクションまたは構造体自体がnullでない限り、呼び出し元はネストされた要素または属性で null
を使用できます。
入力変数値の使用
変数を宣言したモジュール内では、その値は 式 内から var.<NAME>
としてアクセスできます。ここで、<NAME>
は宣言ブロックで指定されたラベルと一致します。
入力変数は variable
ブロックによって *作成* されますが、var
という名前のオブジェクトの属性として *参照* します。
resource "aws_instance" "example" {
instance_type = "t2.micro"
ami = var.image_id
}
変数に割り当てられた値は、宣言されたモジュール内の式でのみアクセスできます。
ルートモジュール変数への値の割り当て
構成のルートモジュールで変数が宣言されている場合、それらはいくつかの方法で設定できます。
-var
コマンドラインオプションを使用して、個別に設定します。- 変数定義(
.tfvars
)ファイルで、コマンドラインで指定するか、自動的にロードします。 - 環境変数として設定します。
以下のセクションでは、これらのオプションについて詳しく説明します。このセクションは、モジュールで説明されているように、親モジュールの構成で入力変数の値が割り当てられる *子* モジュールには適用されません。
コマンドラインの変数
コマンドラインで個々の変数を指定するには、tofu plan
および tofu apply
コマンドを実行するときに -var
オプションを使用します。
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"}'
上記の例は、Linux や macOS などの Unix スタイルのシェルに適した構文を示しています。 Windows コマンドプロンプトの追加の例を含む、シェルクォートの詳細については、コマンドラインの入力変数を参照してください。
1つのコマンドで -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 コマンドを連続して実行する場合に役立ちます。たとえば、Unix システムの bash
プロンプトで
$ 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
オプション。指定された順序で処理されます。
マップ値とオブジェクト値を持つ変数は、他の変数と同じように動作します。最後に見つかった値が以前の値を上書きします。これは、マップ値を上書きするのではなく*マージする*以前のバージョンの OpenTofu からの変更です。