Skip to content

feat(scheduler,admission): implement in-place pod resize accounting and queue admission - #2021

Merged
gshaibi merged 41 commits into
mainfrom
claude/pr-1997-implementation-2f767b
Aug 24, 2026
Merged

feat(scheduler,admission): implement in-place pod resize accounting and queue admission#2021
gshaibi merged 41 commits into
mainfrom
claude/pr-1997-implementation-2f767b

Conversation

@gshaibi

@gshaibi gshaibi commented Aug 6, 2026

Copy link
Copy Markdown
Member

Description

Implements the design from #1997 (research issue #1906).

Effective-request accounting (KEP-1287 / in-place pod vertical scaling)

When Kubernetes performs an in-place pod resize, the pod may temporarily be running with different resources than its spec declares. This PR makes the scheduler charge for the effective resource consumption rather than the raw spec:

  • pkg/scheduler/cache/pod_transform.go — Preserves ContainerStatus.AllocatedResources and ContainerStatus.Resources (enacted resources) in the informer compact transform so resize state is visible to the scheduler without increasing informer memory footprint unnecessarily. Also retains the PodResizePending condition.
  • pkg/scheduler/api/pod_info/effective_requests.go — Implements the effective-request model: max(spec, enacted, allocated) per container/resource for normal/Deferred/InProgress resizes; max(enacted, allocated) when PodResizePending=Infeasible (so an infeasible target does not inflate accounting).
  • pkg/scheduler/api/pod_info/pod_info.gogetPodResourceWithoutInitContainers now uses the effective-request model.

Best-effort pods/resize admission webhook

A new validating webhook rejects resize requests that would push a queue over its configured limits, without blocking legitimate resizes when the webhook is unavailable:

  • pkg/admission/webhook/v1alpha2/podhooks/pod_resize_validator.go — Computes delta = max(proposed - old spec, 0) and walks the queue hierarchy. Rejects if any queue would exceed its CPU/memory Limit (all workloads) or Quota (non-preemptible workloads only). Best-effort: lookup failures (PodGroup, Queue, PriorityClass) allow the resize.
  • cmd/admission/app/app.go — Registers the webhook at /validate--v1-pod-resize with failurePolicy=ignore so webhook unavailability never blocks a legitimate resize.

Related Issues

Implements the design from #1997 (research issue #1906).
Related: #1894 (addresses the resize-status fragment), #1872 (deferred resize eviction — separate track, #2051).

Checklist

  • Self-reviewed
  • Added/updated tests (if needed)
  • Updated documentation (if needed)
  • Added a changelog fragment via make changelog (or applied the skip-changelog label). Do not edit CHANGELOG.md directly — pending fragments are folded into it at release time.

Breaking Changes

None.

Additional Notes

The design document added by the first commit in this branch (docs: propose in-place pod resize accounting and queue admission) describes the design rationale in full. The commits in this PR implement that design.

Test coverage:

  • pkg/scheduler/api/pod_info/effective_requests_test.go — 7 tests covering: no-status fallback, normal upsize uses max, downsize-in-progress uses enacted, infeasible excludes spec, multiple containers, isPodResizeInfeasible, maxResourceList
  • pkg/admission/webhook/v1alpha2/podhooks/pod_resize_validator_test.go — 9 tests covering: non-KAI pod allowed, no PodGroup allowed, downsize allowed, CPU limit exceeded denied, CPU limit not exceeded allowed, memory limit exceeded denied, unlimited limit allowed, non-preemptible quota exceeded denied, preemptible-only quota exceeded allowed

gshaibi added 2 commits August 5, 2026 20:49
Adds design document for effective-request accounting and best-effort
webhook admission for in-place pod resizes. Fixes #1906.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…nd queue admission

Implements the design from PR #1997:

1. Effective-request accounting (KEP-1287):
   - Preserve ContainerStatus.Resources and AllocatedResources in the
     scheduler informer compact transform (pod_transform.go) so resize
     state is visible to the scheduler.
   - Compute effective pod requests as max(spec, enacted, allocated) per
     container; exclude spec when PodResizePending=Infeasible so infeasible
     resize targets do not inflate accounting.

2. Best-effort pods/resize admission webhook:
   - New PodResizeValidator validates pods/resize subresource updates.
   - Computes delta = max(proposed - old spec, 0) and rejects if any queue
     on the hierarchy would exceed its CPU/memory limit (all workloads) or
     CPU/memory quota (non-preemptible workloads).
   - failurePolicy=ignore so webhook unavailability never blocks a resize.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
@coderabbitai

coderabbitai Bot commented Aug 6, 2026

Copy link
Copy Markdown
Contributor

Important

Review skipped

Auto reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: f9762ec5-8ddb-4c31-b084-4844dc8d1a48

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
@gshaibi
gshaibi marked this pull request as draft August 6, 2026 06:40
Signed-off-by: gshaibi <gshaibi@nvidia.com>
@github-actions

github-actions Bot commented Aug 6, 2026

Copy link
Copy Markdown

📊 Performance Benchmark Results

Comparing PR (claude/pr-1997-implementation-2f767b) vs main branch — click to expand
goos: linux
goarch: amd64
pkg: github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/actions
cpu: AMD EPYC 9V74 80-Core Processor                
                                    │ main-bench.txt │           pr-bench.txt            │
                                    │     sec/op     │   sec/op     vs base              │
