1616 ServerClientError ,
1717)
1818from dstack ._internal .core .models .common import ApplyAction
19- from dstack ._internal .core .models .configurations import AnyRunConfiguration
19+ from dstack ._internal .core .models .configurations import RUN_PRIORITY_DEFAULT , AnyRunConfiguration
2020from dstack ._internal .core .models .instances import (
2121 InstanceAvailability ,
2222 InstanceOfferWithAvailability ,
@@ -434,7 +434,12 @@ async def apply_plan(
434434 # FIXME: potentially long write transaction
435435 # Avoid getting run_model after update
436436 await session .execute (
437- update (RunModel ).where (RunModel .id == current_resource .id ).values (run_spec = run_spec .json ())
437+ update (RunModel )
438+ .where (RunModel .id == current_resource .id )
439+ .values (
440+ run_spec = run_spec .json (),
441+ priority = run_spec .configuration .priority ,
442+ )
438443 )
439444 run = await get_run_by_name (
440445 session = session ,
@@ -495,6 +500,7 @@ async def submit_run(
495500 status = RunStatus .SUBMITTED ,
496501 run_spec = run_spec .json (),
497502 last_processed_at = submitted_at ,
503+ priority = run_spec .configuration .priority ,
498504 )
499505 session .add (run_model )
500506
@@ -852,6 +858,13 @@ def _get_job_submission_cost(job_submission: JobSubmission) -> float:
852858
853859
854860def _validate_run_spec_and_set_defaults (run_spec : RunSpec ):
861+ # This function may set defaults for null run_spec values,
862+ # although most defaults are resolved when building job_spec
863+ # so that we can keep both the original user-supplied value (null in run_spec)
864+ # and the default in job_spec.
865+ # If a property is stored in job_spec - resolve the default there.
866+ # Server defaults are preferable over client defaults so that
867+ # the defaults depend on the server version, not the client version.
855868 if run_spec .run_name is not None :
856869 validate_dstack_resource_name (run_spec .run_name )
857870 for mount_point in run_spec .configuration .volumes :
@@ -875,11 +888,14 @@ def _validate_run_spec_and_set_defaults(run_spec: RunSpec):
875888 raise ServerClientError (
876889 f"Maximum utilization_policy.time_window is { settings .SERVER_METRICS_RUNNING_TTL_SECONDS } s"
877890 )
891+ if run_spec .configuration .priority is None :
892+ run_spec .configuration .priority = RUN_PRIORITY_DEFAULT
878893 set_resources_defaults (run_spec .configuration .resources )
879894
880895
881896_UPDATABLE_SPEC_FIELDS = ["repo_code_hash" , "configuration" ]
882- _CONF_TYPE_TO_UPDATABLE_FIELDS = {
897+ _CONF_UPDATABLE_FIELDS = ["priority" ]
898+ _TYPE_SPECIFIC_CONF_UPDATABLE_FIELDS = {
883899 "dev-environment" : ["inactivity_duration" ],
884900 # Most service fields can be updated via replica redeployment.
885901 # TODO: Allow updating other fields when rolling deployment is supported.
@@ -915,12 +931,9 @@ def _check_can_update_configuration(
915931 raise ServerClientError (
916932 f"Configuration type changed from { current .type } to { new .type } , cannot update"
917933 )
918- updatable_fields = _CONF_TYPE_TO_UPDATABLE_FIELDS .get (new .type )
919- if updatable_fields is None :
920- raise ServerClientError (
921- f"Can only update { ', ' .join (_CONF_TYPE_TO_UPDATABLE_FIELDS )} configurations."
922- f" Not { new .type } "
923- )
934+ updatable_fields = _CONF_UPDATABLE_FIELDS + _TYPE_SPECIFIC_CONF_UPDATABLE_FIELDS .get (
935+ new .type , []
936+ )
924937 diff = diff_models (current , new )
925938 changed_fields = list (diff .keys ())
926939 for key in changed_fields :
0 commit comments