自定义调度器

使用自定义调度器,可以通过编写调度器的代码来实现带有特定标签的 Pod 只能调度到特定节点上的功能

具体步骤如下:

创建一个带有net-speed: fast 标签的 NodeSelector,用于选择带有对应标签的节点:

nodeSelector := map[string]string{
    "net-speed": "fast",
}

创建一个调度器扩展程序,实现对于满足条件的 Pod 只在标有 net-speed: fast 标签的节点上调度的逻辑:

func schedulerExtender(pod *v1.Pod, nodeInfo *schedulernodeinfo.NodeInfo) (*framework.Status, time.Duration) {
    if _, ok := pod.ObjectMeta.Labels["net-speed"]; !ok {
        // 如果 Pod 没有带有 net-speed 标签,直接允许调度到所有节点
        return nil, 0
    }

    if _, ok := nodeInfo.Node().Labels["net-speed"]; !ok {
        // 如果节点不带有 net-speed 标签,拒绝调度
        return framework.NewStatus(framework.Unschedulable, "node does not have net-speed:1G label"), 0
    }

    // 如果节点和 Pod 都带有 net-speed: 1G 标签,允许调度到这个节点上
    return nil, 0
}

使用调度器框架(例如 kube-scheduler)注册调度器扩展程序,使得调度器能够调用它:

func main() {
    // 创建 scheduler framework 配置
    schedConfig := frameworkconfig.Config{
        Plugins: &frameworkplugins.Config{
            PreFilter: &preemptor.Preemptor{},
            Filter: &frameworkplugins.FilterConfig{
                Plugins: []frameworkplugins.Plugin{
                    &podtopologyspread.TopologySpread{},
                    &nodeaffinity.NodeAffinity{},
                    &nodeports.NodePorts{},
                },
            },
            PostFilter: &frameworkplugins.PostFilterConfig{
                Plugins: []frameworkplugins.Plugin{
                    &defaultbinder.DefaultBinder{},
                },
            },
            Score: &frameworkplugins.ScoreConfig{
                Plugins: []frameworkplugins.Plugin{
                    &nodeResourcesFit{},
                    &nodeResourcesLeastAllocated{},
                    &nodeResourcesMostAllocated{},
                    &nodeResourcesMatching{},
                    &podTopologySpread{},
                },
            },
            Reserve: &frameworkplugins.ReserveConfig{
                Plugins: []frameworkplugins.Plugin{
                    &volumeBinding{},
                },
            },
        },
    }

    // 注册 scheduler extender
    framework.RegisterPlugin(&framework.Plugin{
        Name: "NetSpeedSchedulerExtender",
        Func: schedulerExtender,
    })

    // 创建 scheduler
    s, err := scheduler.New(
        config.GetClientSet(),
        config.GetInformerFactory(),
        framework.NewDefaultFramework(schedConfig),
        factory.NewCachedCSRFinder(config.GetClientSet()),
    )
    if err != nil {
        klog.Fatalf("Error creating scheduler: %v", err)
    }

    // 启动 scheduler
    s.Run()
}

这样,只有带有 net-speed: 1G标签的节点能够被带有对应标签的 Pod 调度,其他节点因为不满足调度器扩展程序的条件而