@sanity/workflow-engine 0.4.0 → 0.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +926 -673
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +279 -4
- package/dist/index.d.ts +279 -4
- package/dist/index.js +926 -673
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.d.cts
CHANGED
|
@@ -6,6 +6,11 @@ export declare interface AbortInstanceArgs extends OperationArgs {
|
|
|
6
6
|
reason?: string;
|
|
7
7
|
}
|
|
8
8
|
|
|
9
|
+
/** The free-text reason recorded on the aborted history entry, if any. */
|
|
10
|
+
export declare function abortReason(
|
|
11
|
+
instance: Pick<WorkflowInstance, "history">,
|
|
12
|
+
): string | undefined;
|
|
13
|
+
|
|
9
14
|
export declare type Action = v.InferOutput<typeof StoredActionSchema>;
|
|
10
15
|
|
|
11
16
|
export declare class ActionDisabledError extends Error {
|
|
@@ -90,6 +95,17 @@ export declare class ActionParamsInvalidError extends Error {
|
|
|
90
95
|
});
|
|
91
96
|
}
|
|
92
97
|
|
|
98
|
+
/** The fireable-action verdict for one action on a task — its `allowed`
|
|
99
|
+
* state, structured `disabledReason`, and declared params, tagged with the
|
|
100
|
+
* owning task. The per-action atom both projections share:
|
|
101
|
+
* {@link availableActions} flattens it across a stage's tasks; a consumer
|
|
102
|
+
* that keeps per-task nesting (e.g. the MCP) maps it over a task's actions
|
|
103
|
+
* directly, so the verdict shape has a single source. */
|
|
104
|
+
export declare function actionVerdict(
|
|
105
|
+
task: TaskEvaluation,
|
|
106
|
+
action: ActionEvaluation,
|
|
107
|
+
): AvailableAction;
|
|
108
|
+
|
|
93
109
|
export declare interface Actor {
|
|
94
110
|
kind: "user" | "ai" | "system";
|
|
95
111
|
id: string;
|
|
@@ -120,6 +136,13 @@ export declare type Assignee =
|
|
|
120
136
|
role: string;
|
|
121
137
|
};
|
|
122
138
|
|
|
139
|
+
/** The assignees recorded for a task in a stage — the runtime half of the
|
|
140
|
+
* "who is this waiting on" answer. Empty when the task is unassigned. */
|
|
141
|
+
export declare function assigneesOf(
|
|
142
|
+
stage: StageEntry | undefined,
|
|
143
|
+
taskName: string,
|
|
144
|
+
): Assignee[];
|
|
145
|
+
|
|
123
146
|
/**
|
|
124
147
|
* Persisted document and effect-queue `_type` discriminators.
|
|
125
148
|
*/
|
|
@@ -6497,6 +6520,30 @@ declare const AuthoringWorkflowSchema: v.StrictObjectSchema<
|
|
|
6497
6520
|
undefined
|
|
6498
6521
|
>;
|
|
6499
6522
|
|
|
6523
|
+
export declare interface AvailableAction {
|
|
6524
|
+
task: string;
|
|
6525
|
+
taskStatus: TaskStatus;
|
|
6526
|
+
action: string;
|
|
6527
|
+
title: string | undefined;
|
|
6528
|
+
allowed: boolean;
|
|
6529
|
+
disabledReason: DisabledReason | undefined;
|
|
6530
|
+
params: ActionParam[];
|
|
6531
|
+
}
|
|
6532
|
+
|
|
6533
|
+
/** Flatten an evaluation's current-stage tasks into the actions the actor
|
|
6534
|
+
* could fire, each carrying whether it's allowed (and why not). */
|
|
6535
|
+
export declare function availableActions(
|
|
6536
|
+
tasks: TaskEvaluation[],
|
|
6537
|
+
): AvailableAction[];
|
|
6538
|
+
|
|
6539
|
+
/** The `workflow.availableActions` result — the projected actions plus the
|
|
6540
|
+
* evaluation they came from, so a consumer can read the instance/stage
|
|
6541
|
+
* context without a second projection. */
|
|
6542
|
+
export declare interface AvailableActionsResult {
|
|
6543
|
+
evaluation: WorkflowEvaluation;
|
|
6544
|
+
actions: AvailableAction[];
|
|
6545
|
+
}
|
|
6546
|
+
|
|
6500
6547
|
declare type Bound<
|
|
6501
6548
|
Args extends {
|
|
6502
6549
|
client: WorkflowClient;
|
|
@@ -6612,6 +6659,13 @@ export declare interface CompleteEffectArgs extends OperationArgs {
|
|
|
6612
6659
|
durationMs?: number;
|
|
6613
6660
|
}
|
|
6614
6661
|
|
|
6662
|
+
/** Compare each definition against the deployed doc at its own docId. */
|
|
6663
|
+
export declare function computeDiffEntries(
|
|
6664
|
+
client: Pick<WorkflowClient, "getDocument">,
|
|
6665
|
+
defs: WorkflowDefinition[],
|
|
6666
|
+
target: DeployTarget,
|
|
6667
|
+
): Promise<DiffEntry[]>;
|
|
6668
|
+
|
|
6615
6669
|
/**
|
|
6616
6670
|
* Thrown when a `fireAction` commit loses the optimistic-locking race on
|
|
6617
6671
|
* all {@link CONCURRENT_FIRE_ACTION_MAX_ATTEMPTS} attempts — every reload +
|
|
@@ -6718,6 +6772,49 @@ export declare function datasetResourceParts(id: string): {
|
|
|
6718
6772
|
*/
|
|
6719
6773
|
export declare const defaultLoggerFactory: LoggerFactory;
|
|
6720
6774
|
|
|
6775
|
+
export declare interface DeleteDefinitionArgs {
|
|
6776
|
+
client: WorkflowClient;
|
|
6777
|
+
/** Engine-scope tags — required. See `validateTags` + `tags.ts`. */
|
|
6778
|
+
tags: string[];
|
|
6779
|
+
/** The Sanity resource the engine's own data lives in. */
|
|
6780
|
+
workflowResource: WorkflowResource;
|
|
6781
|
+
/** Cross-resource routing — see `StartInstanceArgs.resourceClients`. */
|
|
6782
|
+
resourceClients?: ResourceClientResolver;
|
|
6783
|
+
/** The definition's `name` — delete addresses the workflow, not a doc id. */
|
|
6784
|
+
definition: string;
|
|
6785
|
+
/** Delete only this deployed version. Default: every deployed version. */
|
|
6786
|
+
version?: number;
|
|
6787
|
+
/**
|
|
6788
|
+
* Abort every non-terminal instance pinned to the targeted versions
|
|
6789
|
+
* before deleting. Instances are ONLY aborted — instance documents are
|
|
6790
|
+
* never deleted; they stay in the lake as the audit record. Without
|
|
6791
|
+
* this flag the delete refuses when such instances exist.
|
|
6792
|
+
*/
|
|
6793
|
+
cascade?: boolean;
|
|
6794
|
+
/** Free-text reason stamped on each cascade-abort history entry. */
|
|
6795
|
+
reason?: string;
|
|
6796
|
+
/** Optional access-state override — see `StartInstanceArgs.access`. */
|
|
6797
|
+
access?: WorkflowAccessOverride;
|
|
6798
|
+
/** URL path for grant resolution — see `StartInstanceArgs.grantsFromPath`. */
|
|
6799
|
+
grantsFromPath?: string;
|
|
6800
|
+
}
|
|
6801
|
+
|
|
6802
|
+
export declare interface DeleteDefinitionResult {
|
|
6803
|
+
/** The definition's `name`. */
|
|
6804
|
+
name: string;
|
|
6805
|
+
/** Versions actually removed, newest first. */
|
|
6806
|
+
deletedVersions: number[];
|
|
6807
|
+
/** Instances hard-stopped by `cascade`, in abort order. Empty without it. */
|
|
6808
|
+
abortedInstanceIds: string[];
|
|
6809
|
+
/**
|
|
6810
|
+
* Orphaned guard docs removed across the definition's statically-named
|
|
6811
|
+
* datasources. Only populated when the LAST version goes — guard docs
|
|
6812
|
+
* are stamped with the version-less `name`, so they stay while any
|
|
6813
|
+
* version remains deployed.
|
|
6814
|
+
*/
|
|
6815
|
+
deletedGuardCount: number;
|
|
6816
|
+
}
|
|
6817
|
+
|
|
6721
6818
|
/**
|
|
6722
6819
|
* Run every guard whose `match` applies and collect those that DENY. Empty
|
|
6723
6820
|
* result ⇒ allowed (optimistically).
|
|
@@ -6771,6 +6868,103 @@ export declare interface DeployDefinitionsResult {
|
|
|
6771
6868
|
*/
|
|
6772
6869
|
export declare function deployStageGuards(args: StageGuardArgs): Promise<void>;
|
|
6773
6870
|
|
|
6871
|
+
/** Where a definition deploys: the engine tags it partitions under, and the
|
|
6872
|
+
* workflow resource it belongs to. Structurally what `deployDefinitions`
|
|
6873
|
+
* receives, minus the definitions themselves. */
|
|
6874
|
+
export declare interface DeployTarget {
|
|
6875
|
+
tags: string[];
|
|
6876
|
+
workflowResource: WorkflowResource;
|
|
6877
|
+
}
|
|
6878
|
+
|
|
6879
|
+
/**
|
|
6880
|
+
* The slice of an instance + its {@link WorkflowEvaluation} the classifier
|
|
6881
|
+
* reads. Narrowed so callers (and tests) can craft an exact stuck permutation
|
|
6882
|
+
* without standing up a full evaluation; {@link diagnoseInputFromEvaluation}
|
|
6883
|
+
* builds it from a real {@link WorkflowEvaluation}.
|
|
6884
|
+
*/
|
|
6885
|
+
export declare interface DiagnoseInput {
|
|
6886
|
+
instance: Pick<
|
|
6887
|
+
WorkflowInstance,
|
|
6888
|
+
| "currentStage"
|
|
6889
|
+
| "stages"
|
|
6890
|
+
| "completedAt"
|
|
6891
|
+
| "abortedAt"
|
|
6892
|
+
| "effectHistory"
|
|
6893
|
+
| "pendingEffects"
|
|
6894
|
+
| "history"
|
|
6895
|
+
>;
|
|
6896
|
+
tasks: TaskEvaluation[];
|
|
6897
|
+
transitions: TransitionEvaluation[];
|
|
6898
|
+
}
|
|
6899
|
+
|
|
6900
|
+
/** Narrow a full {@link WorkflowEvaluation} to the {@link DiagnoseInput} the
|
|
6901
|
+
* classifier reads. */
|
|
6902
|
+
export declare function diagnoseInputFromEvaluation(
|
|
6903
|
+
evaluation: WorkflowEvaluation,
|
|
6904
|
+
): DiagnoseInput;
|
|
6905
|
+
|
|
6906
|
+
/**
|
|
6907
|
+
* Classify an instance. Terminal states win first; then the genuine stuck
|
|
6908
|
+
* causes (nothing advances on its own or via a normal action); then `waiting`
|
|
6909
|
+
* (an action is available — healthy); else `progressing` (a transition is
|
|
6910
|
+
* already satisfied and will cascade).
|
|
6911
|
+
*/
|
|
6912
|
+
export declare function diagnoseInstance(input: DiagnoseInput): Diagnosis;
|
|
6913
|
+
|
|
6914
|
+
/** The `workflow.diagnose` result — the verdict plus the evaluation it was
|
|
6915
|
+
* derived from, so a consumer can render the supporting evidence (current
|
|
6916
|
+
* stage tasks + transitions) without a second projection. */
|
|
6917
|
+
export declare interface DiagnoseResult {
|
|
6918
|
+
evaluation: WorkflowEvaluation;
|
|
6919
|
+
diagnosis: Diagnosis;
|
|
6920
|
+
}
|
|
6921
|
+
|
|
6922
|
+
export declare type Diagnosis =
|
|
6923
|
+
| {
|
|
6924
|
+
state: "progressing";
|
|
6925
|
+
}
|
|
6926
|
+
| {
|
|
6927
|
+
state: "waiting";
|
|
6928
|
+
task: string;
|
|
6929
|
+
assignees: Assignee[];
|
|
6930
|
+
actions: string[];
|
|
6931
|
+
}
|
|
6932
|
+
| {
|
|
6933
|
+
state: "completed";
|
|
6934
|
+
at: string;
|
|
6935
|
+
}
|
|
6936
|
+
| {
|
|
6937
|
+
state: "aborted";
|
|
6938
|
+
at: string;
|
|
6939
|
+
reason?: string;
|
|
6940
|
+
}
|
|
6941
|
+
| {
|
|
6942
|
+
state: "stuck";
|
|
6943
|
+
cause: StuckCause;
|
|
6944
|
+
};
|
|
6945
|
+
|
|
6946
|
+
export declare interface DiffEntry {
|
|
6947
|
+
name: string;
|
|
6948
|
+
version: number;
|
|
6949
|
+
status: "create" | "update" | "unchanged";
|
|
6950
|
+
docId: string;
|
|
6951
|
+
expected: Record<string, unknown>;
|
|
6952
|
+
existing?: Record<string, unknown>;
|
|
6953
|
+
}
|
|
6954
|
+
|
|
6955
|
+
/**
|
|
6956
|
+
* Compare one local definition against a deployed document (or its
|
|
6957
|
+
* absence), classifying it as create / update / unchanged using the
|
|
6958
|
+
* engine's own no-op verdict. Pure — callers own the fetch, so the same
|
|
6959
|
+
* comparison serves both deploy's exact-docId lookup and `definition
|
|
6960
|
+
* diff`'s latest-version query.
|
|
6961
|
+
*/
|
|
6962
|
+
export declare function diffEntry(
|
|
6963
|
+
def: WorkflowDefinition,
|
|
6964
|
+
existingRaw: Record<string, unknown> | undefined,
|
|
6965
|
+
target: DeployTarget,
|
|
6966
|
+
): DiffEntry;
|
|
6967
|
+
|
|
6774
6968
|
export declare type DisabledReason =
|
|
6775
6969
|
| {
|
|
6776
6970
|
/**
|
|
@@ -7060,10 +7254,22 @@ export declare interface Engine {
|
|
|
7060
7254
|
evaluateInstance: (
|
|
7061
7255
|
args: Bound<EvaluateArgs>,
|
|
7062
7256
|
) => ReturnType<typeof evaluateInstance>;
|
|
7257
|
+
/** Diagnose why an instance is or isn't progressing — a classified
|
|
7258
|
+
* {@link DiagnoseResult} plus the evaluation it was derived from. */
|
|
7259
|
+
diagnose: (args: Bound<EvaluateArgs>) => Promise<DiagnoseResult>;
|
|
7260
|
+
/** The actions firable on the instance's current stage, each flagged
|
|
7261
|
+
* allowed/disabled, plus the evaluation they came from. */
|
|
7262
|
+
availableActions: (
|
|
7263
|
+
args: Bound<EvaluateArgs>,
|
|
7264
|
+
) => Promise<AvailableActionsResult>;
|
|
7063
7265
|
/** Admin override — bypass filters/transitions and force the stage. */
|
|
7064
7266
|
setStage: (args: Bound<SetStageArgs>) => Promise<DispatchResult>;
|
|
7065
7267
|
/** Admin override — hard-stop an in-flight instance where it stands. */
|
|
7066
7268
|
abortInstance: (args: Bound<AbortInstanceArgs>) => Promise<DispatchResult>;
|
|
7269
|
+
/** Admin override — remove a deployed definition (instances are only ever aborted, never deleted). */
|
|
7270
|
+
deleteDefinition: (
|
|
7271
|
+
args: Bound<DeleteDefinitionArgs>,
|
|
7272
|
+
) => Promise<DeleteDefinitionResult>;
|
|
7067
7273
|
/** Fetch a workflow instance by id. */
|
|
7068
7274
|
getInstance: (args: { instanceId: string }) => Promise<WorkflowInstance>;
|
|
7069
7275
|
/** The reactive {@link WatchSet} for an instance — every document whose
|
|
@@ -8160,6 +8366,12 @@ export declare interface OpAppliedSummary {
|
|
|
8160
8366
|
resolved?: Record<string, unknown>;
|
|
8161
8367
|
}
|
|
8162
8368
|
|
|
8369
|
+
/** The instance's current, not-yet-exited {@link StageEntry}, if it has one —
|
|
8370
|
+
* the engine's canonical {@link findOpenStageEntry}, over the diagnosis input. */
|
|
8371
|
+
export declare function openStage(
|
|
8372
|
+
instance: Pick<WorkflowInstance, "currentStage" | "stages">,
|
|
8373
|
+
): StageEntry | undefined;
|
|
8374
|
+
|
|
8163
8375
|
export declare interface OperationArgs {
|
|
8164
8376
|
client: WorkflowClient;
|
|
8165
8377
|
/** Engine-scope tags — required. */
|
|
@@ -11417,6 +11629,31 @@ export declare function stripSystemFields(
|
|
|
11417
11629
|
doc: Record<string, unknown>,
|
|
11418
11630
|
): Record<string, unknown>;
|
|
11419
11631
|
|
|
11632
|
+
/**
|
|
11633
|
+
* Why an in-flight instance is genuinely blocked — nothing advances it on its
|
|
11634
|
+
* own OR via a normal action. Ordered most- to least-actionable in
|
|
11635
|
+
* {@link diagnoseInstance}: a failed effect is the root cause even when it left
|
|
11636
|
+
* its task looking merely "active", so it wins over the task- and
|
|
11637
|
+
* transition-level symptoms it produces. Note an active task awaiting a human
|
|
11638
|
+
* action is NOT here — that's the healthy {@link Diagnosis} `waiting` state.
|
|
11639
|
+
*/
|
|
11640
|
+
export declare type StuckCause =
|
|
11641
|
+
| {
|
|
11642
|
+
kind: "failed-effect";
|
|
11643
|
+
effect: EffectHistoryEntry;
|
|
11644
|
+
}
|
|
11645
|
+
| {
|
|
11646
|
+
kind: "hung-effect";
|
|
11647
|
+
effect: PendingEffect;
|
|
11648
|
+
}
|
|
11649
|
+
| {
|
|
11650
|
+
kind: "failed-task";
|
|
11651
|
+
task: string;
|
|
11652
|
+
}
|
|
11653
|
+
| {
|
|
11654
|
+
kind: "no-transition-fires";
|
|
11655
|
+
};
|
|
11656
|
+
|
|
11420
11657
|
/**
|
|
11421
11658
|
* A document the reactive layer should subscribe to, with its GDR
|
|
11422
11659
|
* exploded so consumers never re-parse: the resource-addressing parts
|
|
@@ -11729,6 +11966,16 @@ export declare const workflow: {
|
|
|
11729
11966
|
deployDefinitions: (
|
|
11730
11967
|
args: DeployDefinitionsArgs,
|
|
11731
11968
|
) => Promise<DeployDefinitionsResult>;
|
|
11969
|
+
/**
|
|
11970
|
+
* Remove a deployed workflow definition (all versions, or one via
|
|
11971
|
+
* `version`). Refuses while non-terminal instances exist unless
|
|
11972
|
+
* `cascade` aborts them first — instances are never deleted, only
|
|
11973
|
+
* aborted in place; see {@link deleteDefinitionInternal} for the
|
|
11974
|
+
* full contract (spawn-referrer check, guard-doc housekeeping).
|
|
11975
|
+
*/
|
|
11976
|
+
deleteDefinition: (
|
|
11977
|
+
args: Clocked<DeleteDefinitionArgs>,
|
|
11978
|
+
) => Promise<DeleteDefinitionResult>;
|
|
11732
11979
|
/**
|
|
11733
11980
|
* Spawn a new workflow instance from a deployed definition.
|
|
11734
11981
|
*
|
|
@@ -11779,10 +12026,9 @@ export declare const workflow: {
|
|
|
11779
12026
|
setStage: (args: Clocked<SetStageArgs>) => Promise<DispatchResult>;
|
|
11780
12027
|
/**
|
|
11781
12028
|
* Admin override — hard-stop an in-flight instance where it stands.
|
|
11782
|
-
* No stage move, no transition effects, pending effects cancelled;
|
|
11783
|
-
*
|
|
11784
|
-
*
|
|
11785
|
-
* so a parent gate waiting on this child re-evaluates.
|
|
12029
|
+
* No stage move, no transition effects, pending effects cancelled;
|
|
12030
|
+
* see {@link abortAndPropagate} for the abort + ancestor-propagation
|
|
12031
|
+
* contract (propagated, not cascaded — the instance is terminal).
|
|
11786
12032
|
*/
|
|
11787
12033
|
abortInstance: (args: Clocked<AbortInstanceArgs>) => Promise<DispatchResult>;
|
|
11788
12034
|
/**
|
|
@@ -11887,6 +12133,26 @@ export declare const workflow: {
|
|
|
11887
12133
|
* `fireAction` to gate writes via the same logic.
|
|
11888
12134
|
*/
|
|
11889
12135
|
evaluate: (args: Clocked<EvaluateArgs>) => Promise<WorkflowEvaluation>;
|
|
12136
|
+
/**
|
|
12137
|
+
* Diagnose why an instance is or isn't progressing. Projects the
|
|
12138
|
+
* instance (the same read as `evaluate`) and classifies it — terminal,
|
|
12139
|
+
* `progressing`, `waiting` (an action is available — healthy), or `stuck`
|
|
12140
|
+
* with a structured cause — returning that verdict as a
|
|
12141
|
+
* {@link DiagnoseResult} alongside the evaluation it came from, so a
|
|
12142
|
+
* consumer can render the supporting evidence without a second projection.
|
|
12143
|
+
* Pure read.
|
|
12144
|
+
*/
|
|
12145
|
+
diagnose: (args: Clocked<EvaluateArgs>) => Promise<DiagnoseResult>;
|
|
12146
|
+
/**
|
|
12147
|
+
* List the actions an actor could fire on an instance's current stage,
|
|
12148
|
+
* each flagged `allowed` (with a structured `disabledReason` when not).
|
|
12149
|
+
* Projects the instance from the actor's perspective and flattens its
|
|
12150
|
+
* tasks' actions. Returns the evaluation alongside the actions so a
|
|
12151
|
+
* consumer can read the instance/stage context. Pure read.
|
|
12152
|
+
*/
|
|
12153
|
+
availableActions: (
|
|
12154
|
+
args: Clocked<EvaluateArgs>,
|
|
12155
|
+
) => Promise<AvailableActionsResult>;
|
|
11890
12156
|
/**
|
|
11891
12157
|
* Materialised spawned children of a parent instance.
|
|
11892
12158
|
*
|
|
@@ -14041,6 +14307,15 @@ export declare interface WorkflowTransaction {
|
|
|
14041
14307
|
* clients drain it structurally.
|
|
14042
14308
|
*/
|
|
14043
14309
|
patch: (patch: any) => WorkflowTransaction;
|
|
14310
|
+
/**
|
|
14311
|
+
* Queue a document delete. Deliberately a transaction-only capability —
|
|
14312
|
+
* the top-level client surface stays delete-free so no engine code path
|
|
14313
|
+
* can casually remove documents; the sole consumer is `deleteDefinition`
|
|
14314
|
+
* housekeeping (definition docs + orphaned guard docs). Both the real
|
|
14315
|
+
* `@sanity/client` Transaction and the test fake's TransactionHandle
|
|
14316
|
+
* carry this shape.
|
|
14317
|
+
*/
|
|
14318
|
+
delete: (id: string) => WorkflowTransaction;
|
|
14044
14319
|
commit: () => Promise<unknown>;
|
|
14045
14320
|
}
|
|
14046
14321
|
|