AllocateAction_SmallCluster-4            107.5m ± 0%   107.3m ± 6%       ~ (p=0.240 n=6)
AllocateAction_MediumCluster-4           128.7m ± 2%   128.2m ± 1%       ~ (p=0.240 n=6)
AllocateAction_LargeCluster-4            190.2m ± 2%   190.8m ± 2%       ~ (p=0.699 n=6)
ReclaimAction_SmallCluster-4             103.5m ± 0%   103.6m ± 0%       ~ (p=0.485 n=6)
ReclaimAction_MediumCluster-4            106.8m ± 1%   106.9m ± 1%       ~ (p=0.818 n=6)
PreemptAction_SmallCluster-4             104.7m ± 0%   104.6m ± 0%       ~ (p=0.394 n=6)
PreemptAction_MediumCluster-4            114.9m ± 1%   115.5m ± 1%       ~ (p=0.180 n=6)
ConsolidationAction_SmallCluster-4       121.2m ± 1%   121.1m ± 0%       ~ (p=0.699 n=6)
ConsolidationAction_MediumCluster-4      257.8m ± 2%   257.8m ± 2%       ~ (p=0.937 n=6)
FullSchedulingCycle_SmallCluster-4       105.8m ± 0%   105.8m ± 0%       ~ (p=0.240 n=6)
FullSchedulingCycle_MediumCluster-4      117.6m ± 2%   117.4m ± 0%       ~ (p=0.485 n=6)
FullSchedulingCycle_LargeCluster-4       153.4m ± 2%   153.0m ± 2%       ~ (p=0.818 n=6)
ManyQueues_MediumCluster-4               132.3m ± 2%   131.8m ± 1%       ~ (p=0.180 n=6)
GangScheduling_MediumCluster-4           148.0m ± 2%   146.7m ± 1%  -0.82% (p=0.026 n=6)
geomean                                  130.4m        130.2m       -0.12%

                                    │ main-bench.txt │            pr-bench.txt             │
                                    │      B/op      │     B/op       vs base              │
AllocateAction_SmallCluster-4           2.075Mi ± 1%    2.102Mi ± 1%  +1.32% (p=0.002 n=6)
AllocateAction_MediumCluster-4          9.903Mi ± 0%   10.025Mi ± 0%  +1.23% (p=0.002 n=6)
AllocateAction_LargeCluster-4           31.27Mi ± 0%    31.56Mi ± 0%  +0.95% (p=0.002 n=6)
ReclaimAction_SmallCluster-4            953.0Ki ± 1%    971.0Ki ± 1%  +1.89% (p=0.002 n=6)
ReclaimAction_MediumCluster-4           3.104Mi ± 0%    3.167Mi ± 0%  +2.03% (p=0.002 n=6)
PreemptAction_SmallCluster-4            1.343Mi ± 1%    1.365Mi ± 0%  +1.68% (p=0.002 n=6)
PreemptAction_MediumCluster-4           5.934Mi ± 0%    6.024Mi ± 0%  +1.51% (p=0.002 n=6)
ConsolidationAction_SmallCluster-4      8.203Mi ± 0%    8.233Mi ± 0%  +0.37% (p=0.002 n=6)
ConsolidationAction_MediumCluster-4     67.76Mi ± 0%    67.85Mi ± 0%  +0.13% (p=0.002 n=6)
FullSchedulingCycle_SmallCluster-4      1.408Mi ± 1%    1.428Mi ± 1%  +1.43% (p=0.002 n=6)
FullSchedulingCycle_MediumCluster-4     6.140Mi ± 0%    6.232Mi ± 0%  +1.50% (p=0.002 n=6)
FullSchedulingCycle_LargeCluster-4      18.35Mi ± 0%    18.58Mi ± 0%  +1.26% (p=0.002 n=6)
ManyQueues_MediumCluster-4              13.13Mi ± 0%    13.25Mi ± 0%  +0.92% (p=0.002 n=6)
GangScheduling_MediumCluster-4          15.33Mi ± 0%    15.57Mi ± 0%  +1.58% (p=0.002 n=6)
geomean                                 6.541Mi         6.624Mi       +1.27%

                                    │ main-bench.txt │           pr-bench.txt            │
                                    │   allocs/op    │  allocs/op   vs base              │
AllocateAction_SmallCluster-4            31.48k ± 0%   30.99k ± 0%  -1.57% (p=0.002 n=6)
AllocateAction_MediumCluster-4           245.8k ± 0%   243.8k ± 0%  -0.81% (p=0.002 n=6)
AllocateAction_LargeCluster-4            1.007M ± 0%   1.002M ± 0%  -0.49% (p=0.002 n=6)
ReclaimAction_SmallCluster-4             8.936k ± 0%   8.687k ± 0%  -2.79% (p=0.002 n=6)
ReclaimAction_MediumCluster-4            28.12k ± 0%   27.12k ± 0%  -3.55% (p=0.002 n=6)
PreemptAction_SmallCluster-4             15.27k ± 0%   14.89k ± 0%  -2.46% (p=0.002 n=6)
PreemptAction_MediumCluster-4            55.29k ± 0%   53.79k ± 0%  -2.71% (p=0.002 n=6)
ConsolidationAction_SmallCluster-4       109.7k ± 0%   109.3k ± 0%  -0.34% (p=0.002 n=6)
ConsolidationAction_MediumCluster-4      1.020M ± 0%   1.019M ± 0%  -0.15% (p=0.002 n=6)
FullSchedulingCycle_SmallCluster-4       19.63k ± 0%   19.26k ± 0%  -1.91% (p=0.002 n=6)
FullSchedulingCycle_MediumCluster-4      136.3k ± 0%   134.8k ± 0%  -1.11% (p=0.002 n=6)
FullSchedulingCycle_LargeCluster-4       537.7k ± 0%   533.9k ± 0%  -0.70% (p=0.002 n=6)
ManyQueues_MediumCluster-4               274.0k ± 0%   272.0k ± 0%  -0.74% (p=0.002 n=6)
GangScheduling_MediumCluster-4           455.4k ± 0%   451.4k ± 0%  -0.88% (p=0.002 n=6)
geomean                                  108.9k        107.4k       -1.45%

pkg: github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/actions/integration_tests/reclaim
                                                          │ main-bench.txt │            pr-bench.txt            │
                                                          │     sec/op     │   sec/op     vs base               │
ReclaimLargeJobs_10Node-4                                     135.9m ±  1%   136.7m ± 0%   +0.55% (p=0.015 n=6)
ReclaimLargeJobs_50Node-4                                     316.0m ±  2%   323.3m ± 5%        ~ (p=0.065 n=6)
ReclaimLargeJobs_100Node-4                                    640.6m ±  5%   633.3m ± 2%        ~ (p=0.699 n=6)
ReclaimLargeJobs_200Node-4                                     1.590 ±  2%    1.590 ± 3%        ~ (p=0.937 n=6)
ReclaimLargeJobs_500Node-4                                     7.106 ±  2%    7.182 ± 2%        ~ (p=0.310 n=6)
ReclaimLargeJobs_1000Node-4                                    31.18 ±  5%    31.26 ± 1%        ~ (p=0.937 n=6)
ReclaimManySingleGPUJobsFullCycle_10Node-4                    154.9m ±  0%   154.4m ± 1%        ~ (p=0.310 n=6)
ReclaimManySingleGPUJobsFullCycle_50Node-4                    969.2m ±  1%   961.4m ± 0%   -0.81% (p=0.009 n=6)
ReclaimManySingleGPUJobsFullCycle_100Node-4                    3.817 ±  7%    3.448 ± 1%   -9.67% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_200Node-4                    19.85 ±  5%    14.67 ± 4%  -26.09% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_500Node-4                    130.6 ± 19%    130.4 ± 4%        ~ (p=0.937 n=6)
ReclaimManySingleGPUJobsFullCycleWithMinRuntime_500Node-4      116.2 ±  5%    118.7 ± 4%        ~ (p=0.394 n=6)
geomean                                                        3.301          3.202        -2.99%

                                                          │ main-bench.txt │            pr-bench.txt            │
                                                          │      B/op      │     B/op      vs base              │
ReclaimLargeJobs_10Node-4                                     17.23Mi ± 1%   17.26Mi ± 0%       ~ (p=0.132 n=6)
ReclaimLargeJobs_50Node-4                                     91.88Mi ± 0%   92.09Mi ± 0%  +0.22% (p=0.004 n=6)
ReclaimLargeJobs_100Node-4                                    204.2Mi ± 0%   204.7Mi ± 0%  +0.21% (p=0.002 n=6)
ReclaimLargeJobs_200Node-4                                    486.2Mi ± 0%   487.0Mi ± 0%  +0.16% (p=0.002 n=6)
ReclaimLargeJobs_500Node-4                                    1.698Gi ± 0%   1.700Gi ± 0%  +0.12% (p=0.002 n=6)
ReclaimLargeJobs_1000Node-4                                   5.141Gi ± 0%   5.145Gi ± 0%  +0.07% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_10Node-4                    14.80Mi ± 0%   14.90Mi ± 0%  +0.71% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_50Node-4                    145.0Mi ± 0%   145.5Mi ± 0%  +0.36% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_100Node-4                   470.7Mi ± 0%   471.6Mi ± 0%  +0.18% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_200Node-4                   1.629Gi ± 0%   1.631Gi ± 0%  +0.11% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_500Node-4                   10.34Gi ± 0%   10.35Gi ± 0%  +0.04% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycleWithMinRuntime_500Node-4     10.34Gi ± 0%   10.35Gi ± 0%  +0.05% (p=0.002 n=6)
geomean                                                       504.5Mi        505.6Mi       +0.20%

                                                          │ main-bench.txt │           pr-bench.txt            │
                                                          │   allocs/op    │  allocs/op   vs base              │
ReclaimLargeJobs_10Node-4                                      242.0k ± 0%   241.4k ± 0%  -0.27% (p=0.037 n=6)
ReclaimLargeJobs_50Node-4                                      1.482M ± 0%   1.478M ± 0%  -0.22% (p=0.002 n=6)
ReclaimLargeJobs_100Node-4                                     3.741M ± 0%   3.735M ± 0%  -0.17% (p=0.002 n=6)
ReclaimLargeJobs_200Node-4                                     10.52M ± 0%   10.51M ± 0%  -0.12% (p=0.002 n=6)
ReclaimLargeJobs_500Node-4                                     45.58M ± 0%   45.54M ± 0%  -0.07% (p=0.002 n=6)
ReclaimLargeJobs_1000Node-4                                    159.5M ± 0%   159.4M ± 0%  -0.04% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_10Node-4                     279.9k ± 0%   278.3k ± 0%  -0.57% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_50Node-4                     3.741M ± 0%   3.733M ± 0%  -0.21% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_100Node-4                    13.33M ± 0%   13.32M ± 0%  -0.12% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_200Node-4                    50.07M ± 0%   50.03M ± 0%  -0.06% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycle_500Node-4                    300.6M ± 0%   300.5M ± 0%  -0.03% (p=0.002 n=6)
ReclaimManySingleGPUJobsFullCycleWithMinRuntime_500Node-4      300.6M ± 0%   300.5M ± 0%  -0.03% (p=0.002 n=6)
geomean                                                        11.69M        11.67M       -0.16%

                                                          │ main-bench.txt │              pr-bench.txt              │
                                                          │ full_cycles/op │ full_cycles/op  vs base                │
ReclaimManySingleGPUJobsFullCycle_10Node-4                      1.000 ± 0%       1.000 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimManySingleGPUJobsFullCycle_50Node-4                      1.000 ± 0%       1.000 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimManySingleGPUJobsFullCycle_100Node-4                     1.000 ± 0%       1.000 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimManySingleGPUJobsFullCycle_200Node-4                     1.000 ± 0%       1.000 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimManySingleGPUJobsFullCycle_500Node-4                     1.000 ± 0%       1.000 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimManySingleGPUJobsFullCycleWithMinRuntime_500Node-4       1.000 ± 0%       1.000 ± 0%       ~ (p=1.000 n=6) ¹
geomean                                                         1.000            1.000       +0.00%
¹ all samples are equal

                                            │          main-bench.txt           │                     pr-bench.txt                     │
                                            │ fit_error_tasks_after_allocate/op │ fit_error_tasks_after_allocate/op  vs base           │
