Kubernetes 1.21版本DaemonSet的OnDelete更新策略未按预期运行
问题原因
该问题属于Kubernetes DaemonSet的默认设计行为,核心是两个独立逻辑的边界差异:
- DaemonSet的
OnDelete更新策略仅作用于Pod模板(spec.template字段)内容变更的升级场景:该策略生效时,控制器不会主动重建已经运行的存量Pod,仅当Pod被手动删除后,才会使用新模板创建Pod。 - DaemonSet控制器的核心协调逻辑完全不受更新策略影响:控制器会持续校验所有已运行DaemonSet Pod的节点是否匹配DaemonSet最新的调度规则(包括nodeSelector、nodeAffinity、污点容忍度等),只要节点不再匹配最新规则,控制器会立即删除该节点上的对应Pod,该行为和更新策略配置无关。
本次操作修改的是DaemonSet的调度规则(新增nodeAffinity排除指定节点),不属于Pod模板更新触发的升级场景,因此OnDelete策略不会生效,控制器直接删除了不符合新调度规则的节点上的Pod。
可行解决方法
以下方案可匹配不同的使用需求:
方案1:断开目标Pod与DaemonSet的所属关系
若需要被排除节点上的现有Pod永久保留,不受DaemonSet后续规则变更影响,可在修改DaemonSet调度规则前,先移除对应Pod的所有者引用:
kubectl patch pod <被排除节点上的DaemonSet Pod名称> -p '{"metadata":{"ownerReferences":[]}}'
移除后该Pod变为独立运行的资源,DaemonSet控制器不会再对其执行任何操作,仅可手动删除。
方案2:使用污点配合实现渐进式下线
若仅需要存量Pod继续运行,手动删除后不再重建,可通过节点污点实现预期效果,无需修改DaemonSet的亲和性规则:
- 给需要排除的节点打NoSchedule污点:
kubectl taint node str-s6000-acs-8 daemonset-exclude=true:NoSchedule
- NoSchedule污点仅影响新Pod调度,不会驱逐已经运行的存量Pod,现有Pod可正常运行
- 后续手动删除该节点上的DaemonSet Pod时,新Pod因无法容忍节点污点不会被调度到该节点,完全匹配预期逻辑。
方案3:使用优先亲和性替代强制亲和性
若可以接受调度规则为优先满足而非强制,可将requiredDuringSchedulingIgnoredDuringExecution替换为preferredDuringSchedulingIgnoredDuringExecution,配置示例如下:
affinity: nodeAffinity: preferredDuringSchedulingIgnoredDuringExecution: - weight: 100 preference: matchExpressions: - key: "test_enabled" operator: "In" values: ["true"] - key: "kubernetes.io/hostname" operator: NotIn values: ["str-s6000-acs-8"]
该配置下DaemonSet控制器不会主动删除已在排除节点上运行的存量Pod,仅当Pod被手动删除后,会优先调度到其他符合条件的节点。
内容的提问来源于stack exchange,提问作者Renuka Manavalan
相关产品推荐
相关产品推荐

