yttに入門してみた
今回は、yttをを用いてYAMLファイルを生成する方法について学習してみました。
yttとは?
公式サイトによると、
Template and patch as needed to easily make your configuration reusable and extensible. Works with your own and third-party YAML configuration.
ということで、YAMLファイルについてテンプレートとパッチを適用することで、設定を簡単に再利用・拡張できるツールということです。YAMLファイルは基本的には静的に指定した値を利用するものですが、yttを用いることでファイルの内容を生成することができます。
使ってみる
公式サイトにてGetting Startedが提供されているので、その内容をもとにいろいろ試してみます。なお、利用するファイルはKubernetesを想定したものも利用します。
インストール
yttのインストール方法はこちらにまとめられています。私の環境ではmacbookなので以下でインストールしました。
brew tap carvel-dev/carvel
brew install ytt
変数の利用
例えば以下のように、同じラベルが複数設定されているYAMLファイルがあったとします。
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app.kubernetes.io/component: controller
app.kubernetes.io/name: app-name
app.kubernetes.io/version: v1.0.0
name: app-name
namespace: default
spec:
replicas: 1
selector:
matchLabels:
app.kubernetes.io/component: controller
app.kubernetes.io/name: app-name
内容を見ると、app-nameという名前でいくつかの値が登録されていることがわかります。これらの値が変わった時に全てを変更する必要がなくなるようにするのがyttで実現でき、以下のようにします。
#@ app_name = "app-name"
#@ version = "v1.0.0"
---
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app.kubernetes.io/component: controller
app.kubernetes.io/name: #@ app_name
app.kubernetes.io/version: #@ version
name: #@ app_name
namespace: default
spec:
replicas: 1
selector:
matchLabels:
app.kubernetes.io/component: controller
app.kubernetes.io/name: #@ app_name
それではこの設定ファイルから反映された結果のYAMLを生成させてみましょう。以下のコマンドを実行することで生成できます。
ytt -f config.yaml
すると、出力は当初作成していたファイルが生成されます。
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app.kubernetes.io/component: controller
app.kubernetes.io/name: app-name
app.kubernetes.io/version: v1.0.0
name: app-name
namespace: default
spec:
replicas: 1
selector:
matchLabels:
app.kubernetes.io/component: controller
app.kubernetes.io/name: app-name
フラグメントによる制御
例えばあるフラグが指定されている時とない時で結果を制御したいような場合、以下のようにすることで実現できます。
#@ app_name = "prometheus-operator"
#@ version = "v0.39.0"
#@ def labels(with_version=False):
app.kubernetes.io/component: controller
app.kubernetes.io/name: #@ app_name
#@ if with_version:
app.kubernetes.io/version: #@ version
#@ end
#@ end
---
apiVersion: apps/v1
kind: Deployment
metadata:
labels: #@ labels(with_version=False)
name: #@ app_name
namespace: default
こちらの設定では、labelsという関数を定義し、with_version=Trueの時はapp.kubernetes.io/versionが指定されますが、with_version=Falseの時は指定されません。その制御は関数呼び出し元で行い、先ほどの例ではlabels: #@ labels(with_version=False) の部分に該当します。
それではそれぞれTrue/Falseにした時の結果をみてみましょう。
`with_version=True`の場合
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app.kubernetes.io/component: controller
app.kubernetes.io/name: prometheus-operator
app.kubernetes.io/version: v0.39.0
name: prometheus-operator
namespace: default
`with_version=False`の場合
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
app.kubernetes.io/component: controller
app.kubernetes.io/name: prometheus-operator
name: prometheus-operator
namespace: default
この結果のように、フラグを用いて制御できていることが確認できます。
別YAMLファイルからデータを読み込む
先ほどまでの例では一つのYAMLファイル内に変数の定義だったりをしていますが、頻繁に変更されるような値をそのファイル内で定義するのはアンチパターンなので、別ファイルで定義したいです。そのような場合にも対応する方法が提供されています。それでは例をみてみましょう。
#@ load("@ytt:data", "data")
apiVersion: apps/v1
kind: Deployment
metadata:
name: #@ data.values.app_name
namespace: #@ data.values.namespace
#@data/values-schema
---
app_name: "app-name"
namespace: "app-namespace"
#@ load("@ytt:data", "data")を実行すると、dataという形で読み込むことができ、値はdata.values.hogehogeの形式で参照できます。この例で言うと、data.values.app_nameでapp-name、data.values.namespaceでapp-namespaceが取得できると言うことになります。
それではこれを実行してみましょう。単純に-fでファイルを追加するだけで実現できます。
ytt -f config.yaml -f schema.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: app-name
namespace: app-namespace
複数ファイルに同時に値を挿入
先ほどの例では1つのファイルに対して値を注入していますが、同時に複数のファイルに対して値を注入できます。サンプルでは便宜上同じ内容のファイルを二つに分けています。
#@ load("@ytt:data", "data")
apiVersion: apps/v1
kind: Deployment
metadata:
name: #@ data.values.app.name
namespace: #@ data.values.app.namespace
#@ load("@ytt:data", "data")
apiVersion: apps/v1
kind: Service
metadata:
name: #@ data.values.app.name
namespace: #@ data.values.app.namespace
#@data/values
---
app:
name: app-name
namespace: app-namespace
それでは実行してみましょう。
ytt -f deployment.yaml -f service.yaml -f value.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: app-name
namespace: app-namespace
---
apiVersion: apps/v1
kind: Service
metadata:
name: app-name
namespace: app-namespace
実行結果を見ると、deployment.yamlとservice.yamlに適用した結果を一つのYAMLファイルとしてまとめられていることが確認できます。
まとめ
今回はyttについて入門してみました。実際にはより様々な機能がありYAMLファイルの制御をより複雑にに実行することができます。ユースケースとしてはKubernetesのマニフェストを記載する時に制御する方法の一つとして利用することになるかなと思います。みなさんもぜひ使ってみてください。
Discussion