ReclaimManySingleGPUJobsFullCycle_500Node-4                         4.000k ± 0%                         4.000k ± 0%  ~ (p=1.000 n=6) ¹
¹ all samples are equal

                                            │          main-bench.txt           │                    pr-bench.txt                    │
                                            │ heap_live_after_allocate_bytes/op │ heap_live_after_allocate_bytes/op  vs base         │
ReclaimManySingleGPUJobsFullCycle_500Node-4                        41.55M ± 76%                        41.55M ± 76%  ~ (p=0.937 n=6)

                                            │         main-bench.txt         │                  pr-bench.txt                   │
                                            │ heap_live_after_cycle_bytes/op │ heap_live_after_cycle_bytes/op  vs base         │
ReclaimManySingleGPUJobsFullCycle_500Node-4                     56.16M ± 56%                     56.18M ± 56%  ~ (p=0.485 n=6)

pkg: github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/actions/preempt
                                  │ main-bench.txt │         pr-bench.txt         │
                                  │     sec/op     │   sec/op     vs base         │
OrderedVictimsQueueConstruction-4      708.0µ ± 1%   709.6µ ± 2%  ~ (p=0.180 n=6)

                                  │ main-bench.txt │          pr-bench.txt           │
                                  │      B/op      │     B/op      vs base           │
OrderedVictimsQueueConstruction-4     114.9Ki ± 0%   114.9Ki ± 0%  ~ (p=1.000 n=6) ¹
¹ all samples are equal

                                  │ main-bench.txt │          pr-bench.txt          │
                                  │   allocs/op    │  allocs/op   vs base           │
OrderedVictimsQueueConstruction-4      4.033k ± 0%   4.033k ± 0%  ~ (p=1.000 n=6) ¹
¹ all samples are equal

pkg: github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/actions/reclaim
                                                         │ main-bench.txt │           pr-bench.txt            │
                                                         │     sec/op     │   sec/op     vs base              │
ReclaimUnschedulableDistributedJob_10Node-4                   145.9m ± 1%   146.9m ± 1%       ~ (p=0.132 n=6)
ReclaimUnschedulableDistributedJob_50Node-4                    3.287 ± 3%    3.383 ± 3%       ~ (p=0.093 n=6)
ReclaimUnschedulableDistributedJob_100Node-4                   16.21 ± 1%    16.76 ± 3%  +3.41% (p=0.002 n=6)
ReclaimUnschedulableDistributedJob_AntiAffinity100Node-4       14.84 ± 1%    15.51 ± 4%  +4.54% (p=0.002 n=6)
ReclaimWithMissingPVCJobs-4                                   2.655m ± 6%   2.668m ± 8%       ~ (p=0.937 n=6)
geomean                                                       789.3m        808.1m       +2.39%

                                                         │ main-bench.txt │            pr-bench.txt            │
                                                         │      B/op      │     B/op      vs base              │
ReclaimUnschedulableDistributedJob_10Node-4                  20.90Mi ± 3%   20.98Mi ± 3%       ~ (p=0.180 n=6)
ReclaimUnschedulableDistributedJob_50Node-4                  1.154Gi ± 0%   1.155Gi ± 0%       ~ (p=0.310 n=6)
ReclaimUnschedulableDistributedJob_100Node-4                 5.560Gi ± 0%   5.560Gi ± 0%       ~ (p=0.589 n=6)
ReclaimUnschedulableDistributedJob_AntiAffinity100Node-4     5.158Gi ± 0%   5.159Gi ± 0%       ~ (p=0.485 n=6)
ReclaimWithMissingPVCJobs-4                                  9.086Ki ± 4%   8.898Ki ± 2%       ~ (p=0.069 n=6)
geomean                                                      92.00Mi        91.70Mi       -0.33%

                                                         │ main-bench.txt │           pr-bench.txt            │
                                                         │   allocs/op    │  allocs/op   vs base              │
ReclaimUnschedulableDistributedJob_10Node-4                   306.1k ± 3%   305.2k ± 3%  -0.29% (p=0.041 n=6)
ReclaimUnschedulableDistributedJob_50Node-4                   27.77M ± 0%   27.76M ± 0%  -0.01% (p=0.002 n=6)
ReclaimUnschedulableDistributedJob_100Node-4                  169.0M ± 0%   169.0M ± 0%       ~ (p=0.180 n=6)
ReclaimUnschedulableDistributedJob_AntiAffinity100Node-4      146.8M ± 0%   146.8M ± 0%  -0.01% (p=0.041 n=6)
ReclaimWithMissingPVCJobs-4                                    170.0 ± 2%    169.0 ± 1%       ~ (p=0.177 n=6)
geomean                                                       2.046M        2.042M       -0.18%

                                                         │ main-bench.txt │             pr-bench.txt             │
                                                         │  duplicate/op  │ duplicate/op  vs base                │
ReclaimUnschedulableDistributedJob_10Node-4                  0.000 ± 0%       0.000 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimUnschedulableDistributedJob_50Node-4                  366.0 ± 0%       366.0 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimUnschedulableDistributedJob_100Node-4                1.020k ± 0%      1.020k ± 0%       ~ (p=1.000 n=6) ¹
ReclaimUnschedulableDistributedJob_AntiAffinity100Node-4    1.020k ± 0%      1.020k ± 0%       ~ (p=1.000 n=6) ¹
geomean                                                                 ²                 +0.00%               ²
¹ all samples are equal
² summaries must be >0 to compute geomean

                                                         │ main-bench.txt │             pr-bench.txt             │
                                                         │  simulated/op  │ simulated/op  vs base                │
ReclaimUnschedulableDistributedJob_10Node-4                    18.00 ± 0%     18.00 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimUnschedulableDistributedJob_50Node-4                    178.0 ± 0%     178.0 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimUnschedulableDistributedJob_100Node-4                   378.0 ± 0%     378.0 ± 0%       ~ (p=1.000 n=6) ¹
ReclaimUnschedulableDistributedJob_AntiAffinity100Node-4       378.0 ± 0%     378.0 ± 0%       ~ (p=1.000 n=6) ¹
geomean                                                        146.3          146.3       +0.00%
¹ all samples are equal

