What you would like to be added?
Allow spec.trainer.numNodes to be modified on a suspended TrainJob. Currently,
spec.trainer is fully immutable after creation (added in #3157), which prevents
users from scaling the number of training nodes on a paused job.
Why is this needed?
Before #3157 (Trainer v2.1), spec.trainer was mutable. Users and dashboards
could pause a TrainJob, change numNodes, and resume. The controller would
reconcile the JobSet with the updated replica count on unsuspend.
PR #3157 added blanket self == oldSelf CEL on spec.trainer to prevent mutations
that would conflict with the running JobSet (e.g., changing image or command mid-run).
This was the right call for most fields, but it also blocked the legitimate use case
of scaling numNodes on a suspended job where no pods are running and the JobSet
can safely be rebuilt.
Use case
- User creates a TrainJob with
numNodes: 1
- Training runs, user pauses the job (checkpoints saved)
- User wants to scale to
numNodes: 2 for faster training
- User edits
spec.trainer.numNodes on the suspended TrainJob
- User resumes → controller rebuilds JobSet with 2 replicas → training resumes from checkpoint
What should stay immutable
All other spec.trainer fields should remain immutable:
image, command, args — changing these on a running distributed job would
cause pod restarts with inconsistent binaries
resourcesPerNode — changing resource requests requires pod recreation
env — changing environment mid-training can corrupt state
numProcPerNode — tied to GPU topology, unsafe to change
Only numNodes should be exempted, and only when suspended.
References
Love this feature?
Give it a 👍 We prioritize the features with most 👍
What you would like to be added?
Allow
spec.trainer.numNodesto be modified on a suspended TrainJob. Currently,spec.traineris fully immutable after creation (added in #3157), which preventsusers from scaling the number of training nodes on a paused job.
Why is this needed?
Before #3157 (Trainer v2.1),
spec.trainerwas mutable. Users and dashboardscould pause a TrainJob, change
numNodes, and resume. The controller wouldreconcile the JobSet with the updated replica count on unsuspend.
PR #3157 added blanket
self == oldSelfCEL onspec.trainerto prevent mutationsthat would conflict with the running JobSet (e.g., changing image or command mid-run).
This was the right call for most fields, but it also blocked the legitimate use case
of scaling
numNodeson a suspended job where no pods are running and the JobSetcan safely be rebuilt.
Use case
numNodes: 1numNodes: 2for faster trainingspec.trainer.numNodeson the suspended TrainJobWhat should stay immutable
All other
spec.trainerfields should remain immutable:image,command,args— changing these on a running distributed job wouldcause pod restarts with inconsistent binaries
resourcesPerNode— changing resource requests requires pod recreationenv— changing environment mid-training can corrupt statenumProcPerNode— tied to GPU topology, unsafe to changeOnly
numNodesshould be exempted, and only when suspended.References
Love this feature?
Give it a 👍 We prioritize the features with most 👍