Pod驱逐的触发机制
Kubernetes网站运维中,Pod驱逐(Eviction)是节点压力管理的核心保护机制。当节点资源压力超过阈值时,kubelet会主动终止Pod以释放资源保障节点稳定运行。理解驱逐机制是SRE稳定性工程的基础能力。Pod驱逐分为两类:硬驱逐(Hard Eviction)由节点资源超过硬性阈值立即触发,软驱逐(Soft Eviction)由资源超过软性阈值且持续超过宽限期触发。
节点压力驱逐的阈值配置
kubelet的驱逐阈值通过–eviction-hard和–eviction-soft参数配置:
# kubelet默认硬驱逐阈值
--eviction-hard=memory.available<100Mi,nodefs.available<10%,nodefs.inodesFree<5%,imagefs.available<15%
# 软驱逐配置示例(需同时配宽限期)
--eviction-soft=memory.available<200Mi,nodefs.available<20%
--eviction-soft-grace-period=memory.available=1m30s,nodefs.available=2m
# 查看当前节点配置
kubectl describe node $NODE | grep -A 20 "Allocated resources"
当节点可用内存低于100Mi时,kubelet立即开始驱逐Pod。驱逐优先级排序为:先驱逐无请求限制的BestEffort Pod,再驱逐超出请求量的Burstable Pod,最后驱逐Guaranteed Pod中占用最多的实例。
Pod驱逐事件的诊断方法
查看驱逐事件记录
# 查看命名空间下所有驱逐事件
kubectl get events -A --field-selector reason=Eviction --sort-by='.lastTimestamp'
# 查看特定节点的驱逐事件
kubectl get events --field-selector reason=Eviction,involvedObject.name=$NODE
# 查看Pod被驱逐的详细原因
kubectl describe pod $POD | grep -A 10 "Events"
# 典型输出:
# Status: Failed
# Reason: Evicted
# Message: The node was low on resource: memory.
# Pod $POD was using 1632Mi, which exceeds its request of 0.
分析节点资源状况
# 查看节点资源使用率
kubectl top nodes
# 查看节点详细资源分配
kubectl describe node $NODE | grep -A 20 "Allocated resources"
# 输出示例:
# Allocated resources:
# CPU Requests: 8200m (51%) CPU Limits: 12600m (78%)
# Memory Requests: 28Gi (72%) Memory Limits: 32Gi (82%)
# 查看节点容量与可分配
kubectl get node $NODE -o jsonpath='{.status.allocatable}'
当CPU Requests超过50%或Memory Requests超过70%时,就该考虑扩容或调度优化。
常见Pod驱逐场景与应对方案
场景一:内存压力驱逐
内存压力是最常见的驱逐原因。诊断步骤:
# 1. 检查节点内存使用
ssh $NODE "free -h"
cat /proc/meminfo | grep -E 'MemAvailable|SwapTotal'
# 2. 查看节点上所有Pod的内存使用
kubectl top pods -A --sort-by=memory --field-selector spec.nodeName=$NODE
# 3. 检查是否有Pod未设置资源限制
kubectl get pods -A -o json | jq -r '.items[] |
select(.spec.nodeName=="NODE_NAME") |
.metadata.name + " mem_limit: " +
(.spec.containers[].resources.limits.memory // "NONE")'
修复方案:为所有Pod设置requests和limits,将BestEffort Pod改为Burstable或Guaranteed;对内存使用增长型服务(如JVM应用)设置合理的内存限制并启用GC调优;考虑使用LimitRange强制命名空间级别的默认资源限制。
场景二:磁盘压力驱逐
节点磁盘空间不足触发驱逐时:
# 检查节点磁盘使用
ssh $NODE "df -h / /var/lib/docker"
# 清理Docker镜像和容器
ssh $NODE "docker system prune -af --volumes"
# 清理已完成的Pod日志
ssh $NODE "find /var/log/pods -name '*.log' -mtime +7 -delete"
# 配置kubelet日志轮转
# /var/lib/kubelet/config.yaml
maxLogFiles: 5
maxLogSizeMB: 50
场景三:PDB配置不当导致级联驱逐
PodDisruptionBudget配置不当可能在节点维护时导致级联故障:
# 检查PDB配置
kubectl get pdb -A -o wide
# 健康的PDB示例
apiVersion: policy/v1
kind: PodDisruptionBudget
metadata:
name: api-server-pdb
spec:
minAvailable: 60% # 不使用100%,留出驱逐空间
selector:
matchLabels:
app: api-server
避免设置minAvailable: 100%或maxUnavailable: 0,这会导致节点排空(drain)操作无限期阻塞,影响集群运维。
Pod驱逐后的调度恢复优化
Pod被驱逐后进入Failed状态,控制器会创建替代Pod重新调度。优化调度恢复速度的方案:
第一,配置Pod优先级和抢占机制。关键业务设置高优先级Class,当集群资源紧张时高优先级Pod可以抢占低优先级Pod的资源。
第二,启用Descheduler进行二次调度优化。长时间运行的集群会出现Pod分布不均衡问题,Descheduler根据策略重新平衡Pod分布:
# Descheduler策略配置
apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
"RemoveDuplicates":
enabled: true
"LowNodeUtilization":
enabled: true
params:
nodeResourceUtilizationThresholds:
thresholds:
cpu: 20
memory: 20
targetThresholds:
cpu: 50
memory: 50
第三,为关键服务配置Topology Spread Constraints,确保Pod在可用区之间均匀分布,单个节点驱逐不会导致服务容量大幅下降。
监控告警体系建设
对于Kubernetes集群稳定性运维,围绕Pod驱逐需要建立三层监控:节点层监控(memory.available、nodefs.available接近驱逐阈值的比例)、Pod层监控(OOMKilled和Evicted事件计数)、业务层监控(服务可用性和请求成功率)。当节点可用内存低于500Mi时触发P2告警,低于200Mi时触发P1告警,为SRE团队预留足够的应急响应窗口。
原创文章,作者:小编,如若转载,请注明出处:https://www.yunthe.com/kubernetes-ji-qun-pod-qu-zhu-wen-ti-zhen-duan-cong-jie-dian/