Legend

  • 📉 Negative delta = Performance improvement (faster)
  • 📈 Positive delta = Performance regression (slower)
  • p-value < 0.05 indicates statistically significant change
Raw benchmark data

PR branch:

goos: linux
goarch: amd64
pkg: github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/actions
cpu: AMD EPYC 9V74 80-Core Processor                
BenchmarkAllocateAction_SmallCluster-4         	       9	 114069422 ns/op	 2222033 B/op	   30992 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107116667 ns/op	 2204503 B/op	   30988 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107391955 ns/op	 2203564 B/op	   30987 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107220762 ns/op	 2214882 B/op	   30991 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107228416 ns/op	 2203429 B/op	   30990 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107330364 ns/op	 2204708 B/op	   30987 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 128282673 ns/op	10530164 B/op	  243765 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 127516622 ns/op	10511434 B/op	  243776 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 128869635 ns/op	10514419 B/op	  243787 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 128975612 ns/op	10512343 B/op	  243783 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 128206604 ns/op	10509986 B/op	  243788 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 128103595 ns/op	10510242 B/op	  243792 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 191211462 ns/op	33094313 B/op	 1002189 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 187921032 ns/op	33102832 B/op	 1002208 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 194224124 ns/op	33093878 B/op	 1002133 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 188311395 ns/op	33099012 B/op	 1002190 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 193170764 ns/op	33119626 B/op	 1002188 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 190444657 ns/op	33095437 B/op	 1002197 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103608804 ns/op	  993685 B/op	    8685 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103510406 ns/op	  997664 B/op	    8687 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103712784 ns/op	  994479 B/op	    8688 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103575107 ns/op	  994535 B/op	    8688 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103549074 ns/op	  994140 B/op	    8687 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103753849 ns/op	  986994 B/op	    8687 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106689524 ns/op	 3321220 B/op	   27120 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106858078 ns/op	 3321916 B/op	   27119 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 107588581 ns/op	 3321505 B/op	   27121 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 107229943 ns/op	 3321084 B/op	   27121 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106697938 ns/op	 3320781 B/op	   27119 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106842471 ns/op	 3320829 B/op	   27120 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104820391 ns/op	 1431664 B/op	   14892 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104719510 ns/op	 1431872 B/op	   14892 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104543962 ns/op	 1436158 B/op	   14894 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104293691 ns/op	 1431600 B/op	   14891 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104288000 ns/op	 1428058 B/op	   14891 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104659735 ns/op	 1432100 B/op	   14894 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 115631928 ns/op	 6327823 B/op	   53794 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 115494211 ns/op	 6315954 B/op	   53791 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 115838514 ns/op	 6316320 B/op	   53793 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 115437217 ns/op	 6324573 B/op	   53794 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 115373171 ns/op	 6311398 B/op	   53789 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 114428795 ns/op	 6315936 B/op	   53792 allocs/op
BenchmarkConsolidationAction_SmallCluster-4    	       9	 121060191 ns/op	 8627546 B/op	  109283 allocs/op
BenchmarkConsolidationAction_SmallCluster-4    	       9	 121240941 ns/op	 8629770 B/op	  109279 allocs/op
BenchmarkConsolidationAction_SmallCluster-4    	       9	 121047044 ns/op	 8643249 B/op	  109290 allocs/op
BenchmarkConsolidationAction_SmallCluster-4    	       9	 121073485 ns/op	 8631177 B/op	  109287 allocs/op

Main branch:

goos: linux
goarch: amd64
pkg: github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/actions
cpu: AMD EPYC 9V74 80-Core Processor                
BenchmarkAllocateAction_SmallCluster-4         	      10	 107512240 ns/op	 2172430 B/op	   31491 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107183496 ns/op	 2186567 B/op	   31484 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107631453 ns/op	 2176742 B/op	   31484 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107695172 ns/op	 2171292 B/op	   31484 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107398992 ns/op	 2187620 B/op	   31494 allocs/op
BenchmarkAllocateAction_SmallCluster-4         	      10	 107507465 ns/op	 2174850 B/op	   31481 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 128252113 ns/op	10383947 B/op	  245788 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 127731652 ns/op	10386258 B/op	  245765 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 130811646 ns/op	10383363 B/op	  245793 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 129452131 ns/op	10380435 B/op	  245761 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 128338724 ns/op	10383092 B/op	  245796 allocs/op
BenchmarkAllocateAction_MediumCluster-4        	       8	 129121649 ns/op	10385901 B/op	  245743 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 191047759 ns/op	32778774 B/op	 1007199 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 189352770 ns/op	32774885 B/op	 1007155 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 189135120 ns/op	32772442 B/op	 1007139 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 191436724 ns/op	32801862 B/op	 1007179 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 187006157 ns/op	32790526 B/op	 1007161 allocs/op
BenchmarkAllocateAction_LargeCluster-4         	       6	 192721438 ns/op	32801536 B/op	 1007178 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103519778 ns/op	  977029 B/op	    8934 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103407373 ns/op	  978431 B/op	    8937 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103654032 ns/op	  974671 B/op	    8937 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103387717 ns/op	  978391 B/op	    8937 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103574845 ns/op	  974364 B/op	    8935 allocs/op
BenchmarkReclaimAction_SmallCluster-4          	      10	 103931885 ns/op	  970415 B/op	    8934 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 107616499 ns/op	 3269305 B/op	   28121 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106821964 ns/op	 3256746 B/op	   28119 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106644009 ns/op	 3256597 B/op	   28119 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106694277 ns/op	 3252980 B/op	   28119 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106845904 ns/op	 3253616 B/op	   28120 allocs/op
BenchmarkReclaimAction_MediumCluster-4         	      10	 106914162 ns/op	 3252610 B/op	   28117 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104593297 ns/op	 1408192 B/op	   15269 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104627104 ns/op	 1407877 B/op	   15267 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104767851 ns/op	 1412013 B/op	   15271 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104671968 ns/op	 1407904 B/op	   15267 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104683754 ns/op	 1404144 B/op	   15267 allocs/op
BenchmarkPreemptAction_SmallCluster-4          	      10	 104774836 ns/op	 1418932 B/op	   15270 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 115561736 ns/op	 6219974 B/op	   55291 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 114706712 ns/op	 6228164 B/op	   55292 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 115108561 ns/op	 6219830 B/op	   55291 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 114645864 ns/op	 6223992 B/op	   55292 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 114518287 ns/op	 6224208 B/op	   55293 allocs/op
BenchmarkPreemptAction_MediumCluster-4         	       9	 115229124 ns/op	 6219917 B/op	   55291 allocs/op
BenchmarkConsolidationAction_SmallCluster-4    	       9	 121172010 ns/op	 8605556 B/op	  109671 allocs/op
BenchmarkConsolidationAction_SmallCluster-4    	       9	 120815146 ns/op	 8602767 B/op	  109663 allocs/op
BenchmarkConsolidationAction_SmallCluster-4    	       9	 122551788 ns/op	 8600248 B/op	  109651 allocs/op
BenchmarkConsolidationAction_SmallCluster-4    	       9	 121251097 ns/op	 8600066 B/op	  109650 allocs/op

