我們的生產環境 kubernetes 集群是用阿里雲服務器自己搭建的高可用集群(詳見之前的博文),這篇博文記錄的是如何通過已有集群的1台 master 服務器的阿里雲ECS鏡像恢復出同樣配置的新集群,kubernetes 版本是 1.17.0。
這台 master 服務器的主機名是 k8s-master0,IP地址是 10.0.1.81。
首先對 k8s-master0 服務器打快照並生成鏡像,用這個鏡像創建新的服務器,新服務器的 hostname 也要用 k8s-master0(如果要換主機名,參考博文),新服務器 IP 地址為10.0.9.171。
通過鏡像創建新集群主要面臨的是 IP 地址變化帶來的問題,為了解決這個問題,需要進行以下幾個操作:
1)替換 /etc/kubernetes 中與 IP 地址關聯的配置
oldip=10.0.1.81
newip=10.0.9.171
cd /etc/kubernetes
find . -type f | xargs grep $oldip
find . -type f | xargs sed -i "s/$oldip/$newip/"
find . -type f | xargs grep $newip
2)給 etcd 啟動命令添加參數(不需要該步驟)
打開 /etc/kubernetes/manifests/etcd.yaml
,給command
添加
--initial-cluster-state=new
--force-new-cluster
3)通過 iptables 將舊 IP 地址映射到新 IP 地址(不需要該步驟)
iptables -t nat -A OUTPUT -d 10.0.1.81 -j DNAT --to-destination 10.0.9.171
4)修改 /etc/hosts 中涉及舊 IP 地址的解析(如果有)
vim /etc/hosts
%s/10.0.1.81/10.0.9.171
5)修改集群配置與舊 IP 地址相關的配置
kubectl -n kube-system edit cm kubeadm-config
%s/10.0.1.81/10.0.9.171
修改好 IP 地址之后,重新生成 etcd-server 證書(這個證書與IP地址關聯)
重新生成相關 ssl 證書(etcd-server, apiserver, apiserver-kubelet-client, front-proxy-client)
cd /etc/kubernetes/pki/etcd
rm server.crt server.key
kubeadm init phase certs etcd-server
rm apiserver.crt apiserver.key
kubeadm init phase certs apiserver --control-plane-endpoint "k8s-api:6443"
rm apiserver-kubelet-client.crt apiserver-kubelet-client.key
kubeadm init phase certs apiserver-kubelet-client
rm front-proxy-client.crt front-proxy-client.key
kubeadm init phase certs front-proxy-client
更新當前用戶的 .kube/config
cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
重啟 kubelet 與 docker 服務之后集群就可以恢復
systemctl restart kubelet && systemctl restart docker
這時通過 kubectl get nodes
命令可以看到 k8s-master0
處於 Ready
狀態(注:如果新 master 服務器使用的是不同的主機名,k8s-master0 會顯示 NotReady)
接着去掉之前在 (不需要該步驟)/etc/kubernetes/manifests/etcd.yaml
中給 etcd 啟動命令添加的參數(需要重啟 kubelet 與 docker 服務使修改生效)
--initial-cluster-state=new
--force-new-cluster
最后生成 node 加入集群的命令
$ kubeadm token create --print-join-command
通過新生成的命令加入新的 node
kubeadm join k8s-api:6443 --token ***** --discovery-token-ca-cert-hash *****
並刪除所有舊的 NotReady 狀態的 node
kubectl delete node $(kubectl get nodes | grep NotReady | cut -d " " -f1)
就大功告成了!
后續博文:
參考資料: