5.4.2. 使用 Operator SDK 来构建基于 Ansible 的 Operator
本流程介绍了使用 Operator SDK 中的工具和库来构建由 Ansible playbook 和模块提供技术支持的简单 Memcached Operator 示例。
先决条件
- 开发工作站上安装 operator SDK v0.19.4 CLI
-
使用具有
cluster-admin
权限的账户访问基于 Kubernetes 的集群 v1.11.3+(如 OpenShift Container Platform 4.6) -
已安装 OpenShift CLI(
oc
)v4.6+ -
ansible
v2.9.0+ -
ansible-runner
v1.1.0+ -
ansible-runner-http
v1.0.0+
流程
创建新 Operator 项目。命名空间范围的 Operator 会监视和管理单一命名空间中的资源。命名空间范围的 Operator 因具有高灵活性而常被视为首选。这类 Operator 支持解耦升级、针对故障和监控隔离命名空间以及区别化 API 定义。
要创建基于 Ansible 的、全命名空间范围的新
memcached-operator
项目并改为新目录,请使用以下命令:$ operator-sdk new memcached-operator \ --api-version=cache.example.com/v1alpha1 \ --kind=Memcached \ --type=ansible
$ cd memcached-operator
这会创建
memcached-operator
项目,专门用于监视 API 版本example.com/v1apha1
和 kindMemcached
的Memcached
资源。自定义 Operator 逻辑。
在本例中,
memcached-operator
会针对每个Memcached
自定义资源 (CR) 执行以下协调逻辑:-
如果尚无
Memcached
部署,创建一个。 -
确保部署的大小与
Memcached
CR 指定的大小相同。
默认情况下,
memcached-operator
会监视Memcached
资源事件,如watches.yaml
文件中所示,并执行 Ansible 角色Memcached
:- version: v1alpha1 group: cache.example.com kind: Memcached
您可选择在
watches.yaml
文件中自定义以下逻辑:指定
role
选项会将 Operator 配置为在通过 Ansible 角色启动ansible-runner
时使用该指定路径。默认情况下,operator-sdk new
命令会填写到您的角色应前往的绝对路径:- version: v1alpha1 group: cache.example.com kind: Memcached role: /opt/ansible/roles/memcached
指定
watches.yaml
文件中的playbook
选项会将 Operator 配置为在通过 Ansible playbook 启动ansible-runner
时使用该指定路径。- version: v1alpha1 group: cache.example.com kind: Memcached playbook: /opt/ansible/playbook.yaml
-
如果尚无
构建 Memcached Ansible 角色。
修改
roles/memcached/
目录下生成的 Ansible 角色。该 Ansible 角色会控制修改资源时所执行的逻辑。定义
Memcached
spec。可完全在 Ansible 中定义基于 Ansible 的 Operator spec。Ansible Operator 会将 CR spec 字段中列出的所有键值对作为变量传递给 Ansible。在运行 Ansible 之前,Operator 会将 spec 字段中所有变量的名称转换为 snake 格式(小写并附带下划线)。例如,spec 中的
serviceAccount
在 Ansible 中会变成service_account
。提示您应在 Ansible 中对变量执行一些类型验证,以确保应用程序收到所需输入。
如果用户未设置
spec
字段,则请修改roles/memcached/defaults/main.yml
文件设置默认值:size: 1
定义
Memcached
部署。定义了
Memcached
spec 后,即可定义资源发生更改时实际应执行的 Ansible。因为这是一个 Ansible 角色,所以默认行为是执行roles/memcached/tasks/main.yml
文件中的任务。目的是在不存在部署的情况下让 Ansible 创建 Deployment,该 Deployment 将运行
memcached:1.4.36-alpine
镜像。Ansible 2.7+ 支持 k8s Ansible 模块,本例利用该模块来控制部署定义。修改
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
变量来控制Memcached
部署的副本数。本示例将默认值设定为1
,但任何用户都可以创建一个 CR 覆盖该默认值。
部署 CRD。
在运行 Operator 之前,Kubernetes 需要了解 Operator 将会监视的新自定义资源定义 (CRD)。部署
Memcached
CRD:$ oc create -f deploy/crds/cache.example.com_memcacheds_crd.yaml
构建并运行 Operator。
有两种方式来构建和运行 Operator:
- 作为 Kubernetes 集群内的一个 pod。
-
作为集群外的 Go 程序,使用
operator-sdk up
命令。
选择以下任一方法:
作为 Kubernetes 集群内的一个 pod 来运行。这是生产环境的首先方法。
构建
memcached-operator
镜像并将其推送至 registry:$ operator-sdk build quay.io/example/memcached-operator:v0.0.1
$ podman push quay.io/example/memcached-operator:v0.0.1
deploy/operator.yaml
文件中会生成 Deployment 清单。本文件中的部署镜像需要从占位符REPLACE_IMAGE
修改为之前构建的镜像。为此,请运行:$ sed -i 's|REPLACE_IMAGE|quay.io/example/memcached-operator:v0.0.1|g' deploy/operator.yaml
部署
memcached-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.yaml
验证
memcached-operator
部署是否正在运行:$ oc get deployment
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE memcached-operator 1 1 1 1 1m
在集群外运行。这是开发阶段的首选方法,可加快部署和测试的速度。
请确保已安装 Ansible Runner 和 Ansible Runner HTTP Plug-in,否则在创建 CR 时,系统会显示 Ansible Runner 出现意外错误。
此外,还务必要确保您的计算机上存在
watches.yaml
文件中引用的角色路径。因为通常会在磁盘上角色所处的位置使用容器,所以必须手动将角色复制到已配置的 Ansible 角色路径中(如/etc/ansible/roles
)。要使用
$HOME/.kube/config
中的默认 Kubernetes 配置文件在本地运行 Operator:$ operator-sdk run --local
要使用所提供的 Kubernetes 配置文件在本地运行 Operator:
$ operator-sdk run --local --kubeconfig=config
创建一个
Memcached
CR。按所示方式修改
deploy/crds/cache_v1alpha1_memcached_cr.yaml
文件并创建一个Memcached
CR:$ 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.yaml
确保
memcached-operator
为 CR 创建部署:$ oc get deployment
输出示例
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE memcached-operator 1 1 1 1 2m example-memcached 3 3 3 3 1m
检查 pod,确认已创建三个副本:
$ 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
更新大小。
将
memcached
CR 中的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.yaml
确认 Operator 已更改部署大小:
$ 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