vars.tf
Terraform変数ファイル()とMakefileという2つのファイルがあります。
私が望むのは、Makefileにvars.tf
Terraformファイルの一部の変数を「読み取る」ことです。
文書vars.tf
:
variable "region" {
default = "us-west-1"
description = "AWS Region"
}
variable "profile" {
default = "bobs-profile"
description = "Please enter your AWS CLI profile name"
}
variable "env" {
default = "dev"
description = "Please label the environment this infrastructure will be deployed to eg dev, uat, prod"
}
vars.tf
Makefileのファイルにリストされている変数を呼び出すことができるようにしたいです。ここに簡単な例があります。
.ONESHELL:
.SHELL := /usr/bin/bash
.PHONY: apply plan prep
VARS="variables/$(ENV)-$(REGION).tfvars"
CURRENT_FOLDER=$(shell basename "$$(pwd)")
AWS_PROFILE"bobs-profile"
たとえば、次の値が必要です。
$(ENV)
$(REGION)
$(AWS_PROFILE)
vars.tf
Makefileが次の変数として実行されるように、Terraformファイルから抽出します。
ENV=dev
REGION=us-west-1
AWS_PROFILE=bobs-profile
これを達成する方法はありますか?
答え1
表示されるファイルは、HCL(HashiCorp構成言語)で作成されました。 JSONに変換して使用できますjq
。
HCLファイルをJSONに変換するには、次のものを使用できますyj
。https://github.com/sclevine/yj)。これにより、次のコマンドがすでにjq
生成されている可能性がありますmake
。
eval "$(
yj -cj <vars.tf |
jq -r '
[
"make",
(.variable[] | keys[]) as $key |
"\($key)=\(.variable[][$key][].default)"
] | @sh'
)"
与えられた例では、次のコマンドが生成されます。
'make' 'env=dev' 'profile=bobs-profile' 'region=us-west-1'
評価時に名前付き変数を実行しmake
、記載された値に設定します。変数は必要に応じて小文字で表示されます。たとえば、この設定は、ENV
Makefileのシェルコマンドの実行方法に影響を与える可能性があります(ENV
これは、シェルの起動時にインポートする必要があるファイルを指すことができるシェルの特殊変数です)。
変数と値をタブ区切りリストにインポートして、シェルから読み取ることもできます。
set --
yj -cj <vars.tf |
jq -r '
(.variable[] | keys[]) as $key |
[ $key, .variable[][$key][].default ] |
@tsv' |
{
while IFS=$'\t' read -r key value; do
set -- "$@" "$key"="$value"
done
make "$@"
}
次に、位置引数リストの変数とその値を収集し、make
それを使用して呼び出します。問題の文書を考慮すると、実行されるコマンドは次のとおりです。
make 'env=dev' 'profile=bobs-profile' 'region=us-west-1'
ちなみに、上記で作成したJSONドキュメントyj
は次のとおりです。
{
"variable": [
{
"region": [
{
"default": "us-west-1",
"description": "AWS Region"
}
],
"profile": [
{
"default": "bobs-profile",
"description": "Please enter your AWS CLI profile name"
}
],
"env": [
{
"default": "dev",
"description": "Please label the environment this infrastructure will be deployed to eg dev, uat, prod"
}
]
}
]
}
答え2
GNUがあると仮定すると、make
このshell
コマンドを使用して外部コマンドの結果をMakefile変数に割り当てることができます。
あなたの場合は、次のものを使用できます。
ENV:=$(shell awk '$$1=="variable" && $$2=="\"env\"" {i=1} $$1=="}" {i=0} i && $$1=="default" {split($$0,a,"\""); print a[2]}' test.tf)
REGION:=$(shell awk '$$1=="variable" && $$2=="\"region\"" {i=1} $$1=="}" {i=0} i && $$1=="default" {split($$0,a,"\""); print a[2]}' test.tf)
AWS_PROFILE:=$(shell awk '$$1=="variable" && $$2=="\"profile\"" {i=1} $$1=="}" {i=0} i && $$1=="default" {split($$0,a,"\""); print a[2]}' test.tf)
variable
これはで始まり、終わる関心領域を探し}
、「正しい」領域が見つかったらフラグを設定します。i
対応するフラグが設定され、キーワードのある行が見つかったら、default
二重引用符()で要素を抽出します" ... "
。
double は ( にかかわらず ) 内容全体を解釈し、リテラルをコマンドに渡すため、前に他のものを追加して「エスケープ」する必要があるため$$
必要です。make
$( ... )
' ... '
$
shell
$
わずかに薄くなりますが(3つの構文解析された構造はすべて基本的に同じであるため、ループ構成が優れています)、うまくいくはずです。