gshaibi added 3 commits August 6, 2026 12:03
- operator: add pods/resize webhook entry (failurePolicy=Ignore) to
  validatingWCForKAIConfig so the handler is reachable in production
- admission: register scheduling/v2 (Queue) and scheduling/v2alpha2
  (PodGroup) in the manager scheme; add RBAC markers for PodGroups,
  Queues, and PriorityClasses so the client can fetch them at runtime
- scheduler: guard isPodResizeInfeasible with Status==ConditionTrue to
  avoid acting on a stale or transitional condition
- admission: replace specPodRequests delta with per-resource, per-container
  delta using max(enacted, allocated) as the effective-old baseline; skip
  resources unchanged in this resize so a stale infeasible spec target does
  not produce a spurious delta
- admission: treat quota==0 as a finite boundary (use >= 0, matching the
  limit check) so non-preemptible upsizes are blocked when quota is zero
- scheduler: apply the KEP-1287 effective-request model to restartable
  init containers (native sidecars) in initContainerEffects so a sidecar
  downsize in progress is not undercounted

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…pod resize validator

- Add InPlacePodResize config struct to Admission API with ValidateQuota and
  BlockUpsizeOnBoundedQueues fields (defaults: true / false)
- Add --validate-pod-resize-quota and --block-upsize-on-bounded-queues CLI flags
- Wire flags from operator buildArgsList through to PodResizeValidator constructor
- validateQuota=false: early-return allows all resizes without quota checks
- blockUpsizeOnBoundedQueues=true: reject any upsize on queues with finite limit
  (all workloads) or finite quota (non-preemptible), regardless of allocation
- Add tests covering both new modes

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…ake validate

- Fix import ordering in app.go (goimports sort)
- Fix struct field alignment in options.go (gofmt)
- Remove trailing blank line in effective_requests.go
- Regenerate CRD with inPlacePodResize fields
- Regenerate admission RBAC with queues/podgroups/priorityclasses rules

Signed-off-by: gshaibi <gshaibi@nvidia.com>
@github-actions

github-actions Bot commented Aug 6, 2026

Copy link
Copy Markdown

Total coverage: 54.6% -> 54.7% (delta 0.10%)

Merging this branch changes the coverage (4 decrease, 4 increase)

Impacted Packages Coverage Δ 🤖
github.com/kai-scheduler/KAI-scheduler/cmd/admission/app 0.00% (ø)
github.com/kai-scheduler/KAI-scheduler/pkg/admission/webhook/v1alpha2/podhooks 61.82% (+61.82%) 🌟
github.com/kai-scheduler/KAI-scheduler/pkg/apis/kai/v1/admission 21.05% (-1.53%) 👎
github.com/kai-scheduler/KAI-scheduler/pkg/common/pod 100.00% (+100.00%) 🌟
github.com/kai-scheduler/KAI-scheduler/pkg/common/podgroup 89.47% (-10.53%) 💀
github.com/kai-scheduler/KAI-scheduler/pkg/operator/operands/admission 85.43% (-0.87%) 👎
github.com/kai-scheduler/KAI-scheduler/pkg/podgroupcontroller/controllers 43.75% (ø)
github.com/kai-scheduler/KAI-scheduler/pkg/podgroupcontroller/controllers/metadata 75.00% (+51.47%) 🌟
github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/api/pod_info 71.05% (-1.77%) 👎
github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/cache 47.51% (+3.22%) 👍
github.com/kai-scheduler/KAI-scheduler/test/e2e/modules/configurations/feature_flags 0.00% (ø)
github.com/kai-scheduler/KAI-scheduler/test/e2e/suites/resize 0.00% (ø)

Coverage by file

Changed files (no unit tests)

