diff --git a/.changelog/14631.txt b/.changelog/14631.txt new file mode 100644 index 000000000..0e4e012f4 --- /dev/null +++ b/.changelog/14631.txt @@ -0,0 +1,3 @@ +```release-note:improvement +cli: Added `-id-prefix-template` option to `nomad job dispatch` +``` diff --git a/api/jobs.go b/api/jobs.go index 4fc048dd5..de77db1a5 100644 --- a/api/jobs.go +++ b/api/jobs.go @@ -431,12 +431,13 @@ func (j *Jobs) Summary(jobID string, q *QueryOptions) (*JobSummary, *QueryMeta, } func (j *Jobs) Dispatch(jobID string, meta map[string]string, - payload []byte, q *WriteOptions) (*JobDispatchResponse, *WriteMeta, error) { + payload []byte, idPrefixTemplate string, q *WriteOptions) (*JobDispatchResponse, *WriteMeta, error) { var resp JobDispatchResponse req := &JobDispatchRequest{ - JobID: jobID, - Meta: meta, - Payload: payload, + JobID: jobID, + Meta: meta, + Payload: payload, + IdPrefixTemplate: idPrefixTemplate, } wm, err := j.client.write("/v1/job/"+url.PathEscape(jobID)+"/dispatch", req, &resp, q) if err != nil { @@ -1342,9 +1343,10 @@ type DesiredUpdates struct { } type JobDispatchRequest struct { - JobID string - Payload []byte - Meta map[string]string + JobID string + Payload []byte + Meta map[string]string + IdPrefixTemplate string } type JobDispatchResponse struct { diff --git a/command/job_dispatch.go b/command/job_dispatch.go index b7ce75212..d8965d1d4 100644 --- a/command/job_dispatch.go +++ b/command/job_dispatch.go @@ -57,6 +57,9 @@ Dispatch Options: Optional identifier used to prevent more than one instance of the job from being dispatched. + -id-prefix-template + Optional prefix template for dispatched job IDs. + -verbose Display full information. ` @@ -107,6 +110,7 @@ func (c *JobDispatchCommand) Run(args []string) int { var detach, verbose bool var idempotencyToken string var meta []string + var idPrefixTemplate string flags := c.Meta.FlagSet(c.Name(), FlagSetClient) flags.Usage = func() { c.Ui.Output(c.Help()) } @@ -114,6 +118,7 @@ func (c *JobDispatchCommand) Run(args []string) int { flags.BoolVar(&verbose, "verbose", false, "") flags.StringVar(&idempotencyToken, "idempotency-token", "", "") flags.Var((*flaghelper.StringFlag)(&meta), "meta", "") + flags.StringVar(&idPrefixTemplate, "id-prefix-template", "", "") if err := flags.Parse(args); err != nil { return 1 @@ -174,7 +179,7 @@ func (c *JobDispatchCommand) Run(args []string) int { w := &api.WriteOptions{ IdempotencyToken: idempotencyToken, } - resp, _, err := client.Jobs().Dispatch(job, metaMap, payload, w) + resp, _, err := client.Jobs().Dispatch(job, metaMap, payload, idPrefixTemplate, w) if err != nil { c.Ui.Error(fmt.Sprintf("Failed to dispatch job: %s", err)) return 1 diff --git a/e2e/scheduler_sysbatch/sysbatch.go b/e2e/scheduler_sysbatch/sysbatch.go index 0d1c8f4df..4ba63f46c 100644 --- a/e2e/scheduler_sysbatch/sysbatch.go +++ b/e2e/scheduler_sysbatch/sysbatch.go @@ -221,7 +221,7 @@ func (tc *SysBatchSchedulerTest) TestJobRunDispatch(f *framework.F) { jobs := nomadClient.Jobs() result, _, err := jobs.Dispatch(jobID, map[string]string{ "KEY": "value", - }, nil, nil) + }, nil, "", nil) require.NoError(t, err) // grab the new dispatched jobID diff --git a/nomad/job_endpoint.go b/nomad/job_endpoint.go index bbb320222..c5819a2d7 100644 --- a/nomad/job_endpoint.go +++ b/nomad/job_endpoint.go @@ -1905,7 +1905,7 @@ func (j *Job) Dispatch(args *structs.JobDispatchRequest, reply *structs.JobDispa // Derive the child job and commit it via Raft - with initial status dispatchJob := parameterizedJob.Copy() - dispatchJob.ID = structs.DispatchedID(parameterizedJob.ID, time.Now()) + dispatchJob.ID = structs.DispatchedID(parameterizedJob.ID, args.IdPrefixTemplate, time.Now()) dispatchJob.ParentID = parameterizedJob.ID dispatchJob.Name = dispatchJob.ID dispatchJob.SetSubmitTime() diff --git a/nomad/structs/structs.go b/nomad/structs/structs.go index cacec36d1..c89bbd637 100644 --- a/nomad/structs/structs.go +++ b/nomad/structs/structs.go @@ -769,6 +769,7 @@ type JobDispatchRequest struct { Payload []byte Meta map[string]string WriteRequest + IdPrefixTemplate string } // JobValidateRequest is used to validate a job @@ -5367,8 +5368,13 @@ func (d *ParameterizedJobConfig) Copy() *ParameterizedJobConfig { // DispatchedID returns an ID appropriate for a job dispatched against a // particular parameterized job -func DispatchedID(templateID string, t time.Time) string { +func DispatchedID(templateID, idPrefixTemplate string, t time.Time) string { u := uuid.Generate()[:8] + + if idPrefixTemplate != "" { + return fmt.Sprintf("%s%s%s-%d-%s", templateID, DispatchLaunchSuffix, idPrefixTemplate, t.Unix(), u) + } + return fmt.Sprintf("%s%s%d-%s", templateID, DispatchLaunchSuffix, t.Unix(), u) } diff --git a/website/content/docs/commands/job/dispatch.mdx b/website/content/docs/commands/job/dispatch.mdx index 9891d7c26..67786b2cc 100644 --- a/website/content/docs/commands/job/dispatch.mdx +++ b/website/content/docs/commands/job/dispatch.mdx @@ -69,6 +69,9 @@ dispatching parameterized jobs. - `-idempotency-token`: Optional identifier used to prevent more than one instance of the job from being dispatched. + +- `-id-prefix-template`: Optional prefix template for dispatched job IDs. + - `-verbose`: Show full information. ## Examples @@ -141,6 +144,21 @@ $ nomad job dispatch -idempotency-token=prod video-encode video-config.json Job "video-encode/dispatch-1485379325-cb38d00d" already dispatched with idempotency token "prod". ``` +Dispatch with an id prefix: + +```shell-session +$ nomad job dispatch -id-prefix-template=config1 video-encode video-config1.json +Jb +Dispatched Job ID = video-encode/dispatch-config1-1485379325-cb38d00d +Evaluation ID = 31199841 + +==> Monitoring evaluation "31199841" + Evaluation triggered by job "example/dispatch-config1-1485379325-cb38d00d" + Allocation "8254b85f" created: node "82ff9c50", group "cache" + Evaluation status changed: "pending" -> "complete" +==> Evaluation "31199841" finished with status "complete" +``` + [eval status]: /docs/commands/eval/status [parameterized job]: /docs/job-specification/parameterized 'Nomad parameterized Job Specification' [multiregion]: /docs/job-specification/multiregion#parameterized-dispatch