Skip to content

Added changes to support alternative recommender #4131

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

Merged
merged 1 commit into from
Nov 16, 2021
Merged
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
18 changes: 18 additions & 0 deletions vertical-pod-autoscaler/deploy/vpa-v1-crd-gen.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -268,6 +268,23 @@ spec:
description: 'Specification of the behavior of the autoscaler. More info:
https://git.k8s.io/community/contributors/devel/api-conventions.md#spec-and-status.'
properties:
recommenders:
description: Recommender responsible for generating recommendation
for this object. List should be empty (then the default recommender
will generate the recommendation) or contain exactly one recommender.
items:
description: VerticalPodAutoscalerRecommenderSelector points to
a specific Vertical Pod Autoscaler recommender. In the future it
might pass parameters to the recommender.
properties:
name:
description: Name of the recommender responsible for generating
recommendation for this object.
type: string
required:
- name
type: object
type: array
resourcePolicy:
description: Controls how the autoscaler computes recommended resources.
The resource policy may be used to set constraints on the recommendations
Expand Down Expand Up @@ -493,6 +510,7 @@ spec:
type: object
served: true
storage: true
subresources: {}
- name: v1beta2
schema:
openAPIV3Schema:
Expand Down
2 changes: 1 addition & 1 deletion vertical-pod-autoscaler/e2e/v1/actuation.go
Original file line number Diff line number Diff line change
Expand Up @@ -321,7 +321,7 @@ var _ = ActuationSuiteE2eDescribe("Actuation", func() {
hamsterResourceList := apiv1.ResourceList{apiv1.ResourceCPU: ParseQuantityOrDie("100m")}
sidecarResourceList := apiv1.ResourceList{apiv1.ResourceCPU: ParseQuantityOrDie("5000m")}

vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Spec.UpdatePolicy.UpdateMode = &mode

vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
Expand Down
26 changes: 13 additions & 13 deletions vertical-pod-autoscaler/e2e/v1/admission_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d := NewHamsterDeploymentWithResources(f, ParseQuantityOrDie("100m") /*cpu*/, ParseQuantityOrDie("100Mi") /*memory*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand All @@ -67,7 +67,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d := NewHamsterDeploymentWithResources(f, ParseQuantityOrDie("100m") /*cpu*/, ParseQuantityOrDie("100Mi") /*memory*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand Down Expand Up @@ -111,7 +111,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d := NewHamsterDeploymentWithGuaranteedResources(f, ParseQuantityOrDie("100m") /*cpu*/, ParseQuantityOrDie("100Mi") /*memory*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand Down Expand Up @@ -142,7 +142,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
ParseQuantityOrDie("150m") /*cpu limit*/, ParseQuantityOrDie("200Mi") /*memory limit*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand Down Expand Up @@ -173,7 +173,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
ParseQuantityOrDie("500m") /*cpu limit*/, ParseQuantityOrDie("500Mi") /*memory limit*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand Down Expand Up @@ -216,7 +216,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d := NewHamsterDeploymentWithResourcesAndLimits(f, startCpuRequest, startMemRequest, startCpuLimit, startMemLimit)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand Down Expand Up @@ -269,7 +269,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
ParseQuantityOrDie("150m") /*cpu limit*/, ParseQuantityOrDie("400Mi") /*memory limit*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand Down Expand Up @@ -311,7 +311,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d.Spec.Template.Spec.Containers = append(d.Spec.Template.Spec.Containers, d.Spec.Template.Spec.Containers[0])
d.Spec.Template.Spec.Containers[1].Name = "hamster2"
ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{
{
Expand Down Expand Up @@ -361,7 +361,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d.Spec.Template.Spec.Containers = append(d.Spec.Template.Spec.Containers, d.Spec.Template.Spec.Containers[0])
d.Spec.Template.Spec.Containers[1].Name = "hamster2"
ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{
{
Expand Down Expand Up @@ -409,7 +409,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d := NewHamsterDeploymentWithResources(f, ParseQuantityOrDie("100m") /*cpu*/, ParseQuantityOrDie("100Mi") /*memory*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand Down Expand Up @@ -446,7 +446,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d := NewHamsterDeploymentWithResources(f, ParseQuantityOrDie("100m") /*cpu*/, ParseQuantityOrDie("100Mi") /*memory*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Status.Recommendation = &vpa_types.RecommendedPodResources{
ContainerRecommendations: []vpa_types.RecommendedContainerResources{{
ContainerName: "hamster",
Expand Down Expand Up @@ -483,7 +483,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d := NewHamsterDeploymentWithResources(f, ParseQuantityOrDie("100m") /*cpu*/, ParseQuantityOrDie("100Mi") /*memory*/)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
InstallVPA(f, vpaCRD)

ginkgo.By("Setting up a hamster deployment")
Expand All @@ -500,7 +500,7 @@ var _ = AdmissionControllerE2eDescribe("Admission-controller", func() {
d := NewHamsterDeployment(f)

ginkgo.By("Setting up a VPA CRD")
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
InstallVPA(f, vpaCRD)

ginkgo.By("Setting up a hamster deployment")
Expand Down
10 changes: 8 additions & 2 deletions vertical-pod-autoscaler/e2e/v1/common.go
Original file line number Diff line number Diff line change
Expand Up @@ -299,7 +299,7 @@ func SetupVPA(f *framework.Framework, cpu string, mode vpa_types.UpdateMode, tar

// SetupVPAForNHamsters creates and installs a simple pod with n hamster containers for e2e test purposes.
func SetupVPAForNHamsters(f *framework.Framework, n int, cpu string, mode vpa_types.UpdateMode, targetRef *autoscaling.CrossVersionObjectReference) {
vpaCRD := NewVPA(f, "hamster-vpa", targetRef)
vpaCRD := NewVPA(f, "hamster-vpa", targetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
vpaCRD.Spec.UpdatePolicy.UpdateMode = &mode

cpuQuantity := ParseQuantityOrDie(cpu)
Expand All @@ -324,7 +324,7 @@ func SetupVPAForNHamsters(f *framework.Framework, n int, cpu string, mode vpa_ty
}

// NewVPA creates a VPA object for e2e test purposes.
func NewVPA(f *framework.Framework, name string, targetRef *autoscaling.CrossVersionObjectReference) *vpa_types.VerticalPodAutoscaler {
func NewVPA(f *framework.Framework, name string, targetRef *autoscaling.CrossVersionObjectReference, recommenders []*vpa_types.VerticalPodAutoscalerRecommenderSelector) *vpa_types.VerticalPodAutoscaler {
updateMode := vpa_types.UpdateModeAuto
vpa := vpa_types.VerticalPodAutoscaler{
ObjectMeta: metav1.ObjectMeta{
Expand All @@ -341,6 +341,12 @@ func NewVPA(f *framework.Framework, name string, targetRef *autoscaling.CrossVer
},
},
}

if len(recommenders) == 0 {
return &vpa
}

vpa.Spec.Recommenders = recommenders
return &vpa
}

Expand Down
127 changes: 125 additions & 2 deletions vertical-pod-autoscaler/e2e/v1/full_vpa.go
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ var _ = FullVpaE2eDescribe("Pods under VPA", func() {
APIVersion: "apps/v1",
Kind: "Deployment",
Name: "hamster",
})
}, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})

vpaClientSet = vpa_clientset.NewForConfigOrDie(config)
vpaClient := vpaClientSet.AutoscalingV1()
Expand Down Expand Up @@ -123,6 +123,129 @@ var _ = FullVpaE2eDescribe("Pods under VPA", func() {
})
})

var _ = FullVpaE2eDescribe("Pods under VPA with default recommender explicitly configured", func() {
var (
rc *ResourceConsumer
vpaClientSet *vpa_clientset.Clientset
vpaCRD *vpa_types.VerticalPodAutoscaler
)
replicas := 3

ginkgo.AfterEach(func() {
rc.CleanUp()
})

// This schedules AfterEach block that needs to run after the AfterEach above and
// BeforeEach that needs to run before the BeforeEach below - thus the order of these matters.
f := framework.NewDefaultFramework("vertical-pod-autoscaling")

ginkgo.BeforeEach(func() {
ns := f.Namespace.Name
ginkgo.By("Setting up a hamster deployment")
rc = NewDynamicResourceConsumer("hamster", ns, KindDeployment,
replicas,
1, /*initCPUTotal*/
10, /*initMemoryTotal*/
1, /*initCustomMetric*/
initialCPU, /*cpuRequest*/
initialMemory, /*memRequest*/
f.ClientSet,
f.ScalesGetter)

ginkgo.By("Setting up a VPA CRD with Recommender explicitly configured")
config, err := framework.LoadConfig()
gomega.Expect(err).NotTo(gomega.HaveOccurred())

vpaCRD = NewVPA(f, "hamster-vpa", &autoscaling.CrossVersionObjectReference{
APIVersion: "apps/v1",
Kind: "Deployment",
Name: "hamster",
}, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{{Name: "default"}})

vpaClientSet = vpa_clientset.NewForConfigOrDie(config)
vpaClient := vpaClientSet.AutoscalingV1()
_, err = vpaClient.VerticalPodAutoscalers(ns).Create(context.TODO(), vpaCRD, metav1.CreateOptions{})
gomega.Expect(err).NotTo(gomega.HaveOccurred())

})

ginkgo.It("have cpu requests growing with usage", func() {
// initial CPU usage is low so a minimal recommendation is expected
err := waitForResourceRequestInRangeInPods(
f, pollTimeout, metav1.ListOptions{LabelSelector: "name=hamster"}, apiv1.ResourceCPU,
ParseQuantityOrDie(minimalCPULowerBound), ParseQuantityOrDie(minimalCPUUpperBound))
gomega.Expect(err).NotTo(gomega.HaveOccurred())

// consume more CPU to get a higher recommendation
rc.ConsumeCPU(600 * replicas)
err = waitForResourceRequestInRangeInPods(
f, pollTimeout, metav1.ListOptions{LabelSelector: "name=hamster"}, apiv1.ResourceCPU,
ParseQuantityOrDie("500m"), ParseQuantityOrDie("1000m"))
gomega.Expect(err).NotTo(gomega.HaveOccurred())
})
})

var _ = FullVpaE2eDescribe("Pods under VPA with non-recognized recommender explicitly configured", func() {
var (
rc *ResourceConsumer
vpaClientSet *vpa_clientset.Clientset
vpaCRD *vpa_types.VerticalPodAutoscaler
)
replicas := 3

ginkgo.AfterEach(func() {
rc.CleanUp()
})

// This schedules AfterEach block that needs to run after the AfterEach above and
// BeforeEach that needs to run before the BeforeEach below - thus the order of these matters.
f := framework.NewDefaultFramework("vertical-pod-autoscaling")

ginkgo.BeforeEach(func() {
ns := f.Namespace.Name
ginkgo.By("Setting up a hamster deployment")
rc = NewDynamicResourceConsumer("hamster", ns, KindDeployment,
replicas,
1, /*initCPUTotal*/
10, /*initMemoryTotal*/
1, /*initCustomMetric*/
initialCPU, /*cpuRequest*/
initialMemory, /*memRequest*/
f.ClientSet,
f.ScalesGetter)

ginkgo.By("Setting up a VPA CRD with Recommender explicitly configured")
config, err := framework.LoadConfig()
gomega.Expect(err).NotTo(gomega.HaveOccurred())

vpaCRD = NewVPA(f, "hamster-vpa", &autoscaling.CrossVersionObjectReference{
APIVersion: "apps/v1",
Kind: "Deployment",
Name: "hamster",
}, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{{Name: "non-recognized"}})

vpaClientSet = vpa_clientset.NewForConfigOrDie(config)
vpaClient := vpaClientSet.AutoscalingV1()
_, err = vpaClient.VerticalPodAutoscalers(ns).Create(context.TODO(), vpaCRD, metav1.CreateOptions{})
gomega.Expect(err).NotTo(gomega.HaveOccurred())

})

ginkgo.It("deployment not updated by non-recognized recommender", func() {
err := waitForResourceRequestInRangeInPods(
f, pollTimeout, metav1.ListOptions{LabelSelector: "name=hamster"}, apiv1.ResourceCPU,
ParseQuantityOrDie(minimalCPULowerBound), ParseQuantityOrDie(minimalCPUUpperBound))
gomega.Expect(err).NotTo(gomega.HaveOccurred())

// consume more CPU to get a higher recommendation
rc.ConsumeCPU(600 * replicas)
err = waitForResourceRequestInRangeInPods(
f, pollTimeout, metav1.ListOptions{LabelSelector: "name=hamster"}, apiv1.ResourceCPU,
ParseQuantityOrDie("500m"), ParseQuantityOrDie("1000m"))
gomega.Expect(err).To(gomega.HaveOccurred())
})
})

var _ = FullVpaE2eDescribe("OOMing pods under VPA", func() {
var (
vpaClientSet *vpa_clientset.Clientset
Expand All @@ -149,7 +272,7 @@ var _ = FullVpaE2eDescribe("OOMing pods under VPA", func() {
APIVersion: "v1",
Kind: "Deployment",
Name: "hamster",
})
}, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})

vpaClientSet = vpa_clientset.NewForConfigOrDie(config)
vpaClient := vpaClientSet.AutoscalingV1()
Expand Down
8 changes: 4 additions & 4 deletions vertical-pod-autoscaler/e2e/v1/recommender.go
Original file line number Diff line number Diff line change
Expand Up @@ -159,7 +159,7 @@ var _ = RecommenderE2eDescribe("VPA CRD object", func() {
APIVersion: "batch/v1",
Kind: "CronJob",
Name: "hamster-cronjob",
})
}, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})

