@deksden-com/dd-flow-cli 0.9.0-beta.15 → 0.9.0-beta.150
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/CHANGELOG.md +895 -0
- package/README.md +140 -6
- package/dist/build-info.json +8 -8
- package/dist/cli/argument-values.js +38 -0
- package/dist/cli/command-inputs.js +386 -0
- package/dist/cli/command-metadata.js +232 -0
- package/dist/cli/command-option-descriptions.js +192 -0
- package/dist/cli/completion-cli.js +70 -0
- package/dist/cli/completion.js +57 -0
- package/dist/cli/diagnostic-invocation.js +46 -0
- package/dist/cli/diagnostic.js +120 -0
- package/dist/cli/error-output.js +52 -0
- package/dist/cli/executor-onboarding.js +76 -0
- package/dist/cli/flows.js +29 -0
- package/dist/cli/harnesses.js +84 -0
- package/dist/cli/help.js +396 -19
- package/dist/cli/hook-ingress.js +102 -0
- package/dist/cli/input-preparation.js +165 -0
- package/dist/cli/memory-flow-admission.js +50 -0
- package/dist/cli/memory-init-invocation.js +85 -0
- package/dist/cli/memory-init.js +249 -0
- package/dist/cli/memory-storage-admission.js +54 -0
- package/dist/cli/memory-storage-qualification.js +105 -0
- package/dist/cli/memory-storage-transition.js +123 -0
- package/dist/cli/memory-upgrade.js +189 -0
- package/dist/cli/models.js +39 -0
- package/dist/cli/native-hook-ingress.js +90 -0
- package/dist/cli/native-hook-preparation.js +55 -0
- package/dist/cli/operator-profiles.js +61 -0
- package/dist/cli/output-options.js +35 -0
- package/dist/cli/response-file.js +72 -0
- package/dist/cli/run-cli.js +1734 -550
- package/dist/cli/runtime-maintenance-diagnostics.js +46 -0
- package/dist/cli/runtime-maintenance-ingress.js +52 -0
- package/dist/cli/runtime-process.js +153 -0
- package/dist/cli/setup.js +150 -0
- package/dist/cli.js +89 -2
- package/dist/domain/diagnostic-aspects.js +103 -0
- package/dist/domain/diagnostic-flows.js +8 -0
- package/dist/domain/stage-catalog.js +1 -1
- package/dist/domain/stage-handler-identities.js +28 -0
- package/dist/harness-runtime/DD-ZCODE.md +112 -0
- package/dist/harness-runtime/OPENCODE-LICENSE.txt +24 -0
- package/dist/harness-runtime/bin/dd-agy.mjs +56 -0
- package/dist/harness-runtime/bin/dd-codex.mjs +27 -0
- package/dist/harness-runtime/bin/dd-droid.mjs +34 -0
- package/dist/harness-runtime/bin/dd-grok.mjs +40 -0
- package/dist/harness-runtime/bin/dd-opencode.mjs +22 -0
- package/dist/harness-runtime/bin/dd-zcode.mjs +87 -0
- package/dist/harness-runtime/lib/adapter-timeouts.d.mts +5 -0
- package/dist/harness-runtime/lib/adapter-timeouts.mjs +34 -0
- package/dist/harness-runtime/lib/agy-error-boundary.mjs +58 -0
- package/dist/harness-runtime/lib/agy-hooks.d.mts +1 -0
- package/dist/harness-runtime/lib/agy-hooks.mjs +9 -0
- package/dist/harness-runtime/lib/agy-native-inspection.mjs +216 -0
- package/dist/harness-runtime/lib/agy-native_pb.js +117 -0
- package/dist/harness-runtime/lib/daemon-observation.d.mts +2 -0
- package/dist/harness-runtime/lib/daemon-observation.mjs +163 -0
- package/dist/harness-runtime/lib/daemon-operations.d.mts +2 -0
- package/dist/harness-runtime/lib/daemon-operations.mjs +462 -0
- package/dist/harness-runtime/lib/dd-agy-daemon.d.mts +6 -0
- package/dist/harness-runtime/lib/dd-agy-daemon.mjs +1096 -0
- package/dist/harness-runtime/lib/dd-agy.mjs +86 -0
- package/dist/harness-runtime/lib/dd-codex-daemon.d.mts +1 -0
- package/dist/harness-runtime/lib/dd-codex-daemon.mjs +231 -0
- package/dist/harness-runtime/lib/dd-codex.d.mts +1 -0
- package/dist/harness-runtime/lib/dd-codex.mjs +954 -0
- package/dist/harness-runtime/lib/dd-droid-daemon.mjs +141 -0
- package/dist/harness-runtime/lib/dd-droid.mjs +626 -0
- package/dist/harness-runtime/lib/dd-grok-daemon.mjs +555 -0
- package/dist/harness-runtime/lib/dd-grok.mjs +180 -0
- package/dist/harness-runtime/lib/dd-opencode-daemon.mjs +622 -0
- package/dist/harness-runtime/lib/dd-opencode.mjs +390 -0
- package/dist/harness-runtime/lib/dd-zcode-daemon.mjs +752 -0
- package/dist/harness-runtime/lib/dd-zcode.mjs +1175 -0
- package/dist/harness-runtime/lib/delegation-instructions.d.mts +14 -0
- package/dist/harness-runtime/lib/delegation-instructions.mjs +157 -0
- package/dist/harness-runtime/lib/dispatch-fence.mjs +14 -0
- package/dist/harness-runtime/lib/driver-recovery.mjs +140 -0
- package/dist/harness-runtime/lib/droid-observation.mjs +66 -0
- package/dist/harness-runtime/lib/entity-references.d.mts +2 -0
- package/dist/harness-runtime/lib/entity-references.mjs +9 -0
- package/dist/harness-runtime/lib/lease-renewal.d.mts +8 -0
- package/dist/harness-runtime/lib/lease-renewal.mjs +37 -0
- package/dist/harness-runtime/lib/lifecycle-command.d.mts +20 -0
- package/dist/harness-runtime/lib/lifecycle-command.mjs +273 -0
- package/dist/harness-runtime/lib/lifecycle-contract.d.mts +10 -0
- package/dist/harness-runtime/lib/lifecycle-contract.mjs +19 -0
- package/dist/harness-runtime/lib/managed-daemon.d.mts +16 -0
- package/dist/harness-runtime/lib/managed-daemon.mjs +698 -0
- package/dist/harness-runtime/lib/managed-flow-env.mjs +15 -0
- package/dist/harness-runtime/lib/model-observations.mjs +101 -0
- package/dist/harness-runtime/lib/native-children.d.mts +23 -0
- package/dist/harness-runtime/lib/native-children.mjs +219 -0
- package/dist/harness-runtime/lib/native-hook-command.d.mts +7 -0
- package/dist/harness-runtime/lib/native-hook-command.mjs +251 -0
- package/dist/harness-runtime/lib/native-request-proof.d.mts +2 -0
- package/dist/harness-runtime/lib/native-request-proof.mjs +65 -0
- package/dist/harness-runtime/lib/native-streams.mjs +45 -0
- package/dist/harness-runtime/lib/observation-clock.d.mts +18 -0
- package/dist/harness-runtime/lib/observation-clock.mjs +95 -0
- package/dist/harness-runtime/lib/opencode-plugin.mjs +85 -0
- package/dist/harness-runtime/lib/operation-context.mjs +5 -0
- package/dist/harness-runtime/lib/operation-errors.d.mts +16 -0
- package/dist/harness-runtime/lib/operation-errors.mjs +127 -0
- package/dist/harness-runtime/lib/operation-progress.d.mts +7 -0
- package/dist/harness-runtime/lib/operation-progress.mjs +114 -0
- package/dist/harness-runtime/lib/process-json.d.mts +5 -0
- package/dist/harness-runtime/lib/process-json.mjs +201 -0
- package/dist/harness-runtime/lib/process-snapshot.mjs +10 -0
- package/dist/harness-runtime/lib/provider-overload-policy.d.mts +15 -0
- package/dist/harness-runtime/lib/provider-overload-policy.mjs +151 -0
- package/dist/harness-runtime/lib/runner-events.mjs +202 -0
- package/dist/harness-runtime/lib/runner-lock.mjs +42 -0
- package/dist/harness-runtime/lib/session-settlement.mjs +30 -0
- package/dist/harness-runtime/lib/setup-progress.d.mts +9 -0
- package/dist/harness-runtime/lib/setup-progress.mjs +53 -0
- package/dist/harness-runtime/lib/tool-observations.d.mts +21 -0
- package/dist/harness-runtime/lib/tool-observations.mjs +228 -0
- package/dist/harness-runtime/lib/zcode-usage.mjs +55 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-1y4a697q.js +81 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-2ny4vxct.js +92 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-6mptkzbc.js +0 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-7x67cf1q.js +52 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-9rqn6x4v.js +16 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-9vdz0zwn.js +1661 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-ecs5ftka.js +1466 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-frbwqjmf.js +145 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-gne7h7mq.js +50 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-gx9wnkzr.js +105 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-m2eywc8w.js +0 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-nwcpakzx.js +12 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-q4g3afnw.js +623 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-qav6mfdz.js +0 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-sxt88q69.js +12 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-t1xa31vm.js +39 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-ve4aws36.js +103 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-vmytr4q8.js +4 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-vt9jbch8.js +36 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-vyas3vgt.js +0 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-wjyeq25y.js +30 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-xgnj2w4v.js +20 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-y2etg5bs.js +9 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-ydhz1zrh.js +238 -0
- package/dist/harness-runtime/vendor/opencode-client/chunks/service-probe-z6qdwcsf.js +62 -0
- package/dist/harness-runtime/vendor/opencode-client/contract.d.ts +1 -0
- package/dist/harness-runtime/vendor/opencode-client/contract.js +12 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/api/api.d.ts +2806 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/api/api.js +0 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/api.d.ts +4 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/api.js +0 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/client.d.ts +2530 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/client.js +15 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/generated/client-error.d.ts +7 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/generated/client-error.js +6 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/generated/client.d.ts +2529 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/generated/client.js +8 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/generated/index.d.ts +2 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/generated/index.js +12 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/index.d.ts +35 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/index.js +75 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/rpc.d.ts +20 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/rpc.js +11 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/service.d.ts +90 -0
- package/dist/harness-runtime/vendor/opencode-client/effect/service.js +187 -0
- package/dist/harness-runtime/vendor/opencode-client/package.json +84 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/api.d.ts +21 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/api.js +0 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/client.d.ts +252 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/client.js +14 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/generated/client-error.d.ts +8 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/generated/client-error.js +6 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/generated/client.d.ts +259 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/generated/client.js +7 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/generated/index.d.ts +3 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/generated/index.js +79 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/generated/types.d.ts +8932 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/generated/types.js +70 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/index.d.ts +6 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/index.js +83 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/rpc.d.ts +32 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/rpc.js +7 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/service.d.ts +24 -0
- package/dist/harness-runtime/vendor/opencode-client/promise/service.js +187 -0
- package/dist/harness-runtime/vendor/opencode-client/pty-handoff.d.ts +12 -0
- package/dist/harness-runtime/vendor/opencode-client/pty-handoff.js +14 -0
- package/dist/harness-runtime/vendor/opencode-client/rpc-runtime.d.ts +20 -0
- package/dist/harness-runtime/vendor/opencode-client/rpc-runtime.js +14 -0
- package/dist/harness-runtime/vendor/opencode-client/service-contender.d.ts +37 -0
- package/dist/harness-runtime/vendor/opencode-client/service-contender.js +10 -0
- package/dist/harness-runtime/vendor/opencode-client/service-probe.d.ts +70 -0
- package/dist/harness-runtime/vendor/opencode-client/service-probe.js +16 -0
- package/dist/harness-runtime/vendor/opencode-client/service-timing.d.ts +12 -0
- package/dist/harness-runtime/vendor/opencode-client/service-timing.js +10 -0
- package/dist/harness-runtime/vendor/opencode-client/service-version.d.ts +2 -0
- package/dist/harness-runtime/vendor/opencode-client/service-version.js +6 -0
- package/dist/harness-runtime/vendor/opencode-client/service.d.ts +52 -0
- package/dist/harness-runtime/vendor/opencode-client/service.js +1 -0
- package/dist/harness-runtime/vendor/opencode-client/shared-events.d.ts +11 -0
- package/dist/harness-runtime/vendor/opencode-client/shared-events.js +8 -0
- package/dist/harness-runtime/vendor/opencode-client/solid/connection.d.ts +37 -0
- package/dist/harness-runtime/vendor/opencode-client/solid/connection.js +10 -0
- package/dist/harness-runtime/vendor/opencode-client/solid/data.d.ts +211 -0
- package/dist/harness-runtime/vendor/opencode-client/solid/data.js +18 -0
- package/dist/harness-runtime/vendor/opencode-client/solid/index.d.ts +3 -0
- package/dist/harness-runtime/vendor/opencode-client/solid/index.js +32 -0
- package/dist/harness-runtime/vendor/opencode-client/solid/pty.d.ts +22 -0
- package/dist/harness-runtime/vendor/opencode-client/solid/pty.js +8 -0
- package/dist/harness-runtime/vendor/opencode-plugin.mjs +3 -0
- package/dist/protocol/local-files.js +18 -9
- package/dist/runtime/context.js +8 -4
- package/dist/schemas/agent-profile.schema.json +1 -1
- package/dist/schemas/code-review-decision.schema.json +9 -0
- package/dist/schemas/code-review-result.schema.json +1 -1
- package/dist/schemas/code-verification.schema.json +7 -5
- package/dist/schemas/code-work-batch.schema.json +2 -2
- package/dist/schemas/diagnostic-stage-result.schema.json +354 -0
- package/dist/schemas/diagnostic-work-result.schema.json +296 -0
- package/dist/schemas/discovery-result.schema.json +184 -0
- package/dist/schemas/execution-bundle.schema.json +211 -0
- package/dist/schemas/execution-settings.schema.json +162 -0
- package/dist/schemas/flow-descriptor.schema.json +54 -0
- package/dist/schemas/flow-run.schema.json +29 -0
- package/dist/schemas/harness-catalog.schema.json +80 -0
- package/dist/schemas/mb-init-compose-result.schema.json +457 -0
- package/dist/schemas/mb-init-discover-result.schema.json +500 -0
- package/dist/schemas/mb-init-finish-result.schema.json +422 -0
- package/dist/schemas/mb-init-preflight-result.schema.json +367 -0
- package/dist/schemas/mb-init-review-result.schema.json +396 -0
- package/dist/schemas/mb-init-verify-result.schema.json +391 -0
- package/dist/schemas/mb-upgrade-stage-result.schema.json +863 -0
- package/dist/schemas/memory-bootstrap-receipt-v2.schema.json +67 -0
- package/dist/schemas/memory-bootstrap-receipt.schema.json +354 -0
- package/dist/schemas/memory-composition-work-result.schema.json +38 -0
- package/dist/schemas/memory-repair-work-result.schema.json +56 -0
- package/dist/schemas/memory-review-correction-plan.schema.json +30 -0
- package/dist/schemas/memory-review-work-result.schema.json +43 -0
- package/dist/schemas/model-catalog.schema.json +153 -0
- package/dist/schemas/plan-review-decision.schema.json +12 -3
- package/dist/schemas/plan-review-result.schema.json +2 -2
- package/dist/schemas/profile-settings.schema.json +122 -0
- package/dist/schemas/project-flow-pack-manifest.schema.json +1 -1
- package/dist/schemas/release-impact.schema.json +3 -3
- package/dist/schemas/release-manifest.schema.json +291 -0
- package/dist/schemas/run-control-receipt.schema.json +118 -0
- package/dist/schemas/run-control-request.schema.json +36 -0
- package/dist/schemas/run-engine-binding.schema.json +1 -1
- package/dist/schemas/stage-start-response.schema.json +4 -0
- package/dist/schemas/vnext-protocol-plan.schema.json +2 -2
- package/dist/services/accepted-intent.js +139 -0
- package/dist/services/branch-context.js +3 -3
- package/dist/services/canon.js +54 -15
- package/dist/services/check-environment.js +21 -0
- package/dist/services/check-runner-evidence.js +562 -0
- package/dist/services/cleanup.js +133 -40
- package/dist/services/cli-operation-classifier.js +26 -63
- package/dist/services/cli-upgrade-allowlist.js +27 -0
- package/dist/services/code-checks.js +1398 -119
- package/dist/services/codex-hook-delivery.js +32 -0
- package/dist/services/command-context.js +80 -0
- package/dist/services/compatibility-preflight.js +16 -3
- package/dist/services/config.js +11 -8
- package/dist/services/continuation-outcome.js +20 -0
- package/dist/services/controller-child-capacity.js +13 -0
- package/dist/services/controller-child-observer.js +115 -0
- package/dist/services/controller-execution.js +94 -0
- package/dist/services/controller-fanout.js +226 -0
- package/dist/services/controller-memory-task.js +45 -0
- package/dist/services/controller-memory-worker.js +49 -0
- package/dist/services/dashboard.js +143 -58
- package/dist/services/descriptor-coordinator-session.js +35 -0
- package/dist/services/descriptor-root-work.js +53 -0
- package/dist/services/descriptor-run-settlement.js +107 -0
- package/dist/services/descriptor-run-start.js +475 -0
- package/dist/services/descriptor-stage-coordinator.js +250 -0
- package/dist/services/descriptor-stage-settlement.js +223 -0
- package/dist/services/descriptor-stage-start.js +175 -0
- package/dist/services/diagnostic-evidence.js +73 -0
- package/dist/services/diagnostic-report-publication.js +72 -0
- package/dist/services/diagnostic-report.js +67 -0
- package/dist/services/diagnostic-run-bundle.js +74 -0
- package/dist/services/diagnostic-snapshot.js +159 -0
- package/dist/services/diagnostic-stage-handlers.js +108 -0
- package/dist/services/diagnostic-stage-results.js +132 -0
- package/dist/services/diagnostic-start.js +84 -0
- package/dist/services/diagnostic-work-batch.js +34 -0
- package/dist/services/diagnostic-work-collection.js +97 -0
- package/dist/services/diagnostic-work-registration.js +101 -0
- package/dist/services/diagnostic-work-results.js +93 -0
- package/dist/services/discovery/agy-discovery.js +2 -0
- package/dist/services/discovery/codex-discovery.js +2 -0
- package/dist/services/discovery/droid-discovery.js +2 -0
- package/dist/services/discovery/grok-discovery.js +2 -0
- package/dist/services/discovery/opencode-discovery.js +2 -0
- package/dist/services/discovery/static.js +31 -0
- package/dist/services/discovery/zcode-discovery.js +2 -0
- package/dist/services/engines.js +354 -163
- package/dist/services/eval-snapshots.js +1316 -150
- package/dist/services/execution-bundles.js +275 -0
- package/dist/services/execution-policy.js +185 -0
- package/dist/services/executor-onboarding.js +56 -0
- package/dist/services/external-work-launch.js +310 -0
- package/dist/services/flow-catalog.js +30 -0
- package/dist/services/flow-descriptors.js +82 -0
- package/dist/services/frozen-engine.js +387 -0
- package/dist/services/generic-execution.js +164 -0
- package/dist/services/harness-adapter.js +355 -36
- package/dist/services/harness-config.js +2 -0
- package/dist/services/harness-discovery.js +29 -0
- package/dist/services/harness-doctor.js +75 -0
- package/dist/services/harness-probe-effects.js +51 -0
- package/dist/services/harness-version-probe.js +100 -0
- package/dist/services/hook-memory-routing.js +188 -0
- package/dist/services/hook-recovery-guard.js +14 -0
- package/dist/services/hook-session-observation.js +24 -0
- package/dist/services/hooks.js +791 -326
- package/dist/services/hybrid-contracts.js +474 -0
- package/dist/services/hybrid-digest.js +14 -0
- package/dist/services/ids.js +29 -1
- package/dist/services/installation-lock.js +95 -0
- package/dist/services/installed-flow-source.js +226 -0
- package/dist/services/lanes.js +78 -65
- package/dist/services/lifecycle-command.js +1 -288
- package/dist/services/lifecycle-contract.js +1 -0
- package/dist/services/lifecycle-invocations.js +2148 -0
- package/dist/services/managed-daemon-binding.js +38 -0
- package/dist/services/managed-lease-monitor.js +133 -0
- package/dist/services/managed-processes.js +449 -69
- package/dist/services/memory-accepted-composition.js +78 -0
- package/dist/services/memory-baseline-preservation.js +65 -0
- package/dist/services/memory-completed-correction-wave.js +328 -0
- package/dist/services/memory-compose-handler.js +400 -0
- package/dist/services/memory-composition-acceptance.js +375 -0
- package/dist/services/memory-composition-graph.js +165 -0
- package/dist/services/memory-composition-registration.js +161 -0
- package/dist/services/memory-composition-work-custody.js +156 -0
- package/dist/services/memory-composition-work-results.js +108 -0
- package/dist/services/memory-corrected-review-acceptance.js +129 -0
- package/dist/services/memory-corrected-review-batch.js +37 -0
- package/dist/services/memory-corrected-review-findings.js +108 -0
- package/dist/services/memory-corrected-review-inputs.js +215 -0
- package/dist/services/memory-corrected-review-projection.js +78 -0
- package/dist/services/memory-corrected-review-receipt.js +178 -0
- package/dist/services/memory-corrected-review-registration.js +192 -0
- package/dist/services/memory-correction-check-receipt.js +235 -0
- package/dist/services/memory-correction-input-owner.js +6 -0
- package/dist/services/memory-custody-snapshot.js +36 -0
- package/dist/services/memory-discover-handler.js +104 -0
- package/dist/services/memory-finish-evidence.js +457 -0
- package/dist/services/memory-finish-handler.js +229 -0
- package/dist/services/memory-finish-integration.js +450 -0
- package/dist/services/memory-finish-readiness.js +169 -0
- package/dist/services/memory-git-integration.js +220 -0
- package/dist/services/memory-historical-corrected-review.js +212 -0
- package/dist/services/memory-historical-original-review.js +143 -0
- package/dist/services/memory-historical-repair-registration.js +105 -0
- package/dist/services/memory-historical-second-review.js +147 -0
- package/dist/services/memory-init-bootstrap-readiness.js +210 -0
- package/dist/services/memory-init-contexts.js +131 -0
- package/dist/services/memory-init-controller-start.js +103 -0
- package/dist/services/memory-init-engine-release.js +223 -0
- package/dist/services/memory-init-git-policy.js +165 -0
- package/dist/services/memory-init-lint-capability.js +203 -0
- package/dist/services/memory-init-native-capacity.js +309 -0
- package/dist/services/memory-init-preflight.js +334 -0
- package/dist/services/memory-init-project-bootstrap.js +599 -0
- package/dist/services/memory-init-request-candidate.js +213 -0
- package/dist/services/memory-init-request-input.js +82 -0
- package/dist/services/memory-init-resource-storage.js +125 -0
- package/dist/services/memory-init-run-allocation.js +81 -0
- package/dist/services/memory-init-run-bundle.js +135 -0
- package/dist/services/memory-init-start.js +181 -0
- package/dist/services/memory-init-startup-custody.js +80 -0
- package/dist/services/memory-init-startup-input.js +240 -0
- package/dist/services/memory-init-storage.js +91 -0
- package/dist/services/memory-init-stores.js +359 -0
- package/dist/services/memory-init-worktrunk-capability.js +174 -0
- package/dist/services/memory-layer-publication.js +611 -0
- package/dist/services/memory-layer.js +221 -0
- package/dist/services/memory-lint-config.js +194 -0
- package/dist/services/memory-native-review-copy.js +103 -0
- package/dist/services/memory-normal-flow-entry.js +87 -0
- package/dist/services/memory-ordinary-defaults.js +129 -0
- package/dist/services/memory-preflight-bootstrap-custody.js +115 -0
- package/dist/services/memory-preflight-handler.js +274 -0
- package/dist/services/memory-repair-current-view.js +299 -0
- package/dist/services/memory-repair-document-delta.js +488 -0
- package/dist/services/memory-repair-history.js +496 -0
- package/dist/services/memory-repair-physical-binding.js +194 -0
- package/dist/services/memory-repair-publication-files.js +152 -0
- package/dist/services/memory-repair-publication-intent.js +27 -0
- package/dist/services/memory-repair-publication-plan.js +162 -0
- package/dist/services/memory-repair-publication-source.js +225 -0
- package/dist/services/memory-repair-publication.js +795 -0
- package/dist/services/memory-repair-registration.js +240 -0
- package/dist/services/memory-repair-work-baseline.js +415 -0
- package/dist/services/memory-repair-work-completion.js +117 -0
- package/dist/services/memory-repair-work-custody.js +73 -0
- package/dist/services/memory-repair-work-results.js +108 -0
- package/dist/services/memory-repair-workspace.js +261 -0
- package/dist/services/memory-repair-writer-copy.js +736 -0
- package/dist/services/memory-result-binding.js +239 -0
- package/dist/services/memory-retained-review-authority.js +138 -0
- package/dist/services/memory-retained-review-results.js +70 -0
- package/dist/services/memory-retained-second-baseline.js +102 -0
- package/dist/services/memory-retained-second-repairs.js +162 -0
- package/dist/services/memory-review-acceptance.js +214 -0
- package/dist/services/memory-review-correction-plan.js +206 -0
- package/dist/services/memory-review-handler.js +585 -0
- package/dist/services/memory-review-inputs.js +246 -0
- package/dist/services/memory-review-limits.js +10 -0
- package/dist/services/memory-review-receipt.js +180 -0
- package/dist/services/memory-review-registration.js +117 -0
- package/dist/services/memory-review-work-custody.js +126 -0
- package/dist/services/memory-review-work-input.js +91 -0
- package/dist/services/memory-review-work-results.js +95 -0
- package/dist/services/memory-second-corrected-review-inputs.js +167 -0
- package/dist/services/memory-second-correction-plan.js +77 -0
- package/dist/services/memory-second-repair-baseline.js +91 -0
- package/dist/services/memory-second-repair-launch.js +614 -0
- package/dist/services/memory-second-repair-registration.js +88 -0
- package/dist/services/memory-second-repair-source.js +187 -0
- package/dist/services/memory-second-review-acceptance.js +115 -0
- package/dist/services/memory-source-observations.js +117 -0
- package/dist/services/memory-stage-dispatch.js +65 -0
- package/dist/services/memory-stage-results.js +290 -0
- package/dist/services/memory-tool-probe.js +25 -0
- package/dist/services/memory-upgrade-analysis-handler.js +243 -0
- package/dist/services/memory-upgrade-bootstrap-readiness.js +251 -0
- package/dist/services/memory-upgrade-evidence.js +100 -0
- package/dist/services/memory-upgrade-inventory.js +442 -0
- package/dist/services/memory-upgrade-publication-custody.js +73 -0
- package/dist/services/memory-upgrade-publication.js +413 -0
- package/dist/services/memory-upgrade-selection.js +430 -0
- package/dist/services/memory-upgrade-start.js +60 -0
- package/dist/services/memory-upgrade-storage-readiness.js +340 -0
- package/dist/services/memory-verification-acceptance.js +156 -0
- package/dist/services/memory-verification-checks.js +317 -0
- package/dist/services/memory-verification-receipt.js +160 -0
- package/dist/services/memory-verify-handler.js +137 -0
- package/dist/services/memory-work-result-json.js +12 -0
- package/dist/services/memory-work-result-preparation.js +64 -0
- package/dist/services/merge-queue.js +228 -149
- package/dist/services/merge-server.js +163 -35
- package/dist/services/migrations.js +164 -114
- package/dist/services/model-catalog.js +109 -0
- package/dist/services/model-discovery.js +46 -0
- package/dist/services/native-daemon-history.js +50 -0
- package/dist/services/native-session-control.js +39 -0
- package/dist/services/operator-profiles.js +236 -0
- package/dist/services/physical-startup.js +45 -0
- package/dist/services/plan-runtime.js +26 -11
- package/dist/services/plans.js +28 -25
- package/dist/services/project-registry.js +97 -0
- package/dist/services/project-summary.js +1 -1
- package/dist/services/projects.js +17 -87
- package/dist/services/prompt-delivery.js +71 -0
- package/dist/services/prompts.js +28 -17
- package/dist/services/protocols.js +163 -87
- package/dist/services/provider-capacity.js +455 -0
- package/dist/services/recovery-observation-budget.js +121 -0
- package/dist/services/recovery-snapshot-database.js +588 -0
- package/dist/services/release-archive-producer.js +52 -0
- package/dist/services/release-archive.js +143 -0
- package/dist/services/release-cache.js +150 -0
- package/dist/services/release-compatibility.js +18 -0
- package/dist/services/release-download.js +67 -0
- package/dist/services/release-envelope.js +104 -0
- package/dist/services/release-manifest.js +45 -0
- package/dist/services/release-payload.js +114 -0
- package/dist/services/release-producer.js +63 -0
- package/dist/services/release-provenance.js +160 -0
- package/dist/services/release-registry.js +66 -0
- package/dist/services/release-source.js +194 -0
- package/dist/services/repair-intents.js +31 -0
- package/dist/services/repair-receipt.js +13 -0
- package/dist/services/review-copy.js +165 -0
- package/dist/services/review-deferral.js +23 -0
- package/dist/services/run-control-receipt.js +56 -0
- package/dist/services/run-control-worker.js +428 -0
- package/dist/services/run-control.js +1092 -0
- package/dist/services/run-controller-adapter.js +400 -0
- package/dist/services/run-controller-capture.js +186 -0
- package/dist/services/run-controller-process.js +205 -0
- package/dist/services/run-controller-recovery.js +295 -0
- package/dist/services/run-controller-state.js +97 -0
- package/dist/services/run-controller.js +1326 -0
- package/dist/services/run-engine-bindings.js +1 -1
- package/dist/services/run-fork.js +147 -0
- package/dist/services/run-health.js +149 -0
- package/dist/services/run-observations.js +152 -0
- package/dist/services/run-projection.js +22 -64
- package/dist/services/run-recovery-guard.js +107 -0
- package/dist/services/run-recovery-runtime.js +112 -0
- package/dist/services/run-recovery.js +456 -0
- package/dist/services/run-start-custody.js +189 -0
- package/dist/services/runs.js +1023 -246
- package/dist/services/runtime-budget.js +446 -0
- package/dist/services/runtime-command.js +43 -0
- package/dist/services/runtime-scope-capture.js +52 -0
- package/dist/services/runtime-scope-control.js +468 -0
- package/dist/services/runtime-scope-resume.js +605 -0
- package/dist/services/runtime-scope-stop.js +211 -0
- package/dist/services/runtime-scope-worker.js +314 -0
- package/dist/services/runtime-service.js +19 -14
- package/dist/services/schema-validation.js +10 -8
- package/dist/services/scope-writer-cleanup.js +27 -0
- package/dist/services/sessions.js +36 -91
- package/dist/services/setup.js +427 -0
- package/dist/services/stage-blocker.js +17 -7
- package/dist/services/stage-context.js +193 -19
- package/dist/services/stage-handlers.js +89 -0
- package/dist/services/stage-lifecycle.js +152 -116
- package/dist/services/stage-pause.js +202 -91
- package/dist/services/stage-report-renderer.js +234 -6
- package/dist/services/stage-work-graph.js +52 -0
- package/dist/services/tooling.js +41 -30
- package/dist/services/usage.js +49 -101
- package/dist/services/verification-matrix.js +393 -0
- package/dist/services/version-status.js +1 -1
- package/dist/services/vnext-code-review.js +235 -88
- package/dist/services/vnext-code.js +327 -226
- package/dist/services/vnext-contracts.js +10 -1
- package/dist/services/vnext-execution-profile.js +80 -5
- package/dist/services/vnext-fanout.js +355 -21
- package/dist/services/vnext-merge.js +332 -111
- package/dist/services/vnext-plan-review.js +287 -132
- package/dist/services/vnext-plan.js +228 -104
- package/dist/services/vnext-protocolize.js +533 -95
- package/dist/services/vnext-specify.js +123 -81
- package/dist/services/vnext-workspace-policy.js +7 -2
- package/dist/services/work-registry.js +1706 -200
- package/dist/services/workspace-bootstrap.js +53 -15
- package/dist/services/workspace-files.js +85 -0
- package/dist/services/worktrees.js +105 -48
- package/dist/shared/entity-references.js +1 -0
- package/dist/shared/errors.js +27 -0
- package/dist/storage/agent-output.js +26 -0
- package/dist/storage/data-preservation.js +65 -0
- package/dist/storage/database.js +930 -40
- package/dist/storage/foreign-key-transaction.js +39 -0
- package/dist/storage/immutable-input.js +45 -0
- package/dist/storage/import-guard.js +159 -0
- package/dist/storage/memory-upgrade-schema-bootstrap.js +38 -0
- package/dist/storage/native-cleanup.js +52 -0
- package/dist/storage/paired-writer-migration.js +424 -0
- package/dist/storage/paths.js +17 -4
- package/dist/storage/projection-lock.js +73 -0
- package/dist/storage/work-references.js +23 -0
- package/dist/storage/writer-contract.js +96 -0
- package/dist/storage/writer-migration.js +346 -0
- package/dist/storage/writer-restore.js +217 -0
- package/package.json +50 -13
- package/tools/create-canon-release.mjs +33 -0
- package/tools/probe-codex-history.mjs +37 -0
- package/tools/produce-hybrid-release.mjs +41 -0
- package/tools/repair-paused-run-status.mjs +84 -0
|
@@ -1,20 +1,29 @@
|
|
|
1
1
|
import fs from "node:fs";
|
|
2
2
|
import path from "node:path";
|
|
3
3
|
import crypto from "node:crypto";
|
|
4
|
+
import { fileURLToPath } from "node:url";
|
|
5
|
+
import semver from "semver";
|
|
4
6
|
import { AppError } from "../shared/errors.js";
|
|
5
7
|
import { requireProjectByRoot } from "./projects.js";
|
|
6
8
|
import { getProjectVersionStatus, resolveStatusProjectRoot } from "./version-status.js";
|
|
7
9
|
import { resolveCanonRoot } from "./canon.js";
|
|
8
10
|
import { getDatabase } from "../storage/database.js";
|
|
11
|
+
import { cleanupScopeWriters } from "./scope-writer-cleanup.js";
|
|
9
12
|
import { resolveProjectRoot } from "../storage/paths.js";
|
|
10
13
|
import { classifyCliOperation } from "./cli-operation-classifier.js";
|
|
11
14
|
import { compatibilityContexts, selectEngine } from "./engines.js";
|
|
12
15
|
import { getCliBuildInfo } from "./build-info.js";
|
|
16
|
+
import { prepareJsonFile } from "../cli/input-preparation.js";
|
|
17
|
+
import { validateSchema } from "./schema-validation.js";
|
|
18
|
+
import { PreparedMemoryInitRuntimeStorage } from "./memory-init-storage.js";
|
|
19
|
+
import { PreparedMemoryInitResourceStorage } from "./memory-init-resource-storage.js";
|
|
20
|
+
import { AdmittedFrozenEngine } from "./frozen-engine.js";
|
|
21
|
+
import { resourceHome } from "./managed-processes.js";
|
|
13
22
|
export function assessMigrationImpact(context, input) {
|
|
14
23
|
const root = resolveStatusProjectRoot({ requestedRoot: input.projectRoot, cwd: process.cwd() });
|
|
15
24
|
if (!root.root)
|
|
16
25
|
throw new AppError("not_found", `Project root does not exist: ${input.projectRoot}`, 1);
|
|
17
|
-
const canon =
|
|
26
|
+
const canon = upgradeCanon(context);
|
|
18
27
|
if (!canon.ok || !canon.canon)
|
|
19
28
|
throw new AppError("canon_unavailable", "Cannot resolve canonical Memory Bank for upgrade impact assessment", 1, { blockers: canon.blockers, bootstrap: canon.bootstrap });
|
|
20
29
|
const status = getProjectVersionStatus({ projectRoot: root.root, rootSource: root.root_source, canon: { root: canon.canon.root, metadata: canon.canon.metadata } });
|
|
@@ -22,53 +31,65 @@ export function assessMigrationImpact(context, input) {
|
|
|
22
31
|
const to = input.targetVersion ?? canon.canon.version;
|
|
23
32
|
const forced = input.mode === "full_migration";
|
|
24
33
|
const impacts = readImpacts(path.join(canon.canon.memorybank_root, "release-impact"));
|
|
25
|
-
const
|
|
34
|
+
const resolved = from && to ? adjacentMigrationChain(from, to, impacts) : null;
|
|
35
|
+
const chain = resolved?.status === "ok"
|
|
36
|
+
? resolved.steps.map(step => impacts.find(item => item.from_version === step.from && item.to_version === step.to))
|
|
37
|
+
: [];
|
|
26
38
|
const domains = new Set();
|
|
27
39
|
const blockers = [];
|
|
28
40
|
let mode = "patch";
|
|
29
41
|
if (!from || !to)
|
|
30
42
|
blockers.push("project or canonical Memory Bank version is unavailable");
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
break;
|
|
37
|
-
}
|
|
38
|
-
chain.push(impact);
|
|
43
|
+
if (to !== canon.canon.version)
|
|
44
|
+
blockers.push("requested target version does not match the selected canon");
|
|
45
|
+
if (resolved?.status === "unsupported")
|
|
46
|
+
blockers.push(resolved.reason ?? "release impact chain is unsupported");
|
|
47
|
+
for (const impact of chain) {
|
|
39
48
|
for (const domain of impact.domains)
|
|
40
49
|
domains.add(domain);
|
|
41
50
|
mode = stricterMode(mode, impact.minimum_upgrade_mode);
|
|
42
51
|
if (impact.path_migration || impact.runtime_migration)
|
|
43
52
|
mode = "full_migration";
|
|
44
|
-
current = impact.to_version;
|
|
45
53
|
}
|
|
46
|
-
if (
|
|
47
|
-
blockers.push(`release impact chain does not reach ${to}`);
|
|
48
|
-
if (status?.flow_pack.status !== "present" && from !== to)
|
|
54
|
+
if (status?.flow_pack.status !== "present")
|
|
49
55
|
blockers.push("project flow-pack provenance is not present");
|
|
56
|
+
else {
|
|
57
|
+
try {
|
|
58
|
+
const file = path.resolve(root.root, status.flow_pack.manifest_path);
|
|
59
|
+
const prepared = prepareJsonFile(file, "Project flow-pack provenance");
|
|
60
|
+
validateSchema({ schemaName: "project-flow-pack-manifest", file, data: prepared.value,
|
|
61
|
+
schemaDir: fileURLToPath(new URL("../schemas/", import.meta.url)) });
|
|
62
|
+
if (!/^[a-f0-9]{40}$/.test(status.flow_pack.source_commit ?? "")
|
|
63
|
+
|| status.flow_pack.canon_version_at_source_commit !== from)
|
|
64
|
+
blockers.push("project flow-pack provenance does not match its declared current version and commit");
|
|
65
|
+
}
|
|
66
|
+
catch (error) {
|
|
67
|
+
if (!(error instanceof AppError) || !["schema_validation", "invalid_json", "validation"].includes(error.code)
|
|
68
|
+
&& !error.code.startsWith("input_file_"))
|
|
69
|
+
throw error;
|
|
70
|
+
blockers.push("project flow-pack provenance is invalid");
|
|
71
|
+
}
|
|
72
|
+
}
|
|
50
73
|
if (blockers.length > 0)
|
|
51
74
|
mode = "full_migration";
|
|
52
75
|
if (forced)
|
|
53
76
|
mode = "full_migration";
|
|
54
77
|
return { ok: true, schema_id: "dd-flow/mb-upgrade-impact-assessment@1", project_root: root.root, source_version: from, target_version: to, mode, forced_full_migration: forced, chain, domains: [...domains].sort(), blockers, required_checks: [...new Set(chain.flatMap((item) => item.required_checks))], next_action: mode === "full_migration" ? "run full mb-upgrade contour" : "run selected mb-upgrade contour" };
|
|
55
78
|
}
|
|
56
|
-
function readImpacts(dir) {
|
|
79
|
+
export function readImpacts(dir) {
|
|
57
80
|
if (!fs.existsSync(dir))
|
|
58
81
|
return [];
|
|
59
|
-
return fs.readdirSync(dir).filter(
|
|
82
|
+
return fs.readdirSync(dir).filter(file => file.endsWith(".json")).sort().map(file => {
|
|
83
|
+
const source = path.join(dir, file);
|
|
60
84
|
try {
|
|
61
|
-
const
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
if (!["patch", "targeted_minor", "full_migration"].includes(String(value.minimum_upgrade_mode)))
|
|
67
|
-
return [];
|
|
68
|
-
return [{ from_version: value.from_version, to_version: value.to_version, minimum_upgrade_mode: value.minimum_upgrade_mode, domains: value.domains.filter((item) => typeof item === "string"), path_migration: value.path_migration === true, runtime_migration: value.runtime_migration === true, required_checks: value.required_checks.filter((item) => typeof item === "string") }];
|
|
85
|
+
const prepared = prepareJsonFile(source, "Canonical release impact");
|
|
86
|
+
validateSchema({ schemaName: "release-impact", file: prepared.file, data: prepared.value,
|
|
87
|
+
schemaDir: fileURLToPath(new URL("../schemas/", import.meta.url)) });
|
|
88
|
+
return { ...prepared.value, source_reference: { path: prepared.file,
|
|
89
|
+
sha256: crypto.createHash("sha256").update(prepared.text).digest("hex") } };
|
|
69
90
|
}
|
|
70
|
-
catch {
|
|
71
|
-
|
|
91
|
+
catch (error) {
|
|
92
|
+
throw new AppError("release_impact_invalid", "Canonical release impact is invalid; it cannot authorize a lightweight upgrade", 1, { file: source, effect: "no_effect", cause: error instanceof AppError ? error.code : "unreadable_release_impact" });
|
|
72
93
|
}
|
|
73
94
|
});
|
|
74
95
|
}
|
|
@@ -147,7 +168,7 @@ export function planMigration(context, input) {
|
|
|
147
168
|
}
|
|
148
169
|
};
|
|
149
170
|
}
|
|
150
|
-
export function
|
|
171
|
+
export function prepareMigrationApply(context, input) {
|
|
151
172
|
const classification = input.classification ?? classifyCliOperation(["migration", "apply"], context.env);
|
|
152
173
|
if (classification.mode !== "mb_upgrade") {
|
|
153
174
|
throw new AppError("upgrade_authorization_required", "Migration apply requires explicit mb-upgrade authorization", 1, {
|
|
@@ -197,7 +218,33 @@ export function applyMigration(context, input) {
|
|
|
197
218
|
});
|
|
198
219
|
}
|
|
199
220
|
const project = requireProjectByRoot(context, resolveProjectRoot(input.projectRoot));
|
|
221
|
+
const current = activeStateSummary(context, project.id);
|
|
222
|
+
if (activeStateBlockers(current).length)
|
|
223
|
+
throw new AppError("migration_active_state", "Migration apply requires a quiescent shared home", 1, { active_state: current });
|
|
224
|
+
return { project, sourceVersion, targetVersion, verifiedBackup, reportEngine, chain };
|
|
225
|
+
}
|
|
226
|
+
export function applyMigration(context, input, prepared = prepareMigrationApply(context, input)) {
|
|
200
227
|
const writeDb = getDatabase(context.ddFlowHome, "migrate");
|
|
228
|
+
let result, primary, failed = false;
|
|
229
|
+
try {
|
|
230
|
+
result = applyPreparedMigration(context, prepared, writeDb);
|
|
231
|
+
}
|
|
232
|
+
catch (error) {
|
|
233
|
+
primary = error;
|
|
234
|
+
failed = true;
|
|
235
|
+
}
|
|
236
|
+
const cleanup = cleanupScopeWriters([{ name: writeDb.path, db: writeDb, rollback: false, close: "always" }]);
|
|
237
|
+
if (failed) {
|
|
238
|
+
if (primary instanceof AppError && cleanup.length)
|
|
239
|
+
primary.details.migration_cleanup_errors = cleanup;
|
|
240
|
+
throw primary;
|
|
241
|
+
}
|
|
242
|
+
if (cleanup.length)
|
|
243
|
+
throw new AppError("migration_cleanup_failed", "Migration receipt is available but its connection could not be closed", 1, { effect: result?.changed ? "committed" : "no_effect", migration_cleanup_errors: cleanup });
|
|
244
|
+
return result;
|
|
245
|
+
}
|
|
246
|
+
function applyPreparedMigration(context, prepared, writeDb) {
|
|
247
|
+
const { project, sourceVersion, targetVersion, verifiedBackup, reportEngine, chain } = prepared;
|
|
201
248
|
const already = writeDb.get("SELECT value_json FROM runtime_config WHERE key = ?", [applyKey(project.id, sourceVersion, targetVersion)]);
|
|
202
249
|
if (already) {
|
|
203
250
|
return { ok: true, schema_id: "dd-flow/mb-upgrade-migration-apply@1", status: "verified_noop", changed: false, backup: verifiedBackup, recovery: JSON.parse(already.value_json) };
|
|
@@ -217,15 +264,14 @@ export function applyMigration(context, input) {
|
|
|
217
264
|
chain: chain.steps.map((step) => ({ ...step, status: "applied" }))
|
|
218
265
|
};
|
|
219
266
|
try {
|
|
220
|
-
writeDb.
|
|
221
|
-
|
|
222
|
-
|
|
267
|
+
writeDb.writeTransaction(() => {
|
|
268
|
+
const current = activeStateSummary({ ...context, db: writeDb }, project.id);
|
|
269
|
+
if (activeStateBlockers(current).length)
|
|
270
|
+
throw new AppError("migration_active_state", "Migration apply requires a quiescent shared home", 1, { active_state: current });
|
|
271
|
+
writeDb.run(`INSERT INTO runtime_config (key, value_json, created_at, updated_at) VALUES (?, ?, ?, ?)`, [applyKey(project.id, sourceVersion, targetVersion), JSON.stringify(result), context.now(), context.now()]);
|
|
272
|
+
});
|
|
223
273
|
}
|
|
224
274
|
catch (error) {
|
|
225
|
-
try {
|
|
226
|
-
writeDb.exec("ROLLBACK");
|
|
227
|
-
}
|
|
228
|
-
catch { /* preserve the original failure */ }
|
|
229
275
|
throw new AppError("migration_apply_failed", "Migration apply failed before upgrade RUN creation or canon sync", 1, {
|
|
230
276
|
recovery: {
|
|
231
277
|
status: "required",
|
|
@@ -235,12 +281,12 @@ export function applyMigration(context, input) {
|
|
|
235
281
|
rollback_route: "restore the verified backup before retrying mb-upgrade apply",
|
|
236
282
|
next_action: "inspect the failed apply and retry only with the same pinned target contract"
|
|
237
283
|
},
|
|
238
|
-
cause: String(error)
|
|
284
|
+
cause: error instanceof AppError ? { code: error.code, message: error.message, details: error.details } : String(error)
|
|
239
285
|
});
|
|
240
286
|
}
|
|
241
287
|
return { ok: true, schema_id: "dd-flow/mb-upgrade-migration-apply@1", status: "applied", changed: true, backup: verifiedBackup, recovery: result };
|
|
242
288
|
}
|
|
243
|
-
export function assertUpgradeRunStorageReady(context, projectRoot) {
|
|
289
|
+
export function assertUpgradeRunStorageReady(context, projectRoot, engine) {
|
|
244
290
|
const project = context.db.get("SELECT id FROM projects WHERE root = ?", [resolveProjectRoot(projectRoot)]);
|
|
245
291
|
if (!project)
|
|
246
292
|
throw new AppError("migration_not_applied", "mb-upgrade RUN requires a registered project with explicit migration apply", 1);
|
|
@@ -250,12 +296,57 @@ export function assertUpgradeRunStorageReady(context, projectRoot) {
|
|
|
250
296
|
if (!source || !target)
|
|
251
297
|
throw new AppError("migration_not_applied", "mb-upgrade RUN requires source and target Memory Bank versions", 1);
|
|
252
298
|
const applied = context.db.get("SELECT value_json FROM runtime_config WHERE key = ?", [applyKey(project.id, source, target)]);
|
|
253
|
-
if (!applied)
|
|
299
|
+
if (!applied || engine !== undefined) {
|
|
300
|
+
const assessment = assessMigrationImpact(context, { projectRoot });
|
|
301
|
+
const blockers = assessment.blockers;
|
|
302
|
+
const chain = assessment.chain;
|
|
303
|
+
if (!blockers.length && (engine !== undefined || chain.every(step => !step.runtime_migration))) {
|
|
304
|
+
const canon = upgradeCanon(context).canon;
|
|
305
|
+
const contract = prepareJsonFile(path.join(canon.flow_root, "flow-contract.json"), "Target flow contract");
|
|
306
|
+
let selectedEngineStorage;
|
|
307
|
+
if (engine !== undefined) {
|
|
308
|
+
if (!(engine instanceof AdmittedFrozenEngine))
|
|
309
|
+
throw new AppError("upgrade_storage_incompatible", "Upgrade requires an admitted selected engine", 1, { effect: "no_effect" });
|
|
310
|
+
const compatibility = prepareJsonFile(path.join(canon.flow_root, "compatibility.json"), "Target engine compatibility");
|
|
311
|
+
validateSchema({ schemaName: "compatibility", file: compatibility.file, data: compatibility.value,
|
|
312
|
+
schemaDir: fileURLToPath(new URL("../schemas/", import.meta.url)) });
|
|
313
|
+
const manifest = engine.manifest();
|
|
314
|
+
if (compatibility.value.memory_bank_version !== target || compatibility.value.dd_flow_cli.flow_contract !== contract.value.id
|
|
315
|
+
|| manifest.package_name !== compatibility.value.dd_flow_cli.package_name || !semver.valid(compatibility.value.dd_flow_cli.min_version)
|
|
316
|
+
|| semver.lt(manifest.package_version, compatibility.value.dd_flow_cli.min_version)
|
|
317
|
+
|| manifest.package_name !== compatibility.value.engine.package_name
|
|
318
|
+
|| !semver.satisfies(manifest.package_version, compatibility.value.engine.version_range, { includePrerelease: true }))
|
|
319
|
+
throw new AppError("upgrade_storage_incompatible", "Selected engine is incompatible with target canon", 1, { effect: "no_effect" });
|
|
320
|
+
selectedEngineStorage = engine.admitMemoryUpgradeStorage(context.ddFlowHome, resourceHome(context));
|
|
321
|
+
}
|
|
322
|
+
// Reuse the executing CLI's physical compatibility checks, not version text
|
|
323
|
+
// or a synthetic apply marker. This does not authorize storage migration.
|
|
324
|
+
const runOwner = fs.lstatSync(context.db.path);
|
|
325
|
+
if (!runOwner.isFile() || runOwner.nlink !== 1)
|
|
326
|
+
throw new AppError("upgrade_storage_incompatible", "Upgrade requires a regular single-linked runtime store", 1, { effect: "no_effect" });
|
|
327
|
+
const run = PreparedMemoryInitRuntimeStorage.prepareUpgrade(context);
|
|
328
|
+
const resource = PreparedMemoryInitResourceStorage.prepare(context);
|
|
329
|
+
const currentOwner = fs.lstatSync(context.db.path);
|
|
330
|
+
if (currentOwner.dev !== runOwner.dev || currentOwner.ino !== runOwner.ino)
|
|
331
|
+
throw new AppError("upgrade_storage_changed", "Runtime store changed during upgrade admission", 1, { effect: "no_effect" });
|
|
332
|
+
const manifest = prepareJsonFile(path.resolve(projectRoot, status.flow_pack.manifest_path), "Current flow-pack provenance");
|
|
333
|
+
return { schema_id: "dd-flow/mb-upgrade-storage-readiness@1", route: "verified-no-op",
|
|
334
|
+
source_version: source, target_version: target, chain,
|
|
335
|
+
current_provenance: { path: manifest.file, sha256: crypto.createHash("sha256").update(manifest.text).digest("hex") },
|
|
336
|
+
target: { root: canon.root, commit: canon.commit, contract_sha256: crypto.createHash("sha256").update(contract.text).digest("hex") },
|
|
337
|
+
...(selectedEngineStorage ? { selected_engine_storage: selectedEngineStorage } : {}),
|
|
338
|
+
stores: [{ ...run.facts(), store_dev: runOwner.dev, store_ino: runOwner.ino }, resource.facts()].map(store => ({ store_kind: store.store_kind,
|
|
339
|
+
store_dev: store.store_dev, store_ino: store.store_ino,
|
|
340
|
+
store_path: store.store_path, schema_sha256: store.schema_sha256,
|
|
341
|
+
executing_writer_version: store.executing_writer_version })) };
|
|
342
|
+
}
|
|
254
343
|
throw new AppError("migration_not_applied", "mb-upgrade RUN requires explicit migration apply before RUN creation", 1, {
|
|
255
344
|
source_version: source,
|
|
256
345
|
target_version: target,
|
|
346
|
+
blockers,
|
|
257
347
|
next_action: "run migration plan, verify and explicit migration apply first"
|
|
258
348
|
});
|
|
349
|
+
}
|
|
259
350
|
const value = recordValue(parseJsonValue(applied.value_json));
|
|
260
351
|
if (!value || !["applied", "verified_noop"].includes(stringValue(value.status) ?? "")) {
|
|
261
352
|
throw new AppError("migration_not_applied", "mb-upgrade RUN has no successful explicit migration apply evidence", 1, {
|
|
@@ -263,6 +354,8 @@ export function assertUpgradeRunStorageReady(context, projectRoot) {
|
|
|
263
354
|
target_version: target
|
|
264
355
|
});
|
|
265
356
|
}
|
|
357
|
+
return { schema_id: "dd-flow/mb-upgrade-storage-readiness@1", route: "existing-apply",
|
|
358
|
+
source_version: source, target_version: target, apply: value };
|
|
266
359
|
}
|
|
267
360
|
export function verifyMigrationReport(_context, input) {
|
|
268
361
|
const filePath = path.resolve(input.file);
|
|
@@ -425,61 +518,45 @@ function hasActiveState(active) {
|
|
|
425
518
|
function applyKey(projectId, source, target) {
|
|
426
519
|
return `mb-upgrade.apply.${projectId}.${source}.${target}`;
|
|
427
520
|
}
|
|
428
|
-
function adjacentMigrationChain(source, target, impacts = []) {
|
|
429
|
-
if (source
|
|
430
|
-
return { status: "ok", steps: [] };
|
|
431
|
-
const sourceParts = parseSemver(source);
|
|
432
|
-
const targetParts = parseSemver(target);
|
|
433
|
-
if (!sourceParts || !targetParts) {
|
|
521
|
+
export function adjacentMigrationChain(source, target, impacts = []) {
|
|
522
|
+
if (semver.valid(source) !== source || semver.valid(target) !== target) {
|
|
434
523
|
return { status: "unsupported", reason: "source or target version is not semver", steps: [] };
|
|
435
524
|
}
|
|
436
|
-
if (
|
|
437
|
-
const steps = [];
|
|
438
|
-
const visited = new Set();
|
|
439
|
-
let current = source;
|
|
440
|
-
while (current !== target) {
|
|
441
|
-
if (visited.has(current))
|
|
442
|
-
return { status: "unsupported", reason: "release impact chain contains a cycle", steps: [] };
|
|
443
|
-
visited.add(current);
|
|
444
|
-
const impact = impacts.find((item) => item.from_version === current);
|
|
445
|
-
if (!impact)
|
|
446
|
-
return { status: "unsupported", reason: `missing adjacent release impact from ${current}`, steps: [] };
|
|
447
|
-
steps.push({
|
|
448
|
-
id: `${impact.from_version}-to-${impact.to_version}`,
|
|
449
|
-
from: impact.from_version,
|
|
450
|
-
to: impact.to_version,
|
|
451
|
-
status: "planned",
|
|
452
|
-
minimum_upgrade_mode: impact.minimum_upgrade_mode,
|
|
453
|
-
domains: impact.domains,
|
|
454
|
-
path_migration: impact.path_migration,
|
|
455
|
-
runtime_migration: impact.runtime_migration,
|
|
456
|
-
required_checks: impact.required_checks
|
|
457
|
-
});
|
|
458
|
-
current = impact.to_version;
|
|
459
|
-
const next = parseSemver(current);
|
|
460
|
-
if (!next || compareParts(next, targetParts) > 0) {
|
|
461
|
-
return { status: "unsupported", reason: `release impact chain overshoots target ${target}`, steps: [] };
|
|
462
|
-
}
|
|
463
|
-
}
|
|
464
|
-
return { status: "ok", steps };
|
|
465
|
-
}
|
|
466
|
-
if (sourceParts.major !== targetParts.major) {
|
|
467
|
-
return { status: "unsupported", reason: "major version migration requires canonical release-impact units", steps: [] };
|
|
468
|
-
}
|
|
469
|
-
if (targetParts.minor < sourceParts.minor || (targetParts.minor === sourceParts.minor && targetParts.patch < sourceParts.patch)) {
|
|
525
|
+
if (semver.gt(source, target))
|
|
470
526
|
return { status: "unsupported", reason: "downgrade migrations are not supported", steps: [] };
|
|
471
|
-
|
|
527
|
+
if (source === target)
|
|
528
|
+
return { status: "ok", steps: [] };
|
|
472
529
|
const steps = [];
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
530
|
+
const visited = new Set();
|
|
531
|
+
let current = source;
|
|
532
|
+
while (current !== target) {
|
|
533
|
+
if (visited.has(current))
|
|
534
|
+
return { status: "unsupported", reason: "release impact chain contains a cycle", steps: [] };
|
|
535
|
+
visited.add(current);
|
|
536
|
+
const matches = impacts.filter(item => item.from_version === current);
|
|
537
|
+
if (matches.length > 1)
|
|
538
|
+
return { status: "unsupported", reason: `ambiguous adjacent release impacts from ${current}`, steps: [] };
|
|
539
|
+
const impact = matches[0];
|
|
540
|
+
if (!impact)
|
|
541
|
+
return { status: "unsupported", reason: `missing adjacent release impact from ${current}`, steps: [] };
|
|
542
|
+
if (semver.valid(impact.to_version) !== impact.to_version || !semver.gt(impact.to_version, current)) {
|
|
543
|
+
return { status: "unsupported", reason: "release impact chain must advance through valid versions", steps: [] };
|
|
544
|
+
}
|
|
545
|
+
if (semver.gt(impact.to_version, target))
|
|
546
|
+
return { status: "unsupported", reason: `release impact chain overshoots target ${target}`, steps: [] };
|
|
476
547
|
steps.push({
|
|
477
|
-
id: `${
|
|
478
|
-
from:
|
|
479
|
-
to:
|
|
480
|
-
status: "planned"
|
|
548
|
+
id: `${impact.from_version}-to-${impact.to_version}`,
|
|
549
|
+
from: impact.from_version,
|
|
550
|
+
to: impact.to_version,
|
|
551
|
+
status: "planned",
|
|
552
|
+
minimum_upgrade_mode: impact.minimum_upgrade_mode,
|
|
553
|
+
domains: impact.domains,
|
|
554
|
+
path_migration: impact.path_migration,
|
|
555
|
+
runtime_migration: impact.runtime_migration,
|
|
556
|
+
required_checks: impact.required_checks,
|
|
557
|
+
...(impact.source_reference ? { source_reference: impact.source_reference } : {})
|
|
481
558
|
});
|
|
482
|
-
current =
|
|
559
|
+
current = impact.to_version;
|
|
483
560
|
}
|
|
484
561
|
return { status: "ok", steps };
|
|
485
562
|
}
|
|
@@ -513,13 +590,7 @@ function activeStateBlockers(active) {
|
|
|
513
590
|
return blockers;
|
|
514
591
|
}
|
|
515
592
|
function readJsonObject(filePath) {
|
|
516
|
-
|
|
517
|
-
try {
|
|
518
|
-
parsed = JSON.parse(fs.readFileSync(filePath, "utf8"));
|
|
519
|
-
}
|
|
520
|
-
catch (error) {
|
|
521
|
-
throw new AppError("invalid_json", `Cannot read migration report: ${filePath}`, 2, { cause: String(error) });
|
|
522
|
-
}
|
|
593
|
+
const { value: parsed } = prepareJsonFile(filePath, "Migration report");
|
|
523
594
|
if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
|
|
524
595
|
throw new AppError("validation", "Migration report must be a JSON object", 2, { file: filePath });
|
|
525
596
|
}
|
|
@@ -535,24 +606,3 @@ function recordValue(value) {
|
|
|
535
606
|
function stringValue(value) {
|
|
536
607
|
return typeof value === "string" && value.length > 0 ? value : null;
|
|
537
608
|
}
|
|
538
|
-
function parseSemver(value) {
|
|
539
|
-
const match = value.match(/^([0-9]+)\.([0-9]+)\.([0-9]+)/);
|
|
540
|
-
if (!match?.[1] || !match[2] || !match[3])
|
|
541
|
-
return null;
|
|
542
|
-
return { major: Number(match[1]), minor: Number(match[2]), patch: Number(match[3]) };
|
|
543
|
-
}
|
|
544
|
-
function compareParts(left, right) {
|
|
545
|
-
if (left.major !== right.major)
|
|
546
|
-
return left.major - right.major;
|
|
547
|
-
if (left.minor !== right.minor)
|
|
548
|
-
return left.minor - right.minor;
|
|
549
|
-
return left.patch - right.patch;
|
|
550
|
-
}
|
|
551
|
-
function nextAdjacent(current, target) {
|
|
552
|
-
if (current.minor < target.minor)
|
|
553
|
-
return { major: current.major, minor: current.minor + 1, patch: 0 };
|
|
554
|
-
return { major: current.major, minor: current.minor, patch: Math.min(current.patch + 1, target.patch) };
|
|
555
|
-
}
|
|
556
|
-
function formatParts(parts) {
|
|
557
|
-
return `${parts.major}.${parts.minor}.${parts.patch}`;
|
|
558
|
-
}
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
import { AppError } from "../shared/errors.js";
|
|
2
|
+
import { validateHybridContract } from "./hybrid-contracts.js";
|
|
3
|
+
import { mergeModelListing } from "./model-discovery.js";
|
|
4
|
+
import { readBoundedReleaseFile } from "./release-source.js";
|
|
5
|
+
// Reviewed adapter fallbacks and retained eval configurations, not vendor
|
|
6
|
+
// availability promises or recommended defaults. Missing facts stay unknown;
|
|
7
|
+
// historical eval qualification/capacity claims are deliberately not imported.
|
|
8
|
+
const seed = {
|
|
9
|
+
schema_id: "dd-flow/model-catalog@1", version: "1.1.0",
|
|
10
|
+
entries: [{ harness: "agy", provider: "google", model: "gemini-3.1-pro-high",
|
|
11
|
+
settings: { reasoning: ["unknown"], mode: ["unknown"] },
|
|
12
|
+
provenance: { kind: "reviewed-seed", source: "https://github.com/deksden-com/dd-flow-cli/blob/2ba2ce2364705cf59fdc48bdd5dc5b37fb7cd784/src/harness-runtime/lib/dd-agy.mjs#L7",
|
|
13
|
+
reviewed_at: "2026-10-07T00:00:00Z" }, availability: "not-observed", qualification: { scope: "seed-only", evidence: null } },
|
|
14
|
+
{ harness: "grok", provider: "xai", model: "grok-4.6",
|
|
15
|
+
settings: { reasoning: ["high"], mode: ["bypassPermissions"] },
|
|
16
|
+
provenance: { kind: "reviewed-seed", source: "https://github.com/deksden-com/dd-flow-cli/blob/2ba2ce2364705cf59fdc48bdd5dc5b37fb7cd784/src/harness-runtime/lib/dd-grok.mjs#L48",
|
|
17
|
+
reviewed_at: "2026-10-07T00:00:00Z" }, availability: "not-observed", qualification: { scope: "seed-only", evidence: null } },
|
|
18
|
+
{ harness: "codex", provider: "unknown", model: "gpt-6.1-sol",
|
|
19
|
+
settings: { reasoning: ["high"], mode: ["unknown"] },
|
|
20
|
+
provenance: { kind: "reviewed-seed", source: "https://github.com/deksden-com/dd-eval/blob/9715970544096fc0288ac8e18f95d4e35997be54/profiles/codex-desktop-gpt-6-1-sol-high.json",
|
|
21
|
+
reviewed_at: "2026-10-07T00:00:00Z" }, availability: "not-observed", qualification: { scope: "seed-only", evidence: null } },
|
|
22
|
+
{ harness: "zcode", provider: "builtin:zai-coding-plan", model: "GLM-5.3",
|
|
23
|
+
settings: { reasoning: ["high"], mode: ["yolo"] },
|
|
24
|
+
provenance: { kind: "reviewed-seed", source: "https://github.com/deksden-com/dd-eval/blob/9715970544096fc0288ac8e18f95d4e35997be54/profiles/zcode-acp-zai-glm-5-3-high.json",
|
|
25
|
+
reviewed_at: "2026-10-07T00:00:00Z" }, availability: "not-observed", qualification: { scope: "seed-only", evidence: null } },
|
|
26
|
+
{ harness: "opencode", provider: "opencode", model: "big-pickle",
|
|
27
|
+
settings: { reasoning: ["default"], mode: ["build"] },
|
|
28
|
+
provenance: { kind: "reviewed-seed", source: "https://github.com/deksden-com/dd-eval/blob/9715970544096fc0288ac8e18f95d4e35997be54/profiles/opencode-server-opencode-big-pickle-default.json",
|
|
29
|
+
reviewed_at: "2026-10-07T00:00:00Z" }, availability: "not-observed", qualification: { scope: "seed-only", evidence: null } },
|
|
30
|
+
{ harness: "droid", provider: "openai", model: "gpt-5.6-sol",
|
|
31
|
+
settings: { reasoning: ["high"], mode: ["auto-high"] },
|
|
32
|
+
provenance: { kind: "reviewed-seed", source: "https://github.com/deksden-com/dd-eval/blob/9715970544096fc0288ac8e18f95d4e35997be54/profiles/droid-cli-openai-gpt-5-6-sol-high.json",
|
|
33
|
+
reviewed_at: "2026-10-07T00:00:00Z" }, availability: "not-observed", qualification: { scope: "seed-only", evidence: null } }]
|
|
34
|
+
};
|
|
35
|
+
const families = ["codex", "zcode", "agy", "opencode", "grok", "droid"];
|
|
36
|
+
const identifier = (value, max = 128) => typeof value === "string" && value.length <= max && /^[A-Za-z0-9][A-Za-z0-9._:/+-]*$/.test(value);
|
|
37
|
+
const providerId = (value) => typeof value === "string" && /^[A-Za-z0-9][A-Za-z0-9._:-]{0,127}$/.test(value);
|
|
38
|
+
function invalid() {
|
|
39
|
+
throw new AppError("model_catalog_input", "Model catalog input requires reviewed seed data and an explicit observation scope; see dd-flow models --help", 2, { effect: "no_effect", help: "models" });
|
|
40
|
+
}
|
|
41
|
+
function readJson(file) {
|
|
42
|
+
let bytes;
|
|
43
|
+
try {
|
|
44
|
+
bytes = readBoundedReleaseFile(file, 4 * 1024 * 1024);
|
|
45
|
+
}
|
|
46
|
+
catch {
|
|
47
|
+
throw new AppError("model_input_unavailable", "Model input must be a bounded readable regular file; see dd-flow models --help", 1, { effect: "no_effect", help: "models" });
|
|
48
|
+
}
|
|
49
|
+
try {
|
|
50
|
+
return JSON.parse(new TextDecoder("utf-8", { fatal: true }).decode(bytes));
|
|
51
|
+
}
|
|
52
|
+
catch {
|
|
53
|
+
return invalid();
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
export function readModelSeed(file) {
|
|
57
|
+
const input = file === undefined ? structuredClone(seed) : readJson(file);
|
|
58
|
+
if (validateHybridContract("model-catalog", input).length)
|
|
59
|
+
invalid();
|
|
60
|
+
const catalog = input;
|
|
61
|
+
if (catalog.entries.length > 10_000 || catalog.entries.some(entry => {
|
|
62
|
+
let source;
|
|
63
|
+
try {
|
|
64
|
+
source = new URL(entry.provenance.source);
|
|
65
|
+
}
|
|
66
|
+
catch {
|
|
67
|
+
return true;
|
|
68
|
+
}
|
|
69
|
+
const reviewed = entry.provenance.reviewed_at;
|
|
70
|
+
return entry.qualification.scope !== "seed-only" || !providerId(entry.provider) || !identifier(entry.model, 256)
|
|
71
|
+
|| !/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(?:\.\d{3})?Z$/.test(reviewed) || !Number.isFinite(Date.parse(reviewed))
|
|
72
|
+
|| new Date(reviewed).toISOString() !== reviewed.replace(/Z$/, reviewed.includes(".") ? "Z" : ".000Z")
|
|
73
|
+
|| source.protocol !== "https:" || source.username !== "" || source.password !== "" || source.search !== ""
|
|
74
|
+
|| entry.provenance.source.length > 2048
|
|
75
|
+
|| [...entry.settings.reasoning, ...entry.settings.mode].some(value => !identifier(value, 64));
|
|
76
|
+
}))
|
|
77
|
+
invalid();
|
|
78
|
+
return structuredClone(catalog);
|
|
79
|
+
}
|
|
80
|
+
/** Offline reader only. A supplied snapshot is an observation, not account authorization. */
|
|
81
|
+
export function listOperatorModels(input) {
|
|
82
|
+
if (input.harness !== undefined && !families.includes(input.harness) || input.provider !== undefined && !providerId(input.provider)
|
|
83
|
+
|| input.model !== undefined && !identifier(input.model, 256)
|
|
84
|
+
|| input.accountSha256 !== undefined && !/^[a-f0-9]{64}$/.test(input.accountSha256)
|
|
85
|
+
|| (input.accountSha256 !== undefined || input.observationFile !== undefined) && (!input.harness || !input.provider || !input.accountSha256))
|
|
86
|
+
invalid();
|
|
87
|
+
// Validate all selectors before opening operator files.
|
|
88
|
+
const catalog = readModelSeed(input.seedFile);
|
|
89
|
+
let entries, reason, observedAt = null;
|
|
90
|
+
if (input.accountSha256) {
|
|
91
|
+
const scope = { harness: input.harness, provider: input.provider, account_sha256: input.accountSha256 };
|
|
92
|
+
const observation = input.observationFile === undefined ? undefined : readJson(input.observationFile);
|
|
93
|
+
const merged = mergeModelListing(catalog, scope, observation);
|
|
94
|
+
entries = merged.entries.map(entry => ({ harness: scope.harness, provider: scope.provider, ...entry }));
|
|
95
|
+
reason = merged.reason;
|
|
96
|
+
observedAt = merged.observed_at;
|
|
97
|
+
}
|
|
98
|
+
else {
|
|
99
|
+
entries = catalog.entries.filter(entry => (!input.harness || entry.harness === input.harness) && (!input.provider || entry.provider === input.provider))
|
|
100
|
+
.map(entry => ({ harness: entry.harness, provider: entry.provider, model: entry.model, seed: structuredClone(entry),
|
|
101
|
+
availability: "unknown", account_access: "unknown", qualified: "unknown" }));
|
|
102
|
+
reason = "account_scope_not_selected";
|
|
103
|
+
}
|
|
104
|
+
if (input.model)
|
|
105
|
+
entries = entries.filter(entry => entry.model === input.model);
|
|
106
|
+
return { catalog_version: catalog.version, observed_at: observedAt, reason, entries,
|
|
107
|
+
families: families.map(harness => ({ harness, seed_status: catalog.entries.some(entry => entry.harness === harness) ? "reviewed_entries" : "not_curated",
|
|
108
|
+
account_access: "unknown", qualified: "unknown" })) };
|
|
109
|
+
}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { AppError } from "../shared/errors.js";
|
|
2
|
+
import { validateHybridContract } from "./hybrid-contracts.js";
|
|
3
|
+
const invalid = () => new AppError("model_discovery_input", "Model discovery input does not match its scoped contract", 2, { effect: "no_effect" });
|
|
4
|
+
export function validateModelScope(scope) {
|
|
5
|
+
if (!scope || typeof scope !== "object" || Array.isArray(scope)
|
|
6
|
+
|| ["harness", "provider", "account_sha256"].some(key => !Object.hasOwn(scope, key))
|
|
7
|
+
|| Object.keys(scope).some(key => !["harness", "provider", "account_sha256"].includes(key))
|
|
8
|
+
|| !["codex", "zcode", "agy", "opencode", "grok", "droid"].includes(scope.harness)
|
|
9
|
+
|| typeof scope.provider !== "string" || !/^[A-Za-z0-9][A-Za-z0-9._:-]{0,127}$/.test(scope.provider)
|
|
10
|
+
|| typeof scope.account_sha256 !== "string" || !/^[a-f0-9]{64}$/.test(scope.account_sha256))
|
|
11
|
+
throw invalid();
|
|
12
|
+
}
|
|
13
|
+
/** Merge only a matching account/provider snapshot. Listed is not authorized or qualified. */
|
|
14
|
+
export function mergeModelListing(seed, scope, observation) {
|
|
15
|
+
validateModelScope(scope);
|
|
16
|
+
if (validateHybridContract("model-catalog", seed).length)
|
|
17
|
+
throw invalid();
|
|
18
|
+
if (observation !== undefined) {
|
|
19
|
+
if (!observation || typeof observation !== "object" || Array.isArray(observation)
|
|
20
|
+
|| ["scope", "observed_at", "status", "complete", "models"].some(key => !Object.hasOwn(observation, key)))
|
|
21
|
+
throw invalid();
|
|
22
|
+
validateModelScope(observation.scope);
|
|
23
|
+
if (Object.keys(observation).some(key => !["scope", "observed_at", "status", "complete", "models"].includes(key))
|
|
24
|
+
|| typeof observation.observed_at !== "string" || !/^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(?:\.\d{3})?Z$/.test(observation.observed_at)
|
|
25
|
+
|| !Number.isFinite(Date.parse(observation.observed_at))
|
|
26
|
+
|| new Date(observation.observed_at).toISOString() !== observation.observed_at.replace(/Z$/, observation.observed_at.includes(".") ? "Z" : ".000Z")
|
|
27
|
+
|| !["listed", "unavailable"].includes(observation.status)
|
|
28
|
+
|| typeof observation.complete !== "boolean" || !Array.isArray(observation.models)
|
|
29
|
+
|| observation.models.length > 10_000 || observation.models.some(model => typeof model !== "string" || !/^[A-Za-z0-9][A-Za-z0-9._:/+-]{0,255}$/.test(model))
|
|
30
|
+
|| new Set(observation.models).size !== observation.models.length
|
|
31
|
+
|| observation.status === "unavailable" && (observation.models.length > 0 || observation.complete))
|
|
32
|
+
throw invalid();
|
|
33
|
+
}
|
|
34
|
+
const matches = observation && observation.scope.harness === scope.harness && observation.scope.provider === scope.provider
|
|
35
|
+
&& observation.scope.account_sha256 === scope.account_sha256;
|
|
36
|
+
const listing = matches && observation.status === "listed" ? observation : undefined;
|
|
37
|
+
const entries = seed.entries.filter(entry => entry.harness === scope.harness && entry.provider === scope.provider);
|
|
38
|
+
const seeded = new Map(entries.map(entry => [entry.model, entry]));
|
|
39
|
+
const names = new Set([...seeded.keys(), ...(listing?.models ?? [])]);
|
|
40
|
+
return { scope: { ...scope }, observed_at: matches ? observation.observed_at : null,
|
|
41
|
+
reason: !observation ? "not_observed" : !matches ? "foreign_scope_ignored" : !listing ? "listing_unavailable" : "scoped_listing",
|
|
42
|
+
entries: [...names].sort().map(model => ({ model,
|
|
43
|
+
seed: seeded.has(model) ? structuredClone(seeded.get(model)) : null,
|
|
44
|
+
availability: listing?.models.includes(model) ? "listed" : listing?.complete ? "not_listed" : "unknown",
|
|
45
|
+
account_access: "unknown", qualified: "unknown" })) };
|
|
46
|
+
}
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import crypto from "node:crypto";
|
|
2
|
+
import { nativeShutdownConfirmed } from "../harness-runtime/lib/native-children.mjs";
|
|
3
|
+
import fs from "node:fs";
|
|
4
|
+
import path from "node:path";
|
|
5
|
+
import { AppError } from "../shared/errors.js";
|
|
6
|
+
import { managedProcessBinding, managedProcessStatus, processTreeIsAlive, resourceHome, retainedResourceHomeMatches } from "./managed-processes.js";
|
|
7
|
+
import { retainedDaemonOperations } from "./run-control.js";
|
|
8
|
+
import { managedProviderBelongsToDaemon } from "./managed-daemon-binding.js";
|
|
9
|
+
/** A replaced daemon is a settled resource, never another Session to resume. */
|
|
10
|
+
export function historicalDaemonSettlement(context, scopeId, record) {
|
|
11
|
+
const metadata = JSON.parse(record.metadata_json);
|
|
12
|
+
if (!record.kind.endsWith("-daemon") || !metadata.state_dir || !path.isAbsolute(metadata.state_dir))
|
|
13
|
+
throw new AppError("runtime_scope_owner_unknown", "Native history requires an absolute daemon directory", 1);
|
|
14
|
+
const current = JSON.parse(fs.readFileSync(path.join(metadata.state_dir, "daemon.json"), "utf8"));
|
|
15
|
+
if (current.resource_process?.id === record.id)
|
|
16
|
+
return null;
|
|
17
|
+
if (record.state !== "stopped" || record.termination_reason !== "daemon_stopped" || !record.pid || !record.pid_started_at || processTreeIsAlive(record))
|
|
18
|
+
throw new AppError("runtime_scope_owner_unknown", "Previous daemon has no physical completion proof", 1);
|
|
19
|
+
const directory = path.join(metadata.state_dir, "daemon-history");
|
|
20
|
+
const matches = fs.readdirSync(directory).filter(name => /^[a-zA-Z0-9-]+\.json$/.test(name)).map(name => {
|
|
21
|
+
const file = path.join(directory, name);
|
|
22
|
+
if (!fs.lstatSync(file).isFile())
|
|
23
|
+
throw new AppError("runtime_scope_owner_unknown", "Daemon history must contain regular receipts", 1);
|
|
24
|
+
const bytes = fs.readFileSync(file, "utf8");
|
|
25
|
+
return { file, bytes, state: JSON.parse(bytes) };
|
|
26
|
+
}).filter(candidate => candidate.state.resource_process?.id === record.id);
|
|
27
|
+
if (matches.length !== 1)
|
|
28
|
+
throw new AppError("runtime_scope_owner_unknown", "Previous daemon has no unique retained receipt", 1);
|
|
29
|
+
const { file, bytes, state } = matches[0], owner = state.config?.runtime_owner;
|
|
30
|
+
if (!state.daemon_id || path.basename(file) !== `${state.daemon_id}.json` || !owner || owner.budget?.scope_id !== scopeId || owner.owner_id !== record.owner_id || owner.role !== metadata.role || owner.state_dir !== metadata.state_dir || owner.adapter_executable !== metadata.adapter_executable || owner.dd_flow_home !== metadata.dd_flow_home || !retainedResourceHomeMatches(context, owner.resource_home) || (owner.project_id ?? null) !== record.project_id || (owner.run_id ?? null) !== record.run_id || (owner.work_id ?? null) !== record.work_id || !record.operation_id?.startsWith(`${owner.operation_id}:`) || state.resource_process?.lease_token !== record.lease_token || state.pid !== record.pid)
|
|
31
|
+
throw new AppError("runtime_scope_owner_unknown", "Archived daemon does not match its registration", 1);
|
|
32
|
+
const closed = state.shutdown_state === "clean" && state.active_tree === false
|
|
33
|
+
? retainedDaemonOperations(metadata.state_dir).find(operation => operation.daemon_id === state.daemon_id && operation.operation === "daemon.stop" && operation.state === "completed" && operation.result?.stopped === true && nativeShutdownConfirmed(operation.result, { daemonId: state.daemon_id ?? "" })) : undefined;
|
|
34
|
+
const fresh = managedProcessStatus(context).find(item => item.id === record.id);
|
|
35
|
+
if (!closed || !fresh || fresh.lease_token !== record.lease_token || fresh.pid !== record.pid || fresh.pid_started_at !== record.pid_started_at || fresh.metadata_json !== record.metadata_json || fresh.state !== "stopped" || fresh.termination_reason !== "daemon_stopped" || processTreeIsAlive(fresh) || fs.readFileSync(file, "utf8") !== bytes)
|
|
36
|
+
throw new AppError("runtime_scope_outcome_unknown", "Previous daemon lacks stable clean shutdown evidence", 1);
|
|
37
|
+
const providers = managedProcessStatus(context).filter(item => managedProviderBelongsToDaemon(item, fresh, state));
|
|
38
|
+
if (state.provider_process && (providers.length !== 1 || providers[0].state !== "stopped" || providers[0].termination_reason !== "daemon_stopped" || !providers[0].operation_id?.startsWith(`${owner.operation_id}:`) || processTreeIsAlive(providers[0])))
|
|
39
|
+
throw new AppError("runtime_scope_outcome_unknown", "Archived provider lacks its exact physical completion proof", 1);
|
|
40
|
+
return { historical: true, process_id: record.id, role: metadata.role, state_dir: metadata.state_dir, daemon_id: state.daemon_id,
|
|
41
|
+
processes: providers.map(item => ({ process_id: item.id, native_settled: true, binding: managedProcessBinding(item, resourceHome(context)) })),
|
|
42
|
+
settled: true, native_settled: true, operation_id: String(closed.operation_id), owner_operation_id: owner.operation_id,
|
|
43
|
+
inventory_version: crypto.createHash("sha256").update(JSON.stringify([bytes, closed])).digest("hex") };
|
|
44
|
+
}
|
|
45
|
+
export function assertHistoricalDaemonSettlement(context, scopeId, proof) {
|
|
46
|
+
const record = managedProcessStatus(context).find(item => item.id === proof.process_id);
|
|
47
|
+
const fresh = record && historicalDaemonSettlement(context, scopeId, record);
|
|
48
|
+
if (!fresh || proof.historical !== true || proof.native_settled !== true || fresh.inventory_version !== proof.inventory_version)
|
|
49
|
+
throw new AppError("runtime_scope_inventory_changed", "Archived daemon settlement changed after observation", 1);
|
|
50
|
+
}
|