mirror of https://github.com/k3s-io/k3s
168 lines
5.9 KiB
Go
168 lines
5.9 KiB
Go
|
/*
|
||
|
Copyright 2014 The Kubernetes Authors.
|
||
|
|
||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||
|
you may not use this file except in compliance with the License.
|
||
|
You may obtain a copy of the License at
|
||
|
|
||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||
|
|
||
|
Unless required by applicable law or agreed to in writing, software
|
||
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||
|
See the License for the specific language governing permissions and
|
||
|
limitations under the License.
|
||
|
*/
|
||
|
|
||
|
package algorithmprovider
|
||
|
|
||
|
import (
|
||
|
"sort"
|
||
|
"strings"
|
||
|
|
||
|
utilfeature "k8s.io/apiserver/pkg/util/feature"
|
||
|
"k8s.io/klog"
|
||
|
"k8s.io/kubernetes/pkg/features"
|
||
|
schedulerapi "k8s.io/kubernetes/pkg/scheduler/apis/config"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/defaultbinder"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/defaultpodtopologyspread"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/imagelocality"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/interpodaffinity"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/nodeaffinity"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/nodename"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/nodeports"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/nodepreferavoidpods"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/noderesources"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/nodeunschedulable"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/nodevolumelimits"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/podtopologyspread"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/queuesort"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/tainttoleration"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/volumebinding"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/volumerestrictions"
|
||
|
"k8s.io/kubernetes/pkg/scheduler/framework/plugins/volumezone"
|
||
|
)
|
||
|
|
||
|
// ClusterAutoscalerProvider defines the default autoscaler provider
|
||
|
const ClusterAutoscalerProvider = "ClusterAutoscalerProvider"
|
||
|
|
||
|
// Registry is a collection of all available algorithm providers.
|
||
|
type Registry map[string]*schedulerapi.Plugins
|
||
|
|
||
|
// NewRegistry returns an algorithm provider registry instance.
|
||
|
func NewRegistry() Registry {
|
||
|
defaultConfig := getDefaultConfig()
|
||
|
applyFeatureGates(defaultConfig)
|
||
|
|
||
|
caConfig := getClusterAutoscalerConfig()
|
||
|
applyFeatureGates(caConfig)
|
||
|
|
||
|
return Registry{
|
||
|
schedulerapi.SchedulerDefaultProviderName: defaultConfig,
|
||
|
ClusterAutoscalerProvider: caConfig,
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// ListAlgorithmProviders lists registered algorithm providers.
|
||
|
func ListAlgorithmProviders() string {
|
||
|
r := NewRegistry()
|
||
|
var providers []string
|
||
|
for k := range r {
|
||
|
providers = append(providers, k)
|
||
|
}
|
||
|
sort.Strings(providers)
|
||
|
return strings.Join(providers, " | ")
|
||
|
}
|
||
|
|
||
|
func getDefaultConfig() *schedulerapi.Plugins {
|
||
|
return &schedulerapi.Plugins{
|
||
|
QueueSort: &schedulerapi.PluginSet{
|
||
|
Enabled: []schedulerapi.Plugin{
|
||
|
{Name: queuesort.Name},
|
||
|
},
|
||
|
},
|
||
|
PreFilter: &schedulerapi.PluginSet{
|
||
|
Enabled: []schedulerapi.Plugin{
|
||
|
{Name: noderesources.FitName},
|
||
|
{Name: nodeports.Name},
|
||
|
{Name: interpodaffinity.Name},
|
||
|
},
|
||
|
},
|
||
|
Filter: &schedulerapi.PluginSet{
|
||
|
Enabled: []schedulerapi.Plugin{
|
||
|
{Name: nodeunschedulable.Name},
|
||
|
{Name: noderesources.FitName},
|
||
|
{Name: nodename.Name},
|
||
|
{Name: nodeports.Name},
|
||
|
{Name: nodeaffinity.Name},
|
||
|
{Name: volumerestrictions.Name},
|
||
|
{Name: tainttoleration.Name},
|
||
|
{Name: nodevolumelimits.EBSName},
|
||
|
{Name: nodevolumelimits.GCEPDName},
|
||
|
{Name: nodevolumelimits.CSIName},
|
||
|
{Name: nodevolumelimits.AzureDiskName},
|
||
|
{Name: volumebinding.Name},
|
||
|
{Name: volumezone.Name},
|
||
|
{Name: interpodaffinity.Name},
|
||
|
},
|
||
|
},
|
||
|
PreScore: &schedulerapi.PluginSet{
|
||
|
Enabled: []schedulerapi.Plugin{
|
||
|
{Name: interpodaffinity.Name},
|
||
|
{Name: defaultpodtopologyspread.Name},
|
||
|
{Name: tainttoleration.Name},
|
||
|
},
|
||
|
},
|
||
|
Score: &schedulerapi.PluginSet{
|
||
|
Enabled: []schedulerapi.Plugin{
|
||
|
{Name: noderesources.BalancedAllocationName, Weight: 1},
|
||
|
{Name: imagelocality.Name, Weight: 1},
|
||
|
{Name: interpodaffinity.Name, Weight: 1},
|
||
|
{Name: noderesources.LeastAllocatedName, Weight: 1},
|
||
|
{Name: nodeaffinity.Name, Weight: 1},
|
||
|
{Name: nodepreferavoidpods.Name, Weight: 10000},
|
||
|
{Name: defaultpodtopologyspread.Name, Weight: 1},
|
||
|
{Name: tainttoleration.Name, Weight: 1},
|
||
|
},
|
||
|
},
|
||
|
Bind: &schedulerapi.PluginSet{
|
||
|
Enabled: []schedulerapi.Plugin{
|
||
|
{Name: defaultbinder.Name},
|
||
|
},
|
||
|
},
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func getClusterAutoscalerConfig() *schedulerapi.Plugins {
|
||
|
caConfig := getDefaultConfig()
|
||
|
// Replace least with most requested.
|
||
|
for i := range caConfig.Score.Enabled {
|
||
|
if caConfig.Score.Enabled[i].Name == noderesources.LeastAllocatedName {
|
||
|
caConfig.Score.Enabled[i].Name = noderesources.MostAllocatedName
|
||
|
}
|
||
|
}
|
||
|
return caConfig
|
||
|
}
|
||
|
|
||
|
func applyFeatureGates(config *schedulerapi.Plugins) {
|
||
|
// Only add EvenPodsSpread if the feature is enabled.
|
||
|
if utilfeature.DefaultFeatureGate.Enabled(features.EvenPodsSpread) {
|
||
|
klog.Infof("Registering EvenPodsSpread predicate and priority function")
|
||
|
f := schedulerapi.Plugin{Name: podtopologyspread.Name}
|
||
|
config.PreFilter.Enabled = append(config.PreFilter.Enabled, f)
|
||
|
config.Filter.Enabled = append(config.Filter.Enabled, f)
|
||
|
config.PreScore.Enabled = append(config.PreScore.Enabled, f)
|
||
|
s := schedulerapi.Plugin{Name: podtopologyspread.Name, Weight: 1}
|
||
|
config.Score.Enabled = append(config.Score.Enabled, s)
|
||
|
}
|
||
|
|
||
|
// Prioritizes nodes that satisfy pod's resource limits
|
||
|
if utilfeature.DefaultFeatureGate.Enabled(features.ResourceLimitsPriorityFunction) {
|
||
|
klog.Infof("Registering resourcelimits priority function")
|
||
|
s := schedulerapi.Plugin{Name: noderesources.ResourceLimitsName}
|
||
|
config.PreScore.Enabled = append(config.PreScore.Enabled, s)
|
||
|
s = schedulerapi.Plugin{Name: noderesources.ResourceLimitsName, Weight: 1}
|
||
|
config.Score.Enabled = append(config.Score.Enabled, s)
|
||
|
}
|
||
|
}
|