...

Source file src/k8s.io/kubernetes/pkg/scheduler/framework/plugins/helper/spread.go

Documentation: k8s.io/kubernetes/pkg/scheduler/framework/plugins/helper

     1  /*
     2  Copyright 2020 The Kubernetes Authors.
     3  
     4  Licensed under the Apache License, Version 2.0 (the "License");
     5  you may not use this file except in compliance with the License.
     6  You may obtain a copy of the License at
     7  
     8      http://www.apache.org/licenses/LICENSE-2.0
     9  
    10  Unless required by applicable law or agreed to in writing, software
    11  distributed under the License is distributed on an "AS IS" BASIS,
    12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  See the License for the specific language governing permissions and
    14  limitations under the License.
    15  */
    16  
    17  package helper
    18  
    19  import (
    20  	appsv1 "k8s.io/api/apps/v1"
    21  	v1 "k8s.io/api/core/v1"
    22  	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
    23  	"k8s.io/apimachinery/pkg/labels"
    24  	"k8s.io/apimachinery/pkg/runtime/schema"
    25  	appslisters "k8s.io/client-go/listers/apps/v1"
    26  	corelisters "k8s.io/client-go/listers/core/v1"
    27  )
    28  
    29  var (
    30  	rcKind = v1.SchemeGroupVersion.WithKind("ReplicationController")
    31  	rsKind = appsv1.SchemeGroupVersion.WithKind("ReplicaSet")
    32  	ssKind = appsv1.SchemeGroupVersion.WithKind("StatefulSet")
    33  )
    34  
    35  // DefaultSelector returns a selector deduced from the Services, Replication
    36  // Controllers, Replica Sets, and Stateful Sets matching the given pod.
    37  func DefaultSelector(
    38  	pod *v1.Pod,
    39  	sl corelisters.ServiceLister,
    40  	cl corelisters.ReplicationControllerLister,
    41  	rsl appslisters.ReplicaSetLister,
    42  	ssl appslisters.StatefulSetLister,
    43  ) labels.Selector {
    44  	labelSet := make(labels.Set)
    45  	// Since services, RCs, RSs and SSs match the pod, they won't have conflicting
    46  	// labels. Merging is safe.
    47  
    48  	if services, err := GetPodServices(sl, pod); err == nil {
    49  		for _, service := range services {
    50  			labelSet = labels.Merge(labelSet, service.Spec.Selector)
    51  		}
    52  	}
    53  	selector := labelSet.AsSelector()
    54  
    55  	owner := metav1.GetControllerOfNoCopy(pod)
    56  	if owner == nil {
    57  		return selector
    58  	}
    59  
    60  	gv, err := schema.ParseGroupVersion(owner.APIVersion)
    61  	if err != nil {
    62  		return selector
    63  	}
    64  
    65  	gvk := gv.WithKind(owner.Kind)
    66  	switch gvk {
    67  	case rcKind:
    68  		if rc, err := cl.ReplicationControllers(pod.Namespace).Get(owner.Name); err == nil {
    69  			labelSet = labels.Merge(labelSet, rc.Spec.Selector)
    70  			selector = labelSet.AsSelector()
    71  		}
    72  	case rsKind:
    73  		if rs, err := rsl.ReplicaSets(pod.Namespace).Get(owner.Name); err == nil {
    74  			if other, err := metav1.LabelSelectorAsSelector(rs.Spec.Selector); err == nil {
    75  				if r, ok := other.Requirements(); ok {
    76  					selector = selector.Add(r...)
    77  				}
    78  			}
    79  		}
    80  	case ssKind:
    81  		if ss, err := ssl.StatefulSets(pod.Namespace).Get(owner.Name); err == nil {
    82  			if other, err := metav1.LabelSelectorAsSelector(ss.Spec.Selector); err == nil {
    83  				if r, ok := other.Requirements(); ok {
    84  					selector = selector.Add(r...)
    85  				}
    86  			}
    87  		}
    88  	default:
    89  		// Not owned by a supported controller.
    90  	}
    91  
    92  	return selector
    93  }
    94  
    95  // GetPodServices gets the services that have the selector that match the labels on the given pod.
    96  func GetPodServices(sl corelisters.ServiceLister, pod *v1.Pod) ([]*v1.Service, error) {
    97  	allServices, err := sl.Services(pod.Namespace).List(labels.Everything())
    98  	if err != nil {
    99  		return nil, err
   100  	}
   101  
   102  	var services []*v1.Service
   103  	for i := range allServices {
   104  		service := allServices[i]
   105  		if service.Spec.Selector == nil {
   106  			// services with nil selectors match nothing, not everything.
   107  			continue
   108  		}
   109  		selector := labels.Set(service.Spec.Selector).AsSelectorPreValidated()
   110  		if selector.Matches(labels.Set(pod.Labels)) {
   111  			services = append(services, service)
   112  		}
   113  	}
   114  
   115  	return services, nil
   116  }
   117  

View as plain text