JsonProject.suggestAssignments#
Proposes resources for requirement slots of a JsonProject. It fills empty slots, repairs broken ones and rebalances valid ones, and scores each step like evaluate. The project isn't modified: the proposal comes back as a change set to commit with apply. Needs a solved project with no edits applied since the last solve or level.
Signature#
slots_json: string, options_json: string: string
Synchronous and read-only. Bad input comes back as an error envelope. The call doesn't throw.
Request#
| Argument | Payload | Required | Description |
|---|---|---|---|
slots_json |
Slot[] |
yes | The slots to fill, repair or rebalance. slots builds them from skills and requirements, and its output can be passed as is. "[]" returns an empty proposal |
options_json |
SuggestOptions |
yes | "{}" for defaults |
SuggestOptions#
The options object for suggestAssignments. Every field can be omitted, and null reads as the default. Unknown fields, such as mode, are rejected with a parse error.
| Field | Type | Required | Default | Description |
|---|---|---|---|---|
baselineId |
string | no | absent (not checked) | Must name the current baseline, or the call fails with stale-baseline |
targets |
string[] | no | ["empty"] |
Which slots may change, judged by the slot's current resource: "empty" (no assignment; filled), "broken" (resource not in allowed; repaired), "valid" (resource in allowed; rebalanced). Each value at most once. [] changes no assignment and only reports invalid |
fixed |
Id[] |
no | [] |
Assignment ids that are never changed. A slot bound to one of them is never visited |
newResourcePenalty |
number | no | 0 |
Cost added for each resource used beyond the reference state, >= 0. 0 balances load only; a large value favors the fewest people |
level |
LevelingOptions | false |
no | false |
With leveling options, every candidate is leveled and scored on the leveled stage, and proposed.leveled is filled. false scores the scheduled stage. true is a validation error |
passes |
number | no | 1 |
Rebalance passes over valid slots, >= 1. Used only when targets contains "valid" |
clearFirst |
boolean | no | false |
Scores against a copy with in-scope leveling_delay / pauses cleared. The clears are added to changes.tasks.update. Separate from level.clearFirst |
Behavior#
- Greedy: slots are visited one at a time, and later slots build on earlier picks.
- It never removes an assignment. It adds one per filled slot, with the slot id as the assignment id, and changes the resource of a repaired or rebalanced one.
- A slot that can't be filled or repaired isn't an error: it's listed in
unfilledorinvalid. - Commit the proposal with
apply(JSON.stringify(result.changes)), thensolvewithout data, orlevelwith the same leveling options whenlevelwas set.
How picks are made and scored: Suggesting assignments.
Response#
The success envelope carries a SuggestResult.
SuggestResult#
| Field | Type | Description |
|---|---|---|
baselineId |
string | The accepted baseline the call scored against |
changes |
SchedulingChanges |
The net proposal, with changes.baselineId set. assignments.add entries are {id, task, resource, value}, assignments.update entries are {id, resource}. With clearFirst, tasks.update holds {id, leveling_delay: 0, pauses: []} per cleared task. Empty buckets and unset fields are omitted, so a proposal with no change is {baselineId} alone. Pass it to apply unchanged |
steps |
SuggestStep[] |
The decisions that changed the proposal, in order |
unfilled |
Id[] |
Targeted empty slots left empty, in visit order |
invalid |
Id[] | Slots whose final resource isn't in allowed, fixed slots included, in visit order |
baseline |
{ cost, resources } |
Cost and number of used resources of the reference state, on the scoring stage |
proposed |
SuggestProposal |
The proposed state measured against the reference state |
SuggestStep#
| Field | Type | Description |
|---|---|---|
slot |
Id |
The slot that changed |
task |
Id | The slot's task |
pass |
number | 0 for a fill or a repair, 1 and up for a rebalance pass |
fromResource |
Id | null |
The previous resource. null for a fill |
toResource |
Id | The chosen resource |
cost |
{ before, after } |
Cost of the state before and after the step, penalty included. before is the previous step's after, or baseline.cost for the first step |
SuggestProposal#
| Field | Type | Description |
|---|---|---|
cost |
number | Cost of the proposed state, penalty included |
resources |
number | Number of used resources in the proposed state |
scheduled |
Metrics |
Scheduled-stage metrics against the reference state |
leveled |
LeveledMetrics |
Leveled-stage metrics. Present only when options.level is set |
Errors#
| Kind | Code | When |
|---|---|---|
project |
no-baseline |
The project has never been solved, or apply ran since the last solve |
project |
stale-baseline |
options.baselineId doesn't name the current baseline |
validation |
null |
Invalid options: newResourcePenalty negative or not finite (newResourcePenalty), passes below 1 (passes), a duplicate in targets (targets[i]), an unknown, inactive or duplicate fixed entry (fixed[i]), invalid level options |
validation |
null |
The accepted state has a cycle (path: null) |
validation |
null |
An invalid slot: duplicate id (slots[i].id), unknown, unscheduled or summary task (slots[i].task), unknown allowed resource (slots[i].allowed[j]), value not finite or <= 0 (slots[i].value), an assignment that is unknown, inactive, on another task or bound by two slots (slots[i].assignment), a slot id equal to another existing assignment's id (slots[i].id) |
validation |
null |
A value the decoder rejects, with path: null: an unknown targets value, level: true |
parse |
null |
Malformed JSON, a wrong JSON type, or an unknown field in a slot or the options |
The JSON is decoded before the project is checked. After that, no-baseline and stale-baseline come first, then the options, the cycle check and the slots, in the order above. The accepted slot values are on the Slot page.
Example#
Fill an open position on task C, then commit the proposal.
const = ;
const = ;
const = new;
slots_json:
options_json (the token comes from the solve result):
Response:
dev2 wins with cost 0. With dev1 the step would cost 2: the overload from working on A and C on the same days.
Related#
Slot- the slots to fillJsonProject.slots- builds slots from skills and requirementsSchedulingChanges- the format of the proposalMetrics- how each state is scored- Suggesting assignments - how picks are made and committed