Changed File Coverage Δ Total Covered Missed 🤖
github.com/kai-scheduler/KAI-scheduler/cmd/admission/app/app.go 0.00% (ø) 53 (+4) 0 53 (+4)
github.com/kai-scheduler/KAI-scheduler/cmd/admission/app/options.go 0.00% (ø) 24 0 24
github.com/kai-scheduler/KAI-scheduler/pkg/admission/webhook/v1alpha2/podhooks/pod_resize_validator.go 80.95% (+80.95%) 84 (+84) 68 (+68) 16 (+16) 🌟
github.com/kai-scheduler/KAI-scheduler/pkg/apis/kai/v1/admission/admission.go 100.00% (ø) 24 (+3) 24 (+3) 0
github.com/kai-scheduler/KAI-scheduler/pkg/apis/kai/v1/admission/zz_generated.deepcopy.go 0.00% (ø) 90 (+18) 0 90 (+18)
github.com/kai-scheduler/KAI-scheduler/pkg/common/pod/status.go 100.00% (+100.00%) 7 (+7) 7 (+7) 0 🌟
github.com/kai-scheduler/KAI-scheduler/pkg/common/podgroup/is_preemptible.go 87.50% (+87.50%) 32 (+32) 28 (+28) 4 (+4) 🌟
github.com/kai-scheduler/KAI-scheduler/pkg/operator/operands/admission/resources.go 88.71% (-1.21%) 124 (+5) 110 (+3) 14 (+2) 👎
github.com/kai-scheduler/KAI-scheduler/pkg/podgroupcontroller/controllers/metadata/pod.go 81.08% (+56.08%) 37 (-11) 30 (+18) 7 (-29) 🌟
github.com/kai-scheduler/KAI-scheduler/pkg/podgroupcontroller/controllers/status_updater.go 75.68% (ø) 37 28 9
github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/api/pod_info/pod_info.go 65.09% (-3.33%) 169 (-21) 110 (-20) 59 (-1) 👎
github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/cache/pod_transform.go 92.73% (-1.39%) 55 (+21) 51 (+19) 4 (+2) 👎
github.com/kai-scheduler/KAI-scheduler/test/e2e/modules/configurations/feature_flags/pod_resize.go 0.00% (ø) 0 0 0
github.com/kai-scheduler/KAI-scheduler/test/e2e/suites/resize/resize_specs.go 0.00% (ø) 0 0 0

Please note that the "Total", "Covered", and "Missed" counts above refer to code statements instead of lines of code. The value in brackets refers to the test coverage of that file in the old version of the code.

Changed unit test files

  • github.com/kai-scheduler/KAI-scheduler/pkg/admission/webhook/v1alpha2/podhooks/pod_resize_validator_test.go
  • github.com/kai-scheduler/KAI-scheduler/pkg/common/pod/status_test.go
  • github.com/kai-scheduler/KAI-scheduler/pkg/common/podgroup/is_preemptible_test.go
  • github.com/kai-scheduler/KAI-scheduler/pkg/operator/operands/admission/admission_test.go
  • github.com/kai-scheduler/KAI-scheduler/pkg/operator/operands/admission/resources_test.go
  • github.com/kai-scheduler/KAI-scheduler/pkg/podgroupcontroller/controllers/metadata/pod_test.go
  • github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/api/pod_info/pod_info_test.go
  • github.com/kai-scheduler/KAI-scheduler/pkg/scheduler/api/pod_info/pod_resize_accounting_test.go
  • github.com/kai-scheduler/KAI-scheduler/test/e2e/suites/resize/resize_suite_test.go

gshaibi added 4 commits August 6, 2026 16:43
…ine, and redistribution

Three bugs in podResizeDelta addressed:

- Sidecar upsizes bypassed admission: now iterates restartable init containers
  (RestartPolicy=Always) using InitContainerStatuses, matching the scheduler's
  initContainerEffects accounting.

- Non-infeasible old spec was excluded from baseline: for normal/Deferred/InProgress
  pods the queue accounts for max(spec, enacted, allocated); the webhook now mirrors
  this instead of always using only max(enacted, allocated).

- Per-container aggregation counted redistribution as growth: moving CPU from
  container A to container B produced a positive delta. Switched to pod-level
  aggregation (sum across all containers before diffing).

The new structure: accumulate newSpecSum, oldSpecSum, effectiveOldSum at the pod
level; skip a resource if newSpecSum[r] == oldSpecSum[r] (unchanged by this resize);
delta = max(0, newSpecSum[r] - effectiveOldSum[r]).

Add three tests: sidecar denied, non-infeasible baseline, redistribution allowed.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…entation-2f767b

# Conflicts:
#	pkg/operator/operands/admission/resources.go
#	pkg/scheduler/cache/pod_transform.go

Signed-off-by: gshaibi <gshaibi@nvidia.com>
Signed-off-by: gshaibi <gshaibi@nvidia.com>
…helpers

Replaces hand-rolled KEP-1287 aggregation with upstream
resource.AggregateContainerRequests(UseStatusResources: true).

- delete effective_requests.go entirely (3 funcs -> upstream)
- collapse getPodResourceWithoutInitContainers + initContainerEffects
  into a single upstream call
- webhook uses resource.IsPodResizeInfeasible instead of a local copy
- retarget effective-request tests at the public aggregation path

KNOWN FAILURE: upstream IsPodResizeInfeasible does not check
condition.Status == True, so a stale Infeasible condition with
Status=False is treated as infeasible.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
gshaibi and others added 14 commits August 9, 2026 16:25
Signed-off-by: gshaibi <gshaibi@nvidia.com>
…ion test

Upstream keys off Reason alone and ignores condition.Status, so the
Status==True guard added in #2021 does not survive the move to
k8s.io/component-helpers.

Accepts upstream semantics and pins the difference so a future upstream
tightening surfaces as a test failure rather than a silent change.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…helpers-prototype

refactor(scheduler): delegate effective-request accounting to k8s.io/component-helpers
…entation-2f767b

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…unting_test.go

The effective_requests.go source it was named after was removed when
aggregation moved to k8s.io/component-helpers. The tests now cover KAI's
wiring of the upstream helper through getPodResourceRequest.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…cePodVerticalScaling

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…g hierarchy

- compactResizeConditions -> compactConditions, matching sibling naming
  (functions are named for the field they compact); drop stale
  'generation-aware' wording
- document that BlockUpsizeOnBoundedQueues has no effect when
  ValidateQuota is false, in API comments, CLI flag help, and CRD

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…cated resources

Queue.Status.Allocated is derived from PodGroup.Status.ResourcesStatus.Allocated,
which summed raw pod spec requests. An Infeasible resize target therefore inflated
queue allocated (e.g. a rejected 64-CPU resize charged 64 CPU), diverging from
scheduler-internal accounting and double-counting in the resize webhook's limit
check. Found by live-cluster testing.

