11.2. Ansible ベース Operator の作成
以下では、Operator SDK における Ansible サポートについての概要を説明し、Operator の作成者に、Ansible Playbook およびモジュールを使用する operator-sdk CLI ツールを使って Ansible ベースの Operator をビルドし、実行するサンプルを示します。
11.2.1. Operator SDK における Ansible サポート リンクのコピーリンクがクリップボードにコピーされました!
Operator Framework は Operator という Kubernetes ネイティブアプリケーションを効果的かつ自動化された拡張性のある方法で管理するためのオープンソースツールキットです。このフレームワークには Operator SDK が含まれ、これは Kubernetes API の複雑性を把握していなくても、それぞれの専門知識に基づいて Operator のブートストラップおよびビルドを実行できるように開発者を支援します。
Operator プロジェクトを生成するための Operator SDK のオプションの 1 つに、Go コードを作成することなしに Kubernetes リソースを統一されたアプリケーションとしてデプロイするために既存の Ansible Playbook およびモジュールを使用できるオプションがあります。
11.2.1.1. カスタムリソースファイル リンクのコピーリンクがクリップボードにコピーされました!
Operator は Kubernetes の拡張メカニズムであるカスタムリソース定義 (CRD) を使用するため、カスタムリソース (CR) は、組み込み済みのネイティブ Kubernetes オブジェクトのように表示され、機能します。
CR ファイル形式は Kubernetes リソースファイルです。オブジェクトには、必須およびオプションフィールドが含まれます。
| フィールド | 説明 |
|---|---|
|
| 作成される CR のバージョン。 |
|
| 作成される CR の種類。 |
|
| 作成される Kubernetes 固有のメタデータ。 |
|
| Ansible に渡される変数のキーと値の一覧。このフィールドは、デフォルトでは空です。 |
|
|
オブジェクトの現在の状態の概要を示します。Ansible ベースの Operator の場合、 |
|
| CR に付加する Kubernetes 固有のアノテーション。 |
CR アノテーションの以下の一覧は Operator の動作を変更します。
| アノテーション | 説明 |
|---|---|
|
|
CR の調整間隔を指定します。この値は標準的な Golang パッケージ |
Ansible ベースの Operator アノテーションの例
apiVersion: "foo.example.com/v1alpha1"
kind: "Foo"
metadata:
name: "example"
annotations:
ansible.operator-sdk/reconcile-period: "30s"
11.2.1.2. 監視ファイル リンクのコピーリンクがクリップボードにコピーされました!
監視ファイルには、Group、Version、および Kind などによって特定される、カスタムリソース (CR) から Ansible ロールまたは Playbook へのマッピングの一覧が含まれます。Operator はこのマッピングファイルが事前に定義された場所の /opt/ansible/watches.yaml にあることを予想します。
| フィールド | 説明 |
|---|---|
|
| 監視する CR のグループ。 |
|
| 監視する CR のバージョン。 |
|
| 監視する CR の種類。 |
|
|
コンテナーに追加される Ansible ロールへのパスです。たとえば、 |
|
|
コンテナーに追加される Ansible Playbook へのパスです。この Playbook は単純にロールを呼び出す方法になります。このフィールドは |
|
| ロールまたは Playbook が特定の CR について実行される調整 期間および頻度。 |
|
|
|
監視ファイルの例
- version: v1alpha1
group: foo.example.com
kind: Foo
role: /opt/ansible/roles/Foo
- version: v1alpha1
group: bar.example.com
kind: Bar
playbook: /opt/ansible/playbook.yml
- version: v1alpha1
group: baz.example.com
kind: Baz
playbook: /opt/ansible/baz.yml
reconcilePeriod: 0
manageStatus: false
11.2.1.2.1. 高度なオプション リンクのコピーリンクがクリップボードにコピーされました!
高度な機能は、それらを GVK (グループ、バージョン、および種類) ごとに監視ファイルに追加して有効にできます。それらは group、version、kind および playbook または role フィールドの下に移行できます。
一部の機能は、カスタムリソース (CR) のアノテーションを使用してリソースごとに上書きできます。オーバーライドできるオプションには、以下に指定されるアノテーションが含まれます。
| 機能 | YAML キー | 説明 | 上書きのアノテーション | デフォルト値 |
|---|---|---|---|---|
| 調整期間 |
| 特定の CR についての調整実行の間隔。 |
|
|
| ステータスの管理 |
|
Operator は各 CR の |
| |
| 依存するリソースの監視 |
| Operator は Ansible によって作成されるリソースを動的に監視できます。 |
| |
| クラスタースコープのリソースの監視 |
| Operator は Ansible によって作成されるクラスタースコープのリソースを監視できます。 |
| |
| 最大 Runner アーティファクト |
| Ansible Runner が各リソースについて Operator コンテナーに保持するアーティファクトディレクトリーの数を管理します。 |
|
|
高度なオプションを含む監視ファイルの例
- version: v1alpha1
group: app.example.com
kind: AppService
playbook: /opt/ansible/playbook.yml
maxRunnerArtifacts: 30
reconcilePeriod: 5s
manageStatus: False
watchDependentResources: False
11.2.1.3. Ansible に送信される追加変数 リンクのコピーリンクがクリップボードにコピーされました!
追加の変数を Ansible に送信し、Operator で管理できます。カスタマーリソース (CR) の spec セクションでは追加変数としてキーと値のペアを渡します。これは、ansible-playbook コマンドに渡される追加変数と同等です。
また Operator は、CR の名前および CR の namespace についての meta フィールドの下に追加の変数を渡します。
以下は CR の例になります。
apiVersion: "app.example.com/v1alpha1"
kind: "Database"
metadata:
name: "example"
spec:
message:"Hello world 2"
newParameter: "newParam"
追加変数として Ansible に渡される構造は以下のとおりです。
{ "meta": {
"name": "<cr_name>",
"namespace": "<cr_namespace>",
},
"message": "Hello world 2",
"new_parameter": "newParam",
"_app_example_com_database": {
<full_crd>
},
}
message および newParameter フィールドは追加変数として上部に設定され、meta は Operator に定義されるように CR の関連メタデータを提供します。meta フィールドは、Ansible のドット表記などを使用してアクセスできます。
- debug:
msg: "name: {{ meta.name }}, {{ meta.namespace }}"
11.2.1.4. Ansible Runner ディレクトリー リンクのコピーリンクがクリップボードにコピーされました!
Ansible Runner はコンテナーに Ansible 実行についての情報を維持します。これは /tmp/ansible-operator/runner/<group>/<version>/<kind>/<namespace>/<name> に置かれます。
追加リソース
-
runnerディレクトリーについての詳細は、Ansible Runner ドキュメントを参照してください。
11.2.2. Operator SDK CLI のインストール リンクのコピーリンクがクリップボードにコピーされました!
Operator SDK には、開発者による新規 Operator プロジェクトの作成、ビルドおよびデプロイを支援をする CLI ツールが含まれます。ワークステーションに SDK CLI をインストールして、独自の Operator のオーサリングを開始することができます。
11.2.2.1. GitHub リリースからのインストール リンクのコピーリンクがクリップボードにコピーされました!
GitHub のプロジェクトから SDK CLI の事前ビルドリリースのバイナリーをダウンロードし、インストールできます。
前提条件
-
dockerv17.03+ -
OpenShift CLI (
oc) v4.1+ (インストール済み) - Kubernetes v1.11.3+ に基づくクラスターへのアクセス
- コンテナーレジストリーへのアクセス
手順
リリースバージョン変数を設定します。
RELEASE_VERSION=v0.8.0リリースバイナリーをダウンロードします。
Linux の場合
$ curl -OJL https://github.com/operator-framework/operator-sdk/releases/download/${RELEASE_VERSION}/operator-sdk-${RELEASE_VERSION}-x86_64-linux-gnuMacOS の場合
$ curl -OJL https://github.com/operator-framework/operator-sdk/releases/download/${RELEASE_VERSION}/operator-sdk-${RELEASE_VERSION}-x86_64-apple-darwin
ダウンロードしたリリースのバイナリーを確認します。
提供された ASC ファイルをダウンロードします。
Linux の場合
$ curl -OJL https://github.com/operator-framework/operator-sdk/releases/download/${RELEASE_VERSION}/operator-sdk-${RELEASE_VERSION}-x86_64-linux-gnu.ascMacOS の場合
$ curl -OJL https://github.com/operator-framework/operator-sdk/releases/download/${RELEASE_VERSION}/operator-sdk-${RELEASE_VERSION}-x86_64-apple-darwin.asc
バイナリーと対応する ASC ファイルを同じディレクトリーに置き、以下のコマンドを実行してバイナリーを確認します。
Linux の場合
$ gpg --verify operator-sdk-${RELEASE_VERSION}-x86_64-linux-gnu.ascMacOS の場合
$ gpg --verify operator-sdk-${RELEASE_VERSION}-x86_64-apple-darwin.asc
保守管理者の公開キーがワークステーションにない場合は、以下のエラーが出されます。
$ gpg --verify operator-sdk-${RELEASE_VERSION}-x86_64-apple-darwin.asc $ gpg: assuming signed data in 'operator-sdk-${RELEASE_VERSION}-x86_64-apple-darwin' $ gpg: Signature made Fri Apr 5 20:03:22 2019 CEST $ gpg: using RSA key <key_id>1 $ gpg: Can't check signature: No public key- 1
- RSA キー文字列。
キーをダウンロードするには、以下のコマンドを実行し、
<key_id>を直前のコマンドの出力で提供された RSA キー文字列に置き換えます。$ gpg [--keyserver keys.gnupg.net] --recv-key "<key_id>"1 - 1
- キーサーバーが設定されていない場合、これを
--keyserverオプションで指定します。
リリースバイナリーを
PATHにインストールします。Linux の場合
$ chmod +x operator-sdk-${RELEASE_VERSION}-x86_64-linux-gnu $ sudo cp operator-sdk-${RELEASE_VERSION}-x86_64-linux-gnu /usr/local/bin/operator-sdk $ rm operator-sdk-${RELEASE_VERSION}-x86_64-linux-gnuMacOS の場合
$ chmod +x operator-sdk-${RELEASE_VERSION}-x86_64-apple-darwin $ sudo cp operator-sdk-${RELEASE_VERSION}-x86_64-apple-darwin /usr/local/bin/operator-sdk $ rm operator-sdk-${RELEASE_VERSION}-x86_64-apple-darwin
CLI ツールが正しくインストールされていることを確認します。
$ operator-sdk version
11.2.2.2. Homebrew からのインストール リンクのコピーリンクがクリップボードにコピーされました!
Homebrew を使用して SDK CLI をインストールできます。
前提条件
手順
brewコマンドを使用して SDK CLI をインストールします。$ brew install operator-sdkCLI ツールが正しくインストールされていることを確認します。
$ operator-sdk version
11.2.2.3. ソースを使用したコンパイルおよびインストール リンクのコピーリンクがクリップボードにコピーされました!
Operator SDK ソースコードを取得して、SDK CLI をコンパイルし、インストールできます。
前提条件
手順
operator-sdkリポジトリーのクローンを作成します。$ mkdir -p $GOPATH/src/github.com/operator-framework $ cd $GOPATH/src/github.com/operator-framework $ git clone https://github.com/operator-framework/operator-sdk $ cd operator-sdk必要なリリースブランチをチェックアウトします。
$ git checkout masterSDK CLI ツールをコンパイルし、インストールします。
$ make dep $ make installこれにより、$GOPATH/bin に CLI バイナリー
operator-sdkがインストールされます。CLI ツールが正しくインストールされていることを確認します。
$ operator-sdk version
11.2.3. Operator SDK を使用した Ansible ベースの Operator のビルド リンクのコピーリンクがクリップボードにコピーされました!
以下の手順では、Operator SDK が提供するツールおよびライブラリーを使用した Ansible Playbook がサポートする単純な Memcached Operator のビルドの例について説明します。
前提条件
- 開発ワークステーションにインストールされる Operator SDK CLI
-
cluster-adminパーミッションを持つアカウントを使用した Kubernetes ベースのクラスターr v1.11.3+ (OpenShift Container Platform 4.2 など) へのアクセス -
OpenShift CLI (
oc) v4.1+ (インストール済み) -
ansiblev2.6.0+ -
ansible-runnerv1.1.0+ -
ansible-runner-httpv1.0.0+
手順
operator-sdk newコマンドを使用して、namespace スコープまたはクラスタースコープのいずれかで 新規 Operator プロジェクトを作成します。以下のいずれかを選択します。namespace スコープ Operator (デフォルト) は単一 namespace でリソースを監視し、管理します。namespace スコープの Operator は柔軟性があるために優先して使用されます。これらの Operator は切り離されたアップグレード、障害対応およびモニタリングのための namespace の分離、および API 定義の差異化を可能にします。
新規の Ansible ベース、namespace スコープの
memcached-operatorプロジェクトを作成し、そのディレクトリーに切り換えるには、以下のコマンドを使用します。$ operator-sdk new memcached-operator \ --api-version=cache.example.com/v1alpha1 \ --kind=Memcached \ --type=ansible $ cd memcached-operatorこれにより、APIVersion
example.com/v1apha1および KindMemcachedの Memcached リソースを監視するためのmemcached-operatorプロジェクトが作成されます。クラスタースコープの Operator はクラスター全体でリソースを監視し、管理します。これは、 クラスター全体で発行される証明書を管理できるようにクラスタースコープのパーミッションでデプロイされ、監視される
cert-managerOperator などの場合に役立ちます。memcached-operatorプロジェクトをクラスタースコープになるように作成し、そのディレクトリーに切り換えるには、以下のコマンドを実行します。$ operator-sdk new memcached-operator \ --cluster-scoped \ --api-version=cache.example.com/v1alpha1 \ --kind=Memcached \ --type=ansible $ cd memcached-operator--cluster-scopedフラグを使用することにより、以下の変更を含む新規の Operator のスキャフォールディングが実行されます。-
deploy/operator.yaml: Pod の namespace に設定するのではなく、WATCH_NAMESPACE=""を設定します。 -
deploy/role.yaml:RoleではなくClusterRoleを使用します。 deploy/role_binding.yaml:-
RoleBindingではなくClusterRoleBindingを使用します。 -
subject の namespace を
REPLACE_NAMESPACEに設定します。これは、Operator がデプロイされる namespace に変更される必要があります。
-
-
Operator ロジックをカスタマイズします。
この例では、
memcached-operatorはそれぞれのMemcachedカスタムリソース (CR) について以下の調整 (reconciliation) ロジックを実行します。-
memcachedDeployment を作成します (ない場合)。 -
Deployment のサイズが
MemcachedCR で指定されるのと同じであることを確認します。
デフォルトで、
memcached-operatorはwatches.yamlファイルに示されるようにMemcachedリソースイベントを監視し、Ansible ロールMemcachedを実行します。- version: v1alpha1 group: cache.example.com kind: Memcachedオプションで、以下のロジックを
watches.yamlファイルでカスタマイズできます。roleオプションを指定して、ansible-runnerを Ansible ロールを使って起動する際に Operator がこの特定のパスを使用するように設定します。デフォルトでは、新規コマンドでロールが置かれる場所への絶対パスが入力されます。- version: v1alpha1 group: cache.example.com kind: Memcached role: /opt/ansible/roles/memcachedplaybookオプションをwatches.yamlファイルに指定して、ansible-runnerを Ansible Playbook で起動する際に Operator がこの指定されたパスを使用するように設定します。- version: v1alpha1 group: cache.example.com kind: Memcached playbook: /opt/ansible/playbook.yaml
-
Memcached Ansible ロールをビルドします。
生成された Ansible ロールを
roles/memcached/ディレクトリーの下で変更します。この Ansible ロールは、リソースの変更時に実行されるロジックを制御します。Memcached仕様を定義します。Ansible ベースの Operator の定義は Ansible 内ですべて実行できます。Ansible Operator は CR 仕様フィールドのすべてのキー/値ペアを 変数として Ansible に渡します。仕様フィールドのすべての変数の名前は、Ansible の実行前に Operator によってスネークケース (小文字 + アンダースコア) に変換されます。たとえば、仕様の
serviceAccountは Ansible ではservice_accountになります。ヒントAnsible で変数についてのタイプの検証を実行し、アプリケーションが予想される入力を受信できることを確認する必要があります。
ユーザーが
specフィールドを設定しない場合、roles/memcached/defaults/main.ymlファイルを変更してデフォルトを設定します。size: 1Memcachedデプロイメントを定義します。Memcached仕様が定義された状態で、リソースの変更に対する Ansible の実行内容を定義できます。これは Ansible ロールであるため、デフォルトの動作はroles/memcached/tasks/main.ymlファイルでタスクを実行します。ここでの目的は、Ansible で
memcached:1.4.36-alpineイメージを実行する Deployement を作成することにあります (Deployment がない場合)。Ansible 2.7+ は k8s Ansible モジュールをサポートします。 この例では、このモジュールを活用し、Deployment 定義を制御します。roles/memcached/tasks/main.ymlを以下に一致するように変更します。- name: start memcached k8s: definition: kind: Deployment apiVersion: apps/v1 metadata: name: '{{ meta.name }}-memcached' namespace: '{{ meta.namespace }}' spec: replicas: "{{size}}" selector: matchLabels: app: memcached template: metadata: labels: app: memcached spec: containers: - name: memcached command: - memcached - -m=64 - -o - modern - -v image: "docker.io/memcached:1.4.36-alpine" ports: - containerPort: 11211注記この例では、
size変数を使用し、MemcachedDeployment のレプリカ数を制御しています。この例では、デフォルトを1に設定しますが、任意のユーザーがこのデフォルトを上書きする CR を作成することができます。
CRD をデプロイします。
Operator の実行前に、Kubernetes は Operator が監視する新規カスタムリソース定義 (CRD) について把握している必要があります。
MemcachedCRD をデプロイします。$ oc create -f deploy/crds/cache_v1alpha1_memcached_crd.yamlOperator をビルドし、実行します 。
Operator をビルドし、実行する方法として 2 つの方法を使用できます。
- Kubernetes クラスター内の Pod を使用
-
operator-sdk upコマンドを使用してクラスター外で Go プログラムを使用
以下の方法のいずれかを選択します。
Kubernetes クラスター内で Pod として実行 します。これは実稼働環境での優先される方法です。
memcached-operatorイメージをビルドし、これをレジストリーにプッシュします。$ operator-sdk build quay.io/example/memcached-operator:v0.0.1 $ podman push quay.io/example/memcached-operator:v0.0.1Deployment マニフェストは
deploy/operator.yamlファイルに生成されます。このファイルの Deployment イメージは、プレースホルダーREPLACE_IMAGEから直前にビルドされたイメージに変更される必要があります。これを実行するには、以下を実行します。$ sed -i 's|REPLACE_IMAGE|quay.io/example/memcached-operator:v0.0.1|g' deploy/operator.yaml--cluster-scoped=trueフラグを使用して Operator を作成した場合、生成されたClusterRoleBindingでサービスアカウント namespace を Operator をデプロイする場所に一致するように更新します。$ export OPERATOR_NAMESPACE=$(oc config view --minify -o jsonpath='{.contexts[0].context.namespace}') $ sed -i "s|REPLACE_NAMESPACE|$OPERATOR_NAMESPACE|g" deploy/role_binding.yamlOSX でこれらの手順を実行している場合には、代わりに以下のコマンドを実行します。
$ sed -i "" 's|REPLACE_IMAGE|quay.io/example/memcached-operator:v0.0.1|g' deploy/operator.yaml $ sed -i "" "s|REPLACE_NAMESPACE|$OPERATOR_NAMESPACE|g" deploy/role_binding.yamlmemcached-operatorをデプロイします。$ oc create -f deploy/service_account.yaml $ oc create -f deploy/role.yaml $ oc create -f deploy/role_binding.yaml $ oc create -f deploy/operator.yamlmemcached-operatorが稼働していることを確認します。$ oc get deployment NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE memcached-operator 1 1 1 1 1m
クラスター外で実行します。この方法は、デプロイメントおよびテストの速度を上げるために開発サイクル時に優先される方法です。
Ansible Runner および Ansible Runner HTTP プラグインがインストールされていることを確認します。 インストールされていない場合、CR の作成時に Ansible Runner から予想しないエラーが発生します。
さらに、
watches.yamlファイルで参照されるロールパスがマシン上にある必要があります。通常、コンテナーはディスク上のロールが置かれる場所で使用されるため、ロールは設定済みの Ansible ロールパス (例:/etc/ansible/roles) に手動でコピーされる必要があります。$HOME/.kube/configにあるデフォルトの Kubernetes 設定ファイルを使って Operator をローカルに実行するには、以下を実行します。$ operator-sdk up local提供された Kubernetes 設定ファイルを使って Operator をローカルに実行するには、以下を実行します。
$ operator-sdk up local --kubeconfig=config
MemcachedCR を作成します。以下に示されるように
deploy/crds/cache_v1alpha1_memcached_cr.yamlファイルを変更し、MemcachedCR を作成します。$ cat deploy/crds/cache_v1alpha1_memcached_cr.yaml apiVersion: "cache.example.com/v1alpha1" kind: "Memcached" metadata: name: "example-memcached" spec: size: 3 $ oc apply -f deploy/crds/cache_v1alpha1_memcached_cr.yamlmemcached-operatorが CR の Deployment を作成できることを確認します。$ oc get deployment NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE memcached-operator 1 1 1 1 2m example-memcached 3 3 3 3 1mPod で 3 つのレプリカが作成されていることを確認します。
$ oc get pods NAME READY STATUS RESTARTS AGE example-memcached-6fd7c98d8-7dqdr 1/1 Running 0 1m example-memcached-6fd7c98d8-g5k7v 1/1 Running 0 1m example-memcached-6fd7c98d8-m7vn7 1/1 Running 0 1m memcached-operator-7cc7cfdf86-vvjqk 1/1 Running 0 2m
サイズを更新します。
memcachedCR のspec.sizeフィールドを3から4に変更し、変更を適用します。$ cat deploy/crds/cache_v1alpha1_memcached_cr.yaml apiVersion: "cache.example.com/v1alpha1" kind: "Memcached" metadata: name: "example-memcached" spec: size: 4 $ oc apply -f deploy/crds/cache_v1alpha1_memcached_cr.yamlOperator が Deployment サイズを変更することを確認します。
$ oc get deployment NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE example-memcached 4 4 4 4 5m
リソースをクリーンアップします。
$ oc delete -f deploy/crds/cache_v1alpha1_memcached_cr.yaml $ oc delete -f deploy/operator.yaml $ oc delete -f deploy/role_binding.yaml $ oc delete -f deploy/role.yaml $ oc delete -f deploy/service_account.yaml $ oc delete -f deploy/crds/cache_v1alpha1_memcached_crd.yaml
11.2.4. K8S Ansible モジュールの使用によるアプリケーションライフサイクルの管理 リンクのコピーリンクがクリップボードにコピーされました!
Ansible を使用して Kubernetes でアプリケーションのライフサイクルを管理するには、k8s Ansible モジュールを使用できます。この Ansible モジュールにより、開発者は既存の Kubernetes リソースファイル (YAML で作成されている) を利用するか、またはネイティブの Ansible でライフサイクル管理を表現することができます。
Ansible を既存の Kubernetes リソースファイルと併用する最大の利点の 1 つに、Ansible のいくつかを変数のみを使う単純な方法でのリソースのカスタマイズを可能にする Jinja テンプレートを使用できる点があります。
このセクションでは、k8s Ansible モジュールの使用法を詳細に説明します。使用を開始するには、Playbook を使用してローカルワークステーションにモジュールをインストールし、これをテストしてから、Operator 内での使用を開始します。
11.2.4.1. k8s Ansible モジュールのインストール リンクのコピーリンクがクリップボードにコピーされました!
k8s Ansible モジュールをローカルワークステーションにインストールするには、以下を実行します。
手順
Ansible 2.6+ をインストールします。
$ sudo yum install ansiblepip を使用して
OpenShift python クライアントパッケージをインストールします。$ pip install openshift
11.2.4.2. k8s Ansible モジュールのローカルでのテスト リンクのコピーリンクがクリップボードにコピーされました!
開発者が毎回 Operator を実行し、再ビルドするのではなく、Ansible コードをローカルマシンから実行する方が利点がある場合があります。
手順
新規 Ansible ベースの Operator プロジェクトを初期化します。
$ operator-sdk new --type ansible --kind Foo --api-version foo.example.com/v1alpha1 foo-operator Create foo-operator/tmp/init/galaxy-init.sh Create foo-operator/tmp/build/Dockerfile Create foo-operator/tmp/build/test-framework/Dockerfile Create foo-operator/tmp/build/go-test.sh Rendering Ansible Galaxy role [foo-operator/roles/Foo]... Cleaning up foo-operator/tmp/init Create foo-operator/watches.yaml Create foo-operator/deploy/rbac.yaml Create foo-operator/deploy/crd.yaml Create foo-operator/deploy/cr.yaml Create foo-operator/deploy/operator.yaml Run git init ... Initialized empty Git repository in /home/dymurray/go/src/github.com/dymurray/opsdk/foo-operator/.git/ Run git init done$ cd foo-operator必要な Ansible ロジックを使用して
roles/Foo/tasks/main.ymlファイルを変更します。この例では、変数の切り替えと共に namespace を作成し、削除します。- name: set test namespace to {{ state }} k8s: api_version: v1 kind: Namespace state: "{{ state }}" ignore_errors: true1 - 1
ignore_errors: trueを設定することにより、存在しないプロジェクトを削除しても失敗しません。
roles/Foo/defaults/main.ymlファイルを、デフォルトでstateをpresentに設定するように変更します。state: present上部ディレクトリーに、
Fooロールを含む Ansible Playbookplaybook.ymlを作成します。- hosts: localhost roles: - FooPlaybook を実行します。
$ ansible-playbook playbook.yml [WARNING]: provided hosts list is empty, only localhost is available. Note that the implicit localhost does not match 'all' PLAY [localhost] *************************************************************************** TASK [Gathering Facts] ********************************************************************* ok: [localhost] Task [Foo : set test namespace to present] changed: [localhost] PLAY RECAP ********************************************************************************* localhost : ok=2 changed=1 unreachable=0 failed=0namespace が作成されていることを確認します。
$ oc get namespace NAME STATUS AGE default Active 28d kube-public Active 28d kube-system Active 28d test Active 3sstateをabsentに設定して Playbook を再実行します。$ ansible-playbook playbook.yml --extra-vars state=absent [WARNING]: provided hosts list is empty, only localhost is available. Note that the implicit localhost does not match 'all' PLAY [localhost] *************************************************************************** TASK [Gathering Facts] ********************************************************************* ok: [localhost] Task [Foo : set test namespace to absent] changed: [localhost] PLAY RECAP ********************************************************************************* localhost : ok=2 changed=1 unreachable=0 failed=0namespace が削除されていることを確認します。
$ oc get namespace NAME STATUS AGE default Active 28d kube-public Active 28d kube-system Active 28d
11.2.4.3. Operator 内での k8s Ansible モジュールのテスト リンクのコピーリンクがクリップボードにコピーされました!
k8s Ansible モジュールをローカルで使用することに慣れたら、カスタムリソース (CR) の変更時に Operator 内で同じ Ansible ロジックをトリガーできます。この例では、Ansible ロールを、Operator が監視する特定の Kubernetes リソースにマップします。このマッピングは監視ファイルで実行されます。
11.2.4.3.1. Ansible ベース Operator のローカルでのテスト リンクのコピーリンクがクリップボードにコピーされました!
Ansible ワークフローのテストをローカルで実行することに慣れたら、ローカルに実行される Ansible ベースの Operator 内でロジックをテストできます。
これを実行するには、Operator プロジェクトの上部ディレクトリーから operator-sdk up local コマンドを使用します。このコマンドは ./watches.yaml ファイルから読み取り、 ~/.kube/config ファイルを使用して k8s Ansible モジュールが実行するように Kubernetes クラスターと通信します。
手順
up localコマンドは./watches.yamlファイルから読み取るため、Operator の作成者はいくつかのオプションを選択できます。roleが単独で残される場合 (デフォルトでは/opt/ansible/roles/<name>)、ロールを Operator から/opt/ansible/roles/ディレクトリーに直接コピーする必要があります。これは、現行ディレクトリーからの変更が反映されないために複雑になります。この代わりに、
roleフィールドを現行ディレクトリーを参照するように変更し、既存の行をコメントアウトします。- version: v1alpha1 group: foo.example.com kind: Foo # role: /opt/ansible/roles/Foo role: /home/user/foo-operator/Fooカスタムリソース定義 (CRD) およびカスタムリソース (CR)
Fooの適切なロールベースアクセス制御 (RBAC) 定義を作成します。operator-sdkコマンドは、deploy/ディレクトリー内にこれらのファイルを自動生成します。$ oc create -f deploy/crds/foo_v1alpha1_foo_crd.yaml $ oc create -f deploy/service_account.yaml $ oc create -f deploy/role.yaml $ oc create -f deploy/role_binding.yamlup localコマンドを実行します。$ operator-sdk up local [...] INFO[0000] Starting to serve on 127.0.0.1:8888 INFO[0000] Watching foo.example.com/v1alpha1, Foo, defaultOperator はリソース
Fooでイベントを監視しているため、CR の作成により、Ansible ロールの実行がトリガーされます。deploy/cr.yamlファイルを表示します。apiVersion: "foo.example.com/v1alpha1" kind: "Foo" metadata: name: "example"specフィールドは設定されていないため、Ansible は追加の変数なしで起動します。次のセクションでは、追加の変数が CR から Ansible に渡される方法について説明します。このため、Operator に同じでデフォルト値を設定することが重要になります。デフォルト変数
stateをpresentに設定し、Fooの CR インスタンスを作成します。$ oc create -f deploy/cr.yamlnamespace
testが作成されていることを確認します。$ oc get namespace NAME STATUS AGE default Active 28d kube-public Active 28d kube-system Active 28d test Active 3sdeploy/cr.yamlファイルを、stateフィールドをabsentに設定するように変更します。apiVersion: "foo.example.com/v1alpha1" kind: "Foo" metadata: name: "example" spec: state: "absent"変更を適用し、namespace が定義されていることを確認します。
$ oc apply -f deploy/cr.yaml $ oc get namespace NAME STATUS AGE default Active 28d kube-public Active 28d kube-system Active 28d
11.2.4.3.2. Ansible ベース Operator のクラスター上でのテスト リンクのコピーリンクがクリップボードにコピーされました!
Ansible ロジックを Ansible ベース Operator 内でローカルに実行することに慣れたら、OpenShift Container Platform などの Kubernetes クラスターの Pod 内で Operator をテストすることができます。Pod のクラスターでの実行は、実稼働環境で優先される方法です。
手順
foo-operatorイメージをビルドし、これをレジストリーにプッシュします。$ operator-sdk build quay.io/example/foo-operator:v0.0.1 $ podman push quay.io/example/foo-operator:v0.0.1Deployment マニフェストは
deploy/operator.yamlファイルに生成されます。このファイルの Deployment イメージはプレースホルダーのREPLACE_IMAGEから以前にビルドされたイメージに変更される必要があります。これを実行するには、以下のコマンドを実行します。$ sed -i 's|REPLACE_IMAGE|quay.io/example/foo-operator:v0.0.1|g' deploy/operator.yamlOSX でこれらの手順を実行している場合には、代わりに以下のコマンドを実行します。
$ sed -i "" 's|REPLACE_IMAGE|quay.io/example/foo-operator:v0.0.1|g' deploy/operator.yamlfoo-operatorをデプロイします。$ oc create -f deploy/crds/foo_v1alpha1_foo_crd.yaml # if CRD doesn't exist already $ oc create -f deploy/service_account.yaml $ oc create -f deploy/role.yaml $ oc create -f deploy/role_binding.yaml $ oc create -f deploy/operator.yamlfoo-operatorが稼働していることを確認します。$ oc get deployment NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE foo-operator 1 1 1 1 1m
11.2.5. k8s_status Ansible モジュールの使用によるカスタムリソースステータスの管理 リンクのコピーリンクがクリップボードにコピーされました!
Ansible ベースの Operator は、カスタムリソース (CR) status サブリソースを以前の Ansible 実行についての一般的な情報で自動的に更新します。これには、以下のように成功したタスクおよび失敗したタスクの数と関連するエラーメッセージが含まれます。
status:
conditions:
- ansibleResult:
changed: 3
completion: 2018-12-03T13:45:57.13329
failures: 1
ok: 6
skipped: 0
lastTransitionTime: 2018-12-03T13:45:57Z
message: 'Status code was -1 and not [200]: Request failed: <urlopen error [Errno
113] No route to host>'
reason: Failed
status: "True"
type: Failure
- lastTransitionTime: 2018-12-03T13:46:13Z
message: Running reconciliation
reason: Running
status: "True"
type: Running
Ansible ベースの Operator は、Operator の作成者が k8s_status Ansible モジュールでカスタムステータスの値を指定することも可能にします。これにより、作成者は必要に応じ、任意のキー/値のペアを使って Ansible から status を更新できます。
デフォルトでは、Ansible ベースの Operator には、上記のように常に汎用的な Ansible 実行出力が含まれます。アプリケーションのステータスが Ansible 出力で更新 されない ようにする必要がある場合に、アプリケーションからステータスを手動で追跡することができます。
手順
CR ステータスをアプリケーションから手動で追跡するには、
manageStatusフィールドをfalseに設定して監視ファイルを更新します。- version: v1 group: api.example.com kind: Foo role: /opt/ansible/roles/Foo manageStatus: false次に、
k8s_statusAnsible モジュールを使用してサブリソースを更新します。たとえば、キーfooおよび値barを使用して更新するには、k8s_statusを以下のように使用することができます。- k8s_status: api_version: app.example.com/v1 kind: Foo name: "{{ meta.name }}" namespace: "{{ meta.namespace }}" status: foo: bar
追加リソース
- Ansible ベース Operator からのユーザー主導のステータス管理を行う方法についての詳細は、「Ansible Operator Status Proposal」を参照してください。
11.2.5.1. ローカルでのテスト時の k8s_status Ansible モジュールの使用 リンクのコピーリンクがクリップボードにコピーされました!
Operator が k8s_status Ansible モジュールを使用し、Operator を operator-sdk up local コマンドでローカルにテストする必要がある場合、モジュールを Ansible が予想する場所にインストールする必要があります。これは、Ansible の library 設定オプションを使用して実行されます。
この例では、ユーザーがサードパーティーの Ansible モジュールを /usr/share/ansible/library/ ディレクトリーに配置することを前提としています。
手順
k8s_statusモジュールをインストールするには、ansible.cfgファイルを、インストール済みの Ansible モジュールを/usr/share/ansible/library/ディレクトリーで検索するように設定します。$ echo "library=/usr/share/ansible/library/" >> /etc/ansible/ansible.cfgk8s_status.pyファイルを/usr/share/ansible/library/ディレクトリーに追加します。$ wget https://raw.githubusercontent.com/openshift/ocp-release-operator-sdk/master/library/k8s_status.py -O /usr/share/ansible/library/k8s_status.py
11.2.6. 追加リソース リンクのコピーリンクがクリップボードにコピーされました!
- Operator SDK によって作成されるプロジェクトディレクトリー構造についての詳細は、「Appendices」を参照してください。
- Reaching for the Stars with Ansible Operator - Red Hat OpenShift Blog
- Operator Development Guide for Red Hat Partners