主题
第十五部分:高可用、故障排查与高级进阶
本章聚焦生产级高可用架构设计、系统故障排查方法论、Service Mesh 引入决策、多集群管理以及性能调优实战。
15.1 高可用架构设计
15.1.1 控制平面高可用
标准 3 master 架构:
LB(HAProxy/Nginx/云 LB)
├── master-1: apiserver + etcd + scheduler + controller-manager
├── master-2: apiserver + etcd + scheduler + controller-manager
└── master-3: apiserver + etcd + scheduler + controller-manager
关键设计:
- etcd 3 节点保证容忍 1 个故障(Quorum = 2)
- apiserver 无状态,多实例前置 LB
- scheduler / controller-manager 通过 Leader Election 保证只有一个活跃
- 使用 keepalived 或云 LB 提供 VIP15.1.2 跨可用区部署
yaml
# 控制节点跨 AZ 分布
topologyKey: topology.kubernetes.io/zone
# 工作节点跨 AZ + 跨机型分布
# Pod 反亲和:确保关键服务不在同一 AZ
affinity:
podAntiAffinity:
requiredDuringSchedulingIgnoredDuringExecution:
- labelSelector:
matchLabels: { app: critical-service }
topologyKey: topology.kubernetes.io/zone15.1.3 5000 节点规模集群设计
控制平面:
- etcd 独立集群(5 节点,SSD 存储,独立网络)
- apiserver 3+ 实例,开启 --watch-cache
- scheduler 开启 percentageOfNodesToScore 优化
节点优化:
- kubelet --kube-api-qps=50 --kube-api-burst=100
- --max-pods=110(根据节点规格调整)
- --serialize-image-pulls=false
网络:
- 使用 eBPF 方案(Cilium)替代 iptables
- NodeLocal DNSCache 减少 CoreDNS 压力
分片策略:
- 按业务域划分多个集群(联邦管理)
- 单集群上限建议 5000 节点 / 15 万 Pod15.2 故障排查方法论
15.2.1 系统化排查流程
故障现象
↓
① 确认范围:单个 Pod / 整个 Service / 整个节点 / 整个集群?
↓
② 检查基础设施:
- 节点状态(kubectl get nodes)
- 网络连通性(ping / curl / dig)
- 存储状态(PVC Bound? PV Available?)
↓
③ 检查控制平面:
- apiserver 响应(kubectl get --raw /healthz)
- etcd 健康(etcdctl endpoint health)
- Controller 日志(journalctl -u kube-controller-manager)
↓
④ 检查具体组件:
- Pod 事件(kubectl describe pod)
- 容器日志(kubectl logs)
- kubelet 日志(journalctl -u kubelet)
- kube-proxy 日志
↓
⑤ 网络抓包(tcpdump / hubble)
↓
⑥ 根因定位 → 修复 → 复盘 → 改进15.2.2 高频故障场景
场景一:Pod Pending
bash
# 排查步骤
kubectl describe pod <name>
# 查看 Events:
# - FailedScheduling → 资源不足 / 污点不匹配 / 亲和性不满足
# - FailedMount → PVC 未绑定 / CSI 异常
# - ErrImagePull → 镜像不存在 / 认证失败
# 进一步检查
kubectl get events --field-selector involvedObject.name=<pod>
kubectl describe node <node> # 查看节点 Allocatable 和条件场景二:Pod CrashLoopBackOff
bash
# 排查步骤
kubectl logs <pod> --previous # 查看上次崩溃的日志
kubectl describe pod <pod> # 查看重启次数和原因
# 常见原因:
# 1. 应用启动失败(配置错误、依赖服务不可达)
# 2. Liveness 探针配置不当
# 3. OOMKilled(内存超限)→ 调大 limits
# 4. 非 PID 1 进程退出 → 使用 tini/dumb-init场景三:Service 无法访问
bash
# 排查链路
1. kubectl get endpoints <svc> # 端点是否存在?
2. kubectl get pod -l app=xxx -o wide # Pod 是否 Running + Ready?
3. 检查 kube-proxy 日志 # iptables/IPVS 规则是否更新?
4. 在 Pod 内 curl ClusterIP # 网络是否通?
5. tcpdump 抓包分析 # 流量到达哪里?场景四:Node NotReady
bash
# 排查步骤
journalctl -u kubelet -n 100 # kubelet 日志
systemctl status containerd # 容器运行时状态
df -h # 磁盘是否满?
free -h # 内存是否耗尽?
dmesg | tail # 内核错误?
# 常见原因:
# 1. PLEG 超时(容器运行时卡死)
# 2. 磁盘满(/var/lib/kubelet、镜像存储)
# 3. kubelet 证书过期
# 4. 网络分区(kubelet 无法连接 apiserver)15.3 Service Mesh 引入决策
15.3.1 何时引入 Service Mesh
✅ 适合引入:
- 微服务数量 > 50 个
- 需要统一的 mTLS、流量灰度、熔断
- 多语言栈,无法统一 SDK
- 有专门的 SRE 团队维护
❌ 不适合引入:
- 服务数量少(< 20 个)
- 团队规模小,维护能力有限
- 对性能极度敏感(Sidecar 增加 ~2ms 延迟)15.3.2 Istio 核心架构
数据平面:Envoy Sidecar(每个 Pod 注入)
→ 拦截所有进出流量
→ 执行 mTLS、路由、限流、熔断
控制平面:istiod
→ Pilot:服务发现、路由规则下发
→ Citadel:证书管理、mTLS
→ Galley:配置验证(已合并到 istiod)15.4 多集群管理
15.4.1 多集群方案对比
| 方案 | 特点 | 适用场景 |
|---|---|---|
| Karmada | CNCF 项目,标准化多集群 API | 统一管理多集群 |
| Cluster API | 声明式集群生命周期管理 | 自动化集群创建/升级 |
| Rancher | UI 管理多集群,集成 GitOps | 中小团队多集群管理 |
| Submariner | 跨集群网络互通 | 跨集群 Service 通信 |
15.4.2 多集群流量架构
多集群入口方案:
1. 全局 LB(云厂商 Global Accelerator / DNS 加权)
2. Service Mesh 跨集群(Istio multi-cluster)
3. Submariner 跨集群 Service(直连 Pod IP)15.5 性能调优实战
15.5.1 etcd 调优
bash
# 存储优化
- 使用 NVMe SSD(IOPS > 10000)
- 独立磁盘挂载 /var/lib/etcd
- 定期 defrag(碎片整理)
# 参数调优
--quota-backend-bytes=8589934592 # 8GB 配额上限
--snapshot-count=10000 # 快照频率
--heartbeat-interval=100 # 心跳间隔(ms)
--election-timeout=1000 # 选举超时(ms)15.5.2 kubelet 调优
bash
--kube-api-qps=50 --kube-api-burst=100 # 提高与 apiserver 通信速率
--serialize-image-pulls=false # 并行拉取镜像
--image-gc-high-threshold=85 # 镜像 GC 高阈值
--image-gc-low-threshold=80 # 镜像 GC 低阈值
--max-pods=110 # 每节点最大 Pod
--cpu-manager-policy=static # CPU 绑核(延迟敏感应用)
--topology-manager-policy=single-numa-node # NUMA 感知15.5.3 apiserver 调优
bash
--max-requests-inflight=3000 # 读请求并发
--max-mutating-requests-inflight=1000 # 写请求并发
--watch-cache-sizes=resource#1000 # Watch 缓存
--event-ttl=1h # 事件保留时间15.6 成本优化
1. 使用 VPA 推荐值调整 requests/limits(减少过度配置)
2. Spot/Preemptible 节点用于无状态工作负载
3. Cluster Autoscaler 按需扩缩节点
4. Karpenter 替代 Cluster Autoscaler(更快、更灵活)
5. 定期清理未使用的 PV、Service、ConfigMap
6. Kubecost 可视化资源成本15.7 本章小结
| 核心概念 | 关键要点 |
|---|---|
| 高可用 | 3 master + etcd 独立集群 + 跨 AZ |
| 故障排查 | 系统化流程:范围 → 基础设施 → 控制平面 → 组件 → 网络 |
| Service Mesh | > 50 微服务 + 统一 mTLS 需求时引入 |
| 多集群 | Karmada/Cluster API/Rancher,按团队规模选型 |
| 性能调优 | etcd SSD + kubelet 并行拉取 + apiserver 并发参数 |
| 成本优化 | VPA 推荐 + Spot 节点 + Karpenter + Kubecost |
练习
- 模拟 Node NotReady 故障(停止 kubelet),练习完整排查流程。
- 在测试集群部署 Istio,观察 Sidecar 注入和 mTLS 流量。
- 使用 VPA 分析现有工作负载的资源推荐值,对比实际配置。
- 设计一个 3 AZ 高可用架构方案,包含控制平面、存储、DNS。