Skip to content

Commit

Permalink
Merge pull request #76275 from krzysztof-jastrzebski/automated-cherry…
Browse files Browse the repository at this point in the history
…-pick-of-#76060-upstream-release-1.13

Automated cherry pick of #76060: Delete only unscheduled pods if node doesn't exist anymore.
  • Loading branch information
k8s-ci-robot committed May 22, 2019
2 parents 285833b + 3aab41f commit b386646
Show file tree
Hide file tree
Showing 2 changed files with 29 additions and 6 deletions.
13 changes: 8 additions & 5 deletions pkg/controller/daemon/daemon_controller.go
Expand Up @@ -966,10 +966,10 @@ func (dsc *DaemonSetsController) manage(ds *apps.DaemonSet, hash string) error {
failedPodsObserved += failedPodsObservedOnNode
}

// Remove pods assigned to not existing nodes when daemonset pods are scheduled by default scheduler.
// Remove unscheduled pods assigned to not existing nodes when daemonset pods are scheduled by scheduler.
// If node doesn't exist then pods are never scheduled and can't be deleted by PodGCController.
if utilfeature.DefaultFeatureGate.Enabled(features.ScheduleDaemonSetPods) {
podsToDelete = append(podsToDelete, getPodsWithoutNode(nodeList, nodeToDaemonPods)...)
podsToDelete = append(podsToDelete, getUnscheduledPodsWithoutNode(nodeList, nodeToDaemonPods)...)
}

// Label new pods using the hash label value of the current history when creating them
Expand Down Expand Up @@ -1542,8 +1542,9 @@ func failedPodsBackoffKey(ds *apps.DaemonSet, nodeName string) string {
return fmt.Sprintf("%s/%d/%s", ds.UID, ds.Status.ObservedGeneration, nodeName)
}

// getPodsWithoutNode returns list of pods assigned to not existing nodes.
func getPodsWithoutNode(runningNodesList []*v1.Node, nodeToDaemonPods map[string][]*v1.Pod) []string {
// getUnscheduledPodsWithoutNode returns list of unscheduled pods assigned to not existing nodes.
// Returned pods can't be deleted by PodGCController so they should be deleted by DaemonSetController.
func getUnscheduledPodsWithoutNode(runningNodesList []*v1.Node, nodeToDaemonPods map[string][]*v1.Pod) []string {
var results []string
isNodeRunning := make(map[string]bool)
for _, node := range runningNodesList {
Expand All @@ -1552,7 +1553,9 @@ func getPodsWithoutNode(runningNodesList []*v1.Node, nodeToDaemonPods map[string
for n, pods := range nodeToDaemonPods {
if !isNodeRunning[n] {
for _, pod := range pods {
results = append(results, pod.Name)
if len(pod.Spec.NodeName) == 0 {
results = append(results, pod.Name)
}
}
}
}
Expand Down
22 changes: 21 additions & 1 deletion pkg/controller/daemon/daemon_controller_test.go
Expand Up @@ -2479,7 +2479,7 @@ func TestDeleteNoDaemonPod(t *testing.T) {
}
}

func TestDeletePodForNotExistingNode(t *testing.T) {
func TestDeleteUnscheduledPodForNotExistingNode(t *testing.T) {
for _, f := range []bool{true, false} {
defer utilfeaturetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.ScheduleDaemonSetPods, f)()
for _, strategy := range updateStrategies() {
Expand All @@ -2493,6 +2493,26 @@ func TestDeletePodForNotExistingNode(t *testing.T) {
addNodes(manager.nodeStore, 0, 1, nil)
addPods(manager.podStore, "node-0", simpleDaemonSetLabel, ds, 1)
addPods(manager.podStore, "node-1", simpleDaemonSetLabel, ds, 1)

podScheduledUsingAffinity := newPod("pod1-node-3", "", simpleDaemonSetLabel, ds)
podScheduledUsingAffinity.Spec.Affinity = &v1.Affinity{
NodeAffinity: &v1.NodeAffinity{
RequiredDuringSchedulingIgnoredDuringExecution: &v1.NodeSelector{
NodeSelectorTerms: []v1.NodeSelectorTerm{
{
MatchFields: []v1.NodeSelectorRequirement{
{
Key: schedulerapi.NodeFieldSelectorKeyNodeName,
Operator: v1.NodeSelectorOpIn,
Values: []string{"node-2"},
},
},
},
},
},
},
}
manager.podStore.Add(podScheduledUsingAffinity)
if f {
syncAndValidateDaemonSets(t, manager, ds, podControl, 0, 1, 0)
} else {
Expand Down

0 comments on commit b386646

Please sign in to comment.