kubernetes 證書在線更新

各個證書的過期時間

/etc/kubernetes/pki/apiserver.crt                #1年有效期
/etc/kubernetes/pki/front-proxy-ca.crt           #10年有效期
/etc/kubernetes/pki/ca.crt                       #10年有效期
/etc/kubernetes/pki/apiserver-etcd-client.crt    #1年有效期
/etc/kubernetes/pki/front-proxy-client.crt       #1年有效期
/etc/kubernetes/pki/etcd/server.crt              #1年有效期
/etc/kubernetes/pki/etcd/ca.crt                  #10年有效期
/etc/kubernetes/pki/etcd/peer.crt                #1年有效期
/etc/kubernetes/pki/etcd/healthcheck-client.crt  #1年有效期
/etc/kubernetes/pki/apiserver-kubelet-client.crt #1年有效期

可用於檢查證書過期時間:

方法1

kubeadm alpha certs check-expiration

方法2

openssl x509 -noout -dates -in /etc/kubernetes/pki/apiserver.crt
kubeadm alpha certs 命令詳解:
Available Commands:
  certificate-key  生成證書和key
  check-expiration  檢測證書過期時間
  renew            續訂Kubernetes集羣的證書
  kubeadm alpha certs命令僅支持v1.15及其以上的版本。
kubeadm alpha certs check-expiration

該命令顯示 /etc/kubernetes/pki 文件夾中的客戶端證書以及 kubeadm 使用的 KUBECONFIG 文件中嵌入的客戶端證書的到期時間/剩餘時間。

如果你運行了一個高可用的集羣,這個命令需要在所有控制面板節點上執行。

接下來我們來更新我們的集羣證書,下面的操作都是在 master 節點上進行,首先備份原有證書:

mkdir /etc/kubernetes.bak
cp -r /etc/kubernetes/pki/ /etc/kubernetes.bak
cp /etc/kubernetes/*.conf /etc/kubernetes.bak
然後備份 etcd 數據目錄:
cp -r /var/lib/etcd /var/lib/etcd.bak

用 Kubernetes 證書 API 更新證書

除了上述的一鍵手動更新證書之外,還可以使用 Kubernetes 證書 API 執行手動證書更新。對於線上環境我們可能並不會去冒險經常更新集羣或者去更新證書,這些畢竟是有風險的,所以我們希望生成的證書有效期足夠長,雖然從安全性角度來說不推薦這樣做,但是對於某些場景下一個足夠長的證書有效期也是非常有必要的。有很多管理員就是去手動更改 kubeadm 的源碼爲10年,然後重新編譯來創建集羣,這種方式雖然可以達到目的,但是不推薦使用這種方式,特別是當你想要更新集羣的時候,還得用新版本進行更新。其實 Kubernetes 提供了一種 API 的方式可以來幫助我們生成一個足夠長證書有效期。
要使用內置的 API 方式來簽名,首先我們需要配置 kube-controller-manager 組件的 --experimental-cluster-signing-duration 參數,將其調整爲10年,我們這裏是 kubeadm 安裝的集羣,所以直接修改靜態 Pod 的 yaml 文件即可:

vim /etc/kubernetes/manifests/kube-controller-manager.yaml
......
spec:
  containers:
  - command:
    - kube-controller-manager
     #設置證書有效期爲 10 年
    - --experimental-cluster-signing-duration=87600h 
    - --client-ca-file=/etc/kubernetes/pki/ca.crt
......

修改完成後 kube-controller-manager 會自動重啓生效。然後我們需要使用下面的命令爲 Kubernetes 證書 API 創建一個證書籤名請求。如果您設置例如 cert-manager 等外部簽名者,則會自動批准證書籤名請求(CSRs)。否者,您必須使用 kubectl certificate 命令手動批准證書。以下 kubeadm 命令輸出要批准的證書名稱,然後等待批准發生:

kubeadm alpha certs renew all --use-api --config kubeadm.yaml &

輸出類似於以下內容:

[1] 2890
[certs] Certificate request "kubeadm-cert-kubernetes-admin-pn99f" created

#然後接下來我們需要去手動批准證書:

kubectl get csr
NAME                                  AGE   REQUESTOR          CONDITION
kubeadm-cert-kubernetes-admin-pn99f   64s   kubernetes-admin   Pending

手動批准證書

kubectl certificate approve kubeadm-cert-kubernetes-admin-pn99f
certificatesigningrequest.certificates.k8s.io/kubeadm-cert-kubernetes-admin-pn99f approved 

用同樣的方式爲處於 Pending 狀態的 csr 執行批准操作,直到所有的 csr 都批准完成爲止。最後所有的 csr 列表狀態如下所示:

kubectl get csr
NAME                                                AGE     REQUESTOR          CONDITION
kubeadm-cert-front-proxy-client-llhrj               30s     kubernetes-admin   Approved,Issued
kubeadm-cert-kube-apiserver-2s6kf                   2m43s   kubernetes-admin   Approved,Issued
kubeadm-cert-kube-apiserver-etcd-client-t9pkx       2m7s    kubernetes-admin   Approved,Issued
kubeadm-cert-kube-apiserver-kubelet-client-pjbjm    108s    kubernetes-admin   Approved,Issued
kubeadm-cert-kube-etcd-healthcheck-client-8dcn8     64s     kubernetes-admin   Approved,Issued
kubeadm-cert-kubernetes-admin-pn99f                 4m29s   kubernetes-admin   Approved,Issued
kubeadm-cert-system:kube-controller-manager-mr86h   79s     kubernetes-admin   Approved,Issued
kubeadm-cert-system:kube-scheduler-t8lnw            17s     kubernetes-admin   Approved,Issued
kubeadm-cert-ydzs-master-cqh4s                      52s     kubernetes-admin   Approved,Issued
kubeadm-cert-ydzs-master-lvbr5                      41s     kubernetes-admin   Approved,Issued

批准完成後檢查證書的有效期:

kubeadm alpha certs check-expiration
CERTIFICATE                EXPIRES                  RESIDUAL TIME   EXTERNALLY MANAGED
admin.conf                 Nov 05, 2029 11:53 UTC   9y              no
apiserver                  Nov 05, 2029 11:54 UTC   9y              no
apiserver-etcd-client      Nov 05, 2029 11:53 UTC   9y              no
apiserver-kubelet-client   Nov 05, 2029 11:54 UTC   9y              no
controller-manager.conf    Nov 05, 2029 11:54 UTC   9y              no
etcd-healthcheck-client    Nov 05, 2029 11:53 UTC   9y              no
etcd-peer                  Nov 05, 2029 11:53 UTC   9y              no
etcd-server                Nov 05, 2029 11:54 UTC   9y              no
front-proxy-client         Nov 05, 2029 11:54 UTC   9y              no
scheduler.conf             Nov 05, 2029 11:53 UTC   9y              no

我們可以看到已經延長小10年了,這是因爲 ca 證書的有效期只有10年。

但是現在我們還不能直接重啓控制面板的幾個組件,這是因爲使用 kubeadm 安裝的集羣對應的 etcd 默認是使用的 /etc/kubernetes/pki/etcd/ca.crt 這個證書進行前面的,而上面我們用命令 kubectl certificate approve 批准過後的證書是使用的默認的 /etc/kubernetes/pki/ca.crt 證書進行簽發的,所以我們需要替換 etcd 中的 ca 機構證書:

先拷貝靜態 Pod 資源清單

cp -r /etc/kubernetes/manifests/ /etc/kubernetes/manifests.bak
vi /etc/kubernetes/manifests/etcd.yaml
......
spec:
  containers:
  - command:
    - etcd
    # 修改爲 CA 文件
    - --peer-trusted-ca-file=/etc/kubernetes/pki/ca.crt
    - --trusted-ca-file=/etc/kubernetes/pki/ca.crt
......
    volumeMounts:
    - mountPath: /var/lib/etcd
      name: etcd-data
    - mountPath: /etc/kubernetes/pki  # 更改證書目錄
      name: etcd-certs
  volumes:
  - hostPath:
      path: /etc/kubernetes/pki  # 將 pki 目錄掛載到 etcd 中去
      type: DirectoryOrCreate
    name: etcd-certs
  - hostPath:
      path: /var/lib/etcd 
      type: DirectoryOrCreate
    name: etcd-data
......

由於 kube-apiserver 要連接 etcd 集羣,所以也需要重新修改對應的 etcd ca 文件:

vim /etc/kubernetes/manifests/kube-apiserver.yaml
......
spec:
  containers:
  - command:
    - kube-apiserver
    # 將etcd ca文件修改爲默認的ca.crt文件
    - --etcd-cafile=/etc/kubernetes/pki/ca.crt
......

除此之外還需要替換 requestheader-client-ca-file 文件,默認是 /etc/kubernetes/pki/front-proxy-ca.crt 文件,現在也需要替換成默認的 CA 文件,否則使用聚合 API,比如安裝了 metrics-server 後執行 kubectl top 命令就會報錯:

cp /etc/kubernetes/pki/ca.crt /etc/kubernetes/pki/front-proxy-ca.crt
cp /etc/kubernetes/pki/ca.key /etc/kubernetes/pki/front-proxy-ca.key

由於是靜態 Pod,修改完成後上面的組件都會自動重啓生效。由於我們當前版本的 kubelet 默認開啓了證書自動輪轉,所以 kubelet 的證書也不用再去管理了,這樣我就將證書更新成10有效期了。在操作之前一定要先對證書目錄進行備份,防止操作錯誤進行回滾。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章