kubeadm certs renew all可续签所有证书,但需重启静态pod导致短暂api不可用;判断过期需执行kubeadm certs check-expiration、crictl ps和openssl命令;必须全量续签并按顺序逐台master重启pod,最后同步admin.conf至.kube/config并校验权限。

kubeadm certs renew 能在线续签,但“不停机”不等于“不中断控制平面服务”。证书更新后必须重启静态 Pod,这会造成短暂(通常 20–60 秒)的 API 不可用。真正在生产环境做到“用户无感”,关键不是跳过重启,而是控制重启节奏、顺序和验证闭环。
怎么判断证书是否已过期且集群还能连上?
先确认问题性质:如果 kubectl get nodes 报 x509: certificate has expired or is not yet valid,但 ssh 还能登录 master 节点,说明只是客户端或部分组件证书失效,控制平面可能仍在运行(尤其是 etcd 和 kube-apiserver 还活着)。此时优先执行检查:
-
kubeadm certs check-expiration—— 查所有证书状态;注意看admin.conf、apiserver、apiserver-kubelet-client这三项,它们最常导致kubectl失效 -
crictl ps | grep -E "(apiserver|controller-manager|scheduler)"—— 确认核心静态 Pod 是否还在运行 -
openssl x509 -in /etc/kubernetes/pki/apiserver.crt -noout -dates—— 直接读取证书时间,绕过 kubeadm 的缓存逻辑
为什么不能只 renew 一部分证书?
看似省事,实则埋雷。比如只运行 kubeadm certs renew apiserver,但漏掉 apiserver-kubelet-client,会导致 kubelet 无法再与 API Server 建立 TLS 连接,节点状态迅速变成 NotReady。高可用集群中各组件证书存在强依赖链:
-
ca.crt是根,所有其他证书都由它签名;kubeadm certs renew all会复用现有 CA,安全且省事 -
etcd-server和etcd-peer过期会导致 etcd 集群分裂,比 API Server 中断更致命 -
front-proxy-client过期会影响使用 OIDC 或 webhook 的认证流程,但不会立刻阻断kubectl
结论:除非你明确知道只有一项证书异常且与其他组件完全解耦(极少见),否则一律用 kubeadm certs renew all。
重启静态 Pod 的时机和顺序怎么控?
这是真正影响“是否算停机”的环节。不要在所有 master 上同时操作:
- 对三主集群,每次只动一个 master 节点:先移走
/etc/kubernetes/manifests/*.yaml,等crictl ps确认该节点上三个控制面容器已退出,再等 20 秒,再移回清单文件 - 等待新 Pod Ready 后(
crictl ps | grep Running+kubectl get nodes --kubeconfig /etc/kubernetes/admin.conf),再操作下一个 master - 切勿在第一个 master 的 kube-apiserver 尚未 Ready 时就去动第二个——否则整个集群 API 将彻底不可用
- 工作节点上的
kubelet会自动轮换自己的 client 证书(如果启用了--rotate-certificates),无需手动干预;但若你看到NodeReady反复震荡,要检查/var/lib/kubelet/pki/kubelet-client-current.pem是否被更新
更新完还要改 .kube/config 吗?
要,而且最容易漏。因为 kubeadm certs renew all 不会自动更新 $HOME/.kube/config 里的 client-certificate-data 字段——它用的是旧的 admin.conf 内容。所以必须手动同步:
-
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config(root 用户) - 普通用户需加
sudo chown $(id -u):$(id -g) $HOME/.kube/config修复权限 - 验证:运行
kubectl config view --raw -o jsonpath='{.users[0].user.client-certificate-data}' | base64 -d | openssl x509 -noout -dates,确认 Not After 时间已更新
这个步骤看起来 trivial,但在自动化脚本里若没做权限适配或路径判断,会导致后续所有 kubectl 操作继续失败——而你刚以为“已经修好了”。











