Skip to content

Commit 7b39611

Browse files
aeon-xruizhang0101
andauthored
[Feat] Support KEDA Auto Scaling in Production Stack Operator (#903)
* init Signed-off-by: aeon-x <talexcao@gmail.com> * update proto Signed-off-by: aeon-x <talexcao@gmail.com> * fix review comments Signed-off-by: aeon-x <talexcao@gmail.com> * fix review comments for autoscaling Signed-off-by: aeon-x <talexcao@gmail.com> * fix lint Signed-off-by: aeon-x <talexcao@gmail.com> --------- Signed-off-by: aeon-x <talexcao@gmail.com> Co-authored-by: Rui Zhang <51696593+ruizhang0101@users.noreply.github.com>
1 parent 276d481 commit 7b39611

7 files changed

Lines changed: 921 additions & 0 deletions

File tree

operator/api/v1alpha1/vllmruntime_types.go

Lines changed: 100 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,96 @@ type DeploymentConfig struct {
5151
SidecarConfig SidecarConfig `json:"sidecarConfig,omitempty"`
5252
}
5353

54+
// ScaleUpPolicy defines the HPA scaling behavior when scaling up
55+
type ScaleUpPolicy struct {
56+
// StabilizationWindowSeconds is the HPA stabilization window for scaling up
57+
// +kubebuilder:default=0
58+
StabilizationWindowSeconds *int32 `json:"stabilizationWindowSeconds,omitempty"`
59+
60+
// PodValue is the max pods to add per period
61+
// +kubebuilder:default=1
62+
// +kubebuilder:validation:Minimum=1
63+
PodValue *int32 `json:"podValue,omitempty"`
64+
65+
// PeriodSeconds is the period for the scale up policy
66+
// +kubebuilder:default=60
67+
// +kubebuilder:validation:Minimum=1
68+
PeriodSeconds *int32 `json:"periodSeconds,omitempty"`
69+
}
70+
71+
// ScaleDownPolicy defines the HPA scaling behavior when scaling down
72+
type ScaleDownPolicy struct {
73+
// StabilizationWindowSeconds is the HPA stabilization window for scaling down
74+
// +kubebuilder:default=300
75+
StabilizationWindowSeconds *int32 `json:"stabilizationWindowSeconds,omitempty"`
76+
77+
// PodValue is the max pods to remove per period
78+
// +kubebuilder:default=1
79+
// +kubebuilder:validation:Minimum=1
80+
PodValue *int32 `json:"podValue,omitempty"`
81+
82+
// PeriodSeconds is the period for the scale down policy
83+
// +kubebuilder:default=60
84+
// +kubebuilder:validation:Minimum=1
85+
PeriodSeconds *int32 `json:"periodSeconds,omitempty"`
86+
87+
// ScaleToZeroDelaySeconds is the wait time before scaling to zero (seconds).
88+
// Only applicable when minReplicas is set to 0.
89+
// +kubebuilder:default=1800
90+
ScaleToZeroDelaySeconds *int32 `json:"scaleToZeroDelaySeconds,omitempty"`
91+
}
92+
93+
// TriggerConfig defines the metric thresholds for autoscaling triggers
94+
type TriggerConfig struct {
95+
// PrometheusAddress is the Prometheus server address for metric queries
96+
// +kubebuilder:default="http://kube-prom-stack-kube-prome-prometheus.monitoring.svc:9090"
97+
PrometheusAddress string `json:"prometheusAddress,omitempty"`
98+
99+
// RequestsRunningThreshold is the per-pod concurrent requests threshold for scaling
100+
// +kubebuilder:default=5
101+
// +kubebuilder:validation:Minimum=1
102+
RequestsRunningThreshold *int32 `json:"requestsRunningThreshold,omitempty"`
103+
104+
// GenerationTokensThreshold is the per-pod generation tokens/s threshold for scaling
105+
// +kubebuilder:default=100
106+
// +kubebuilder:validation:Minimum=1
107+
GenerationTokensThreshold *int32 `json:"generationTokensThreshold,omitempty"`
108+
109+
// PromptTokensThreshold is the per-pod prompt tokens/s threshold for scaling
110+
// +kubebuilder:default=100
111+
// +kubebuilder:validation:Minimum=1
112+
PromptTokensThreshold *int32 `json:"promptTokensThreshold,omitempty"`
113+
}
114+
115+
// AutoscalingConfig defines the KEDA autoscaling configuration
116+
type AutoscalingConfig struct {
117+
// Enabled enables autoscaling
118+
Enabled bool `json:"enabled,omitempty"`
119+
120+
// MinReplicas is the minimum number of replicas (defaults to 1, set to 0 to enable scale-to-zero)
121+
// +kubebuilder:default=1
122+
// +kubebuilder:validation:Minimum=0
123+
MinReplicas *int32 `json:"minReplicas,omitempty"`
124+
125+
// MaxReplicas is the maximum number of replicas
126+
// +kubebuilder:validation:Required
127+
// +kubebuilder:validation:Minimum=1
128+
MaxReplicas int32 `json:"maxReplicas"`
129+
130+
// PollingInterval is how often KEDA checks metrics (seconds)
131+
// +kubebuilder:default=15
132+
PollingInterval *int32 `json:"pollingInterval,omitempty"`
133+
134+
// ScaleUpPolicy defines the scaling behavior when scaling up
135+
ScaleUpPolicy ScaleUpPolicy `json:"scaleUpPolicy,omitempty"`
136+
137+
// ScaleDownPolicy defines the scaling behavior when scaling down
138+
ScaleDownPolicy ScaleDownPolicy `json:"scaleDownPolicy,omitempty"`
139+
140+
// Triggers defines the metric thresholds for autoscaling
141+
Triggers TriggerConfig `json:"triggers,omitempty"`
142+
}
143+
54144
// VLLMRuntimeSpec defines the desired state of VLLMRuntime
55145
type VLLMRuntimeSpec struct {
56146
// Model configuration
@@ -67,6 +157,9 @@ type VLLMRuntimeSpec struct {
67157

68158
// Deployment configuration
69159
DeploymentConfig DeploymentConfig `json:"deploymentConfig"`
160+
161+
// Autoscaling configuration
162+
AutoscalingConfig *AutoscalingConfig `json:"autoscalingConfig,omitempty"`
70163
}
71164

72165
// VLLMConfig defines the vLLM server configuration
@@ -231,10 +324,17 @@ type VLLMRuntimeStatus struct {
231324

232325
// Last updated timestamp
233326
LastUpdated metav1.Time `json:"lastUpdated,omitempty"`
327+
328+
// Current replica count (used by scale subresource)
329+
Replicas int32 `json:"replicas,omitempty"`
330+
331+
// Label selector for pods (used by scale subresource for HPA AverageValue)
332+
Selector string `json:"selector,omitempty"`
234333
}
235334

236335
// +kubebuilder:object:root=true
237336
// +kubebuilder:subresource:status
337+
// +kubebuilder:subresource:scale:specpath=.spec.deploymentConfig.replicas,statuspath=.status.replicas,selectorpath=.status.selector
238338
// +kubebuilder:resource:shortName=vr
239339

240340
// VLLMRuntime is the Schema for the vllmruntimes API

operator/api/v1alpha1/zz_generated.deepcopy.go

Lines changed: 128 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)