前回、Cluster API Provider vSphereを使ってKubernetesクラスタを作成してみました。今回は、Kubernetesクラスタを作成した際にvSphere CSI ControllerがCrashLoopBackOffとなる事象について原因を追ってみたので書いてみようと思います。
構成
- vCenter 7.0 U3
- ESXi 7.0 Update 3
- Kubespray
- kubernetes v1.25.5
- Cluster API v1.3.2
- vSphere CPI v1.18.1
- vSphere CSI v2.1.0
- kubernetes v1.25.5はサポートされない
発生した事象について
前回、Cluster APIを使ってKubernetesクラスタを作成し、calicoのインストールが完了後のpodの状態がこちらです。vsphere-csi-controller が CrashLoopBackOff となっています。
$ KUBECONFIG=vsphere-quickstart.kubeconfig kubectl get pod -A NAMESPACE NAME READY STATUS RESTARTS AGE kube-system calico-kube-controllers-74677b4c5f-m77w8 1/1 Running 0 16m kube-system calico-node-7bcpz 1/1 Running 0 16m kube-system calico-node-w7fs9 1/1 Running 0 16m kube-system calico-node-wckhz 1/1 Running 0 16m kube-system calico-node-zlc5b 1/1 Running 0 16m kube-system coredns-565d847f94-chn5z 1/1 Running 0 21m kube-system coredns-565d847f94-dn4zq 1/1 Running 0 21m kube-system etcd-vsphere-quickstart-d7r7k 1/1 Running 0 21m kube-system kube-apiserver-vsphere-quickstart-d7r7k 1/1 Running 0 21m kube-system kube-controller-manager-vsphere-quickstart-d7r7k 1/1 Running 0 21m kube-system kube-proxy-br9fn 1/1 Running 0 20m kube-system kube-proxy-cvfzq 1/1 Running 0 20m kube-system kube-proxy-qxlj2 1/1 Running 0 20m kube-system kube-proxy-rmzww 1/1 Running 0 21m kube-system kube-scheduler-vsphere-quickstart-d7r7k 1/1 Running 0 21m kube-system kube-vip-vsphere-quickstart-d7r7k 1/1 Running 0 21m kube-system vsphere-cloud-controller-manager-ctkr7 1/1 Running 0 20m kube-system vsphere-cloud-controller-manager-hl5w2 1/1 Running 0 20m kube-system vsphere-cloud-controller-manager-r9dhk 1/1 Running 0 20m kube-system vsphere-csi-controller-5d6484644d-nqwlh 4/5 CrashLoopBackOff 8 (37s ago) 21m kube-system vsphere-csi-node-h9p2x 3/3 Running 0 21m kube-system vsphere-csi-node-hbgsl 3/3 Running 0 20m kube-system vsphere-csi-node-tr99v 3/3 Running 0 20m kube-system vsphere-csi-node-xk2jq 3/3 Running 0 20m
ログの確認
まずは、vsphere-csi-controllerの状態について以下のコマンドで確認してみます。ログを見ると、以下のようなエラーが発生します。エラーは、vCenter名の証明書が不明な認証局によって署名されているためです。デフォルトでは、vCenterは証明書を発行する認証局(VMCA)があり、自己署名証明書を作成しています。
$ KUBECONFIG=vsphere-quickstart.kubeconfig kubectl logs vsphere-csi-controller-5d6484644d-nqwlh -c vsphere-csi-controller -n kube-system level=fatal msg="grpc failed" error="Post https://vcsa-1.home.lab:443/sdk: x509: certificate signed by unknown authority"
自己署名証明書を使うオプションががあり、csi-vsphere.conf で insecure-flag
を利用する必要があります。
Create a Kubernetes Secret for vSphere Container Storage Plug-in
Cluster APIを使ってKubernetesクラスタで、vSphere CSIのcsi-vsphere.confの設定がどのようになっているかを確認するには、以下のコマンドを実行します。
$ KUBECONFIG=vsphere-quickstart.kubeconfig kubectl edit secret csi-vsphere-config -n kube-system # Please edit the object below. Lines beginning with a '#' will be ignored, # and an empty file will abort the edit. If an error occurs while saving this file will be # reopened with the relevant failures. # apiVersion: v1 data: csi-vsphere.conf: <設定値> kind: Secret metadata: creationTimestamp: "<date>" name: csi-vsphere-config namespace: kube-system resourceVersion: "3908" uid: 2b96cb9c-5444-425a-a625-f1b6c4ca5754 type: Opaque
csi-vsphere.confにbase64でエンコードされた設定値が入っており、値を確認してみます。設定値を見ると、 insecure-flag
が設定されていないことが分かります。
$ echo "設定値" | base64 -d [Global] cluster-id = "default/vsphere-quickstart" [VirtualCenter "vcsa-1.home.lab"] user = "vCenter username" password = "vCenter password" datacenters = "datacenter name" [Network] public-network = "portgroup name"
csi-vsphere.confの定義ファイルに、 insecure-flag = "true" を追加し、base64でデコードします。
$ vi csi-vsphere.conf [Global] cluster-id = "default/vsphere-quickstart" [VirtualCenter "vcsa-1.home.lab"] insecure-flag = "true" user = "vCenter username" password = "vCenter password" datacenters = "datacenter name" [Network] public-network = "portgroup name" $ base64 csi-vsphere.conf <出力値>
base64でデコードした値をsecretのcsi-vsphere.confに入力し、保存します。
$ KUBECONFIG=vsphere-quickstart.kubeconfig kubectl edit secret csi-vsphere-config -n kube-system # Please edit the object below. Lines beginning with a '#' will be ignored, # and an empty file will abort the edit. If an error occurs while saving this file will be # reopened with the relevant failures. # apiVersion: v1 data: csi-vsphere.conf: <値を入れ替え> kind: Secret metadata: creationTimestamp: "<date>" name: csi-vsphere-config namespace: kube-system resourceVersion: "3908" uid: 2b96cb9c-5444-425a-a625-f1b6c4ca5754 type: Opaque
podを再起動し、vsphere-csi-controllerが起動してくることを確認します。
$ KUBECONFIG=vsphere-quickstart.kubeconfig kubectl rollout restart deploy vsphere-csi-controller -n kube-system
再起動後のpodの状態はこちらです。
$ KUBECONFIG=vsphere-quickstart.kubeconfig kubectl get pod -A NAMESPACE NAME READY STATUS RESTARTS AGE kube-system calico-kube-controllers-74677b4c5f-87sdx 1/1 Running 0 66m kube-system calico-node-26nls 1/1 Running 0 66m kube-system calico-node-kgnzr 1/1 Running 0 66m kube-system calico-node-qhmm6 1/1 Running 0 66m kube-system calico-node-rpsbk 1/1 Running 0 66m kube-system coredns-565d847f94-drphk 1/1 Running 0 68m kube-system coredns-565d847f94-qc66x 1/1 Running 0 68m kube-system etcd-vsphere-quickstart-9nzbv 1/1 Running 0 68m kube-system kube-apiserver-vsphere-quickstart-9nzbv 1/1 Running 0 68m kube-system kube-controller-manager-vsphere-quickstart-9nzbv 1/1 Running 0 68m kube-system kube-proxy-9ntsx 1/1 Running 0 68m kube-system kube-proxy-dqrpj 1/1 Running 0 67m kube-system kube-proxy-v5j24 1/1 Running 0 67m kube-system kube-proxy-zqp7h 1/1 Running 0 67m kube-system kube-scheduler-vsphere-quickstart-9nzbv 1/1 Running 0 68m kube-system kube-vip-vsphere-quickstart-9nzbv 1/1 Running 0 68m kube-system vsphere-cloud-controller-manager-4fmp2 1/1 Running 0 67m kube-system vsphere-cloud-controller-manager-r7sq7 1/1 Running 0 67m kube-system vsphere-cloud-controller-manager-z6dcx 1/1 Running 0 67m kube-system vsphere-csi-controller-d695747dc-qhjqs 5/5 Running 0 35s kube-system vsphere-csi-node-98z65 3/3 Running 0 67m kube-system vsphere-csi-node-jjx8r 3/3 Running 0 67m kube-system vsphere-csi-node-rfg6w 3/3 Running 0 67m kube-system vsphere-csi-node-stlbj 3/3 Running 0 68m
起動はできましたが、vsphere-csi-controllerのバージョンを確認してみると、v2.1.0を利用していることが分かります。
VMware vSphere Container Storage Plug-inのリリースノートを見ると、v2.1.0はKubernetes v1.19までしかサポートしていないことが分かります。
VMware vSphere Container Storage Plug-in 2.1 Release Notes
この問題については、こちらのissueでも議論されているようでした。
vSphere CSI Controllerがデプロイされる動作
Cluster API Provider vSphereで、vSphere CSI Controllerが自動的にデプロイされている理由としては、ClusterResourceSetが利用されています。
ClusterResourceSetは、workload clusterを作成した際に、workload clusterに追加のコンポーネントを自動的にインストールできるようにする実験的な機能です。
CNIを毎回コマンドでインストールしているため、自動でインストールされると便利ではあります。
ClusterResourceSetの設定内容について確認してみようと思います。
workload clusterを作成する際に、cluster.yamlを作成しましたが、こちらの中身を見てみます。
$ clusterctl generate cluster vsphere-quickstart \ --infrastructure vsphere \ --kubernetes-version v1.25.5 \ --control-plane-machine-count 1 \ --worker-machine-count 3 > cluster.yaml
ClusterResourceSetのリソースの中に、csi-vsphere-configがあることが分かります。csi-vsphere-configの中身には、insecure-flag
が設定されていないことが分かります。
$ vi cluster.yaml --- apiVersion: addons.cluster.x-k8s.io/v1beta1 kind: ClusterResourceSet metadata: labels: cluster.x-k8s.io/cluster-name: vsphere-quickstart name: vsphere-quickstart-crs-0 namespace: default spec: clusterSelector: matchLabels: cluster.x-k8s.io/cluster-name: vsphere-quickstart resources: - kind: Secret name: vsphere-csi-controller - kind: ConfigMap name: vsphere-csi-controller-role - kind: ConfigMap name: vsphere-csi-controller-binding - kind: Secret name: csi-vsphere-config - kind: ConfigMap name: csi.vsphere.vmware.com - kind: ConfigMap name: vsphere-csi-node - kind: ConfigMap name: vsphere-csi-controller - kind: Secret name: cloud-controller-manager - kind: Secret name: cloud-provider-vsphere-credentials - kind: ConfigMap name: cpi-manifests : --- apiVersion: v1 kind: Secret metadata: name: csi-vsphere-config namespace: default stringData: data: | apiVersion: v1 kind: Secret metadata: name: csi-vsphere-config namespace: kube-system stringData: csi-vsphere.conf: |+ [Global] cluster-id = "default/vsphere-quickstart" [VirtualCenter "vcsa-1.home.lab"] user = "vCenter username" password = "vCenter password" datacenters = "datacenter name" [Network] public-network = "portgroup name" type: Opaque type: addons.cluster.x-k8s.io/resource-set
cluster.yamlのcsi-vsphere-configを書き換えても、vsphere-csi-controllerが起動してくることが分かりました。
また、csi-vsphere-configにthumbprintオプションを追加し、vCenterのサーバー証明書のthumbprintやvCenterのCAのthumbprintを指定してみましたが、エラーは解消しませんでした。
現状は、csi-vsphere-configを書き換えても、vSphere CSIはサポートされない組み合わせとなってしまうため、ClusterResourceSetを使う場合でもバージョンの更新が課題になってきそうに見えています。
Continuous ClusterResourceSetStrategy · Issue #4807 · kubernetes-sigs/cluster-api · GitHub
また、clusterctl.yamlで EXP_CLUSTER_RESOURCE_SET
を false にしても、Taintの設定上podが起動してこないため、現状は一度vSphere CSIを削除し、最新バージョンのvSphere CSIをインストールし直さないといけないようには見えており、他にいい方法がないか気になっています。