InstallVPA(f, vpaCRD)

Expand Down Expand Up @@ -187,7 +187,7 @@ var _ = RecommenderE2eDescribe("VPA CRD object", func() {
)

ginkgo.By("Setting up a VPA CRD")
vpaCRD = NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD = NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
InstallVPA(f, vpaCRD)

vpaClientSet = getVpaClientSet(f)
Expand Down Expand Up @@ -304,7 +304,7 @@ func getMilliCpu(resources apiv1.ResourceList) int64 {

// createVpaCRDWithMinMaxAllowed creates vpa object with min and max resources allowed.
func createVpaCRDWithMinMaxAllowed(f *framework.Framework, minAllowed, maxAllowed apiv1.ResourceList) *vpa_types.VerticalPodAutoscaler {
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
containerResourcePolicies := []vpa_types.ContainerResourcePolicy{
{
ContainerName: GetHamsterContainerNameByIndex(0),
Expand Down Expand Up @@ -361,7 +361,7 @@ var _ = RecommenderE2eDescribe("VPA CRD object", func() {
// createVpaCRDWithContainerScalingModes creates vpa object with containers policies
// having assigned given scaling modes respectively.
func createVpaCRDWithContainerScalingModes(f *framework.Framework, modes ...vpa_types.ContainerScalingMode) *vpa_types.VerticalPodAutoscaler {
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef)
vpaCRD := NewVPA(f, "hamster-vpa", hamsterTargetRef, []*vpa_types.VerticalPodAutoscalerRecommenderSelector{})
containerResourcePolicies := make([]vpa_types.ContainerResourcePolicy, len(modes), len(modes))
for i := range modes {
containerResourcePolicies[i] = vpa_types.ContainerResourcePolicy{
Expand Down

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

Loading