Switch to the same upstream aggregation the scheduler uses
(AggregateContainerRequests): KEP-1287 effective requests for allocated
(UseStatusResources), spec-only for requested. This also closes a pre-existing
undercount: init-phase peak and sidecars now count toward podgroup/queue
allocated, matching what the scheduler has always reserved internally.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…tion, dedup capacity checks

Move IsPreemptible (with its PriorityClass fallback chain: specific -> global
default -> DefaultPodGroupPriority) from podgroupcontroller utilities to
pkg/common/podgroup, and use it in the resize webhook instead of a divergent
local resolver. The webhook assumed priority 0 for unset/missing priority
classes while the controller fell back to defaults - so a pod counted in
AllocatedNonPreemptible could skip the webhook's quota check entirely.
The checker and the accountant now share one implementation.

Merge checkLimit and checkNonPreemptibleQuota into checkCapacityBound,
parameterized by bound and allocated pool. The earlier quota>0 vs limit>=0
sentinel bug was drift between these two copies.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
E2E suite (test/e2e/suites/resize/) covers the resize admission webhook
(deny past queue limit, allow within, downsizes) and effective-request
accounting end to end (infeasible resize target must not inflate
Queue.status.allocated). Skips on clusters older than 1.33. Resize calls
retry on conflict: the kubelet writes pod status concurrently during a
resize.

User docs (docs/in-place-resize/) cover the effective-request charging
model, webhook semantics including best-effort fail-open behavior, and
the inPlacePodResize config fields.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
Signed-off-by: gshaibi <gshaibi@nvidia.com>
GetConnectivity stores the calling node's context; ginkgo cancels it when
the node exits, so a TestContext created in BeforeEach fails every client
call from the It body with 'context canceled'. Follow the quota-suite
pattern: connectivity, skips, and cleanup live inside each spec.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
Replace the raw admission.Handler with the generic admission.Validator[*corev1.Pod]
and register through the webhook builder with WithValidatorCustomPath, matching
the sibling webhooks. The custom path is still required: the canonical
/validate--v1-pod path belongs to the general pod validator.

Removes the manual decoder, the scheme constructor parameter, and the
request-encoding helpers in tests, which now call ValidateUpdate directly.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
Signed-off-by: gshaibi <gshaibi@nvidia.com>
…erred charge as a contract

Generation-aware Infeasible was rejected during implementation (the
observedGeneration field requires a non-GA gate; upstream reason-only
semantics adopted and pinned by a characterization test) - update the
design to match. Note that the Deferred max(spec, actual) charge is a
dependency of deferred-resize eviction (#1872 / #2051): the reserved
target prevents backfill thrash after victim eviction.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
Comment thread cmd/admission/app/app.go Outdated
Comment thread cmd/admission/app/options.go Outdated
Comment thread docs/developer/designs/in-place-pod-resize/README.md Outdated
…emantics

Review feedback: the resize webhook's rules are disjoint from the pod
validator's (pods/resize subresource only, no double validation) and the
failure policies differ, which is why it is a separate endpoint. Define
best-effort (fail-open) in the flag help.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
Signed-off-by: gshaibi <gshaibi@nvidia.com>
Signed-off-by: gshaibi <gshaibi@nvidia.com>

@davidLif davidLif left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

ReclaimUnschedulableDistributedJob - degredation. This might be due to AggregateContainerRequests

Comment thread .changes/unreleased/changed-20260810-114327.yaml
Comment thread README.md Outdated
Comment thread test/e2e/suites/resize/resize_test.go Outdated
Comment thread test/e2e/suites/resize/resize_test.go Outdated
Comment thread pkg/operator/operands/admission/admission_test.go Outdated
Signed-off-by: gshaibi <gshaibi@nvidia.com>
Follow the DescribeAllocateElasticSpecs shape: Ordered container, queues and
skips once in BeforeAll, TestContextCleanup in AfterEach, ClusterCleanup in
AfterAll. Add feature_flags.SetInPlacePodResizeValidation to patch the kai
config's inPlacePodResize settings (with admission rollout wait) and pin
validateQuota=true for the suite, restoring defaults in AfterAll.

Signed-off-by: gshaibi <gshaibi@nvidia.com>
…n comment

Signed-off-by: gshaibi <gshaibi@nvidia.com>
@gshaibi

gshaibi commented Aug 19, 2026

Copy link
Copy Markdown
Member Author

ReclaimUnschedulableDistributedJob - degredation. This might be due to AggregateContainerRequests

I've rerun the test and it looks ok now, probably was just a hiccup.

Comment thread pkg/operator/operands/admission/admission_test.go Outdated
Comment thread pkg/operator/operands/admission/resources.go Outdated
Comment thread cmd/admission/app/app.go Outdated
Comment thread cmd/admission/app/options.go
Comment thread docs/in-place-resize/README.md
Comment thread pkg/admission/webhook/v1alpha2/podhooks/pod_resize_validator.go
itsomri
itsomri previously approved these changes Aug 19, 2026
Signed-off-by: gshaibi <gshaibi@nvidia.com>
Signed-off-by: gshaibi <gshaibi@nvidia.com>
@gshaibi
gshaibi force-pushed the claude/pr-1997-implementation-2f767b branch from c9971a9 to 022046f Compare August 22, 2026 19:43
@gshaibi
gshaibi enabled auto-merge August 23, 2026 12:59
@gshaibi
gshaibi added this pull request to the merge queue Aug 24, 2026
Merged via the queue into main with commit 920e8a0 Aug 24, 2026
17 checks passed
@gshaibi
gshaibi deleted the claude/pr-1997-implementation-2f767b branch August 24, 2026 07:56
@KaiPilotBot

Copy link
Copy Markdown
Collaborator

📝 Changelog fragment recorded

Thanks! This PR added the changelog fragment(s) below. Pending fragments are folded into CHANGELOG.md at release time, so it was intentionally not modified by this PR — your entry will appear in the next release:

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants