Skip to content

[WIP] feat: Load the SchedulerConfig from a configuration file/text and make it easier to add plugins #881

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 8 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions PROJECT
Original file line number Diff line number Diff line change
Expand Up @@ -24,4 +24,12 @@ resources:
kind: InferenceModel
path: sigs.k8s.io/gateway-api-inference-extension/api/v1alpha1
version: v1alpha1
- api:
crdVersion: v1
namespaced: true
domain: x-k8s.io
group: inference
kind: EndpointPickerConfig
path: sigs.k8s.io/gateway-api-inference-extension/api/config/v1alpha1
version: v1alpha1
version: "3"
29 changes: 29 additions & 0 deletions api/config/v1alpha1/defaults.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
/*
Copyright 2025 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 v1alpha1

// SetDefaults_EndpointPickerConfig sets default values in a
// EndpointPickerConfig struct.
//
// This naming convension is required by the defalter-gen code.
func SetDefaults_EndpointPickerConfig(cfg *EndpointPickerConfig) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should use this function to default the parameters of the various in-tree plugins because defaulting is associated with the api version. I believe this function will be automatically invoked the file is decoded.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In general this "extension point" is used to set default values in the CR in question. Look at the examples you pointed me to. I don't think it should be used to specify default values for parameters of plugins. The plugins should handle that themselves.

This could be used, if we wanted to create default configurations, albeit in a round about way.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The in-tree plugins config types should be part of the versioned api, their defaulting should be as well.

See as an example: https://github.com/kubernetes/kubernetes/blob/master/pkg/scheduler/apis/config/v1/defaults.go

We can handle that as a followup though to keep this PR focused on defining the api.

for idx, pluginConfig := range cfg.Plugins {
if pluginConfig.Name == "" {
cfg.Plugins[idx].Name = pluginConfig.PluginName
}
}
}
22 changes: 22 additions & 0 deletions api/config/v1alpha1/doc.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
/*
Copyright 2025 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 v1alpha1 contains API Schema definitions for the
// inference.networking.x-k8s.io API group.
//
// +kubebuilder:object:generate=true
// +groupName=inference.networking.x-k8s.io
package v1alpha1
86 changes: 86 additions & 0 deletions api/config/v1alpha1/endpointpickerconfig_types.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
/*
Copyright 2025 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 v1alpha1

import (
"encoding/json"

metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
)

// +k8s:defaulter-gen=true
// +kubebuilder:object:root=true

// EndpointPickerConfig is the Schema for the endpointpickerconfigs API
type EndpointPickerConfig struct {
metav1.TypeMeta `json:",inline"`

// +required
// +kubebuilder:validation:Required
// Plugins is the list of plugins that will be instantiated.
Plugins []PluginSpec `json:"plugins"`

// +required
// +kubebuilder:validation:Required
// SchedulingProfiles is the list of named SchedulingProfiles
// that will be created.
SchedulingProfiles []SchedulingProfile `json:"schedulingProfiles"`
}
type PluginSpec struct {
// +optional
// Name provides a name for SchedulingProfile plugin entries to
// reference. If omitted, the value of the PluginName field
// will be used.
Name string `json:"name"`
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can we pls document all the parameters and their semantics

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done


// +required
// +kubebuilder:validation:Required
// PluginName specifies the plugin to be instantiated.
PluginName string `json:"pluginName"`

// +optional
// Parameters are the set of parameters to be passed to the plugin's
// factory function. The factory function is responsible
// to parse the parameters.
Parameters json.RawMessage `json:"parameters"`
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in kube-scheduler, we used runtime.Object, probably allows us to use k8s api-machinery functions for decoding https://github.com/kubernetes/kubernetes/blob/master/pkg/scheduler/apis/config/types.go#L207

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looking at the code in the K8S scheduler, runtime.Object is simply cast to the appropriate type used by the plugin. Those types seem to include a standard K8S TypeMeta stanza. You want every plugin's parameters object to start with apiVersion and kind? You were trying to same extra name tags, isn't here even more acute?

Also if we go with runtime.Object, every plugin with parameters would need to register it's schema in the global schema for the config...

}

type SchedulingProfile struct {
// +kubebuilder:validation:Required
// Name specifies the name of this SvhedulingProfile
Name string `json:"name"`

// +required
// +kubebuilder:validation:Required
// Plugins is the list of plugins for this SchedulingProfile. They are assigned
// to the appropriate "slots" based on their type.
Plugins []SchedulingProfilePlugin `json:"plugins"`
}

type SchedulingProfilePlugin struct {
// +required
// +kubebuilder:validation:Required
// PluginRef specifies a partiular Plugin instance to be associated with
// this SchedulingProfile. The reference is to the name of an
// entry of the Plugins defined in the configuration's Plugins
// section
PluginRef string `json:"pluginRef"`

// +optional
// Weight is the weight fo be used if this plugin is a Scorer.
Weight *int `json:"weight"`
}
126 changes: 126 additions & 0 deletions api/config/v1alpha1/zz_generated.deepcopy.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

38 changes: 38 additions & 0 deletions api/config/v1alpha1/zz_generated.defaults.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

69 changes: 69 additions & 0 deletions api/config/v1alpha1/zz_generated.register.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading