Skip to content

Commit e3ea44f

Browse files
committed
fixup
Signed-off-by: Anatolii Bazko <[email protected]>
1 parent 34713b8 commit e3ea44f

File tree

9 files changed

+62
-64
lines changed

9 files changed

+62
-64
lines changed

apis/controller/v1alpha1/devworkspaceoperatorconfig_types.go

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -183,10 +183,11 @@ type WorkspaceConfig struct {
183183
// the value "0" should be used. By default, the memory limit is 128Mi and the memory request is 64Mi.
184184
// No CPU limit or request is added by default.
185185
DefaultContainerResources *corev1.ResourceRequirements `json:"defaultContainerResources,omitempty"`
186-
// ContainerResourceCaps defines the maximum resource requirements enforced for all
187-
// workspace containers. If a container specifies higher limits or requests, they
188-
// will be capped at these maximum values. This is not applied to initContainers or
189-
// the projectClone container.
186+
// ContainerResourceCaps defines the maximum resource requirements enforced for workspace
187+
// containers. If a container specifies limits or requests that exceed these values, they
188+
// will be capped at the maximum. Note: Caps only apply when resources are already specified
189+
// on a container. For containers without resource specifications, use DefaultContainerResources
190+
// instead. These resource caps do not apply to initContainers or the projectClone container.
190191
ContainerResourceCaps *corev1.ResourceRequirements `json:"containerResourceCaps,omitempty"`
191192
// PodAnnotations defines the metadata.annotations for DevWorkspace pods created by the DevWorkspace Operator.
192193
PodAnnotations map[string]string `json:"podAnnotations,omitempty"`

deploy/bundle/manifests/controller.devfile.io_devworkspaceoperatorconfigs.yaml

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

deploy/deployment/kubernetes/combined.yaml

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

deploy/deployment/kubernetes/objects/devworkspaceoperatorconfigs.controller.devfile.io.CustomResourceDefinition.yaml

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

deploy/deployment/openshift/combined.yaml

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

deploy/deployment/openshift/objects/devworkspaceoperatorconfigs.controller.devfile.io.CustomResourceDefinition.yaml

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

deploy/templates/crd/bases/controller.devfile.io_devworkspaceoperatorconfigs.yaml

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

pkg/library/resources/helper.go

Lines changed: 4 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -231,37 +231,21 @@ func ApplyCaps(resources, caps *corev1.ResourceRequirements) *corev1.ResourceReq
231231
if capLimit.IsZero() {
232232
continue
233233
}
234-
if result.Limits == nil {
235-
result.Limits = corev1.ResourceList{}
236-
}
237234
existingLimit, hasExisting := result.Limits[resourceName]
238-
if !hasExisting || existingLimit.IsZero() {
239-
// No existing limit, use caps as maximum
240-
result.Limits[resourceName] = capLimit
241-
} else if existingLimit.Cmp(capLimit) > 0 {
242-
// Existing limit is higher than caps, apply caps maximum
235+
if hasExisting && existingLimit.Cmp(capLimit) > 0 {
243236
result.Limits[resourceName] = capLimit
244237
}
245-
// Otherwise, keep existing limit (it's already lower than or equal to caps)
246238
}
247239

248240
// Apply caps requests as maximum values (use the smaller of existing and caps)
249241
for resourceName, capRequest := range caps.Requests {
250242
if capRequest.IsZero() {
251243
continue
252244
}
253-
if result.Requests == nil {
254-
result.Requests = corev1.ResourceList{}
255-
}
256245
existingRequest, hasExisting := result.Requests[resourceName]
257-
if !hasExisting || existingRequest.IsZero() {
258-
// No existing request, use caps as maximum
259-
result.Requests[resourceName] = capRequest
260-
} else if existingRequest.Cmp(capRequest) > 0 {
261-
// Existing request is higher than caps, apply caps maximum
246+
if hasExisting && existingRequest.Cmp(capRequest) > 0 {
262247
result.Requests[resourceName] = capRequest
263248
}
264-
// Otherwise, keep existing request (it's already lower than or equal to caps)
265249
}
266250

267251
result = handleCapsEdgeCase(result, caps, corev1.ResourceMemory)
@@ -291,7 +275,8 @@ func handleCapsEdgeCase(resources, caps *corev1.ResourceRequirements, resourceNa
291275
}
292276
case capResLimit.IsZero() && !capResRequest.IsZero():
293277
// Only a resource request cap was set, and it's higher than the existing limit.
294-
// Adjust the limit up to match the capped request.
278+
// It means, that invalid state (limit < request) existed in the original resources before caps were applied.
279+
// Since the request is adjusted by the caps, we also adjust the limit up to match the capped request.
295280
if resRequest.Equal(capResRequest) {
296281
result.Limits[resourceName] = capResRequest
297282
} else {

pkg/library/resources/helper_test.go

Lines changed: 23 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -312,22 +312,16 @@ func TestApplyCaps(t *testing.T) {
312312
expected *corev1.ResourceRequirements
313313
}{
314314
{
315-
name: "Applies all caps values to empty resources",
315+
name: "Doesn't apply all caps values to empty resources",
316316
base: &corev1.ResourceRequirements{},
317317
caps: getResourceRequirements("2000Mi", "200Mi", "2000m", "200m"),
318-
expected: getResourceRequirements("2000Mi", "200Mi", "2000m", "200m"),
319-
},
320-
{
321-
name: "Applies all caps values",
322-
base: getResourceRequirements("3000Mi", "500Mi", "3000m", "500m"),
323-
caps: getResourceRequirements("2000Mi", "200Mi", "2000m", "200m"),
324-
expected: getResourceRequirements("2000Mi", "200Mi", "2000m", "200m"),
318+
expected: &corev1.ResourceRequirements{},
325319
},
326320
{
327-
name: "Keeps existing values when within caps bounds",
328-
base: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
321+
name: "Doesn't apply all caps values to '0' resources",
322+
base: getResourceRequirements("0", "0", "0", "0"),
329323
caps: getResourceRequirements("2000Mi", "200Mi", "2000m", "200m"),
330-
expected: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
324+
expected: getResourceRequirements("0", "0", "0", "0"),
331325
},
332326
{
333327
name: "Does not apply empty caps fields",
@@ -336,28 +330,40 @@ func TestApplyCaps(t *testing.T) {
336330
expected: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
337331
},
338332
{
339-
name: "Handles nil caps",
333+
name: "Does not apply nil caps",
340334
base: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
341335
caps: nil,
342336
expected: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
343337
},
344338
{
345-
name: "Ignores '0' fields in caps",
339+
name: "Does not apply '0' caps",
346340
base: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
347341
caps: getResourceRequirements("0", "0", "0", "0"),
348342
expected: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
349343
},
344+
{
345+
name: "Applies all caps values",
346+
base: getResourceRequirements("3000Mi", "500Mi", "3000m", "500m"),
347+
caps: getResourceRequirements("2000Mi", "200Mi", "2000m", "200m"),
348+
expected: getResourceRequirements("2000Mi", "200Mi", "2000m", "200m"),
349+
},
350+
{
351+
name: "Keeps existing values when within caps bounds",
352+
base: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
353+
caps: getResourceRequirements("2000Mi", "200Mi", "2000m", "200m"),
354+
expected: getResourceRequirements("1000Mi", "100Mi", "1000m", "100m"),
355+
},
350356
{
351357
name: "Adjusts request when caps limit creates conflict",
352-
base: getResourceRequirements("2000Mi", "1000Mi", "", "1000m"),
358+
base: getResourceRequirements("2000Mi", "1000Mi", "2000m", "1000m"),
353359
caps: getResourceRequirements("500Mi", "", "500m", ""),
354360
expected: getResourceRequirements("500Mi", "500Mi", "500m", "500m"),
355361
},
356362
{
357363
name: "Adjusts limit when caps request creates conflict",
358-
base: getResourceRequirements("500Mi", "", "500m", ""),
359-
caps: getResourceRequirements("", "1000Mi", "", "1000m"),
360-
expected: getResourceRequirements("1000Mi", "1000Mi", "1000m", "1000m"),
364+
base: getResourceRequirements("1000Mi", "2000Mi", "1000m", "2000m"),
365+
caps: getResourceRequirements("", "1500Mi", "", "1500m"),
366+
expected: getResourceRequirements("1500Mi", "1500Mi", "1500m", "1500m"),
361367
},
362368
}
363369
for _, tt := range tests {

0 commit comments

Comments
 (0)