@lostgradient/weft 0.23.1 → 0.24.1
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/README.md +72 -4
- package/dist/cli/codegen-emit-dedup.d.ts +81 -0
- package/dist/cli/codegen-emit-dedup.js +45 -0
- package/dist/cli/codegen-emit-registry.d.ts +90 -0
- package/dist/cli/codegen-emit-registry.js +50 -0
- package/dist/cli/codegen-emit.d.ts +26 -39
- package/dist/cli/codegen-emit.js +4 -27
- package/dist/cli/codegen-validate.d.ts +49 -0
- package/dist/cli/codegen-validate.js +186 -0
- package/dist/cli/codegen.js +6 -87
- package/dist/cli/conformance.js +5 -2
- package/dist/cli/generated/operation-catalog.snapshot.json +381 -3
- package/dist/cli/generated/operation-client.generated.d.ts +350 -10
- package/dist/cli/generated/operation-client.generated.js +14 -0
- package/dist/cli/output.js +1 -1
- package/dist/cli/parse-schedule-arguments.js +15 -3
- package/dist/cli/schedule.js +2 -1
- package/dist/cli/storage-factory.js +2 -0
- package/dist/cli/types.d.ts +2 -1
- package/dist/cli/workflow-commands.js +2 -0
- package/dist/cli-main.js +1 -1
- package/dist/client/http-client-requests.js +6 -9
- package/dist/client/start-body.js +1 -0
- package/dist/core/application-payload-digest.d.ts +42 -0
- package/dist/core/application-payload-digest.js +76 -0
- package/dist/core/application-primitive-abort.d.ts +50 -0
- package/dist/core/application-primitive-abort.js +40 -0
- package/dist/core/application-primitive-attempt-registry.d.ts +74 -0
- package/dist/core/application-primitive-attempt-registry.js +73 -0
- package/dist/core/application-primitive-codec.d.ts +36 -0
- package/dist/core/application-primitive-codec.js +56 -0
- package/dist/core/application-primitive-commit.d.ts +67 -0
- package/dist/core/application-primitive-commit.js +66 -0
- package/dist/core/application-primitive-guards.d.ts +62 -0
- package/dist/core/application-primitive-guards.js +89 -0
- package/dist/core/application-primitive-payload.d.ts +29 -0
- package/dist/core/application-primitive-payload.js +65 -0
- package/dist/core/application-primitive-timing.d.ts +18 -0
- package/dist/core/application-primitive-timing.js +22 -0
- package/dist/core/atomic-state.js +2 -0
- package/dist/core/catalog/codec.d.ts +40 -0
- package/dist/core/catalog/codec.js +45 -0
- package/dist/core/catalog/errors.d.ts +104 -0
- package/dist/core/catalog/errors.js +41 -0
- package/dist/core/catalog/index.d.ts +25 -0
- package/dist/core/catalog/index.js +22 -0
- package/dist/core/catalog/reference-counts.d.ts +120 -0
- package/dist/core/catalog/reference-counts.js +28 -0
- package/dist/core/catalog/removal.d.ts +105 -0
- package/dist/core/catalog/removal.js +30 -0
- package/dist/core/catalog/storage-io.d.ts +101 -0
- package/dist/core/catalog/storage-io.js +106 -0
- package/dist/core/catalog/types.d.ts +108 -0
- package/dist/core/catalog/types.js +0 -0
- package/dist/core/catalog/workflow-catalog.d.ts +165 -0
- package/dist/core/catalog/workflow-catalog.js +198 -0
- package/dist/core/compare-codepoint.d.ts +13 -0
- package/dist/core/compare-codepoint.js +7 -0
- package/dist/core/compression.js +2 -0
- package/dist/core/context/attributes.d.ts +1 -1
- package/dist/core/context/durable-operations.d.ts +2 -2
- package/dist/core/context/index.js +5 -3
- package/dist/core/context/state-namespace.d.ts +1 -1
- package/dist/core/contract/build.d.ts +64 -0
- package/dist/core/contract/build.js +99 -0
- package/dist/core/contract/compatibility.d.ts +187 -0
- package/dist/core/contract/compatibility.js +37 -0
- package/dist/core/contract/failure.d.ts +64 -0
- package/dist/core/contract/failure.js +4 -0
- package/dist/core/contract/hash.d.ts +92 -0
- package/dist/core/contract/hash.js +34 -0
- package/dist/core/contract/index.d.ts +21 -0
- package/dist/core/contract/index.js +22 -0
- package/dist/core/contract/limits.d.ts +74 -0
- package/dist/core/contract/limits.js +1 -0
- package/dist/core/contract/manifest-parse-schema.d.ts +37 -0
- package/dist/core/contract/manifest-parse-schema.js +106 -0
- package/dist/core/contract/manifest-parse.d.ts +76 -0
- package/dist/core/contract/manifest-parse.js +189 -0
- package/dist/core/contract/manifest.d.ts +56 -0
- package/dist/core/contract/manifest.js +31 -0
- package/dist/core/contract/normalize.d.ts +97 -0
- package/dist/core/contract/normalize.js +127 -0
- package/dist/core/contract/revision.d.ts +29 -0
- package/dist/core/contract/revision.js +5 -0
- package/dist/core/contract/types.d.ts +274 -0
- package/dist/core/contract/types.js +1 -0
- package/dist/core/engine/activity-resolution.js +17 -17
- package/dist/core/engine/bulk-operations-purge.js +14 -20
- package/dist/core/engine/bulk-operations-retry.d.ts +9 -0
- package/dist/core/engine/bulk-operations-retry.js +177 -0
- package/dist/core/engine/bulk-operations-shared.d.ts +18 -0
- package/dist/core/engine/bulk-operations-shared.js +14 -0
- package/dist/core/engine/bulk-operations.js +8 -167
- package/dist/core/engine/callback-creators-bundles.js +4 -2
- package/dist/core/engine/callback-creators-core.js +9 -1
- package/dist/core/engine/callback-creators-schedule.js +2 -2
- package/dist/core/engine/catalog-activation.d.ts +40 -0
- package/dist/core/engine/catalog-activation.js +17 -0
- package/dist/core/engine/catalog-events.d.ts +36 -0
- package/dist/core/engine/catalog-events.js +15 -0
- package/dist/core/engine/catalog-readiness.d.ts +49 -0
- package/dist/core/engine/catalog-readiness.js +61 -0
- package/dist/core/engine/catalog-removal.d.ts +236 -0
- package/dist/core/engine/catalog-removal.js +123 -0
- package/dist/core/engine/catalog-tombstone-recovery.d.ts +56 -0
- package/dist/core/engine/catalog-tombstone-recovery.js +39 -0
- package/dist/core/engine/constraints.js +5 -1
- package/dist/core/engine/construction.d.ts +2 -2
- package/dist/core/engine/construction.js +4 -2
- package/dist/core/engine/decode-revision.d.ts +32 -0
- package/dist/core/engine/decode-revision.js +9 -0
- package/dist/core/engine/disposal.d.ts +6 -2
- package/dist/core/engine/disposal.js +26 -3
- package/dist/core/engine/dynamic-source-errors.d.ts +81 -0
- package/dist/core/engine/dynamic-source-errors.js +25 -0
- package/dist/core/engine/dynamic-source-execution.d.ts +173 -0
- package/dist/core/engine/dynamic-source-execution.js +108 -0
- package/dist/core/engine/engine-internal-types.d.ts +16 -0
- package/dist/core/engine/engine-workflows-namespace.d.ts +140 -0
- package/dist/core/engine/engine-workflows-namespace.js +51 -0
- package/dist/core/engine/finalizer-metadata.d.ts +22 -0
- package/dist/core/engine/finalizer-metadata.js +12 -0
- package/dist/core/engine/handle-result.js +2 -0
- package/dist/core/engine/index.d.ts +91 -0
- package/dist/core/engine/index.js +78 -6
- package/dist/core/engine/inline-launch-queue.js +1 -1
- package/dist/core/engine/internals.d.ts +54 -15
- package/dist/core/engine/internals.js +6 -0
- package/dist/core/engine/lifecycle/checkpoint-launch.d.ts +29 -0
- package/dist/core/engine/lifecycle/checkpoint-launch.js +75 -0
- package/dist/core/engine/lifecycle/delayed-start-registration.d.ts +30 -0
- package/dist/core/engine/lifecycle/delayed-start-registration.js +11 -0
- package/dist/core/engine/lifecycle/fork-helpers.d.ts +33 -1
- package/dist/core/engine/lifecycle/fork-helpers.js +3 -1
- package/dist/core/engine/lifecycle/recovery-revision-groups.d.ts +75 -0
- package/dist/core/engine/lifecycle/recovery-revision-groups.js +64 -0
- package/dist/core/engine/lifecycle/resume-generation-guard.d.ts +58 -0
- package/dist/core/engine/lifecycle/resume-generation-guard.js +11 -0
- package/dist/core/engine/lifecycle/resume.js +18 -9
- package/dist/core/engine/lifecycle/shared.d.ts +43 -0
- package/dist/core/engine/lifecycle/standalone-claim-acquire.d.ts +12 -0
- package/dist/core/engine/lifecycle/standalone-claim-acquire.js +6 -0
- package/dist/core/engine/lifecycle/start-commit-errors.d.ts +12 -0
- package/dist/core/engine/lifecycle/start-commit-errors.js +6 -0
- package/dist/core/engine/lifecycle/start-commit.d.ts +22 -7
- package/dist/core/engine/lifecycle/start-commit.js +49 -15
- package/dist/core/engine/lifecycle/start-exec.d.ts +18 -2
- package/dist/core/engine/lifecycle/start-exec.js +7 -5
- package/dist/core/engine/lifecycle/start-or-signal-create.js +1 -3
- package/dist/core/engine/lifecycle/start-or-signal.js +1 -1
- package/dist/core/engine/lifecycle/start-precondition-attribution.d.ts +49 -0
- package/dist/core/engine/lifecycle/start-precondition-attribution.js +13 -0
- package/dist/core/engine/lifecycle/start-revision-resolution.d.ts +34 -0
- package/dist/core/engine/lifecycle/start-revision-resolution.js +11 -0
- package/dist/core/engine/lifecycle/start-state.d.ts +16 -0
- package/dist/core/engine/lifecycle/start-state.js +60 -0
- package/dist/core/engine/lifecycle/start-terminal-conflict-purge.d.ts +66 -3
- package/dist/core/engine/lifecycle/start-terminal-conflict-purge.js +13 -3
- package/dist/core/engine/lifecycle/start.d.ts +16 -6
- package/dist/core/engine/lifecycle/start.js +39 -66
- package/dist/core/engine/lifecycle/transition.d.ts +3 -4
- package/dist/core/engine/lifecycle/transition.js +30 -80
- package/dist/core/engine/lifecycle.d.ts +4 -2
- package/dist/core/engine/lifecycle.js +6 -6
- package/dist/core/engine/listing.js +15 -1
- package/dist/core/engine/memo-durable-activity.js +4 -1
- package/dist/core/engine/nonterminal-revision-count.d.ts +25 -0
- package/dist/core/engine/nonterminal-revision-count.js +16 -0
- package/dist/core/engine/operations-time.d.ts +5 -23
- package/dist/core/engine/operations-time.js +13 -11
- package/dist/core/engine/ownership-bootstrap.d.ts +1 -1
- package/dist/core/engine/pinned-schedule-revision-count.d.ts +26 -0
- package/dist/core/engine/pinned-schedule-revision-count.js +19 -0
- package/dist/core/engine/pinned-schedule-revision.d.ts +76 -0
- package/dist/core/engine/pinned-schedule-revision.js +53 -0
- package/dist/core/engine/registration.d.ts +106 -0
- package/dist/core/engine/registration.js +28 -7
- package/dist/core/engine/retention.js +9 -2
- package/dist/core/engine/revision-errors.d.ts +71 -0
- package/dist/core/engine/revision-errors.js +13 -0
- package/dist/core/engine/schedule-revision-fire.d.ts +17 -0
- package/dist/core/engine/schedule-revision-fire.js +3 -0
- package/dist/core/engine/schedule-run.js +2 -1
- package/dist/core/engine/schedules.d.ts +2 -1
- package/dist/core/engine/schedules.js +28 -9
- package/dist/core/engine/source-diagnostics.d.ts +76 -0
- package/dist/core/engine/source-diagnostics.js +105 -0
- package/dist/core/engine/source-registration.d.ts +42 -0
- package/dist/core/engine/source-registration.js +38 -0
- package/dist/core/engine/source-resolution.d.ts +101 -0
- package/dist/core/engine/source-resolution.js +154 -0
- package/dist/core/engine/source-runtime-state.d.ts +92 -0
- package/dist/core/engine/source-runtime-state.js +36 -0
- package/dist/core/engine/storage-io.d.ts +19 -2
- package/dist/core/engine/storage-io.js +21 -2
- package/dist/core/engine/termination/finalizer-registration.d.ts +18 -0
- package/dist/core/engine/termination/finalizer-registration.js +21 -0
- package/dist/core/engine/termination/finalizer.d.ts +16 -19
- package/dist/core/engine/termination/finalizer.js +3 -3
- package/dist/core/engine/time-operation-callbacks.d.ts +32 -0
- package/dist/core/engine/time-operation-callbacks.js +0 -0
- package/dist/core/engine/validation/schedule-cadence.d.ts +16 -0
- package/dist/core/engine/validation/schedule-cadence.js +20 -0
- package/dist/core/engine/validation/schedule-options.d.ts +4 -1
- package/dist/core/engine/validation/schedule-options.js +14 -0
- package/dist/core/engine/validation/schedule-revision.d.ts +24 -0
- package/dist/core/engine/validation/schedule-revision.js +21 -0
- package/dist/core/engine/validation/schedule-warnings.d.ts +11 -0
- package/dist/core/engine/validation/schedule-warnings.js +5 -0
- package/dist/core/engine/validation/schedule.d.ts +4 -3
- package/dist/core/engine/validation/schedule.js +15 -26
- package/dist/core/engine/validation.js +5 -2
- package/dist/core/engine/workflow-claim-reclaim-target.d.ts +1 -1
- package/dist/core/engine/workflow-claim-reclaim-target.js +16 -2
- package/dist/core/engine/workflow-retention-deadline.d.ts +16 -0
- package/dist/core/engine/workflow-retention-deadline.js +33 -0
- package/dist/core/events/catalog-events.d.ts +117 -0
- package/dist/core/events/catalog-events.js +62 -0
- package/dist/core/events/event-map.d.ts +11 -0
- package/dist/core/events/index.d.ts +2 -0
- package/dist/core/events/index.js +2 -0
- package/dist/core/events/workflow-source-events.d.ts +102 -0
- package/dist/core/events/workflow-source-events.js +57 -0
- package/dist/core/execution-strategy.d.ts +7 -0
- package/dist/core/inline-execution-strategy.context-options.d.ts +1 -1
- package/dist/core/inline-execution-strategy.js +1 -1
- package/dist/core/mailbox-admission.d.ts +26 -0
- package/dist/core/mailbox-admission.js +130 -0
- package/dist/core/mailbox-claims.d.ts +251 -0
- package/dist/core/mailbox-claims.js +0 -0
- package/dist/core/mailbox-codec.d.ts +32 -0
- package/dist/core/mailbox-codec.js +221 -0
- package/dist/core/mailbox-contract.d.ts +290 -0
- package/dist/core/mailbox-contract.js +0 -0
- package/dist/core/mailbox-delivery.d.ts +37 -0
- package/dist/core/mailbox-delivery.js +193 -0
- package/dist/core/mailbox-guards.d.ts +78 -0
- package/dist/core/mailbox-guards.js +58 -0
- package/dist/core/mailbox-index-codec.d.ts +41 -0
- package/dist/core/mailbox-index-codec.js +71 -0
- package/dist/core/mailbox-internals.d.ts +156 -0
- package/dist/core/mailbox-internals.js +154 -0
- package/dist/core/mailbox-maintenance.d.ts +29 -0
- package/dist/core/mailbox-maintenance.js +196 -0
- package/dist/core/mailbox-settlement.d.ts +69 -0
- package/dist/core/mailbox-settlement.js +206 -0
- package/dist/core/mailbox-storage.d.ts +117 -0
- package/dist/core/mailbox-storage.js +115 -0
- package/dist/core/mailbox-transition-helpers.d.ts +70 -0
- package/dist/core/mailbox-transition-helpers.js +43 -0
- package/dist/core/mailbox-transitions-recovery.d.ts +28 -0
- package/dist/core/mailbox-transitions-recovery.js +64 -0
- package/dist/core/mailbox-transitions.d.ts +138 -0
- package/dist/core/mailbox-transitions.js +180 -0
- package/dist/core/mailbox-types.d.ts +406 -0
- package/dist/core/mailbox-types.js +16 -0
- package/dist/core/mailbox-validation.d.ts +65 -0
- package/dist/core/mailbox-validation.js +73 -0
- package/dist/core/mailbox-waits.d.ts +50 -0
- package/dist/core/mailbox-waits.js +97 -0
- package/dist/core/mailbox.d.ts +163 -0
- package/dist/core/mailbox.js +211 -0
- package/dist/core/outbox-claims.d.ts +307 -0
- package/dist/core/outbox-claims.js +0 -0
- package/dist/core/outbox-codec.d.ts +24 -0
- package/dist/core/outbox-codec.js +257 -0
- package/dist/core/outbox-contract.d.ts +346 -0
- package/dist/core/outbox-contract.js +0 -0
- package/dist/core/outbox-delivery.d.ts +34 -0
- package/dist/core/outbox-delivery.js +149 -0
- package/dist/core/outbox-drain.d.ts +29 -0
- package/dist/core/outbox-drain.js +158 -0
- package/dist/core/outbox-enqueue.d.ts +24 -0
- package/dist/core/outbox-enqueue.js +115 -0
- package/dist/core/outbox-guards.d.ts +76 -0
- package/dist/core/outbox-guards.js +60 -0
- package/dist/core/outbox-index-codec.d.ts +33 -0
- package/dist/core/outbox-index-codec.js +71 -0
- package/dist/core/outbox-internals.d.ts +99 -0
- package/dist/core/outbox-internals.js +159 -0
- package/dist/core/outbox-listing.d.ts +12 -0
- package/dist/core/outbox-listing.js +38 -0
- package/dist/core/outbox-maintenance.d.ts +28 -0
- package/dist/core/outbox-maintenance.js +191 -0
- package/dist/core/outbox-operations.d.ts +18 -0
- package/dist/core/outbox-operations.js +46 -0
- package/dist/core/outbox-runner.d.ts +30 -0
- package/dist/core/outbox-runner.js +217 -0
- package/dist/core/outbox-settlement.d.ts +57 -0
- package/dist/core/outbox-settlement.js +183 -0
- package/dist/core/outbox-storage.d.ts +107 -0
- package/dist/core/outbox-storage.js +127 -0
- package/dist/core/outbox-transition-helpers.d.ts +83 -0
- package/dist/core/outbox-transition-helpers.js +63 -0
- package/dist/core/outbox-transitions-recovery.d.ts +30 -0
- package/dist/core/outbox-transitions-recovery.js +42 -0
- package/dist/core/outbox-transitions.d.ts +145 -0
- package/dist/core/outbox-transitions.js +236 -0
- package/dist/core/outbox-types.d.ts +400 -0
- package/dist/core/outbox-types.js +20 -0
- package/dist/core/outbox-validation.d.ts +101 -0
- package/dist/core/outbox-validation.js +127 -0
- package/dist/core/outbox-waits.d.ts +39 -0
- package/dist/core/outbox-waits.js +88 -0
- package/dist/core/outbox.d.ts +156 -0
- package/dist/core/outbox.js +234 -0
- package/dist/core/registry-limits.d.ts +49 -0
- package/dist/core/registry-limits.js +10 -0
- package/dist/core/registry-schema-conversion.d.ts +20 -0
- package/dist/core/registry-schema-conversion.js +22 -0
- package/dist/core/registry-snapshot.d.ts +91 -42
- package/dist/core/registry-snapshot.js +39 -77
- package/dist/core/registry-workflow-contract-draft.d.ts +32 -0
- package/dist/core/registry-workflow-contract-draft.js +28 -0
- package/dist/core/registry-workflow-manifest.d.ts +122 -0
- package/dist/core/registry-workflow-manifest.js +92 -0
- package/dist/core/source/errors.d.ts +55 -0
- package/dist/core/source/errors.js +13 -0
- package/dist/core/source/index.d.ts +19 -0
- package/dist/core/source/index.js +4 -0
- package/dist/core/source/resolvers.d.ts +45 -0
- package/dist/core/source/resolvers.js +9 -0
- package/dist/core/source/types.d.ts +211 -0
- package/dist/core/source/types.js +0 -0
- package/dist/core/source/validate.d.ts +91 -0
- package/dist/core/source/validate.js +62 -0
- package/dist/core/source/workflow-source.d.ts +43 -0
- package/dist/core/source/workflow-source.js +16 -0
- package/dist/core/types/checkpoint.d.ts +14 -0
- package/dist/core/types/schedules.d.ts +52 -1
- package/dist/core/types/state.d.ts +16 -0
- package/dist/core/types/workflow-registries.d.ts +7 -0
- package/dist/core/types/workflow-registry.d.ts +12 -0
- package/dist/core/versioning.js +2 -0
- package/dist/core/weft-error.d.ts +1 -1
- package/dist/core/weft-error.js +12 -1
- package/dist/core/worker-execution-strategy.d.ts +1 -0
- package/dist/core/worker-execution-strategy.js +13 -1
- package/dist/core/worker-fault-handling.d.ts +10 -0
- package/dist/core/worker-fault-handling.js +1 -0
- package/dist/core/worker-inbound-message.d.ts +1 -0
- package/dist/core/worker-inbound-message.js +1 -0
- package/dist/core/worker-protocol-guard.js +4 -0
- package/dist/core/worker-protocol.d.ts +7 -0
- package/dist/core/worker-protocol.js +2 -1
- package/dist/core/worker-turn-watchdog.d.ts +8 -1
- package/dist/core/worker-turn-watchdog.js +3 -2
- package/dist/diagnostics/format.js +5 -0
- package/dist/diagnostics/types.d.ts +24 -0
- package/dist/diagnostics/version-check.js +8 -2
- package/dist/http.js +2 -2
- package/dist/index.d.ts +25 -4
- package/dist/index.js +57 -0
- package/dist/indexeddb.js +1 -1
- package/dist/json-schema.js +3 -3
- package/dist/mcp/resources.js +2 -0
- package/dist/runtime/portable.d.ts +9 -1
- package/dist/server/fault-to-json-rpc.js +4 -1
- package/dist/server/handler/auth-context-principal.js +4 -0
- package/dist/server/index.d.ts +11 -0
- package/dist/server/json-rpc-http.js +2 -0
- package/dist/server/json-rpc-websocket.js +6 -4
- package/dist/server/operation-catalog/index.d.ts +1 -1
- package/dist/server/operation-catalog/pipeline-helpers.js +2 -0
- package/dist/server/operation-catalog/types.d.ts +17 -0
- package/dist/server/operation-fault.d.ts +5 -0
- package/dist/server/operation-fault.js +4 -1
- package/dist/server/operations/activate-workflow-revision.d.ts +30 -0
- package/dist/server/operations/activate-workflow-revision.js +69 -0
- package/dist/server/operations/create-schedule.d.ts +2 -0
- package/dist/server/operations/create-schedule.js +10 -6
- package/dist/server/operations/fleet-events-subscription.js +1 -1
- package/dist/server/operations/fork-workflow.js +1 -1
- package/dist/server/operations/get-active-workflow-revision.d.ts +32 -0
- package/dist/server/operations/get-active-workflow-revision.js +46 -0
- package/dist/server/operations/get-catalog-diagnostics.d.ts +113 -0
- package/dist/server/operations/get-catalog-diagnostics.js +65 -0
- package/dist/server/operations/get-registry.js +17 -4
- package/dist/server/operations/get-task-detail-schema.d.ts +8 -0
- package/dist/server/operations/get-task-detail-schema.js +1 -0
- package/dist/server/operations/get-task-detail.d.ts +8 -0
- package/dist/server/operations/get-task-detail.js +1 -0
- package/dist/server/operations/get-task-diagnostics.d.ts +4 -4
- package/dist/server/operations/get-workflow-revision.d.ts +25 -0
- package/dist/server/operations/get-workflow-revision.js +50 -0
- package/dist/server/operations/install-workflow-revision.d.ts +27 -0
- package/dist/server/operations/install-workflow-revision.js +46 -0
- package/dist/server/operations/list-workflow-revisions.d.ts +20 -0
- package/dist/server/operations/list-workflow-revisions.js +40 -0
- package/dist/server/operations/preload-workflow-revision.d.ts +28 -0
- package/dist/server/operations/preload-workflow-revision.js +60 -0
- package/dist/server/operations/schedule-faults.d.ts +1 -0
- package/dist/server/operations/schedule-faults.js +32 -4
- package/dist/server/operations/schedule-rest-body.d.ts +1 -0
- package/dist/server/operations/schedule-rest-body.js +2 -1
- package/dist/server/operations/start-or-signal-workflow.js +1 -1
- package/dist/server/operations/start-workflow.js +1 -1
- package/dist/server/operations/static-registrations.js +42 -0
- package/dist/server/operations/storage.js +2 -2
- package/dist/server/operations/submit-review-decision.js +1 -1
- package/dist/server/operations/update-schedule.d.ts +2 -0
- package/dist/server/operations/update-schedule.js +4 -2
- package/dist/server/operations/workflow-catalog-operation-helpers.d.ts +59 -0
- package/dist/server/operations/workflow-catalog-operation-helpers.js +162 -0
- package/dist/server/runtime/task-dispatch-envelope.d.ts +14 -0
- package/dist/server/runtime/task-dispatch-envelope.js +32 -0
- package/dist/server/runtime/task-dispatch-revision.d.ts +29 -0
- package/dist/server/runtime/task-dispatch-revision.js +13 -0
- package/dist/server/runtime/task-dispatch.js +12 -37
- package/dist/server/runtime/task-ledger-recovery.js +1 -1
- package/dist/server/runtime/task-ledger-runtime.d.ts +14 -2
- package/dist/server/runtime/task-ledger-runtime.js +5 -3
- package/dist/server/runtime/task-polling.js +9 -3
- package/dist/server/runtime/task-reconciliation.js +2 -1
- package/dist/server/runtime/websocket-upgrade.js +2 -0
- package/dist/server/runtime/websocket-worker.js +9 -0
- package/dist/server/task-ledger-codec.d.ts +9 -0
- package/dist/server/task-ledger-codec.js +4 -1
- package/dist/server/task-ledger-transition-helpers.js +1 -0
- package/dist/server/task-ledger-types.d.ts +9 -0
- package/dist/server/task-ledger.d.ts +1 -1
- package/dist/server/task-ledger.js +2 -1
- package/dist/server/task-queue-types.d.ts +2 -0
- package/dist/storage/bun-sql.js +51 -6
- package/dist/storage/catalog-keys.d.ts +64 -0
- package/dist/storage/catalog-keys.js +8 -0
- package/dist/storage/compressed-storage.js +1 -1
- package/dist/storage/derived-operations.js +1 -1
- package/dist/storage/index.d.ts +28 -1
- package/dist/storage/interface.d.ts +28 -1
- package/dist/storage/interface.js +1 -1
- package/dist/storage/key-encoding.d.ts +15 -0
- package/dist/storage/key-encoding.js +3 -0
- package/dist/storage/key-prefixes.d.ts +1 -1
- package/dist/storage/key-prefixes.js +16 -0
- package/dist/storage/lmdb.d.ts +54 -1
- package/dist/storage/lmdb.js +1 -1
- package/dist/storage/mailbox-keys.d.ts +80 -0
- package/dist/storage/mailbox-keys.js +14 -0
- package/dist/storage/memory.js +1 -1
- package/dist/storage/neon.js +2 -2
- package/dist/storage/node-sqlite-loader.d.ts +1 -1
- package/dist/storage/node-sqlite.js +51 -6
- package/dist/storage/outbox-keys.d.ts +77 -0
- package/dist/storage/outbox-keys.js +14 -0
- package/dist/storage/postgres.js +2 -2
- package/dist/storage/resolve.js +1 -1
- package/dist/storage/scoped-storage.js +1 -1
- package/dist/storage/storage-configuration.d.ts +6 -0
- package/dist/storage/testing.js +1 -1
- package/dist/storage/turso.js +2 -2
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/dist/web-extension.js +1 -1
- package/dist/worker/manifest/registry-contract-builder.d.ts +21 -3
- package/dist/worker/manifest/registry-contract-builder.js +40 -31
- package/dist/worker/protocol-messages.d.ts +17 -0
- package/dist/worker/protocol-schemas.d.ts +32 -0
- package/dist/worker/protocol-schemas.js +7 -3
- package/dist/worker/protocol-task-result.js +35 -3
- package/dist/worker/protocol.js +1 -1
- package/dist/worker/registry/types.d.ts +2 -0
- package/dist/worker/registry.d.ts +1 -1
- package/dist/worker/registry.js +3 -1
- package/dist/workers/workflow-runner.d.ts +9 -0
- package/dist/workers/workflow-runner.js +9 -2
- package/dist/workers/workflow-worker-entry.js +9 -4
- package/package.json +2 -2
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
import {
|
|
2
|
+
KEYS,
|
|
3
|
+
requireStorageCapability,
|
|
4
|
+
storageConditionalBatch
|
|
5
|
+
} from "../../storage/interface.js";
|
|
6
|
+
import { compareCodepoint } from "../compare-codepoint.js";
|
|
7
|
+
import {
|
|
8
|
+
checkWorkflowCompatibility,
|
|
9
|
+
DEFAULT_WORKFLOW_COMPATIBILITY_POLICY
|
|
10
|
+
} from "../contract/compatibility.js";
|
|
11
|
+
import { validateWorkflowOrActivityName } from "../types/name-grammar.js";
|
|
12
|
+
import { encodeActivePointer, manifestsAreByteIdentical } from "./codec.js";
|
|
13
|
+
import {
|
|
14
|
+
WorkflowCatalogActivationConflictError,
|
|
15
|
+
WorkflowCatalogActiveEntryMissingError,
|
|
16
|
+
WorkflowCatalogConflictError
|
|
17
|
+
} from "./errors.js";
|
|
18
|
+
import { removeCatalogEntry } from "./removal.js";
|
|
19
|
+
import {
|
|
20
|
+
readActivePointer,
|
|
21
|
+
readCatalogEntry,
|
|
22
|
+
scanCatalogEntriesForName,
|
|
23
|
+
writeCatalogEntry
|
|
24
|
+
} from "./storage-io.js";
|
|
25
|
+
const MAX_ACTIVATE_REGISTERED_ATTEMPTS = 5;
|
|
26
|
+
|
|
27
|
+
export class WorkflowCatalog {
|
|
28
|
+
#storage;
|
|
29
|
+
#entries;
|
|
30
|
+
#active;
|
|
31
|
+
constructor(storage, seed) {
|
|
32
|
+
this.#storage = storage;
|
|
33
|
+
this.#entries = seed?.entries ?? new Map;
|
|
34
|
+
this.#active = seed?.active ?? new Map;
|
|
35
|
+
}
|
|
36
|
+
getEntry(name, revision) {
|
|
37
|
+
return this.#entries.get(name)?.get(revision);
|
|
38
|
+
}
|
|
39
|
+
listRevisions(name) {
|
|
40
|
+
const byName = this.#entries.get(name);
|
|
41
|
+
return byName === void 0 ? [] : [...byName.values()];
|
|
42
|
+
}
|
|
43
|
+
resolveActive(name) {
|
|
44
|
+
return this.#active.get(name);
|
|
45
|
+
}
|
|
46
|
+
async resolveEntry(name, revision) {
|
|
47
|
+
const cached = this.getEntry(name, revision);
|
|
48
|
+
if (cached !== void 0)
|
|
49
|
+
return { manifest: cached.manifest, installedAt: cached.installedAt };
|
|
50
|
+
const durable = await readCatalogEntry(this.#storage, name, revision);
|
|
51
|
+
if (durable === null)
|
|
52
|
+
return;
|
|
53
|
+
this.#cacheEntry(name, revision, durable);
|
|
54
|
+
return durable;
|
|
55
|
+
}
|
|
56
|
+
async listInstalledRevisions(name) {
|
|
57
|
+
return (await scanCatalogEntriesForName(this.#storage, name)).toSorted((a, b) => compareCodepoint(a.manifest.revision, b.manifest.revision));
|
|
58
|
+
}
|
|
59
|
+
async hasInstalled(name, revision) {
|
|
60
|
+
if (this.getEntry(name, revision) !== void 0)
|
|
61
|
+
return !0;
|
|
62
|
+
return await readCatalogEntry(this.#storage, name, revision) !== null;
|
|
63
|
+
}
|
|
64
|
+
async resolveActiveDurable(name) {
|
|
65
|
+
return await readActivePointer(this.#storage, name) ?? void 0;
|
|
66
|
+
}
|
|
67
|
+
async remove(name, revision) {
|
|
68
|
+
requireStorageCapability(this.#storage, "conditionalBatch", "workflow catalog removal");
|
|
69
|
+
const result = await removeCatalogEntry(this.#storage, name, revision);
|
|
70
|
+
if (result.outcome === "removed")
|
|
71
|
+
this.#entries.get(name)?.delete(revision);
|
|
72
|
+
return result;
|
|
73
|
+
}
|
|
74
|
+
async install(manifest, definition) {
|
|
75
|
+
validateWorkflowOrActivityName(manifest.name, "workflow");
|
|
76
|
+
const existing = this.getEntry(manifest.name, manifest.revision);
|
|
77
|
+
if (existing !== void 0) {
|
|
78
|
+
if (!manifestsAreByteIdentical(existing.manifest, manifest))
|
|
79
|
+
throw new WorkflowCatalogConflictError(manifest.name, manifest.revision);
|
|
80
|
+
return existing;
|
|
81
|
+
}
|
|
82
|
+
const durable = await readCatalogEntry(this.#storage, manifest.name, manifest.revision);
|
|
83
|
+
if (durable !== null)
|
|
84
|
+
return this.#adoptDurableEntry(manifest, durable, definition);
|
|
85
|
+
const installedAt = Date.now();
|
|
86
|
+
if (!await writeCatalogEntry(this.#storage, manifest, installedAt)) {
|
|
87
|
+
const raced = await readCatalogEntry(this.#storage, manifest.name, manifest.revision);
|
|
88
|
+
if (raced === null)
|
|
89
|
+
throw new WorkflowCatalogConflictError(manifest.name, manifest.revision);
|
|
90
|
+
return this.#adoptDurableEntry(manifest, raced, definition);
|
|
91
|
+
}
|
|
92
|
+
return this.#cacheEntry(manifest.name, manifest.revision, {
|
|
93
|
+
manifest,
|
|
94
|
+
installedAt,
|
|
95
|
+
...definition === void 0 ? {} : { definition }
|
|
96
|
+
});
|
|
97
|
+
}
|
|
98
|
+
#adoptDurableEntry(manifest, durable, definition) {
|
|
99
|
+
if (!manifestsAreByteIdentical(durable.manifest, manifest))
|
|
100
|
+
throw new WorkflowCatalogConflictError(manifest.name, manifest.revision);
|
|
101
|
+
return this.#cacheEntry(manifest.name, manifest.revision, {
|
|
102
|
+
manifest: durable.manifest,
|
|
103
|
+
installedAt: durable.installedAt,
|
|
104
|
+
...definition === void 0 ? {} : { definition }
|
|
105
|
+
});
|
|
106
|
+
}
|
|
107
|
+
#cacheEntry(name, revision, entry) {
|
|
108
|
+
let byName = this.#entries.get(name);
|
|
109
|
+
if (byName === void 0) {
|
|
110
|
+
byName = new Map;
|
|
111
|
+
this.#entries.set(name, byName);
|
|
112
|
+
}
|
|
113
|
+
byName.set(revision, entry);
|
|
114
|
+
return entry;
|
|
115
|
+
}
|
|
116
|
+
async activateRegistered(name, manifest, definition) {
|
|
117
|
+
requireStorageCapability(this.#storage, "conditionalBatch", "workflow catalog activation");
|
|
118
|
+
await this.install(manifest, definition);
|
|
119
|
+
for (let attempt = 1;attempt <= MAX_ACTIVATE_REGISTERED_ATTEMPTS; attempt++) {
|
|
120
|
+
const current = await readActivePointer(this.#storage, name);
|
|
121
|
+
if (current !== null && current.revision === manifest.revision) {
|
|
122
|
+
this.#active.set(name, current);
|
|
123
|
+
return current;
|
|
124
|
+
}
|
|
125
|
+
const nextGeneration = current === null ? 1 : current.generation + 1, nextPointer = {
|
|
126
|
+
revision: manifest.revision,
|
|
127
|
+
generation: nextGeneration,
|
|
128
|
+
activatedAt: Date.now()
|
|
129
|
+
};
|
|
130
|
+
if (await storageConditionalBatch(this.#storage, [
|
|
131
|
+
{
|
|
132
|
+
key: KEYS.catalogActive(name),
|
|
133
|
+
expectedValue: current === null ? null : encodeActivePointer(current)
|
|
134
|
+
}
|
|
135
|
+
], [{ type: "put", key: KEYS.catalogActive(name), value: encodeActivePointer(nextPointer) }])) {
|
|
136
|
+
this.#active.set(name, nextPointer);
|
|
137
|
+
return nextPointer;
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
throw new WorkflowCatalogActivationConflictError(name, MAX_ACTIVATE_REGISTERED_ATTEMPTS);
|
|
141
|
+
}
|
|
142
|
+
async activateCandidate(name, candidateManifest, options) {
|
|
143
|
+
requireStorageCapability(this.#storage, "conditionalBatch", "workflow catalog activation");
|
|
144
|
+
await this.install(candidateManifest);
|
|
145
|
+
const currentPointer = await readActivePointer(this.#storage, name), refusal = await this.#refuseIncompatibleOrStaleCandidate(name, candidateManifest, currentPointer, options);
|
|
146
|
+
if (refusal !== void 0)
|
|
147
|
+
return refusal;
|
|
148
|
+
const nextGeneration = currentPointer === null ? 1 : currentPointer.generation + 1, nextPointer = {
|
|
149
|
+
revision: candidateManifest.revision,
|
|
150
|
+
generation: nextGeneration,
|
|
151
|
+
activatedAt: Date.now()
|
|
152
|
+
};
|
|
153
|
+
if (!await storageConditionalBatch(this.#storage, [
|
|
154
|
+
{
|
|
155
|
+
key: KEYS.catalogActive(name),
|
|
156
|
+
expectedValue: currentPointer === null ? null : encodeActivePointer(currentPointer)
|
|
157
|
+
}
|
|
158
|
+
], [{ type: "put", key: KEYS.catalogActive(name), value: encodeActivePointer(nextPointer) }]))
|
|
159
|
+
return { applied: !1, reason: "conflict" };
|
|
160
|
+
this.#active.set(name, nextPointer);
|
|
161
|
+
return { applied: !0, pointer: nextPointer };
|
|
162
|
+
}
|
|
163
|
+
async#refuseIncompatibleOrStaleCandidate(name, candidateManifest, currentPointer, options) {
|
|
164
|
+
if (currentPointer === null)
|
|
165
|
+
return this.#refuseStaleFirstActivation(options);
|
|
166
|
+
const generationRefusal = this.#refuseMissingOrStaleGeneration(currentPointer, options);
|
|
167
|
+
if (generationRefusal !== void 0)
|
|
168
|
+
return generationRefusal;
|
|
169
|
+
return this.#refuseIncompatibleCandidate(name, candidateManifest, currentPointer, options);
|
|
170
|
+
}
|
|
171
|
+
#refuseStaleFirstActivation(options) {
|
|
172
|
+
if (options?.expectedGeneration !== void 0 && options.expectedGeneration !== 0)
|
|
173
|
+
return { applied: !1, reason: "stale-generation", currentGeneration: 0 };
|
|
174
|
+
return;
|
|
175
|
+
}
|
|
176
|
+
#refuseMissingOrStaleGeneration(currentPointer, options) {
|
|
177
|
+
if (options?.expectedGeneration === void 0)
|
|
178
|
+
return {
|
|
179
|
+
applied: !1,
|
|
180
|
+
reason: "expected-generation-required",
|
|
181
|
+
currentGeneration: currentPointer.generation
|
|
182
|
+
};
|
|
183
|
+
if (options.expectedGeneration !== currentPointer.generation)
|
|
184
|
+
return {
|
|
185
|
+
applied: !1,
|
|
186
|
+
reason: "stale-generation",
|
|
187
|
+
currentGeneration: currentPointer.generation
|
|
188
|
+
};
|
|
189
|
+
return;
|
|
190
|
+
}
|
|
191
|
+
async#refuseIncompatibleCandidate(name, candidateManifest, currentPointer, options) {
|
|
192
|
+
const currentEntry = await this.resolveEntry(name, currentPointer.revision);
|
|
193
|
+
if (currentEntry === void 0)
|
|
194
|
+
throw new WorkflowCatalogActiveEntryMissingError(name, currentPointer.revision);
|
|
195
|
+
const verdict = checkWorkflowCompatibility(currentEntry.manifest, candidateManifest, options?.policy ?? DEFAULT_WORKFLOW_COMPATIBILITY_POLICY);
|
|
196
|
+
return verdict.compatible ? void 0 : { applied: !1, reason: "incompatible", verdict };
|
|
197
|
+
}
|
|
198
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Order two strings by codepoint rather than `localeCompare` (project rule:
|
|
3
|
+
* deterministic comparisons in runtime logic). A standalone leaf module so
|
|
4
|
+
* every codepoint sort across the registry-snapshot family of modules —
|
|
5
|
+
* `registry-snapshot.ts`'s `sortedWorkflows`/`sortedActivities` and
|
|
6
|
+
* `registry-workflow-manifest.ts`'s scoped-activity sort — shares one
|
|
7
|
+
* implementation of the unreachable-in-isolation tie branch, rather than
|
|
8
|
+
* each defining its own uncovered copy, without creating an import cycle
|
|
9
|
+
* between those two modules.
|
|
10
|
+
*
|
|
11
|
+
* @module core/compare-codepoint
|
|
12
|
+
*/
|
|
13
|
+
export declare function compareCodepoint(a: string, b: string): number;
|
package/dist/core/compression.js
CHANGED
|
@@ -3,5 +3,5 @@ import type { ContextInternals } from './internals.ts';
|
|
|
3
3
|
export declare function validateAttribute(internals: ContextInternals, key: string, value: SearchAttributeValue): void;
|
|
4
4
|
export declare function setAttribute(internals: ContextInternals, key: string, value: SearchAttributeValue): void;
|
|
5
5
|
export declare function setAttributes(internals: ContextInternals, attributes: Record<string, SearchAttributeValue>): void;
|
|
6
|
-
export declare function getAttribute
|
|
6
|
+
export declare function getAttribute(internals: ContextInternals, key: string): SearchAttributeValue | undefined;
|
|
7
7
|
export declare function getAttributes(internals: ContextInternals): Readonly<Record<string, SearchAttributeValue>>;
|
|
@@ -43,8 +43,8 @@ export declare function readOrInitConditionDeadline(internals: ContextInternals,
|
|
|
43
43
|
*/
|
|
44
44
|
export declare function waitUntil(context: Context, internals: ContextInternals, predicate: () => boolean, timeout?: Duration): Generator<ContextOperationRequest, boolean | void, unknown>;
|
|
45
45
|
export declare function getVersion(_context: Context, internals: ContextInternals, changeId: string, minSupported: number, maxSupported: number): Generator<ContextOperationRequest, number, unknown>;
|
|
46
|
-
export declare function waitForUpdate
|
|
47
|
-
payload:
|
|
46
|
+
export declare function waitForUpdate(context: Context, internals: ContextInternals, name: string): Generator<ContextOperationRequest, {
|
|
47
|
+
payload: unknown;
|
|
48
48
|
respond: (result: unknown) => void;
|
|
49
49
|
}, unknown>;
|
|
50
50
|
export declare function review(context: Context, internals: ContextInternals, options: HumanReviewOptions): Generator<ContextOperationRequest, HumanReviewResult, unknown>;
|
|
@@ -114,9 +114,11 @@ export class Context {
|
|
|
114
114
|
if (prepared.cached)
|
|
115
115
|
return;
|
|
116
116
|
const execute = () => durableOperations.completePreparedSleepOperation(this, prepared);
|
|
117
|
-
if (!internals.workflowInterceptor)
|
|
118
|
-
|
|
119
|
-
|
|
117
|
+
if (!internals.workflowInterceptor) {
|
|
118
|
+
yield* execute();
|
|
119
|
+
return;
|
|
120
|
+
}
|
|
121
|
+
yield* internals.workflowInterceptor.sleep({
|
|
120
122
|
workflowId: this.workflowId,
|
|
121
123
|
duration: prepared.milliseconds,
|
|
122
124
|
headers: new Map
|
|
@@ -6,7 +6,7 @@ import type { ContextOperationRequest } from './operation-request.ts';
|
|
|
6
6
|
interface WorkflowAtomicStateOperationCache {
|
|
7
7
|
nextStep(): number;
|
|
8
8
|
has(step: number): boolean;
|
|
9
|
-
get
|
|
9
|
+
get(step: number): unknown;
|
|
10
10
|
set(step: number, value: unknown): void;
|
|
11
11
|
}
|
|
12
12
|
export declare function createStateNamespace(context: Context, internals: ContextInternals): WorkflowStateNamespace;
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Convert an authoring-time workflow definition into a {@link WorkflowContract}.
|
|
3
|
+
*
|
|
4
|
+
* Every `DefinitionSchema` (workflow input/output, every signal/update/query,
|
|
5
|
+
* every activity, the finalizer) is converted through the existing
|
|
6
|
+
* `definitionSchemaToJsonSchema()` — this module does not reimplement schema
|
|
7
|
+
* conversion, and it does not reimplement the "unsupported construct emits
|
|
8
|
+
* `unknown`" behavior, which lives entirely in `weft codegen`'s emitter.
|
|
9
|
+
*
|
|
10
|
+
* @module core/contract/build
|
|
11
|
+
*/
|
|
12
|
+
import { WeftError } from '../weft-error.ts';
|
|
13
|
+
import type { WorkflowContract, WorkflowContractSource } from './types.ts';
|
|
14
|
+
/** Discriminates which part of a workflow contract source failed conversion. */
|
|
15
|
+
type ContractEntityKind = 'workflow' | 'signal' | 'update' | 'query' | 'activity' | 'finalizer';
|
|
16
|
+
/**
|
|
17
|
+
* Thrown when {@link buildWorkflowContract} cannot convert a registered
|
|
18
|
+
* `DefinitionSchema` to JSON Schema — no built-in vendor adapter and no
|
|
19
|
+
* structural `~standard.jsonSchema` converter. Mirrors
|
|
20
|
+
* `RegistrySchemaConversionError`'s `entityKind`/`entityName`/`direction`
|
|
21
|
+
* fields; not root-exported, matching that error's precedent (build-tooling
|
|
22
|
+
* errors surfaced to the caller of the builder, not part of the public error
|
|
23
|
+
* vocabulary).
|
|
24
|
+
*
|
|
25
|
+
* @example
|
|
26
|
+
* ```ts
|
|
27
|
+
* import { WorkflowContractConversionError } from '@lostgradient/weft';
|
|
28
|
+
*
|
|
29
|
+
* try {
|
|
30
|
+
* throw new WorkflowContractConversionError('activity', 'charge', 'inputSchema', new Error('boom'));
|
|
31
|
+
* } catch (error) {
|
|
32
|
+
* console.log(error instanceof WorkflowContractConversionError); // true
|
|
33
|
+
* }
|
|
34
|
+
* ```
|
|
35
|
+
*/
|
|
36
|
+
export declare class WorkflowContractConversionError extends WeftError<'WorkflowContractConversionError'> {
|
|
37
|
+
readonly entityKind: ContractEntityKind;
|
|
38
|
+
readonly entityName: string;
|
|
39
|
+
readonly direction: 'inputSchema' | 'outputSchema';
|
|
40
|
+
constructor(entityKind: ContractEntityKind, entityName: string, direction: 'inputSchema' | 'outputSchema', cause: unknown);
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Build a normalized {@link WorkflowContract} from an authoring-time workflow
|
|
44
|
+
* definition.
|
|
45
|
+
*
|
|
46
|
+
* Accepts anything structurally matching {@link WorkflowContractSource} —
|
|
47
|
+
* both `WorkflowDefinition` and `BuiltWorkflowDefinition` (the return type
|
|
48
|
+
* of `workflow({...}).execute(fn)`) satisfy it directly, with no cast.
|
|
49
|
+
*
|
|
50
|
+
* Throws {@link WorkflowContractConversionError} if any declared schema
|
|
51
|
+
* (workflow input/output, a signal/update/query input/output, an activity
|
|
52
|
+
* input/output, or the finalizer's input/output) cannot be converted to JSON
|
|
53
|
+
* Schema.
|
|
54
|
+
*
|
|
55
|
+
* @example
|
|
56
|
+
* ```ts
|
|
57
|
+
* import { buildWorkflowContract } from '@lostgradient/weft';
|
|
58
|
+
*
|
|
59
|
+
* const contract = buildWorkflowContract({ name: 'checkout', version: '2.1.0' });
|
|
60
|
+
* console.log(contract.name, contract.workflowVersion); // checkout 2.1.0
|
|
61
|
+
* ```
|
|
62
|
+
*/
|
|
63
|
+
export declare function buildWorkflowContract(source: WorkflowContractSource): WorkflowContract;
|
|
64
|
+
export {};
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
import { definitionSchemaToJsonSchema } from "../types/definition-schema-to-json.js";
|
|
2
|
+
import { DEFAULT_WORKFLOW_VERSION } from "../versioning.js";
|
|
3
|
+
import { WeftError } from "../weft-error.js";
|
|
4
|
+
import { normalizeWorkflowContract } from "./normalize.js";
|
|
5
|
+
|
|
6
|
+
export class WorkflowContractConversionError extends WeftError {
|
|
7
|
+
entityKind;
|
|
8
|
+
entityName;
|
|
9
|
+
direction;
|
|
10
|
+
constructor(entityKind, entityName, direction, cause) {
|
|
11
|
+
const causeMessage = cause instanceof Error ? cause.message : String(cause);
|
|
12
|
+
super("WorkflowContractConversionError", `Failed to convert ${direction} for ${entityKind} "${entityName}": ${causeMessage}`, { cause });
|
|
13
|
+
this.entityKind = entityKind;
|
|
14
|
+
this.entityName = entityName;
|
|
15
|
+
this.direction = direction;
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
function convertSchema(entityKind, entityName, direction, schema) {
|
|
19
|
+
try {
|
|
20
|
+
return definitionSchemaToJsonSchema(schema, direction === "inputSchema" ? "input" : "output");
|
|
21
|
+
} catch (cause) {
|
|
22
|
+
throw new WorkflowContractConversionError(entityKind, entityName, direction, cause);
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
function buildMessageContract(entityKind, entityName, source) {
|
|
26
|
+
const entry = {};
|
|
27
|
+
if (source.inputSchema !== void 0)
|
|
28
|
+
entry.inputSchema = convertSchema(entityKind, entityName, "inputSchema", source.inputSchema);
|
|
29
|
+
if (source.outputSchema !== void 0)
|
|
30
|
+
entry.outputSchema = convertSchema(entityKind, entityName, "outputSchema", source.outputSchema);
|
|
31
|
+
return entry;
|
|
32
|
+
}
|
|
33
|
+
function buildActivityContract(workflowName, activityName, source) {
|
|
34
|
+
return buildMessageContract("activity", `${workflowName}.${activityName}`, source);
|
|
35
|
+
}
|
|
36
|
+
function buildMessageRecord(workflowName, entityKind, sources) {
|
|
37
|
+
if (sources === void 0)
|
|
38
|
+
return;
|
|
39
|
+
const localKeys = Object.keys(sources);
|
|
40
|
+
if (localKeys.length === 0)
|
|
41
|
+
return;
|
|
42
|
+
const built = Object.create(null);
|
|
43
|
+
for (const localKey of localKeys) {
|
|
44
|
+
const source = sources[localKey], wireName = source.name;
|
|
45
|
+
if (Object.hasOwn(built, wireName))
|
|
46
|
+
throw Error(`Duplicate ${entityKind} runtime name "${wireName}" in workflow "${workflowName}"`);
|
|
47
|
+
built[wireName] = buildMessageContract(entityKind, `${workflowName}.${entityKind}.${wireName}`, source);
|
|
48
|
+
}
|
|
49
|
+
return built;
|
|
50
|
+
}
|
|
51
|
+
function buildActivityRecord(workflowName, sources) {
|
|
52
|
+
if (sources === void 0)
|
|
53
|
+
return;
|
|
54
|
+
const names = Object.keys(sources);
|
|
55
|
+
if (names.length === 0)
|
|
56
|
+
return;
|
|
57
|
+
const built = Object.create(null);
|
|
58
|
+
for (const name of names)
|
|
59
|
+
built[name] = buildActivityContract(workflowName, name, sources[name]);
|
|
60
|
+
return built;
|
|
61
|
+
}
|
|
62
|
+
function applyDescriptionAndTags(draft, source) {
|
|
63
|
+
if (source.description !== void 0)
|
|
64
|
+
draft.description = source.description;
|
|
65
|
+
if (source.tags !== void 0 && source.tags.length > 0)
|
|
66
|
+
draft.tags = [...source.tags];
|
|
67
|
+
}
|
|
68
|
+
function applySchemas(draft, source) {
|
|
69
|
+
if (source.inputSchema !== void 0)
|
|
70
|
+
draft.inputSchema = convertSchema("workflow", source.name, "inputSchema", source.inputSchema);
|
|
71
|
+
if (source.outputSchema !== void 0)
|
|
72
|
+
draft.outputSchema = convertSchema("workflow", source.name, "outputSchema", source.outputSchema);
|
|
73
|
+
}
|
|
74
|
+
function applyMessageRecords(draft, source) {
|
|
75
|
+
const signals = buildMessageRecord(source.name, "signal", source.signals);
|
|
76
|
+
if (signals !== void 0)
|
|
77
|
+
draft.signals = signals;
|
|
78
|
+
const updates = buildMessageRecord(source.name, "update", source.updates);
|
|
79
|
+
if (updates !== void 0)
|
|
80
|
+
draft.updates = updates;
|
|
81
|
+
const queries = buildMessageRecord(source.name, "query", source.queries);
|
|
82
|
+
if (queries !== void 0)
|
|
83
|
+
draft.queries = queries;
|
|
84
|
+
}
|
|
85
|
+
export function buildWorkflowContract(source) {
|
|
86
|
+
const draft = {
|
|
87
|
+
name: source.name,
|
|
88
|
+
workflowVersion: source.version ?? DEFAULT_WORKFLOW_VERSION
|
|
89
|
+
};
|
|
90
|
+
applyDescriptionAndTags(draft, source);
|
|
91
|
+
applySchemas(draft, source);
|
|
92
|
+
applyMessageRecords(draft, source);
|
|
93
|
+
const activities = buildActivityRecord(source.name, source.activities);
|
|
94
|
+
if (activities !== void 0)
|
|
95
|
+
draft.activities = activities;
|
|
96
|
+
if (source.finalizer !== void 0)
|
|
97
|
+
draft.finalizer = buildMessageContract("finalizer", `${source.name}.finalizer`, source.finalizer);
|
|
98
|
+
return normalizeWorkflowContract(draft);
|
|
99
|
+
}
|
|
@@ -0,0 +1,187 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Structured compatibility verdicts between two workflow revision manifests.
|
|
3
|
+
*
|
|
4
|
+
* `checkWorkflowCompatibility()` answers "may `candidate` automatically
|
|
5
|
+
* activate in place of `current`" as a bounded, machine-readable
|
|
6
|
+
* {@link WorkflowCompatibilityVerdict} rather than a thrown error or a bare
|
|
7
|
+
* boolean—a catalog or refresh orchestrator can report every reason a
|
|
8
|
+
* candidate revision was rejected, but never override one during automatic
|
|
9
|
+
* activation (the reasons are policy-fixed except for one deliberate knob,
|
|
10
|
+
* see {@link WorkflowCompatibilityPolicy}).
|
|
11
|
+
*
|
|
12
|
+
* The five reasons this module can report mirror, and in one case literally
|
|
13
|
+
* call, checks that already exist elsewhere in the codebase rather than
|
|
14
|
+
* reinventing them:
|
|
15
|
+
*
|
|
16
|
+
* - `workflow-version-incompatible` calls {@link checkVersionCompatibility}
|
|
17
|
+
* from `core/versioning.ts`—the exact primitive
|
|
18
|
+
* `derivePreparedExecutionState()` (`core/engine/lifecycle/persist.ts`)
|
|
19
|
+
* already uses to reject a stored checkpoint against a re-registered
|
|
20
|
+
* workflow. This module never modifies that primitive; it reuses it as-is
|
|
21
|
+
* so the two answers can never disagree.
|
|
22
|
+
* - `contract-hash-mismatch` and `manifest-version-unsupported` reuse the
|
|
23
|
+
* same names `parseWorkflowRevisionManifest()`
|
|
24
|
+
* (`WorkflowRevisionManifestRejectionReason`, `./failure.ts`) already uses
|
|
25
|
+
* for structurally similar situations—hostile-input rejection there,
|
|
26
|
+
* activation compatibility here. The two unions are intentionally
|
|
27
|
+
* independent; the shared literal is vocabulary reuse, not a coupling.
|
|
28
|
+
* `manifest-version-unsupported` specifically is unreachable through this
|
|
29
|
+
* module's own type-safe surface today—`WorkflowRevisionManifest.manifestVersion`
|
|
30
|
+
* is typed as the single supported literal, and every in-repo producer
|
|
31
|
+
* ({@link buildWorkflowRevisionManifest}, {@link parseWorkflowRevisionManifest})
|
|
32
|
+
* guarantees it—so it costs nothing to check here and exists for the
|
|
33
|
+
* consumer this module is exported for but does not yet have: a future
|
|
34
|
+
* catalog or refresh system comparing a manifest it read from storage or
|
|
35
|
+
* the wire, which may not have round-tripped through
|
|
36
|
+
* `parseWorkflowRevisionManifest()` immediately before the comparison.
|
|
37
|
+
* Widening the parameter type to accept that case is deferred to whichever
|
|
38
|
+
* catalog work (WFT-9) first needs a type-safe way to trigger it.
|
|
39
|
+
*
|
|
40
|
+
* `checkWorkflowCompatibility()` is pure and synchronous: both manifests
|
|
41
|
+
* already carry their computed `contractHash`/`revision`, so no hashing
|
|
42
|
+
* happens here.
|
|
43
|
+
*
|
|
44
|
+
* @module core/contract/compatibility
|
|
45
|
+
*/
|
|
46
|
+
import type { WorkflowRevisionManifest } from './types.ts';
|
|
47
|
+
/**
|
|
48
|
+
* One bounded, machine-readable reason `candidate` is not compatible with
|
|
49
|
+
* `current`. Closed union, safe to use as a metric label—exactly the five
|
|
50
|
+
* reasons named by the Activation Compatibility issue, in the fixed order
|
|
51
|
+
* {@link checkWorkflowCompatibility} evaluates and reports them.
|
|
52
|
+
*
|
|
53
|
+
* @example
|
|
54
|
+
* ```ts
|
|
55
|
+
* import type { WorkflowCompatibilityReason } from '@lostgradient/weft';
|
|
56
|
+
*
|
|
57
|
+
* const counts = new Map<WorkflowCompatibilityReason, number>();
|
|
58
|
+
* counts.set('contract-hash-mismatch', 1);
|
|
59
|
+
* console.log(counts.get('contract-hash-mismatch'));
|
|
60
|
+
* ```
|
|
61
|
+
*/
|
|
62
|
+
export type WorkflowCompatibilityReason = 'name-mismatch' | 'manifest-version-unsupported' | 'contract-hash-mismatch' | 'workflow-version-incompatible' | 'artifact-revision-mismatch';
|
|
63
|
+
/**
|
|
64
|
+
* The structured result of {@link checkWorkflowCompatibility}: either fully
|
|
65
|
+
* compatible, or incompatible with the complete, ordered list of every
|
|
66
|
+
* applicable {@link WorkflowCompatibilityReason}—never just the first one
|
|
67
|
+
* found. A refresh orchestrator may report every reason here; it may never
|
|
68
|
+
* treat an incompatible verdict as compatible during automatic activation.
|
|
69
|
+
*
|
|
70
|
+
* @example
|
|
71
|
+
* ```ts
|
|
72
|
+
* import type { WorkflowCompatibilityVerdict } from '@lostgradient/weft';
|
|
73
|
+
*
|
|
74
|
+
* const verdict: WorkflowCompatibilityVerdict = {
|
|
75
|
+
* compatible: false,
|
|
76
|
+
* reasons: ['contract-hash-mismatch'],
|
|
77
|
+
* };
|
|
78
|
+
* console.log(verdict.compatible ? 'ok' : verdict.reasons.join(', '));
|
|
79
|
+
* ```
|
|
80
|
+
*/
|
|
81
|
+
export type WorkflowCompatibilityVerdict = Readonly<{
|
|
82
|
+
compatible: true;
|
|
83
|
+
}> | Readonly<{
|
|
84
|
+
compatible: false;
|
|
85
|
+
reasons: readonly WorkflowCompatibilityReason[];
|
|
86
|
+
}>;
|
|
87
|
+
/**
|
|
88
|
+
* Declared compatibility policy accepted by {@link checkWorkflowCompatibility}.
|
|
89
|
+
*
|
|
90
|
+
* `requireExactRevision` is the *only* tunable axis. `name-mismatch`,
|
|
91
|
+
* `manifest-version-unsupported`, `contract-hash-mismatch`, and
|
|
92
|
+
* `workflow-version-incompatible` can never be loosened by policy—a
|
|
93
|
+
* refresh system may report those reasons but may not override them during
|
|
94
|
+
* automatic activation, which is the literal mechanism the Activation
|
|
95
|
+
* Compatibility issue asks for.
|
|
96
|
+
*
|
|
97
|
+
* - `true` (the strict default): a candidate whose `revision` differs from
|
|
98
|
+
* `current`'s—even when `contractHash` is identical—reports
|
|
99
|
+
* `artifact-revision-mismatch` and is not compatible.
|
|
100
|
+
* - `false`: a `revision`-only difference is tolerated; `artifact-revision-mismatch`
|
|
101
|
+
* is never reported. What that difference *means* depends on how `revision`
|
|
102
|
+
* was produced. Under the default content-derived revision
|
|
103
|
+
* ({@link deriveWorkflowRevision}), a `revision`-only difference is always a
|
|
104
|
+
* documentation-only edit (`contract.description` or `contract.tags`, since
|
|
105
|
+
* `contractHash` deliberately excludes both). Under a caller-supplied
|
|
106
|
+
* revision (`buildWorkflowRevisionManifest(contract, { revision })`), a
|
|
107
|
+
* `revision`-only difference can be any artifact-identity change the caller
|
|
108
|
+
* chose to encode there (a build id, a deployment tag)—`false` tolerates
|
|
109
|
+
* that too, since this module has no way to distinguish an opaque supplied
|
|
110
|
+
* revision from a derived one by inspecting the manifest alone. Do not set
|
|
111
|
+
* `false` when your manifests use explicit revisions unless you intend to
|
|
112
|
+
* accept any `revision` change as compatible. Under the default
|
|
113
|
+
* content-derived revision, a `contractHash` difference always implies a
|
|
114
|
+
* `revision` difference too (`revision`'s full-contract digest is a strict
|
|
115
|
+
* superset of what `contractHash` covers); under a caller-supplied
|
|
116
|
+
* revision, two manifests can share the same `revision` string despite
|
|
117
|
+
* different `contractHash` values, since the caller controls that string
|
|
118
|
+
* independently of contract content. Either way,
|
|
119
|
+
* `contract-hash-mismatch` is unaffected by this setting and still blocks
|
|
120
|
+
* activation on its own.
|
|
121
|
+
*
|
|
122
|
+
* @example
|
|
123
|
+
* ```ts
|
|
124
|
+
* import type { WorkflowCompatibilityPolicy } from '@lostgradient/weft';
|
|
125
|
+
*
|
|
126
|
+
* const lenient: WorkflowCompatibilityPolicy = { requireExactRevision: false };
|
|
127
|
+
* console.log(lenient.requireExactRevision);
|
|
128
|
+
* ```
|
|
129
|
+
*/
|
|
130
|
+
export interface WorkflowCompatibilityPolicy {
|
|
131
|
+
/**
|
|
132
|
+
* Whether an exact `revision` match is required for compatibility, on top
|
|
133
|
+
* of the four never-tunable reasons. Defaults to `true` when omitted or
|
|
134
|
+
* when the policy object itself omits the field.
|
|
135
|
+
*/
|
|
136
|
+
requireExactRevision?: boolean;
|
|
137
|
+
}
|
|
138
|
+
/**
|
|
139
|
+
* The strict default policy `checkWorkflowCompatibility` uses when no
|
|
140
|
+
* policy argument is supplied. Exported so a catalog can name the default
|
|
141
|
+
* explicitly—in a log line, a configuration default, a test fixture—rather
|
|
142
|
+
* than relying on an implicit fallback. Frozen: `checkWorkflowCompatibility`
|
|
143
|
+
* consults this exact object as the default argument for every call that
|
|
144
|
+
* omits a policy, so a caller that mutated it would silently change the
|
|
145
|
+
* default for every other caller in the process.
|
|
146
|
+
*
|
|
147
|
+
* @example
|
|
148
|
+
* ```ts
|
|
149
|
+
* import { DEFAULT_WORKFLOW_COMPATIBILITY_POLICY } from '@lostgradient/weft';
|
|
150
|
+
*
|
|
151
|
+
* console.log(DEFAULT_WORKFLOW_COMPATIBILITY_POLICY.requireExactRevision); // true
|
|
152
|
+
* ```
|
|
153
|
+
*/
|
|
154
|
+
export declare const DEFAULT_WORKFLOW_COMPATIBILITY_POLICY: Readonly<Required<WorkflowCompatibilityPolicy>>;
|
|
155
|
+
/**
|
|
156
|
+
* Compare two workflow revision manifests and report whether `candidate` is
|
|
157
|
+
* compatible with `current`—the pure comparison behind automatic
|
|
158
|
+
* activation. Symmetric: `checkWorkflowCompatibility(a, b, policy)` and
|
|
159
|
+
* `checkWorkflowCompatibility(b, a, policy)` always agree, since every
|
|
160
|
+
* underlying check is an equality or bounded-value comparison with no
|
|
161
|
+
* directionality.
|
|
162
|
+
*
|
|
163
|
+
* Every applicable reason is collected and returned in the fixed order
|
|
164
|
+
* `name-mismatch`, `manifest-version-unsupported`, `contract-hash-mismatch`,
|
|
165
|
+
* `workflow-version-incompatible`, `artifact-revision-mismatch`—the
|
|
166
|
+
* function never short-circuits on the first reason found.
|
|
167
|
+
*
|
|
168
|
+
* @example
|
|
169
|
+
* ```ts
|
|
170
|
+
* import {
|
|
171
|
+
* buildWorkflowContract,
|
|
172
|
+
* buildWorkflowRevisionManifest,
|
|
173
|
+
* checkWorkflowCompatibility,
|
|
174
|
+
* } from '@lostgradient/weft';
|
|
175
|
+
*
|
|
176
|
+
* const current = await buildWorkflowRevisionManifest(
|
|
177
|
+
* buildWorkflowContract({ name: 'checkout', version: '1.0.0' }),
|
|
178
|
+
* );
|
|
179
|
+
* const candidate = await buildWorkflowRevisionManifest(
|
|
180
|
+
* buildWorkflowContract({ name: 'checkout', version: '2.0.0' }),
|
|
181
|
+
* );
|
|
182
|
+
*
|
|
183
|
+
* const verdict = checkWorkflowCompatibility(current, candidate);
|
|
184
|
+
* console.log(verdict.compatible); // false
|
|
185
|
+
* ```
|
|
186
|
+
*/
|
|
187
|
+
export declare function checkWorkflowCompatibility(current: WorkflowRevisionManifest, candidate: WorkflowRevisionManifest, policy?: WorkflowCompatibilityPolicy): WorkflowCompatibilityVerdict;
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import { checkVersionCompatibility } from "../versioning.js";
|
|
2
|
+
import { WORKFLOW_REVISION_MANIFEST_VERSION } from "./types.js";
|
|
3
|
+
export const DEFAULT_WORKFLOW_COMPATIBILITY_POLICY = Object.freeze({
|
|
4
|
+
requireExactRevision: !0
|
|
5
|
+
});
|
|
6
|
+
function isSupportedWorkflowRevisionManifestVersion(version) {
|
|
7
|
+
return version === WORKFLOW_REVISION_MANIFEST_VERSION;
|
|
8
|
+
}
|
|
9
|
+
function isNameMismatch(current, candidate) {
|
|
10
|
+
return current.name !== candidate.name;
|
|
11
|
+
}
|
|
12
|
+
function isManifestVersionUnsupported(current, candidate) {
|
|
13
|
+
return !isSupportedWorkflowRevisionManifestVersion(current.manifestVersion) || !isSupportedWorkflowRevisionManifestVersion(candidate.manifestVersion);
|
|
14
|
+
}
|
|
15
|
+
function isContractHashMismatch(current, candidate) {
|
|
16
|
+
return current.contractHash !== candidate.contractHash;
|
|
17
|
+
}
|
|
18
|
+
function isWorkflowVersionIncompatible(current, candidate) {
|
|
19
|
+
return checkVersionCompatibility(current.workflowVersion, candidate.workflowVersion) === "incompatible";
|
|
20
|
+
}
|
|
21
|
+
function isArtifactRevisionMismatch(current, candidate) {
|
|
22
|
+
return current.revision !== candidate.revision;
|
|
23
|
+
}
|
|
24
|
+
export function checkWorkflowCompatibility(current, candidate, policy = DEFAULT_WORKFLOW_COMPATIBILITY_POLICY) {
|
|
25
|
+
const requireExactRevision = policy.requireExactRevision ?? !0, reasons = [];
|
|
26
|
+
if (isNameMismatch(current, candidate))
|
|
27
|
+
reasons.push("name-mismatch");
|
|
28
|
+
if (isManifestVersionUnsupported(current, candidate))
|
|
29
|
+
reasons.push("manifest-version-unsupported");
|
|
30
|
+
if (isContractHashMismatch(current, candidate))
|
|
31
|
+
reasons.push("contract-hash-mismatch");
|
|
32
|
+
if (isWorkflowVersionIncompatible(current, candidate))
|
|
33
|
+
reasons.push("workflow-version-incompatible");
|
|
34
|
+
if (requireExactRevision && isArtifactRevisionMismatch(current, candidate))
|
|
35
|
+
reasons.push("artifact-revision-mismatch");
|
|
36
|
+
return reasons.length === 0 ? { compatible: !0 } : { compatible: !1, reasons };
|
|
37
|
+
}
|