@moretea-labs/forge 1.8.0 → 1.8.2
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/AGENTS.md +73 -7
- package/CHANGELOG.md +34 -0
- package/CLAUDE.md +17 -2
- package/CONTRIBUTING.md +3 -2
- package/README.en.md +24 -3
- package/README.md +10 -6
- package/README.zh-CN.md +5 -3
- package/THIRD_PARTY_NOTICES.md +1 -2
- package/adapters/chatgpt/browser-delivery-host.ts +7 -1
- package/adapters/chatgpt/browser-delivery-runtime.ts +531 -56
- package/adapters/chatgpt/controller-binding-store.ts +101 -22
- package/adapters/chatgpt/controller-round-host.ts +15 -25
- package/adapters/chatgpt/controller-round-settlement-store.ts +58 -4
- package/adapters/chatgpt/provider-delivery.ts +229 -2
- package/adapters/chatgpt/work-conversation-binding-store.ts +99 -54
- package/adapters/computer/chatgpt-extension-target.ts +708 -0
- package/adapters/computer/chrome-extension/background.js +541 -0
- package/adapters/computer/chrome-extension/content.js +402 -0
- package/adapters/computer/chrome-extension/core.js +24 -0
- package/adapters/computer/chrome-extension/manifest.json +32 -0
- package/adapters/computer/desktop-operator-discovery.ts +11 -31
- package/adapters/computer/desktop-operator-provider.ts +18 -6
- package/adapters/computer/interaction-target-authority.ts +178 -24
- package/adapters/mcp/access-mode.ts +18 -39
- package/adapters/mcp/auth.ts +2 -7
- package/adapters/mcp/instructions.ts +6 -5
- package/adapters/mcp/multi-repository.ts +10 -47
- package/adapters/mcp/oauth.ts +73 -0
- package/adapters/mcp/paths.ts +4 -1
- package/adapters/mcp/runtime-gateway/bounded-result-runtime.ts +62 -0
- package/adapters/mcp/runtime-gateway/cognition-settlement.ts +201 -0
- package/adapters/mcp/runtime-gateway/context-adapter.ts +490 -113
- package/adapters/mcp/runtime-gateway/context-pack-sidecar.ts +83 -0
- package/adapters/mcp/runtime-gateway/controller-authority-adapter.ts +20 -5
- package/adapters/mcp/runtime-gateway/core-capability-adapter.ts +258 -0
- package/adapters/mcp/runtime-gateway/engineering-preconditions.ts +10 -27
- package/adapters/mcp/runtime-gateway/engineering-tool-contract.ts +15 -0
- package/adapters/mcp/runtime-gateway/execution-tools.ts +14 -54
- package/adapters/mcp/runtime-gateway/gateway-execution-adapter.ts +2 -1
- package/adapters/mcp/runtime-gateway/plugin-adapter.ts +132 -47
- package/adapters/mcp/runtime-gateway/process-tools.ts +173 -23
- package/adapters/mcp/runtime-gateway/protected-computer-adapter.ts +16 -4
- package/adapters/mcp/runtime-gateway/recovery-adapter.ts +69 -52
- package/adapters/mcp/runtime-gateway/repository-compat-adapter.ts +4 -35
- package/adapters/mcp/runtime-gateway/result-adapter.ts +10 -4
- package/adapters/mcp/runtime-gateway/router.ts +19 -507
- package/adapters/mcp/runtime-gateway/routing-policy.ts +506 -0
- package/adapters/mcp/runtime-gateway/runtime-observation-adapter.ts +15 -66
- package/adapters/mcp/runtime-gateway/runtime-readiness-observation.ts +218 -0
- package/adapters/mcp/runtime-gateway/runtime-tool-definitions.ts +123 -178
- package/adapters/mcp/runtime-gateway/runtime-tools.ts +11 -5
- package/adapters/mcp/runtime-gateway/scheduler-adapter.ts +37 -1
- package/adapters/mcp/runtime-gateway/shared-adapter.ts +20 -0
- package/adapters/mcp/runtime-gateway/status-inbox-adapter.ts +416 -270
- package/adapters/mcp/runtime-gateway/typescript-navigation-sidecar.ts +140 -0
- package/adapters/mcp/runtime-gateway/work-adapter.ts +262 -3123
- package/adapters/mcp/runtime-gateway/work-controller-operations.ts +257 -0
- package/adapters/mcp/runtime-gateway/work-detail-projection.ts +60 -0
- package/adapters/mcp/runtime-gateway/work-input-wire-migration.ts +229 -0
- package/adapters/mcp/runtime-gateway/work-learning-operations.ts +145 -0
- package/adapters/mcp/runtime-gateway/work-list-projection.ts +38 -0
- package/adapters/mcp/runtime-gateway/work-plan-operations.ts +382 -0
- package/adapters/mcp/runtime-gateway/work-repair-adapter.ts +308 -0
- package/adapters/mcp/runtime-gateway/work-requirement-operations.ts +148 -0
- package/adapters/mcp/runtime-gateway/work-semantic-operations.ts +320 -0
- package/adapters/mcp/runtime-gateway/work-workflow-operations.ts +113 -0
- package/adapters/mcp/runtime-gateway/workflow-supervisor-adapter.ts +180 -0
- package/adapters/mcp/server.ts +91 -26
- package/adapters/mcp/setup.ts +5 -13
- package/adapters/mcp/tool-mapping/access-tools.ts +0 -6
- package/adapters/mcp/tool-mapping/legacy-tool-service.ts +703 -3092
- package/adapters/mcp/tool-mapping/post-finalize-work-attribution.ts +5 -10
- package/adapters/mcp/tool-mapping/repository-tools.ts +170 -213
- package/adapters/mcp/toolset-names.ts +11 -37
- package/adapters/mcp/toolset.ts +19 -92
- package/{src/cli → adapters}/mcp/transports/AGENTS.md +5 -5
- package/{src/cli → adapters}/mcp/transports/CLAUDE.md +5 -5
- package/adapters/mcp/transports/http-observation.ts +377 -0
- package/adapters/mcp/transports/http-post-lifecycle.ts +19 -0
- package/adapters/mcp/transports/http.ts +200 -683
- package/adapters/mcp/transports/oauth-http.ts +322 -0
- package/adapters/mcp/transports/session-registry.ts +6 -0
- package/adapters/mcp/tunnels/openai-secure-tunnel.ts +89 -5
- package/adapters/mcp/types.ts +0 -6
- package/assets/hooks/lib/session-state.sh +0 -38
- package/assets/hooks/post-bash.sh +1 -1
- package/assets/hooks/post-tool-observer.sh +0 -5
- package/assets/hooks/prompt-guard.sh +0 -55
- package/assets/partials/04-project-structure.partial.md +1 -1
- package/assets/partials/07-footer.partial.md +1 -1
- package/assets/partials-agents/02-operating-mode.partial.md +1 -1
- package/assets/partials-agents/08-deep-docs.partial.md +1 -1
- package/assets/plugin-registry.v1.json +6 -4
- package/assets/reference-configs/agentic-development-flow.md +26 -1
- package/assets/reference-configs/external-tooling.md +0 -76
- package/assets/reference-configs/global-working-rules.md +19 -0
- package/assets/reference-configs/release-deploy.md +1 -1
- package/assets/templates/helpers/architecture-queue.sh +1 -1
- package/assets/templates/helpers/check-agent-tooling.sh +1 -327
- package/assets/templates/helpers/check-task-workflow.sh +1 -1
- package/assets/templates/helpers/ensure-task-workflow.sh +0 -14
- package/assets/templates/helpers/migrate-project-template.sh +2 -2
- package/assets/workflow-contract.v1.json +0 -2
- package/docs/README.md +5 -2
- package/docs/architecture/CURRENT.md +205 -51
- package/docs/architecture/decisions/20260803-release-identity-binding-and-exit-policy.md +14 -5
- package/docs/architecture/decisions/20260823-immediate-controller-relay.md +6 -3
- package/docs/architecture/decisions/20260904-ios-device-migration-baseline.md +42 -0
- package/docs/architecture/decisions/20260907-assistant-learning-loop.md +2 -0
- package/docs/architecture/decisions/20260907-controller-round-transition-policy.md +19 -4
- package/docs/architecture/decisions/20260916-workflow-supervisor-authority.md +249 -0
- package/docs/architecture/decisions/20260917-cognitive-memory-foundation.md +82 -0
- package/docs/architecture/decisions/20260918-stable-candidate-release-lifecycle.md +234 -0
- package/docs/architecture/decisions/20260919-autonomous-work-liveness.md +62 -0
- package/docs/architecture/decisions/20260924-thin-semantic-working-context.md +74 -0
- package/docs/architecture/decisions/20261001-supervisor-turn-authority.md +342 -0
- package/docs/architecture/decisions/20261005-forge-v3-desktop-client-boundary.md +77 -0
- package/docs/architecture/decisions/20261009-exact-code-context-discovery.md +19 -0
- package/docs/architecture/decisions/20261009-generated-xcode-cache-retention.md +37 -0
- package/docs/architecture/decisions/20261011-autonomous-continuation-convergence.md +597 -0
- package/docs/architecture/decisions/20261017-edit-session-finalization-reconciliation.md +17 -0
- package/docs/architecture/decisions/20261019-retire-host-skills.md +16 -0
- package/docs/architecture/diagrams/agentic-dev-plugin-architecture.html +1 -1
- package/docs/architecture/domains/public-surface.md +3 -5
- package/docs/architecture/domains/verification.md +6 -5
- package/docs/architecture/domains/workflow-engine.md +6 -0
- package/docs/architecture/modules/controller-runtime/transport-lifecycle.md +3 -3
- package/docs/architecture/requests/2026-09-04-computer-plugin-workflow-taxonomy.md +4 -4
- package/docs/architecture/reviews/20261015-code-search-runtime-acceptance.md +75 -0
- package/docs/forge-plugin-management.md +16 -4
- package/docs/operations/controller-browser-plugin.md +23 -0
- package/docs/operations/controller-performance-and-502.md +17 -0
- package/docs/operations/controller-reliability-runbook.md +2 -2
- package/docs/operations/features.md +6 -7
- package/docs/operations/features.zh-CN.md +1 -1
- package/docs/operations/github-repository.md +4 -4
- package/docs/operations/github-semantic-release-projection.md +20 -0
- package/docs/operations/homebrew.md +2 -2
- package/docs/operations/mcp-tool-exposure.md +13 -52
- package/docs/operations/releasing.md +2 -0
- package/docs/operations/runtime-performance-diagnostics.md +8 -0
- package/docs/operations/standalone-disaster-recovery.md +15 -7
- package/docs/tutorials/01-install-and-start.zh-CN.md +1 -1
- package/docs/tutorials/03-first-repository-task.md +2 -0
- package/docs/wiki/Computer-and-Plugins.md +78 -0
- package/docs/wiki/Computer-and-Plugins.zh-CN.md +88 -0
- package/docs/wiki/Home.md +16 -2
- package/docs/wiki/Implementation.md +25 -13
- package/docs/wiki/Installation.md +28 -32
- package/docs/wiki/Integrations.md +4 -0
- package/docs/wiki/Quick-Start.md +35 -22
- package/docs/wiki/Releases-and-Upgrades.md +15 -25
- package/docs/wiki/_Sidebar.md +5 -1
- package/package.json +25 -25
- package/packages/kernel/cognition/api/index.ts +6 -0
- package/packages/kernel/cognition/application/activation-service.ts +451 -0
- package/packages/kernel/cognition/application/consolidation-service.ts +185 -0
- package/packages/kernel/cognition/application/legacy-experience-adapter.ts +38 -0
- package/packages/kernel/cognition/application/memory-service.ts +64 -0
- package/packages/kernel/cognition/domain/learning.ts +106 -0
- package/packages/kernel/cognition/domain/memory.ts +254 -0
- package/packages/kernel/controller/api/index.ts +1 -0
- package/packages/kernel/controller/application/continuation-service.ts +281 -0
- package/packages/kernel/controller/application/controller-round-service.ts +12 -0
- package/packages/kernel/controller/domain/controller-round-transition-policy.ts +242 -21
- package/packages/kernel/controller/domain/controller-round.ts +4 -1
- package/packages/kernel/controller/domain/execution-quality.ts +3 -1
- package/packages/kernel/controller/infrastructure/controller-round-store.ts +689 -103
- package/packages/kernel/controller/infrastructure/controller-session-store.ts +348 -97
- package/packages/kernel/controller/ports/controller-host.ts +2 -0
- package/packages/kernel/identity/api/index.ts +10 -0
- package/packages/kernel/identity/domain/activity-projection.ts +43 -0
- package/packages/kernel/identity/domain/capability-broker.ts +60 -0
- package/packages/kernel/identity/domain/grant.ts +72 -0
- package/packages/kernel/identity/domain/owned-resource.ts +116 -0
- package/packages/kernel/identity/domain/user-request.ts +93 -0
- package/packages/kernel/identity/infrastructure/activity-projection-store.ts +87 -0
- package/packages/kernel/identity/infrastructure/capability-broker.ts +81 -0
- package/packages/kernel/identity/infrastructure/grant-store.ts +284 -0
- package/packages/kernel/identity/infrastructure/owned-resource-store.ts +259 -0
- package/packages/kernel/identity/infrastructure/user-request-store.ts +182 -0
- package/packages/kernel/scheduler/api/index.ts +0 -2
- package/packages/kernel/scheduler/application/eligibility.ts +4 -1
- package/packages/kernel/scheduler/application/schedule-service.ts +3 -0
- package/packages/kernel/scheduler/application/settlement.ts +0 -15
- package/packages/kernel/scheduler/domain/schedule.ts +87 -0
- package/packages/kernel/scheduler/infrastructure/schedule-store.ts +166 -143
- package/packages/kernel/work/api/index.ts +3 -2
- package/packages/kernel/work/application/work-service.ts +18 -42
- package/packages/kernel/work/domain/current-task-lineage.ts +104 -0
- package/packages/kernel/work/domain/engineering-design.ts +10 -5
- package/packages/kernel/work/domain/engineering-profile.ts +8 -12
- package/packages/kernel/work/domain/evaluation-promotion-receipt.ts +186 -0
- package/packages/kernel/work/domain/execution-concurrency.ts +19 -26
- package/packages/kernel/work/domain/execution-snapshot.ts +0 -31
- package/packages/kernel/work/domain/implementation-review.ts +14 -331
- package/packages/kernel/work/domain/objective-graph.ts +119 -0
- package/packages/kernel/work/domain/project-engineering-contract.ts +23 -1
- package/packages/kernel/work/domain/repository-completion-receipt.ts +1 -1
- package/packages/kernel/work/domain/state-machine.ts +34 -65
- package/packages/kernel/work/domain/types.ts +57 -51
- package/packages/kernel/work/infrastructure/work-contract-store.ts +847 -729
- package/packages/kernel/work/ports/work-contract-store.ts +5 -2
- package/packages/plugin-runtime/browser/provider-registry.ts +12 -36
- package/packages/plugin-runtime/browser/session-authority.ts +2 -1
- package/packages/plugin-runtime/computer/chatgpt-identity.ts +24 -0
- package/packages/plugin-runtime/computer/conversation-target.ts +153 -0
- package/packages/plugin-runtime/computer/index.ts +2 -0
- package/packages/plugin-runtime/computer/target-authority.ts +26 -1
- package/packages/plugin-runtime/external/unix-jsonl-transport.ts +142 -18
- package/packages/protocols/computer/contract.ts +27 -1
- package/scripts/activate-source-baseline.ts +7 -9
- package/scripts/assemble-template.ts +11 -72
- package/scripts/canary-controller-semantic-wait.ts +12 -24
- package/scripts/check-mcp-compatibility.ts +94 -201
- package/scripts/check-package-identity.mjs +0 -5
- package/scripts/check-runtime-architecture.mjs +921 -239
- package/scripts/forge-local-recovery-helper.mjs +93 -15
- package/scripts/init-project.sh +0 -46
- package/scripts/install-ios-hid-toolchain.sh +60 -0
- package/scripts/install-standalone-recovery.ts +1 -1
- package/scripts/lib/project-init-lib.sh +6 -3
- package/scripts/migrate-windows-wsl-controller-home.ts +2 -0
- package/scripts/open-source-audit-allowlist.txt +1 -3
- package/scripts/run-bounded-command.mjs +5 -0
- package/scripts/run-governed-gate.ts +2 -1
- package/scripts/run-mobile-monitor-bridge.ts +0 -1
- package/scripts/smoke-control-plane-failure-domain.ts +94 -0
- package/scripts/smoke-ios-physical-device.ts +38 -10
- package/scripts/smoke-mcp-http-runtime.ts +12 -8
- package/scripts/smoke-mcp-tool-surface.ts +27 -41
- package/scripts/smoke-runtime-recovery.ts +12 -43
- package/scripts/smoke-schedule-engine.ts +23 -15
- package/scripts/smoke-unattended-transport-recovery.ts +223 -0
- package/scripts/smoke-user-request-continuation-restart.ts +232 -0
- package/scripts/smoke-workflow-supervisor-chrome-adapter.ts +95 -0
- package/scripts/smoke-workflow-supervisor-process-restart.ts +276 -0
- package/scripts/smoke-workflow-supervisor-restart-recovery.ts +150 -0
- package/scripts/smoke-workflow-supervisor.ts +103 -0
- package/scripts/sync-generated-authority.mjs +0 -1
- package/scripts/verify-forge-runtime.sh +2 -1
- package/src/cli/agent-jobs/executor-health.ts +12 -35
- package/src/cli/agent-jobs/integration.ts +20 -51
- package/src/cli/agent-jobs/job-manager.ts +7 -3
- package/src/cli/chatgpt-browser/file-policy.ts +2 -2
- package/src/cli/commands/brain-assistant.ts +27 -13
- package/src/cli/commands/brain.ts +13 -15
- package/src/cli/commands/chatgpt.ts +1 -163
- package/src/cli/commands/doctor.ts +1 -143
- package/src/cli/commands/global-runtime.ts +3 -196
- package/src/cli/commands/init-hook.ts +6 -23
- package/src/cli/commands/init.ts +3 -252
- package/src/cli/commands/mcp.ts +0 -5
- package/src/cli/commands/prompt-guard-decision.ts +0 -2
- package/src/cli/commands/recovery.ts +137 -135
- package/src/cli/commands/repository.ts +17 -1
- package/src/cli/commands/runtime.ts +3 -3
- package/src/cli/commands/setup-execution.ts +41 -0
- package/src/cli/commands/setup-profile.ts +8 -0
- package/src/cli/controller/check-runner.ts +13 -2
- package/src/cli/controller/completion-backlog.ts +3 -3
- package/src/cli/controller/completion-orchestrator.ts +5 -44
- package/src/cli/controller/completion-target.ts +3 -72
- package/src/cli/controller/composite-operations.ts +1 -1
- package/src/cli/controller/context/instruction-context.ts +1 -1
- package/src/cli/controller/context/known-paths.ts +2 -2
- package/src/cli/controller/context/query-planning.ts +11 -4
- package/src/cli/controller/context/rule-resolution.ts +2 -2
- package/src/cli/controller/context/source-materializer.ts +83 -102
- package/src/cli/controller/context/structural-provider.ts +84 -0
- package/src/cli/controller/context/structural.ts +6 -6
- package/src/cli/controller/context/types.ts +8 -9
- package/src/cli/controller/context-pack.ts +107 -84
- package/src/cli/controller/execution-completion.ts +4 -7
- package/src/cli/controller/execution-policy.ts +36 -153
- package/src/cli/controller/governance.ts +2 -3
- package/src/cli/controller/issue-store.ts +4 -99
- package/src/cli/controller/launch-agents.ts +59 -18
- package/src/cli/controller/operational-plan.ts +25 -52
- package/src/cli/controller/runtime-config.ts +5 -1
- package/src/cli/controller/stuck-state-migration.ts +2 -3
- package/src/cli/controller/systemd-user.ts +42 -10
- package/src/cli/editing/edit-session.ts +18 -12
- package/src/cli/github/github.ts +4 -4
- package/src/cli/github/semantic-projection.ts +174 -0
- package/src/cli/hook/prompt-intents.ts +0 -9
- package/src/cli/index.ts +1 -43
- package/src/cli/local-bridge/connector-freshness.ts +1 -12
- package/src/cli/local-bridge/console-automations.ts +19 -14
- package/src/cli/local-bridge/console-view-models.ts +4 -13
- package/src/cli/local-bridge/facade-api.ts +64 -193
- package/src/cli/local-bridge/server.ts +24 -147
- package/src/cli/local-bridge/types.ts +0 -1
- package/src/cli/mcp/oauth-client-retirement.ts +74 -0
- package/src/cli/repositories/command-classifier.ts +0 -9
- package/src/cli/repositories/command-executor.ts +29 -23
- package/src/cli/repositories/command-scope.ts +37 -18
- package/src/cli/repositories/controller-home.ts +48 -0
- package/src/cli/repositories/ephemeral-workspace.ts +20 -30
- package/src/cli/repositories/git-command-executor.ts +2 -2
- package/src/cli/repositories/locks.ts +20 -0
- package/src/cli/repositories/registry.ts +79 -12
- package/src/cli/repositories/safe-patch.ts +2 -12
- package/src/cli/repositories/structured-git.ts +101 -5
- package/src/cli/repository/inspector.ts +185 -343
- package/src/cli/repository/session-cache.ts +92 -6
- package/src/effects/process-runner.ts +17 -1
- package/src/runtime/context/assistant-context.ts +20 -7
- package/src/runtime/context/assistant-work-context.ts +89 -27
- package/src/runtime/context/automatic-learning.ts +565 -0
- package/src/runtime/context/cognitive-attention.ts +173 -0
- package/src/runtime/context/cognitive-skill-canary.ts +158 -0
- package/src/runtime/context/context-closure.ts +46 -9
- package/src/runtime/context/context-pack-process.ts +103 -0
- package/src/runtime/context/context-plane.ts +1 -9
- package/src/runtime/context/direct-controller-learning.ts +298 -0
- package/src/runtime/context/generic-lsp-provider.ts +1 -1
- package/src/runtime/context/semantic-navigation-contract.ts +16 -0
- package/src/runtime/context/semantic-navigation.ts +7 -35
- package/src/runtime/context/typescript-navigation-process.ts +145 -0
- package/src/runtime/context/typescript-navigation.ts +89 -3
- package/src/runtime/control-plane/cleanup-artifact-retention.ts +215 -12
- package/src/runtime/control-plane/concurrency/work-execution-concurrency.ts +9 -47
- package/src/runtime/control-plane/execution/controller-authority-recovery.ts +34 -4
- package/src/runtime/control-plane/execution/edit-validation-coordinator.ts +29 -20
- package/src/runtime/control-plane/execution/execution-identity.ts +23 -3
- package/src/runtime/control-plane/execution/repository-work-attribution.ts +7 -30
- package/src/runtime/control-plane/execution/retained-work-resume.ts +206 -199
- package/src/runtime/control-plane/execution/session-store.ts +31 -1
- package/src/runtime/control-plane/execution/validation.ts +6 -8
- package/src/runtime/control-plane/execution/work-authority-reconciler.ts +13 -42
- package/src/runtime/control-plane/execution/work-check-evidence.ts +137 -0
- package/src/runtime/control-plane/execution/work-completion-authority.ts +30 -85
- package/src/runtime/control-plane/execution/work-delivery-service.ts +616 -0
- package/src/runtime/control-plane/execution/work-evidence-policy.ts +12 -50
- package/src/runtime/control-plane/execution/work-execution-support.ts +50 -149
- package/src/runtime/control-plane/execution/work-handle-authority.ts +197 -110
- package/src/runtime/control-plane/execution/work-handle-store.ts +72 -44
- package/src/runtime/control-plane/execution/work-head-settlement.ts +53 -20
- package/src/runtime/control-plane/execution/work-lifecycle-audit.ts +52 -29
- package/src/runtime/control-plane/execution/work-operation-service.ts +60 -34
- package/src/runtime/control-plane/execution/work-preparation-service.ts +231 -267
- package/src/runtime/control-plane/execution/work-process-evidence.ts +2 -2
- package/src/runtime/control-plane/execution/work-remote-delivery.ts +2 -3
- package/src/runtime/control-plane/execution/work-revision-diff.ts +39 -0
- package/src/runtime/control-plane/execution/work-terminal-cleanup.ts +201 -199
- package/src/runtime/control-plane/execution/work-validation-reconciler.ts +33 -85
- package/src/runtime/control-plane/execution/work-verification-service.ts +406 -50
- package/src/runtime/control-plane/execution/work-verification-snapshot.ts +6 -2
- package/src/runtime/control-plane/facade/capability-registry.ts +364 -37
- package/src/runtime/control-plane/facade/check-normalization.ts +3 -9
- package/src/runtime/control-plane/facade/codex-delegation.ts +10 -11
- package/src/runtime/control-plane/facade/controller-connection.ts +135 -0
- package/src/runtime/control-plane/facade/goal-workloop-access.ts +1 -20
- package/src/runtime/control-plane/facade/goal-workloop.ts +281 -1753
- package/src/runtime/control-plane/facade/handoff-inbox-application.ts +12 -25
- package/src/runtime/control-plane/facade/handoff-inbox-store.ts +256 -52
- package/src/runtime/control-plane/facade/index.ts +0 -1
- package/src/runtime/control-plane/facade/operation-digest.ts +12 -15
- package/src/runtime/control-plane/facade/plan-contract-store.ts +451 -991
- package/src/runtime/control-plane/facade/policy-gate.ts +0 -23
- package/src/runtime/control-plane/facade/repository-work-admission.ts +12 -22
- package/src/runtime/control-plane/facade/requirement-authority.ts +102 -199
- package/src/runtime/control-plane/facade/requirement-board.ts +3 -3
- package/src/runtime/control-plane/facade/rh-work-operation-contract.ts +51 -14
- package/src/runtime/control-plane/facade/self-healing-loop.ts +18 -53
- package/src/runtime/control-plane/facade/suggested-actions.ts +15 -18
- package/src/runtime/control-plane/facade/types.ts +49 -108
- package/src/runtime/control-plane/facade/work-continuation.ts +9 -9
- package/src/runtime/control-plane/generated-cache-retention.ts +206 -59
- package/src/runtime/control-plane/global-scheduler/autonomous-continuation.ts +248 -0
- package/src/runtime/control-plane/global-scheduler/durable-admission.ts +1 -1
- package/src/runtime/control-plane/global-scheduler/maintenance.ts +256 -117
- package/src/runtime/control-plane/global-scheduler/reconciliation.ts +3 -12
- package/src/runtime/control-plane/global-scheduler/scheduler.ts +66 -40
- package/src/runtime/control-plane/global-scheduler/wake-signal.ts +42 -2
- package/src/runtime/control-plane/governance/access-policy.ts +19 -2
- package/src/runtime/control-plane/governance/authorization.ts +20 -3
- package/src/runtime/control-plane/governance/external-effects.ts +1 -1
- package/src/runtime/control-plane/launcher/chatgpt-round-continuation.ts +63 -300
- package/src/runtime/control-plane/launcher/chatgpt-work-continuation.ts +29 -300
- package/src/runtime/control-plane/launcher/local-conversation-controller.ts +238 -0
- package/src/runtime/control-plane/launcher/provider-mcp-bootstrap.ts +5 -2
- package/src/runtime/control-plane/launcher/thin-launcher.ts +96 -240
- package/src/runtime/control-plane/persistence/cognition-store.ts +820 -0
- package/src/runtime/control-plane/persistence/experience-store.ts +162 -29
- package/src/runtime/control-plane/persistence/requirement-store.ts +216 -74
- package/src/runtime/control-plane/persistence/sqlite-store.ts +113 -6
- package/src/runtime/control-plane/release-retention.ts +135 -47
- package/src/runtime/control-plane/repository-namespace-retention.ts +2 -2
- package/src/runtime/control-plane/runtime-cleanup.ts +295 -107
- package/src/runtime/control-plane/workspace/project-onboarding.ts +80 -0
- package/src/runtime/control-plane/workspace/semantic-sync-service.ts +19 -5
- package/src/runtime/control-plane/workspace/workspace-store.ts +169 -0
- package/src/runtime/diagnostics/incident-repair.ts +313 -146
- package/src/runtime/diagnostics/mcp-timing.ts +114 -0
- package/src/runtime/evidence/artifact-store.ts +158 -40
- package/src/runtime/evidence/evidence-store.ts +112 -8
- package/src/runtime/evidence/output-handle-index.ts +225 -0
- package/src/runtime/evidence/result-store.ts +158 -44
- package/src/runtime/evidence/sensitive-output.ts +22 -2
- package/src/runtime/execution/jobs/child-reference.ts +11 -0
- package/src/runtime/execution/jobs/receipt-recovery.ts +1 -11
- package/src/runtime/execution/jobs/store.ts +3 -4
- package/src/runtime/execution/managed-workspace.ts +57 -0
- package/src/runtime/execution/process-runtime/check-facade.ts +1 -1
- package/src/runtime/execution/process-runtime/check-result-retention.ts +2 -2
- package/src/runtime/execution/process-runtime/check-result.ts +105 -1
- package/src/runtime/execution/process-runtime/check-runner-sidecar.ts +18 -8
- package/src/runtime/execution/process-runtime/command-facade.ts +82 -30
- package/src/runtime/execution/process-runtime/gc.ts +15 -2
- package/src/runtime/execution/process-runtime/handle-index.ts +176 -0
- package/src/runtime/execution/process-runtime/host-command-lane.ts +139 -0
- package/src/runtime/execution/process-runtime/index.ts +3 -0
- package/src/runtime/execution/process-runtime/lightweight-managed.ts +251 -72
- package/src/runtime/execution/process-runtime/persisted-check.ts +3 -3
- package/src/runtime/execution/process-runtime/process-runner-entry.ts +47 -5
- package/src/runtime/execution/process-runtime/process-scope.ts +160 -0
- package/src/runtime/execution/process-runtime/resource-claims.ts +65 -61
- package/src/runtime/execution/process-runtime/runtime.ts +55 -18
- package/src/runtime/execution/process-runtime/store.ts +30 -2
- package/src/runtime/execution/process-runtime/types.ts +6 -1
- package/src/runtime/execution/thin-harness/execution-router.ts +16 -16
- package/src/runtime/execution/thin-harness/fast-executor.ts +2 -2
- package/src/runtime/execution/thin-harness/search-worker.ts +2 -2
- package/src/runtime/execution/workers/executor.ts +3 -8
- package/src/runtime/maintenance/cleanup.ts +41 -5
- package/src/runtime/platform/service-inventory.ts +130 -0
- package/src/runtime/platform/service-manager.ts +8 -0
- package/src/runtime/plugins/action-application.ts +97 -29
- package/src/runtime/plugins/app-store-connect-adapter.ts +290 -18
- package/src/runtime/plugins/browser-adapter.ts +1124 -333
- package/src/runtime/plugins/browser-automation-service.ts +23 -3
- package/src/runtime/plugins/browser-macos-bridge.ts +431 -137
- package/src/runtime/plugins/browser-manifest-surface.ts +47 -12
- package/src/runtime/plugins/browser-native-session-service.ts +63 -13
- package/src/runtime/plugins/browser-registration.ts +18 -0
- package/src/runtime/plugins/browser-runtime.ts +40 -36
- package/src/runtime/plugins/browser-session-authority.ts +2 -2
- package/src/runtime/plugins/browser-session-store.ts +46 -76
- package/src/runtime/plugins/capability-authorization-grants.ts +258 -62
- package/src/runtime/plugins/computer-chatgpt-browser-adapter-installer.ts +228 -0
- package/src/runtime/plugins/computer-registration.ts +298 -20
- package/src/runtime/plugins/desktop-operator-external-policy.ts +36 -4
- package/src/runtime/plugins/desktop-operator-registration.ts +12 -4
- package/src/runtime/plugins/external-adapter.ts +42 -6
- package/src/runtime/plugins/external-registration.ts +21 -1
- package/src/runtime/plugins/github-adapter.ts +30 -3
- package/src/runtime/plugins/gmail-adapter.ts +189 -3
- package/src/runtime/plugins/google-calendar-adapter.ts +2 -2
- package/src/runtime/plugins/google-shared.ts +24 -12
- package/src/runtime/plugins/google-tasks-adapter.ts +2 -2
- package/src/runtime/plugins/ios/remote-xpc-hid.ts +70 -30
- package/src/runtime/plugins/ios-adapter.ts +46 -41
- package/src/runtime/plugins/ios-agent-device.ts +54 -4
- package/src/runtime/plugins/ios-device-ownership.ts +103 -0
- package/src/runtime/plugins/ios-physical-device.ts +497 -79
- package/src/runtime/plugins/lightweight-action.ts +208 -2
- package/src/runtime/plugins/local-system-adapter.ts +12 -100
- package/src/runtime/plugins/managed-process-adapter.ts +12 -5
- package/src/runtime/plugins/plugin-action-sidecar.ts +17 -13
- package/src/runtime/plugins/plugin-management-adapter.ts +1 -1
- package/src/runtime/plugins/store.ts +682 -435
- package/src/runtime/plugins/types.ts +24 -0
- package/src/runtime/plugins/xiaohongshu-publish.ts +16 -0
- package/src/runtime/projections/git-status-sampler.ts +2 -19
- package/src/runtime/projections/invalidation.ts +7 -3
- package/src/runtime/projections/materialized-view.ts +80 -36
- package/src/runtime/recovery/actions.ts +4 -4
- package/src/runtime/recovery/capability-action-application.ts +46 -45
- package/src/runtime/recovery/lifecycle-inventory.ts +30 -40
- package/src/runtime/recovery/maintenance-executor.ts +374 -123
- package/src/runtime/recovery/probe.ts +2 -2
- package/src/runtime/recovery/store.ts +29 -11
- package/src/runtime/release/release-coordinator.ts +312 -0
- package/src/runtime/release/release-session.ts +716 -0
- package/src/runtime/release/release-state-migration.ts +25 -0
- package/src/runtime/resources/leases/store.ts +56 -25
- package/src/runtime/root/computer-composition.ts +191 -6
- package/src/runtime/root/controller-progression-composition.ts +254 -0
- package/src/runtime/root/controller-round-composition.ts +20 -1
- package/src/runtime/root/deployment-topology.ts +106 -0
- package/src/runtime/root/entry.ts +4 -3
- package/src/runtime/root/known-good-recovery.ts +184 -0
- package/src/runtime/root/local-bridge.ts +0 -1
- package/src/runtime/root/mcp-transport.ts +111 -18
- package/src/runtime/root/ownership.ts +261 -9
- package/src/runtime/root/package-connector-service.ts +227 -29
- package/src/runtime/root/package-runtime-release.ts +117 -30
- package/src/runtime/root/package-runtime-service.ts +24 -24
- package/src/runtime/root/release-execution-canary.ts +57 -12
- package/src/runtime/root/release-loader.ts +90 -8
- package/src/runtime/root/release-manifest.ts +80 -40
- package/src/runtime/root/release-materialize.ts +372 -106
- package/src/runtime/root/release-store.ts +395 -36
- package/src/runtime/root/runtime-lane.ts +191 -0
- package/src/runtime/root/runtime.ts +160 -29
- package/src/runtime/root/scheduled-controller-composition.ts +29 -3
- package/src/runtime/root/service-runner.ts +2 -2
- package/src/runtime/root/service.ts +126 -44
- package/src/runtime/root/status.ts +48 -0
- package/src/runtime/root/types.ts +32 -9
- package/src/runtime/root/workflow-supervisor-composition.ts +681 -0
- package/src/runtime/root/workflow-supervisor-runtime.ts +564 -0
- package/src/runtime/root/write-fence.ts +50 -2
- package/src/runtime/safe-tooling/google-credential-store.ts +67 -22
- package/src/runtime/safe-tooling/google-oauth-broker.ts +25 -7
- package/src/runtime/safe-tooling/ios-development.ts +22 -8
- package/src/runtime/safe-tooling/job-summary.ts +1 -1
- package/src/runtime/safe-tooling/workspace-auth.ts +5 -2
- package/src/runtime/shared/atomic-text-file.ts +21 -0
- package/src/runtime/shared/bounded-child-supervisor.ts +9 -1
- package/src/runtime/shared/json-files.ts +8 -3
- package/src/runtime/shared/process-environment.ts +20 -9
- package/src/runtime/shared/response-budget.ts +1 -3
- package/src/runtime/standalone-recovery/controller-home-migration.ts +16 -24
- package/src/runtime/standalone-recovery/core.ts +3792 -417
- package/src/runtime/standalone-recovery/entry.ts +507 -45
- package/src/runtime/standalone-recovery/installer.ts +262 -148
- package/src/runtime/standalone-recovery/mcp-server.ts +29 -193
- package/src/runtime/standalone-recovery/operation-lock.ts +12 -2
- package/src/runtime/standalone-recovery/performance.ts +54 -16
- package/src/runtime/standalone-recovery/release.ts +53 -5
- package/src/runtime/standalone-recovery/service-labels.ts +5 -2
- package/src/runtime/standalone-recovery/watchdog-heartbeat.ts +5 -2
- package/src/runtime/workflow/schedules/browser-probe.ts +17 -6
- package/src/runtime/workflow/schedules/chatgpt-automation-migration.ts +11 -3
- package/src/runtime/workflow/schedules/engine.ts +166 -178
- package/src/runtime/workflow/schedules/pending-activation.ts +11 -4
- package/src/runtime/workflow/schedules/work-continuation.ts +95 -11
- package/src/runtime/workflows/runtime.ts +15 -19
- package/src/testing/test-governance.ts +5 -1
- package/supervisor/chatgpt-conversation.ts +23 -0
- package/supervisor/client.ts +218 -0
- package/supervisor/control-plane.ts +963 -0
- package/supervisor/entry.ts +15 -0
- package/supervisor/forge-validators.ts +147 -0
- package/supervisor/index.ts +5 -0
- package/supervisor/native-browser-adapter.ts +1151 -0
- package/supervisor/native-messaging/host.ts +58 -0
- package/supervisor/native-messaging/manifest.ts +26 -0
- package/supervisor/native-messaging/protocol.ts +27 -0
- package/supervisor/paths.ts +18 -0
- package/supervisor/protocol.ts +250 -0
- package/supervisor/server.ts +412 -0
- package/supervisor/store.ts +1870 -0
- package/supervisor/tsconfig.json +8 -0
- package/supervisor/types.ts +261 -0
- package/SKILL.md +0 -427
- package/adapters/chatgpt/controller-host.ts +0 -119
- package/adapters/mcp/controller-round-compatibility.ts +0 -184
- package/adapters/mcp/frozen-client-semantic-compatibility.ts +0 -292
- package/adapters/mcp/runtime-gateway/work-compat-adapter.ts +0 -502
- package/adapters/mcp/runtime-gateway/work-validation-reconciler.ts +0 -1
- package/adapters/mcp/toolset-selection.ts +0 -41
- package/agents/openai.yaml +0 -4
- package/assets/skill-hooks.json +0 -41
- package/assets/skill-version.json +0 -189
- package/assets/skills/claude-review/SKILL.md +0 -231
- package/assets/skills/codex-review/SKILL.md +0 -103
- package/assets/templates/helpers/check-skill-version.ts +0 -193
- package/packages/kernel/progression/api/index.ts +0 -2
- package/packages/kernel/progression/application/projector.ts +0 -211
- package/packages/kernel/progression/domain/types.ts +0 -116
- package/packages/kernel/progression/index.ts +0 -1
- package/packages/kernel/scheduler/application/continuation-service.ts +0 -212
- package/packages/kernel/scheduler/domain/continuation.ts +0 -38
- package/packages/kernel/scheduler/infrastructure/continuation-dispatch-store.ts +0 -38
- package/packages/kernel/work/domain/admission-policy.ts +0 -34
- package/scripts/benchmark-background-check-overlap.ts +0 -228
- package/scripts/benchmark-computer-hotpath.ts +0 -255
- package/scripts/benchmark-controller-hotpath.ts +0 -212
- package/scripts/benchmark-controller-round2.ts +0 -191
- package/scripts/benchmark-ios-agent-device.ts +0 -511
- package/scripts/benchmark-mcp-host.sh +0 -117
- package/scripts/benchmark-mcp-transport.ts +0 -169
- package/scripts/benchmark-operational-memory-activation.ts +0 -235
- package/scripts/benchmark-operational-shadow.ts +0 -28
- package/scripts/benchmark-quality-harness.ts +0 -146
- package/scripts/benchmark-route-session-concurrency.ts +0 -915
- package/scripts/benchmark-thin-harness-gateway-ab.ts +0 -632
- package/scripts/benchmark-thin-harness-mcp-e2e.ts +0 -498
- package/scripts/benchmark-thin-harness.ts +0 -251
- package/scripts/benchmark-typescript-navigation.ts +0 -186
- package/scripts/benchmark-work-efficiency.ts +0 -334
- package/scripts/build-controller-ui.ts +0 -28
- package/scripts/check-npm-release.sh +0 -32
- package/scripts/check-public-release-surface.sh +0 -19
- package/scripts/check-release-published.sh +0 -57
- package/scripts/check-release-readiness.sh +0 -37
- package/scripts/check-release-version.mjs +0 -74
- package/scripts/check-skill-version.ts +0 -5
- package/scripts/check-tarball-install-smoke.sh +0 -150
- package/scripts/ensure-codegraph.sh +0 -16
- package/scripts/package-source-archive.sh +0 -147
- package/scripts/public-release-files.txt +0 -39
- package/scripts/public-release.ts +0 -174
- package/scripts/publish-release-tarball.sh +0 -27
- package/scripts/route-nl-vs-ts-eval.ts +0 -679
- package/scripts/run-skill-hook.ts +0 -244
- package/scripts/stage-runtime-release.ts +0 -44
- package/scripts/sync-codex-installed-copies.sh +0 -182
- package/src/cli/commands/tools.ts +0 -167
- package/src/cli/controller/progress.ts +0 -656
- package/src/cli/controller/work-mode.ts +0 -181
- package/src/cli/local-bridge/console-assets.ts +0 -17
- package/src/cli/local-bridge/dashboard.ts +0 -17
- package/src/cli/local-bridge/frontend/src/App.tsx +0 -10
- package/src/cli/local-bridge/frontend/src/components/Button.tsx +0 -1
- package/src/cli/local-bridge/frontend/src/components/DetailPane.tsx +0 -3
- package/src/cli/local-bridge/frontend/src/components/SearchField.tsx +0 -1
- package/src/cli/local-bridge/frontend/src/components/SectionHeader.tsx +0 -1
- package/src/cli/local-bridge/frontend/src/components/Segmented.tsx +0 -1
- package/src/cli/local-bridge/frontend/src/components/StatusText.tsx +0 -3
- package/src/cli/local-bridge/frontend/src/design/icons.tsx +0 -11
- package/src/cli/local-bridge/frontend/src/design/tokens.css +0 -8
- package/src/cli/local-bridge/frontend/src/features/automations/AutomationsView.tsx +0 -153
- package/src/cli/local-bridge/frontend/src/features/capabilities/CapabilitiesView.tsx +0 -37
- package/src/cli/local-bridge/frontend/src/features/overview/OverviewView.tsx +0 -183
- package/src/cli/local-bridge/frontend/src/features/repositories/RepositoriesView.tsx +0 -2
- package/src/cli/local-bridge/frontend/src/features/system/SystemView.tsx +0 -2
- package/src/cli/local-bridge/frontend/src/features/work/WorkView.tsx +0 -4
- package/src/cli/local-bridge/frontend/src/lib/api.ts +0 -30
- package/src/cli/local-bridge/frontend/src/lib/format.ts +0 -4
- package/src/cli/local-bridge/frontend/src/lib/routes.ts +0 -7
- package/src/cli/local-bridge/frontend/src/main.tsx +0 -1
- package/src/cli/local-bridge/frontend/src/shell/AppShell.tsx +0 -1
- package/src/cli/local-bridge/frontend/src/shell/CommandBar.tsx +0 -2
- package/src/cli/local-bridge/frontend/src/shell/Sidebar.tsx +0 -4
- package/src/cli/local-bridge/frontend/src/styles.css +0 -28
- package/src/cli/local-bridge/frontend/src/types.ts +0 -15
- package/src/cli/local-bridge/frontend/src/vite-env.d.ts +0 -1
- package/src/cli/local-bridge/frontend/vite.config.ts +0 -27
- package/src/cli/local-bridge/ui-dist/app.css +0 -1
- package/src/cli/local-bridge/ui-dist/app.js +0 -11228
- package/src/cli/mcp/access-mode.ts +0 -2
- package/src/cli/mcp/access-tools.ts +0 -2
- package/src/cli/mcp/audit.ts +0 -2
- package/src/cli/mcp/auth.ts +0 -2
- package/src/cli/mcp/instructions.ts +0 -2
- package/src/cli/mcp/legacy-context.ts +0 -2
- package/src/cli/mcp/legacy-tool-service.ts +0 -2
- package/src/cli/mcp/multi-repository.ts +0 -2
- package/src/cli/mcp/oauth.ts +0 -2
- package/src/cli/mcp/openai-secure-tunnel.ts +0 -2
- package/src/cli/mcp/paths.ts +0 -2
- package/src/cli/mcp/policy.ts +0 -2
- package/src/cli/mcp/post-finalize-work-attribution.ts +0 -2
- package/src/cli/mcp/proxy-env.ts +0 -2
- package/src/cli/mcp/readiness-projection.ts +0 -2
- package/src/cli/mcp/redaction.ts +0 -2
- package/src/cli/mcp/repo.ts +0 -2
- package/src/cli/mcp/repository-tools.ts +0 -2
- package/src/cli/mcp/server.ts +0 -2
- package/src/cli/mcp/setup.ts +0 -2
- package/src/cli/mcp/tool-capability-cache.ts +0 -2
- package/src/cli/mcp/tool-contract.ts +0 -2
- package/src/cli/mcp/tools.ts +0 -2
- package/src/cli/mcp/toolset-names.ts +0 -2
- package/src/cli/mcp/toolset-selection.ts +0 -2
- package/src/cli/mcp/toolset.ts +0 -2
- package/src/cli/mcp/transports/http.ts +0 -2
- package/src/cli/mcp/transports/session-registry.ts +0 -2
- package/src/cli/mcp/transports/stdio.ts +0 -2
- package/src/cli/mcp/types.ts +0 -2
- package/src/cli/mcp/umbrella-tools.ts +0 -2
- package/src/cli/tools/codegraph.ts +0 -695
- package/src/core/adoption/helper-wrapper-plan.ts +0 -159
- package/src/runtime/context/codegraph-cache-boundary.ts +0 -255
- package/src/runtime/context/codegraph-read-provider.ts +0 -611
- package/src/runtime/context/codegraph-sidecar.cjs +0 -248
- package/src/runtime/control-plane/codegraph-cache-retention.ts +0 -164
- package/src/runtime/control-plane/execution/content-equivalent-commit-authority.ts +0 -169
- package/src/runtime/control-plane/execution/direct-canonical-work-reconciliation.ts +0 -85
- package/src/runtime/control-plane/execution/direct-edit-work-completion.ts +0 -655
- package/src/runtime/control-plane/execution/work-finalization-service.ts +0 -2850
- package/src/runtime/control-plane/execution/work-path-scope.ts +0 -37
- package/src/runtime/control-plane/execution/work-task-receipt.ts +0 -468
- package/src/runtime/control-plane/facade/controller-round-relay.ts +0 -3
- package/src/runtime/control-plane/facade/work-admission-policy.ts +0 -142
- package/src/runtime/control-plane/facade/work-implementation-review.ts +0 -2
- package/src/runtime/control-plane/facade/work-state-machine.ts +0 -2
- package/src/runtime/control-plane/facade/work-task-projection.ts +0 -66
- package/src/runtime/control-plane/routing/index.ts +0 -1
- package/src/runtime/control-plane/routing/route-policy.ts +0 -401
- package/src/runtime/control-plane/routing/workspace-admission.ts +0 -70
- package/src/runtime/gateway/mcp/execution-tools.ts +0 -2
- package/src/runtime/gateway/mcp/legacy-ios-tool-adapter.ts +0 -2
- package/src/runtime/gateway/mcp/persisted-check-process.ts +0 -2
- package/src/runtime/gateway/mcp/process-tools.ts +0 -2
- package/src/runtime/gateway/mcp/router.ts +0 -2
- package/src/runtime/gateway/mcp/runtime-tool-definitions.ts +0 -2
- package/src/runtime/gateway/mcp/runtime-tools.ts +0 -2
- package/src/runtime/gateway/mcp/work-validation-reconciler.ts +0 -2
- package/src/runtime/plugins/browser-provider-registry.ts +0 -2
|
@@ -2,36 +2,58 @@ import { existsSync } from "fs";
|
|
|
2
2
|
import { join } from "path";
|
|
3
3
|
import { runProcess } from '../../../src/effects/process-runner';
|
|
4
4
|
import type { MultiRepositoryMcpToolContext } from "../multi-repository";
|
|
5
|
-
import {
|
|
5
|
+
import { controllerExposureSnapshot, controllerToolSurfaceStatus } from "../toolset";
|
|
6
6
|
import { result } from "./result-adapter";
|
|
7
|
-
import { selected } from "./shared-adapter";
|
|
8
|
-
import {
|
|
9
|
-
import { listExecutionJobs } from "../../../src/runtime/execution/jobs/store";
|
|
7
|
+
import { selected, selectedOptional } from "./shared-adapter";
|
|
8
|
+
import { SEMANTIC_SCOPE_KEY } from "../../../src/cli/repositories/controller-home";
|
|
10
9
|
import type { ExecutionJob } from '../../../src/runtime/execution/jobs/types';
|
|
11
10
|
import { getProcessRecord, isManagedProcessActive, processRuntimeResourceDiagnostics } from "../../../src/runtime/execution/process-runtime";
|
|
12
|
-
import {
|
|
13
|
-
import { readSchedulerHealthSnapshot } from "../../../src/runtime/control-plane/global-scheduler/scheduler";
|
|
14
|
-
import { evaluateActiveRuntimeSourceDrift, formatRuntimeSourceDriftMessage, readRuntimeGeneration, type RuntimeSourceIdentity } from "../../../src/runtime/control-plane/runtime-generation";
|
|
15
|
-
import { projectionObservation, readRepositoryProjectionSnapshot } from "../../../src/runtime/projections/materialized-view";
|
|
16
|
-
import { buildRuntimeOperationalView, classifyRuntimeReadinessSemantics, evaluateRuntimeHealth, RUNTIME_HEALTH_THRESHOLDS, type RuntimeOperationalView, type GradedObservation } from "../../../src/runtime/health";
|
|
17
|
-
import { buildControllerTaskLedgerProjection } from "../../../src/cli/controller/task-ledger";
|
|
18
|
-
import { legacyIssueAuthorityRetired } from "../../../src/cli/controller/legacy-issue-cutover";
|
|
11
|
+
import { formatRuntimeSourceDriftMessage, readRuntimeGeneration } from "../../../src/runtime/control-plane/runtime-generation";
|
|
19
12
|
import { listControllerChecks } from "../../../src/cli/controller/check-runner";
|
|
20
13
|
import { buildCheckExecutionSchedule } from "../../../src/runtime/execution/process-runtime/check-scheduling";
|
|
21
|
-
import { FORGE_MCP_SCHEMA_VERSION, FORGE_TOOL_SURFACE, FORGE_VERSION } from "../../../src/cli/controller/runtime-config";
|
|
22
|
-
import { resolveLocalBridgeSurface } from "../../../src/runtime/shared/local-bridge-surface";
|
|
23
14
|
import { listAssistantPluginManifests } from "../../../src/runtime/plugins/store";
|
|
24
15
|
import { cachedGitIdentity, gitSnapshot } from "../../../src/cli/repository/inspector";
|
|
25
16
|
import { buildRuntimeMaintenanceStatus } from "../../../src/runtime/recovery";
|
|
26
|
-
import { allowedFacadeOperations, buildFacadeResult, listCapabilityDescriptors, summarizeCapabilityGroups, listHandoffAttentionItems,
|
|
17
|
+
import { allowedFacadeOperations, buildFacadeResult, listCapabilityDescriptors, summarizeCapabilityGroups, listHandoffAttentionItems, normalizeCheckIds, buildWorkContinuationSnapshot, listPlanContracts, summarizePlanContract, runHandoffInboxApplication, type FacadeTool } from "../../../src/runtime/control-plane/facade";
|
|
27
18
|
import { buildJobOperationDigest } from '../../../src/runtime/control-plane/facade/operation-digest';
|
|
28
|
-
import { readActiveWorkCandidates, type InvalidActiveWorkCandidate } from "../../../packages/kernel/work/api/index";
|
|
19
|
+
import { getWorkContract, readActiveWorkCandidates, semanticWorkState, type InvalidActiveWorkCandidate } from "../../../packages/kernel/work/api/index";
|
|
20
|
+
import { listWorkHandles } from '../../../src/runtime/control-plane/execution/work-handle-store';
|
|
29
21
|
import { observeRuntimeStatus } from "../../../src/runtime/root/status";
|
|
30
22
|
import { getControllerSession } from "../../../packages/kernel/controller/api/index";
|
|
23
|
+
import { listActiveOccurrences, listSchedules, scheduleOwnsWork } from "../../../packages/kernel/scheduler/api/index";
|
|
31
24
|
import { summarizeHandoffItem } from '../../../src/runtime/control-plane/facade';
|
|
32
25
|
import type { CallToolResult } from '../../../packages/protocols/mcp/tool-contract';
|
|
33
|
-
import {
|
|
26
|
+
import { triggerResolvedHandoffContinuation } from '../../../src/runtime/workflow/schedules/work-continuation';
|
|
27
|
+
import { getUserRequest, listUserRequests, recordUserRequest, resolveUserRequest, type UserRequest } from '../../../packages/kernel/identity/api/index';
|
|
28
|
+
import { controllerReadinessEvidence, runtimeSourceSnapshotStatus } from './runtime-readiness-observation';
|
|
29
|
+
import { readRuntimeReleaseAuthority } from '../../../src/runtime/root/release-store';
|
|
30
|
+
import { getWorkflowSupervisorConsumerStatus, getWorkflowSupervisorContinuationProof } from '../../../supervisor/client';
|
|
31
|
+
import { resolveWorkflowSupervisorForgeHome } from '../../../supervisor/paths';
|
|
32
|
+
export { ageMs, probeLocalControllerHealth, localControllerDiagnosticMatchesRuntime, controllerReadinessEvidence, runtimeSourceSnapshotStatus } from './runtime-readiness-observation';
|
|
33
|
+
export type { ControllerReadinessSignals } from './runtime-readiness-observation';
|
|
34
34
|
|
|
35
|
+
export const PRIMARY_WORK_RUNTIME_ACTIVITIES = [
|
|
36
|
+
'running',
|
|
37
|
+
'waiting_for_user',
|
|
38
|
+
'scheduled',
|
|
39
|
+
'recoverable',
|
|
40
|
+
'needs_reconciliation',
|
|
41
|
+
] as const;
|
|
42
|
+
export type PrimaryWorkRuntimeActivity = (typeof PRIMARY_WORK_RUNTIME_ACTIVITIES)[number];
|
|
43
|
+
|
|
44
|
+
/** Read-only runtime projection. These facts never mutate or extend semantic Work state. */
|
|
45
|
+
export function primaryWorkRuntimeActivity(facts: {
|
|
46
|
+
running: boolean;
|
|
47
|
+
waitingForUser: boolean;
|
|
48
|
+
scheduled: boolean;
|
|
49
|
+
needsReconciliation: boolean;
|
|
50
|
+
}): PrimaryWorkRuntimeActivity {
|
|
51
|
+
if (facts.running) return 'running';
|
|
52
|
+
if (facts.waitingForUser) return 'waiting_for_user';
|
|
53
|
+
if (facts.scheduled) return 'scheduled';
|
|
54
|
+
if (facts.needsReconciliation) return 'needs_reconciliation';
|
|
55
|
+
return 'recoverable';
|
|
56
|
+
}
|
|
35
57
|
|
|
36
58
|
export const GIT_IDENTITY_SAMPLE_TTL_MS = Math.max(1_000, Number(process.env.FORGE_GIT_IDENTITY_SAMPLE_TTL_MS ?? 3_000));
|
|
37
59
|
|
|
@@ -79,7 +101,7 @@ export function summarizeWorkListItem(job: ExecutionJob): Record<string, unknown
|
|
|
79
101
|
createdAt: job.createdAt,
|
|
80
102
|
updatedAt: job.updatedAt,
|
|
81
103
|
suggestedNextAction: digest.suggestedNextActions[0],
|
|
82
|
-
detailPointer: { tool: '
|
|
104
|
+
detailPointer: { tool: 'rh_work', operation: 'get', work_id: job.jobId },
|
|
83
105
|
};
|
|
84
106
|
}
|
|
85
107
|
|
|
@@ -103,210 +125,6 @@ export function invalidFacadeOperation(tool: FacadeTool, operation: string): Cal
|
|
|
103
125
|
}
|
|
104
126
|
|
|
105
127
|
|
|
106
|
-
export function ageMs(value: string | undefined): number | undefined {
|
|
107
|
-
if (!value) return undefined;
|
|
108
|
-
const parsed = Date.parse(value);
|
|
109
|
-
return Number.isFinite(parsed) ? Math.max(0, Date.now() - parsed) : undefined;
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
export async function probeLocalControllerHealth(endpoint: string | undefined): Promise<Record<string, unknown> | null> {
|
|
113
|
-
if (!endpoint) return null;
|
|
114
|
-
const controller = new AbortController();
|
|
115
|
-
const timeout = setTimeout(() => controller.abort(), 1_500);
|
|
116
|
-
try {
|
|
117
|
-
const url = new URL(endpoint);
|
|
118
|
-
url.pathname = '/health';
|
|
119
|
-
url.search = '';
|
|
120
|
-
url.hash = '';
|
|
121
|
-
const response = await fetch(url, { signal: controller.signal, headers: { accept: 'application/json' } });
|
|
122
|
-
if (!response.ok) return null;
|
|
123
|
-
return await response.json() as Record<string, unknown>;
|
|
124
|
-
} catch {
|
|
125
|
-
return null;
|
|
126
|
-
} finally {
|
|
127
|
-
clearTimeout(timeout);
|
|
128
|
-
}
|
|
129
|
-
}
|
|
130
|
-
|
|
131
|
-
export function localControllerDiagnosticMatchesRuntime(
|
|
132
|
-
payload: Record<string, unknown> | null,
|
|
133
|
-
expected: { generation?: string } = {},
|
|
134
|
-
): boolean {
|
|
135
|
-
return payload?.status === 'ok'
|
|
136
|
-
&& payload.toolSurface === FORGE_TOOL_SURFACE
|
|
137
|
-
&& payload.schemaVersion === FORGE_MCP_SCHEMA_VERSION
|
|
138
|
-
&& payload.version === FORGE_VERSION
|
|
139
|
-
&& (expected.generation === undefined || payload.generation === expected.generation);
|
|
140
|
-
}
|
|
141
|
-
|
|
142
|
-
export interface ControllerReadinessSignals {
|
|
143
|
-
externalEndpoint?: GradedObservation;
|
|
144
|
-
mcpHandshake?: GradedObservation;
|
|
145
|
-
sessionContinuity?: GradedObservation;
|
|
146
|
-
}
|
|
147
|
-
|
|
148
|
-
export async function controllerReadinessEvidence(
|
|
149
|
-
ctx: MultiRepositoryMcpToolContext,
|
|
150
|
-
repository = ctx.explicitRepository,
|
|
151
|
-
signals: ControllerReadinessSignals = {},
|
|
152
|
-
) {
|
|
153
|
-
const daemon = readForgeRuntimeStatus(ctx.controllerHome);
|
|
154
|
-
const scheduler = readSchedulerHealthSnapshot(ctx.controllerHome);
|
|
155
|
-
const projectionSnapshot = repository ? readRepositoryProjectionSnapshot(ctx.controllerHome, repository.repoId) : undefined;
|
|
156
|
-
const projection = projectionSnapshot?.projection;
|
|
157
|
-
const taskLedger = repository && !legacyIssueAuthorityRetired(repository.canonicalRoot)
|
|
158
|
-
? buildControllerTaskLedgerProjection(repository.canonicalRoot)
|
|
159
|
-
: undefined;
|
|
160
|
-
const projectionReconciliation = projectionSnapshot
|
|
161
|
-
? reconcileReadinessProjectionSource(projectionSnapshot, taskLedger)
|
|
162
|
-
: undefined;
|
|
163
|
-
const localBridgeSurface = repository
|
|
164
|
-
? resolveLocalBridgeSurface({
|
|
165
|
-
controllerHome: ctx.controllerHome,
|
|
166
|
-
repoRoot: repository.canonicalRoot,
|
|
167
|
-
allowProcessScan: false,
|
|
168
|
-
})
|
|
169
|
-
: undefined;
|
|
170
|
-
const localBridgeEndpoint = localBridgeSurface?.endpoint;
|
|
171
|
-
const shouldProbeLocalBridge = Boolean(
|
|
172
|
-
localBridgeSurface?.enabled
|
|
173
|
-
&& localBridgeSurface.endpointConfigured
|
|
174
|
-
&& localBridgeEndpoint
|
|
175
|
-
&& localBridgeSurface.mode !== 'disabled',
|
|
176
|
-
);
|
|
177
|
-
const localBridgeLiveHealth = shouldProbeLocalBridge
|
|
178
|
-
? await probeLocalControllerHealth(localBridgeEndpoint)
|
|
179
|
-
: null;
|
|
180
|
-
const localBridgeEndpointReachable = localBridgeLiveHealth !== null;
|
|
181
|
-
const localBridgeExpectedSurface = shouldProbeLocalBridge
|
|
182
|
-
? localControllerDiagnosticMatchesRuntime(localBridgeLiveHealth, {
|
|
183
|
-
generation: localBridgeSurface?.generation,
|
|
184
|
-
})
|
|
185
|
-
: true;
|
|
186
|
-
const schedulerHeartbeatAgeMs = ageMs(scheduler.lastTickAt);
|
|
187
|
-
const dispatchHeartbeatAgeMs = ageMs(scheduler.lastDispatchAt);
|
|
188
|
-
const localBridgeObservation = {
|
|
189
|
-
enabled: localBridgeSurface?.enabled ?? false,
|
|
190
|
-
requiredForReadiness: localBridgeSurface?.requiredForReadiness ?? false,
|
|
191
|
-
mode: localBridgeSurface?.mode ?? ('disabled' as const),
|
|
192
|
-
endpoint: localBridgeEndpoint,
|
|
193
|
-
endpointReachable: shouldProbeLocalBridge ? localBridgeEndpointReachable : true,
|
|
194
|
-
expectedSurface: localBridgeExpectedSurface,
|
|
195
|
-
processAlive: localBridgeSurface?.processRunning,
|
|
196
|
-
runtimeStateFresh: localBridgeSurface?.source === 'service-runtime'
|
|
197
|
-
|| localBridgeSurface?.source === 'repo-runtime',
|
|
198
|
-
error: localBridgeSurface?.error,
|
|
199
|
-
};
|
|
200
|
-
const runtimeHealth = evaluateRuntimeHealth({
|
|
201
|
-
daemon: {
|
|
202
|
-
status: daemon.status,
|
|
203
|
-
error: daemon.error,
|
|
204
|
-
// Scheduler ticks are emitted by the Canonical Forge Runtime process and provide
|
|
205
|
-
// its continuously refreshed heartbeat without introducing a second timer.
|
|
206
|
-
heartbeatAgeMs: schedulerHeartbeatAgeMs,
|
|
207
|
-
},
|
|
208
|
-
scheduler: {
|
|
209
|
-
status: daemon.degraded ? 'degraded' : daemon.status,
|
|
210
|
-
heartbeatAgeMs: schedulerHeartbeatAgeMs,
|
|
211
|
-
dispatchHeartbeatAgeMs,
|
|
212
|
-
},
|
|
213
|
-
workers: {
|
|
214
|
-
queueDepth: projection?.queueDepth,
|
|
215
|
-
runningWorkers: projection?.runningWorkers,
|
|
216
|
-
activeLeases: projection?.activeLeases,
|
|
217
|
-
activeAttentionCount: projection?.currentAttention.length,
|
|
218
|
-
},
|
|
219
|
-
projection: projectionSnapshot ? projectionObservation(projectionSnapshot, projectionReconciliation) : {
|
|
220
|
-
readable: true,
|
|
221
|
-
persisted: true,
|
|
222
|
-
},
|
|
223
|
-
localBridge: localBridgeObservation,
|
|
224
|
-
runtimeStorage: { readable: true, ready: true },
|
|
225
|
-
...signals,
|
|
226
|
-
});
|
|
227
|
-
const operationalView: RuntimeOperationalView = buildRuntimeOperationalView({
|
|
228
|
-
health: runtimeHealth,
|
|
229
|
-
handoffs: repository
|
|
230
|
-
? listHandoffItems({ controllerHome: ctx.controllerHome, repoId: repository.repoId, status: 'all', limit: 100 })
|
|
231
|
-
: [],
|
|
232
|
-
jobs: repository ? listExecutionJobs(ctx.controllerHome, repository.repoId, 100) : [],
|
|
233
|
-
});
|
|
234
|
-
const reasons: Array<{ code: string; message: string }> = runtimeHealth.activeBlockers.map((item) => ({
|
|
235
|
-
code: item.code === 'SCHEDULER_NOT_PROGRESSING'
|
|
236
|
-
? 'DISPATCH_LOOP_STALLED'
|
|
237
|
-
: item.code === 'LEASE_WITHOUT_WORKER' || item.code === 'WORKER_NOT_RUNNING'
|
|
238
|
-
? 'WORKER_NOT_RUNNING'
|
|
239
|
-
: item.code,
|
|
240
|
-
message: item.message,
|
|
241
|
-
}));
|
|
242
|
-
if (
|
|
243
|
-
reasons.some((item) => item.code === 'WORKER_NOT_RUNNING')
|
|
244
|
-
&& (dispatchHeartbeatAgeMs === undefined || dispatchHeartbeatAgeMs > RUNTIME_HEALTH_THRESHOLDS.queueProgressStaleMs)
|
|
245
|
-
) {
|
|
246
|
-
reasons.push({
|
|
247
|
-
code: 'QUEUE_NOT_PROGRESSING',
|
|
248
|
-
message: 'Queued Jobs have not received a recent dispatch heartbeat.',
|
|
249
|
-
});
|
|
250
|
-
}
|
|
251
|
-
const ready = runtimeHealth.ready;
|
|
252
|
-
return {
|
|
253
|
-
ready,
|
|
254
|
-
state: ready ? runtimeHealth.state === 'healthy' ? 'ready' as const : 'degraded' as const : daemon.status === 'ready' ? 'degraded' as const : 'not_ready' as const,
|
|
255
|
-
reasons,
|
|
256
|
-
warnings: runtimeHealth.warnings.map((item) => ({ code: item.code, message: item.message })),
|
|
257
|
-
health: runtimeHealth,
|
|
258
|
-
operationalView,
|
|
259
|
-
daemon,
|
|
260
|
-
durableScheduler: {
|
|
261
|
-
status: runtimeHealth.components.scheduler.ready ? 'ready' : daemon.status === 'ready' ? 'degraded' : 'not_ready',
|
|
262
|
-
loopStartedAt: scheduler.loopStartedAt,
|
|
263
|
-
lastTickAt: scheduler.lastTickAt,
|
|
264
|
-
lastDispatchAt: scheduler.lastDispatchAt,
|
|
265
|
-
lastReconcileAt: scheduler.lastReconcileAt,
|
|
266
|
-
heartbeatAgeMs: schedulerHeartbeatAgeMs,
|
|
267
|
-
dispatchHeartbeatAgeMs,
|
|
268
|
-
},
|
|
269
|
-
workerLoop: {
|
|
270
|
-
status: projection?.runningWorkers ? 'running' : projection?.queueDepth ? 'idle' : 'ready',
|
|
271
|
-
queueDepth: projection?.queueDepth ?? 0,
|
|
272
|
-
runningWorkers: projection?.runningWorkers ?? 0,
|
|
273
|
-
activeLeases: projection?.activeLeases ?? 0,
|
|
274
|
-
activeAttentionCount: projection?.currentAttention.length ?? 0,
|
|
275
|
-
consuming: (projection?.queueDepth ?? 0) === 0 || (projection?.runningWorkers ?? 0) > 0,
|
|
276
|
-
},
|
|
277
|
-
localBridge: repository ? {
|
|
278
|
-
running: Boolean(localBridgeSurface?.enabled)
|
|
279
|
-
&& runtimeHealth.components.localBridge.ready
|
|
280
|
-
&& (!shouldProbeLocalBridge || (localBridgeEndpointReachable && localBridgeExpectedSurface)),
|
|
281
|
-
endpoint: localBridgeEndpoint,
|
|
282
|
-
error: localBridgeSurface?.error,
|
|
283
|
-
inferredPid: localBridgeSurface?.pid,
|
|
284
|
-
statusSource: localBridgeSurface?.source ?? 'none',
|
|
285
|
-
health: runtimeHealth.components.localBridge,
|
|
286
|
-
} : undefined,
|
|
287
|
-
projection,
|
|
288
|
-
projectionSnapshot,
|
|
289
|
-
taskLedger,
|
|
290
|
-
projectionReconciliation,
|
|
291
|
-
semantics: classifyRuntimeReadinessSemantics(runtimeHealth),
|
|
292
|
-
};
|
|
293
|
-
}
|
|
294
|
-
|
|
295
|
-
export function runtimeSourceSnapshotStatus(
|
|
296
|
-
active: RuntimeSourceIdentity | undefined,
|
|
297
|
-
currentRuntimeRoot?: string,
|
|
298
|
-
) {
|
|
299
|
-
const drift = evaluateActiveRuntimeSourceDrift(active, {
|
|
300
|
-
currentRuntimeRoot,
|
|
301
|
-
});
|
|
302
|
-
return {
|
|
303
|
-
current: drift.current,
|
|
304
|
-
restartRequired: drift.restartRequired,
|
|
305
|
-
reasons: drift.reasons,
|
|
306
|
-
code: drift.code,
|
|
307
|
-
};
|
|
308
|
-
}
|
|
309
|
-
|
|
310
128
|
export function repositoryExecutionReadiness(
|
|
311
129
|
repoRoot: string,
|
|
312
130
|
availableChecks: ReturnType<typeof listControllerChecks>,
|
|
@@ -406,21 +224,35 @@ export async function callStatusInboxAdapter(
|
|
|
406
224
|
ports: StatusInboxAdapterPorts,
|
|
407
225
|
): Promise<CallToolResult | undefined> {
|
|
408
226
|
if (name === 'rh_status') {
|
|
409
|
-
const repository =
|
|
227
|
+
const repository = selectedOptional(ctx, args);
|
|
410
228
|
const operation = String(args.operation ?? 'get');
|
|
411
229
|
if (!allowedFacadeOperations('rh_status').includes(operation)) {
|
|
412
230
|
return invalidFacadeOperation('rh_status', operation);
|
|
413
231
|
}
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
232
|
+
// Instance-level status stays available with zero (or several) registered
|
|
233
|
+
// repositories: only the repository-derived sections need a target.
|
|
234
|
+
const store = repository
|
|
235
|
+
? {
|
|
236
|
+
controllerHome: ctx.controllerHome,
|
|
237
|
+
repoId: repository.repoId,
|
|
238
|
+
revisionContains: (ancestorRevision: string, descendantRevision: string) =>
|
|
239
|
+
repositoryRevisionContains(repository.canonicalRoot, ancestorRevision, descendantRevision),
|
|
240
|
+
}
|
|
241
|
+
: undefined;
|
|
420
242
|
if (operation === 'repair') {
|
|
243
|
+
if (!repository) {
|
|
244
|
+
return result(buildFacadeResult({
|
|
245
|
+
status: 'blocked',
|
|
246
|
+
summary: 'REPOSITORY_CONTEXT_REQUIRED_FOR_REPAIR: rh_status repair needs an explicit repository target.',
|
|
247
|
+
data: { operation, repositoryContext: null },
|
|
248
|
+
}) as unknown as Record<string, unknown>, true);
|
|
249
|
+
}
|
|
421
250
|
return await ports.repair(ctx, repository, args);
|
|
422
251
|
}
|
|
423
|
-
const
|
|
252
|
+
const requestedDetailLevel = args.detail_level === 'detail' ? 'detail' : 'summary';
|
|
253
|
+
// Repository detail needs a repository; the instance-level summary remains
|
|
254
|
+
// available and reports the downgrade explicitly instead of failing.
|
|
255
|
+
const detailLevel = repository ? requestedDetailLevel : 'summary';
|
|
424
256
|
if (detailLevel === 'summary') {
|
|
425
257
|
const startedAt = performance.now();
|
|
426
258
|
let summaryTimingMark = startedAt;
|
|
@@ -435,8 +267,8 @@ export async function callStatusInboxAdapter(
|
|
|
435
267
|
// Summary answers only whether this repository can work now. Reuse one
|
|
436
268
|
// porcelain-v2 sample for branch/HEAD/dirty and avoid the full Git
|
|
437
269
|
// status/diff-stat, access-policy, and inventory construction paths.
|
|
438
|
-
const repositoryIdentity = cachedGitIdentity(repository.canonicalRoot);
|
|
439
|
-
const repositoryIdentityAgeMs = Math.max(0, Date.now() - repositoryIdentity.sampledAt);
|
|
270
|
+
const repositoryIdentity = repository ? cachedGitIdentity(repository.canonicalRoot) : undefined;
|
|
271
|
+
const repositoryIdentityAgeMs = repositoryIdentity ? Math.max(0, Date.now() - repositoryIdentity.sampledAt) : undefined;
|
|
440
272
|
markSummaryPhase('git');
|
|
441
273
|
const runtimeGeneration = readRuntimeGeneration(ctx.controllerHome);
|
|
442
274
|
const runtimeSource = runtimeSourceSnapshotStatus(
|
|
@@ -457,29 +289,39 @@ export async function callStatusInboxAdapter(
|
|
|
457
289
|
: 'RUNTIME_SOURCE_SNAPSHOT_STALE');
|
|
458
290
|
const runtimeReadiness = observation.snapshot?.readiness;
|
|
459
291
|
const releaseDiagnostic = runtimeReadiness?.diagnostics.releaseCoherence;
|
|
460
|
-
const activeWorkProjection =
|
|
292
|
+
const activeWorkProjection = repository && store
|
|
293
|
+
? readActiveWorkCandidates({ ...store, limit: 3 })
|
|
294
|
+
: { contracts: [], invalid: [] };
|
|
461
295
|
const activeWorkSnapshot = activeWorkProjection.contracts.map((entry) => ({
|
|
462
296
|
workId: entry.workId,
|
|
463
|
-
|
|
464
|
-
mode: entry.mode,
|
|
297
|
+
state: entry.semanticState,
|
|
465
298
|
objective: entry.objective.slice(0, 160),
|
|
466
299
|
semantics: buildWorkContinuationSnapshot(entry).semantics,
|
|
467
300
|
nextSafeAction: buildWorkContinuationSnapshot(entry).nextSafeAction,
|
|
468
301
|
}));
|
|
469
|
-
|
|
470
|
-
|
|
302
|
+
// Plans are authored semantic context: without a repository target the
|
|
303
|
+
// instance-level semantic scope carries them.
|
|
304
|
+
const activePlanSnapshot = (repository && store
|
|
305
|
+
? listPlanContracts({ ...store, status: 'active', limit: 3 })
|
|
306
|
+
: listPlanContracts({ controllerHome: ctx.controllerHome, scopeKey: SEMANTIC_SCOPE_KEY, status: 'active', limit: 3 })
|
|
307
|
+
).map(summarizePlanContract);
|
|
308
|
+
const pendingHandoffAttention = store ? listHandoffAttentionItems(store, 100) : [];
|
|
471
309
|
const pendingHandoffSnapshot = pendingHandoffAttention.slice(0, 4);
|
|
472
310
|
const pendingHandoffCount = pendingHandoffAttention.length;
|
|
473
311
|
markSummaryPhase('controller_state');
|
|
474
|
-
const preferredFacadeTools = ['rh_access', 'rh_status', 'rh_inbox', 'rh_context', 'rh_work'] as const;
|
|
312
|
+
const preferredFacadeTools = ['rh_access', 'rh_status', 'rh_inbox', 'rh_context', 'rh_work', 'capability_execute'] as const;
|
|
475
313
|
const facade = buildFacadeResult({
|
|
476
314
|
status: ready ? 'ok' : 'blocked',
|
|
477
315
|
summary: ready ? 'Controller and MCP tool surface are ready for bounded work.' : 'Controller or MCP tool surface needs attention before work.',
|
|
478
316
|
data: {
|
|
479
317
|
operation,
|
|
480
|
-
repoId: repository.repoId,
|
|
318
|
+
...(repository ? { repoId: repository.repoId } : {}),
|
|
319
|
+
/** Null means this answer is ForgeInstance-scoped, not repository-scoped. */
|
|
320
|
+
repositoryContext: repository ? { repoId: repository.repoId, checkoutId: repository.activeCheckoutId } : null,
|
|
321
|
+
requestedDetailLevel,
|
|
481
322
|
readiness: {
|
|
482
323
|
ready,
|
|
324
|
+
readyFor: 'bounded_execution',
|
|
483
325
|
reasonCodes: [...new Set(reasonCodes)],
|
|
484
326
|
diagnostics: {
|
|
485
327
|
runtime: { ready: observation.ready },
|
|
@@ -503,6 +345,11 @@ export async function callStatusInboxAdapter(
|
|
|
503
345
|
},
|
|
504
346
|
semantics: {
|
|
505
347
|
executionReady: observation.ready,
|
|
348
|
+
// Summary is intentionally the cheap Runtime snapshot path. It
|
|
349
|
+
// reports bounded execution readiness without pretending that the
|
|
350
|
+
// full scheduler/worker diagnostics for unattended continuation ran.
|
|
351
|
+
autonomousContinuationReady: null,
|
|
352
|
+
autonomousContinuationBlockers: null,
|
|
506
353
|
maintenanceHealthy: null,
|
|
507
354
|
maintenanceCandidateCount: 0,
|
|
508
355
|
releaseReady: releaseDiagnostic?.outcome === 'pass',
|
|
@@ -513,21 +360,23 @@ export async function callStatusInboxAdapter(
|
|
|
513
360
|
},
|
|
514
361
|
observedAt: observation.observedAt,
|
|
515
362
|
},
|
|
516
|
-
repositoryState:
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
363
|
+
repositoryState: repositoryIdentity
|
|
364
|
+
? {
|
|
365
|
+
branch: repositoryIdentity.branch,
|
|
366
|
+
head: repositoryIdentity.head,
|
|
367
|
+
dirty: repositoryIdentity.dirty,
|
|
368
|
+
observedAt: new Date(repositoryIdentity.sampledAt).toISOString(),
|
|
369
|
+
observationAgeMs: repositoryIdentityAgeMs,
|
|
370
|
+
observationMaxAgeMs: GIT_IDENTITY_SAMPLE_TTL_MS,
|
|
371
|
+
observationPolicy: 'bounded_sample_with_mutation_invalidation',
|
|
372
|
+
sourceSnapshotAgeMs: runtimeGeneration?.source.observedAt
|
|
373
|
+
? Math.max(0, Date.now() - Date.parse(runtimeGeneration.source.observedAt))
|
|
374
|
+
: undefined,
|
|
375
|
+
sourceSnapshotStale,
|
|
376
|
+
sourceSnapshotReasons: runtimeSource.reasons,
|
|
377
|
+
runtimeSourceDirty: runtimeSource.current?.dirty === true,
|
|
378
|
+
}
|
|
379
|
+
: null,
|
|
531
380
|
toolArchitecture: {
|
|
532
381
|
facadeTools: [...preferredFacadeTools],
|
|
533
382
|
domainSchemaLoading: 'status_summary_runtime_snapshot',
|
|
@@ -581,6 +430,15 @@ export async function callStatusInboxAdapter(
|
|
|
581
430
|
(payload.responseMeta as { structuredPayloadBytes: number }).structuredPayloadBytes = Buffer.byteLength(JSON.stringify(payload), 'utf8');
|
|
582
431
|
return result(payload, facade.status !== 'ok');
|
|
583
432
|
}
|
|
433
|
+
// Detail is repository-derived; without a repository target the requested
|
|
434
|
+
// detail level was already downgraded to the instance-level summary above.
|
|
435
|
+
if (!repository || !store) {
|
|
436
|
+
return result(buildFacadeResult({
|
|
437
|
+
status: 'blocked',
|
|
438
|
+
summary: 'REPOSITORY_CONTEXT_REQUIRED_FOR_DETAIL: rh_status detail needs an explicit repository target.',
|
|
439
|
+
data: { operation, repositoryContext: null },
|
|
440
|
+
}) as unknown as Record<string, unknown>, true);
|
|
441
|
+
}
|
|
584
442
|
const detailTimingStartedAt = performance.now();
|
|
585
443
|
let detailTimingMark = detailTimingStartedAt;
|
|
586
444
|
const detailPhaseTimingsMs: Record<string, number> = {};
|
|
@@ -590,6 +448,7 @@ export async function callStatusInboxAdapter(
|
|
|
590
448
|
detailTimingMark = now;
|
|
591
449
|
};
|
|
592
450
|
const readiness = await controllerReadinessEvidence(ctx, repository);
|
|
451
|
+
const runtimeObservation = observeRuntimeStatus(ctx.controllerHome);
|
|
593
452
|
markDetailPhase('readiness');
|
|
594
453
|
const liveGit = gitSnapshot(repository.canonicalRoot);
|
|
595
454
|
markDetailPhase('git');
|
|
@@ -598,7 +457,7 @@ export async function callStatusInboxAdapter(
|
|
|
598
457
|
const runtimeSource = runtimeSourceSnapshotStatus(readiness.daemon.source, ctx.runtimeSourceRoot);
|
|
599
458
|
const sourceSnapshotStale = runtimeSource.restartRequired;
|
|
600
459
|
const exposure = controllerExposureSnapshot(ctx);
|
|
601
|
-
const localRegisteredToolNames =
|
|
460
|
+
const localRegisteredToolNames = [...exposure.actualToolNames].sort();
|
|
602
461
|
markDetailPhase('tool_surface');
|
|
603
462
|
const toolSurfaceReady = exposure.ready && exposure.missingToolNames.length === 0;
|
|
604
463
|
// Ordinary interactive execution depends on the execution axis only.
|
|
@@ -647,8 +506,77 @@ export async function callStatusInboxAdapter(
|
|
|
647
506
|
});
|
|
648
507
|
}
|
|
649
508
|
const toolSurfaceComputed = exposure.expectedToolNames.length > 0 || exposure.actualToolNames.length > 0 || toolSurfaceReady;
|
|
509
|
+
const activeReleaseAuthority = readRuntimeReleaseAuthority(ctx.controllerHome);
|
|
510
|
+
let autonomousContinuationProof: Awaited<ReturnType<typeof getWorkflowSupervisorContinuationProof>>;
|
|
511
|
+
let autonomousContinuationProofObservation: 'proven' | 'missing' | 'unavailable' = 'missing';
|
|
512
|
+
if (activeReleaseAuthority?.committedAt) {
|
|
513
|
+
try {
|
|
514
|
+
autonomousContinuationProof = await getWorkflowSupervisorContinuationProof(
|
|
515
|
+
resolveWorkflowSupervisorForgeHome(ctx.controllerHome),
|
|
516
|
+
{
|
|
517
|
+
repoId: repository.repoId,
|
|
518
|
+
activeReleaseId: activeReleaseAuthority.active.releaseId,
|
|
519
|
+
notBefore: activeReleaseAuthority.committedAt,
|
|
520
|
+
},
|
|
521
|
+
);
|
|
522
|
+
autonomousContinuationProofObservation = autonomousContinuationProof ? 'proven' : 'missing';
|
|
523
|
+
} catch {
|
|
524
|
+
autonomousContinuationProofObservation = 'unavailable';
|
|
525
|
+
}
|
|
526
|
+
}
|
|
527
|
+
let autonomousContinuationConsumerStatus: Awaited<ReturnType<typeof getWorkflowSupervisorConsumerStatus>> | undefined;
|
|
528
|
+
let autonomousContinuationConsumerObservation: 'observed' | 'unavailable' = 'unavailable';
|
|
529
|
+
try {
|
|
530
|
+
autonomousContinuationConsumerStatus = await getWorkflowSupervisorConsumerStatus(
|
|
531
|
+
resolveWorkflowSupervisorForgeHome(ctx.controllerHome),
|
|
532
|
+
);
|
|
533
|
+
autonomousContinuationConsumerObservation = 'observed';
|
|
534
|
+
} catch {
|
|
535
|
+
autonomousContinuationConsumerObservation = 'unavailable';
|
|
536
|
+
}
|
|
537
|
+
const dueConsumerFailure = Boolean(
|
|
538
|
+
autonomousContinuationConsumerStatus?.dueCommand
|
|
539
|
+
&& autonomousContinuationConsumerStatus.lastFailure
|
|
540
|
+
&& (!autonomousContinuationConsumerStatus.lastFailure.effectId
|
|
541
|
+
|| autonomousContinuationConsumerStatus.lastFailure.effectId === autonomousContinuationConsumerStatus.dueCommand.effectId),
|
|
542
|
+
);
|
|
543
|
+
const autonomousContinuationConsumerReady = autonomousContinuationConsumerObservation === 'observed'
|
|
544
|
+
&& autonomousContinuationConsumerStatus?.enabled === true
|
|
545
|
+
&& autonomousContinuationConsumerStatus.running === true
|
|
546
|
+
&& autonomousContinuationConsumerStatus.lastTickStartedAt !== undefined
|
|
547
|
+
&& autonomousContinuationConsumerStatus.stalled === false
|
|
548
|
+
&& !dueConsumerFailure;
|
|
549
|
+
const autonomousContinuationReady = readiness.ready
|
|
550
|
+
&& toolSurfaceReady
|
|
551
|
+
&& !sourceSnapshotStale
|
|
552
|
+
&& autonomousContinuationProofObservation === 'proven'
|
|
553
|
+
&& autonomousContinuationConsumerReady;
|
|
554
|
+
const autonomousContinuationBlockers = [...new Set([
|
|
555
|
+
...readinessReasons
|
|
556
|
+
.map((reason) => reason.code)
|
|
557
|
+
.filter((code): code is string => typeof code === 'string' && code.length > 0),
|
|
558
|
+
...(autonomousContinuationProofObservation === 'proven'
|
|
559
|
+
? []
|
|
560
|
+
: [autonomousContinuationProofObservation === 'unavailable'
|
|
561
|
+
? 'AUTONOMOUS_CONTINUATION_LIVE_PROOF_UNAVAILABLE'
|
|
562
|
+
: 'AUTONOMOUS_CONTINUATION_LIVE_PROOF_MISSING']),
|
|
563
|
+
...(autonomousContinuationConsumerObservation === 'unavailable'
|
|
564
|
+
? ['AUTONOMOUS_CONTINUATION_CONSUMER_STATUS_UNAVAILABLE']
|
|
565
|
+
: autonomousContinuationConsumerStatus?.enabled !== true
|
|
566
|
+
? ['AUTONOMOUS_CONTINUATION_CONSUMER_DISABLED']
|
|
567
|
+
: autonomousContinuationConsumerStatus.running !== true
|
|
568
|
+
? ['AUTONOMOUS_CONTINUATION_CONSUMER_NOT_RUNNING']
|
|
569
|
+
: autonomousContinuationConsumerStatus.lastTickStartedAt === undefined
|
|
570
|
+
? ['AUTONOMOUS_CONTINUATION_CONSUMER_NOT_OBSERVED']
|
|
571
|
+
: autonomousContinuationConsumerStatus.stalled
|
|
572
|
+
? ['AUTONOMOUS_CONTINUATION_CONSUMER_STALLED']
|
|
573
|
+
: dueConsumerFailure
|
|
574
|
+
? ['AUTONOMOUS_CONTINUATION_CONSUMER_DEGRADED']
|
|
575
|
+
: []),
|
|
576
|
+
])];
|
|
650
577
|
const readinessWithToolSurface = {
|
|
651
578
|
ready: effectiveReady,
|
|
579
|
+
readyFor: 'bounded_execution' as const,
|
|
652
580
|
reasonCodes: [...new Set(
|
|
653
581
|
readinessReasons
|
|
654
582
|
.map((reason) => reason.code)
|
|
@@ -656,7 +584,7 @@ export async function callStatusInboxAdapter(
|
|
|
656
584
|
)],
|
|
657
585
|
diagnostics: {
|
|
658
586
|
runtime: {
|
|
659
|
-
ready:
|
|
587
|
+
ready: runtimeObservation.ready,
|
|
660
588
|
},
|
|
661
589
|
toolSurface: {
|
|
662
590
|
ready: toolSurfaceReady,
|
|
@@ -672,6 +600,22 @@ export async function callStatusInboxAdapter(
|
|
|
672
600
|
},
|
|
673
601
|
semantics: {
|
|
674
602
|
executionReady,
|
|
603
|
+
// Runtime/tool health is necessary but not sufficient. Thin acceptance
|
|
604
|
+
// requires a fresh exact-active-release Supervisor ledger proof of
|
|
605
|
+
// CONTINUE -> CONTINUE -> DONE spanning at least one Runtime reconnect.
|
|
606
|
+
autonomousContinuationReady,
|
|
607
|
+
autonomousContinuationBlockers,
|
|
608
|
+
autonomousContinuationConsumer: {
|
|
609
|
+
observation: autonomousContinuationConsumerObservation,
|
|
610
|
+
...(autonomousContinuationConsumerStatus ? { status: autonomousContinuationConsumerStatus } : {}),
|
|
611
|
+
},
|
|
612
|
+
autonomousContinuationProof: {
|
|
613
|
+
observation: autonomousContinuationProofObservation,
|
|
614
|
+
activeReleaseId: activeReleaseAuthority?.active.releaseId,
|
|
615
|
+
activeReleaseAuthorityRevision: activeReleaseAuthority?.revision,
|
|
616
|
+
activeReleaseCommittedAt: activeReleaseAuthority?.committedAt,
|
|
617
|
+
...(autonomousContinuationProof ? { proof: autonomousContinuationProof } : {}),
|
|
618
|
+
},
|
|
675
619
|
maintenanceHealthy,
|
|
676
620
|
maintenanceCandidateCount,
|
|
677
621
|
maintenanceObservation,
|
|
@@ -702,6 +646,39 @@ export async function callStatusInboxAdapter(
|
|
|
702
646
|
const pendingHandoffCount = pendingHandoffAttention.length;
|
|
703
647
|
const activeWorkProjection = readActiveWorkCandidates({ ...store, limit: 200 });
|
|
704
648
|
const activeContracts = activeWorkProjection.contracts;
|
|
649
|
+
// Reuse the exact WorkHandle and semantic Work authorities consulted by
|
|
650
|
+
// delivery. This is a read-only diagnosis, never a delivery admission gate.
|
|
651
|
+
const receivingOwners = detailLevel === 'detail'
|
|
652
|
+
? listWorkHandles(ctx.controllerHome, repository.repoId)
|
|
653
|
+
.filter((handle) => {
|
|
654
|
+
if (handle.checkoutId !== repository.activeCheckoutId
|
|
655
|
+
|| handle.branch !== liveGit.branch
|
|
656
|
+
|| handle.state === 'cleaned' || handle.state === 'failed') return false;
|
|
657
|
+
const contract = getWorkContract(store, handle.workContractId ?? handle.workId);
|
|
658
|
+
return Boolean(contract && semanticWorkState(contract) === 'open');
|
|
659
|
+
})
|
|
660
|
+
.sort((left, right) => left.workId.localeCompare(right.workId))
|
|
661
|
+
: [];
|
|
662
|
+
const headDriftedOwners = receivingOwners.filter((handle) =>
|
|
663
|
+
Boolean(handle.expectedHead && handle.expectedHead !== liveGit.head));
|
|
664
|
+
const repositoryDeliveryBlockers = [
|
|
665
|
+
...(receivingOwners.length > 1 ? ['WORK_CANONICAL_MUTATION_OWNERSHIP_AMBIGUOUS']
|
|
666
|
+
: receivingOwners.length ? ['WORK_DELIVERY_TARGET_WORK_ACTIVE'] : []),
|
|
667
|
+
...(headDriftedOwners.length ? ['WORK_HANDLE_HEAD_CHANGED'] : []),
|
|
668
|
+
...(liveGit.dirty ? ['WORK_DELIVERY_TARGET_DIRTY'] : []),
|
|
669
|
+
];
|
|
670
|
+
const repositoryDeliveryNextSafeAction =
|
|
671
|
+
receivingOwners.length > 1
|
|
672
|
+
? 'Multiple open WorkHandles claim this checkout. Resolve canonical ownership before any Git mutation; do not guess or bypass a writer.'
|
|
673
|
+
: headDriftedOwners.length && liveGit.dirty
|
|
674
|
+
? 'Owning Work: review the uncommitted paths against successor commits, converge its edits, then use explicit work_prepare successor adoption only if ancestry and path disjointness are proven.'
|
|
675
|
+
: headDriftedOwners.length
|
|
676
|
+
? 'Owning Work: verify exact HEAD ancestry and use work_prepare with expected_previous_head/adopt_candidate_head; never silently rebase or reset.'
|
|
677
|
+
: liveGit.dirty
|
|
678
|
+
? 'Owning writer: review and verify the existing dirty paths, then commit through its authorized Work before integrating another candidate; never auto-stash or reset.'
|
|
679
|
+
: receivingOwners.length
|
|
680
|
+
? 'The receiving Work owns this checkout. Integrate reviewed source commits using its own authorized Git path, then reconcile each source Work through canonical deliver_work.'
|
|
681
|
+
: 'For a validated source Work, use canonical repository.git.deliver_work; this read-only projection does not check live mutation leases or grant integration authority.';
|
|
705
682
|
markDetailPhase('work_state');
|
|
706
683
|
const activePrimaryWork = activeContracts.filter((contract) => (contract.lifecycleRole ?? 'primary') === 'primary');
|
|
707
684
|
const activeExecutionChildren = activeContracts.filter((contract) => contract.lifecycleRole === 'execution_child');
|
|
@@ -712,14 +689,62 @@ export async function callStatusInboxAdapter(
|
|
|
712
689
|
.map((processId) => getProcessRecord(ctx.controllerHome, repository.repoId, processId))
|
|
713
690
|
.filter((process): process is NonNullable<typeof process> => Boolean(process && isManagedProcessActive(process)));
|
|
714
691
|
markDetailPhase('process_state');
|
|
715
|
-
const
|
|
716
|
-
const
|
|
717
|
-
|
|
692
|
+
const activePrimaryWorkIds = new Set(activePrimaryWork.map((contract) => contract.workId));
|
|
693
|
+
const activeProcessWorkIds = new Set(
|
|
694
|
+
activeProcessRecords
|
|
695
|
+
.map((process) => process.workId)
|
|
696
|
+
.filter((workId): workId is string => Boolean(workId && activePrimaryWorkIds.has(workId))),
|
|
697
|
+
);
|
|
698
|
+
const activeControllerWorkIds = new Set(
|
|
699
|
+
activePrimaryWork
|
|
700
|
+
.filter((contract) => Boolean(getControllerSession({ controllerHome: ctx.controllerHome, repoId: repository.repoId }, contract.workId)))
|
|
701
|
+
.map((contract) => contract.workId),
|
|
702
|
+
);
|
|
703
|
+
const runningPrimaryWorkIds = new Set([...activeProcessWorkIds, ...activeControllerWorkIds]);
|
|
718
704
|
markDetailPhase('controller_sessions');
|
|
719
|
-
|
|
705
|
+
|
|
706
|
+
const waitingForUserPrimaryWorkIds = new Set(
|
|
707
|
+
pendingHandoffAttention
|
|
708
|
+
.map((item) => item.workId?.trim())
|
|
709
|
+
.filter((workId): workId is string => Boolean(workId && activePrimaryWorkIds.has(workId))),
|
|
710
|
+
);
|
|
711
|
+
const schedules = listSchedules(ctx.controllerHome, repository.repoId);
|
|
712
|
+
const activeOccurrenceScheduleIds = new Set(
|
|
713
|
+
listActiveOccurrences(ctx.controllerHome, repository.repoId).map((occurrence) => occurrence.scheduleId),
|
|
714
|
+
);
|
|
715
|
+
const scheduledPrimaryWorkIds = new Set<string>();
|
|
716
|
+
for (const schedule of schedules) {
|
|
717
|
+
if (!schedule.enabled && !activeOccurrenceScheduleIds.has(schedule.scheduleId)) continue;
|
|
718
|
+
for (const workId of activePrimaryWorkIds) {
|
|
719
|
+
if (scheduleOwnsWork(schedule, workId)) scheduledPrimaryWorkIds.add(workId);
|
|
720
|
+
}
|
|
721
|
+
}
|
|
722
|
+
const primaryWorkActivities = activePrimaryWork.map((contract) => ({
|
|
723
|
+
workId: contract.workId,
|
|
724
|
+
activity: primaryWorkRuntimeActivity({
|
|
725
|
+
running: runningPrimaryWorkIds.has(contract.workId),
|
|
726
|
+
waitingForUser: waitingForUserPrimaryWorkIds.has(contract.workId),
|
|
727
|
+
scheduled: scheduledPrimaryWorkIds.has(contract.workId),
|
|
728
|
+
needsReconciliation: buildWorkContinuationSnapshot(contract).reconciliationRequired,
|
|
729
|
+
}),
|
|
730
|
+
}));
|
|
731
|
+
const primaryWorkActivityCounts: Record<PrimaryWorkRuntimeActivity, number> = {
|
|
732
|
+
running: 0,
|
|
733
|
+
waiting_for_user: 0,
|
|
734
|
+
scheduled: 0,
|
|
735
|
+
recoverable: 0,
|
|
736
|
+
needs_reconciliation: 0,
|
|
737
|
+
};
|
|
738
|
+
for (const projection of primaryWorkActivities) primaryWorkActivityCounts[projection.activity] += 1;
|
|
739
|
+
markDetailPhase('work_activity');
|
|
740
|
+
const preferredFacadeTools = ['rh_access', 'rh_status', 'rh_inbox', 'rh_context', 'rh_work', 'capability_execute'] as const;
|
|
720
741
|
const facade = buildFacadeResult({
|
|
721
742
|
status: effectiveReady ? 'ok' : 'blocked',
|
|
722
|
-
summary: effectiveReady
|
|
743
|
+
summary: effectiveReady
|
|
744
|
+
? autonomousContinuationReady
|
|
745
|
+
? 'Controller and MCP tool surface are ready for bounded work and autonomous continuation.'
|
|
746
|
+
: 'Controller and MCP tool surface are ready for bounded work; autonomous continuation needs attention.'
|
|
747
|
+
: 'Controller or MCP tool surface needs attention before bounded work.',
|
|
723
748
|
data: {
|
|
724
749
|
operation,
|
|
725
750
|
repoId: repository.repoId,
|
|
@@ -750,9 +775,28 @@ export async function callStatusInboxAdapter(
|
|
|
750
775
|
activePrimaryWorkCount: activePrimaryWork.length,
|
|
751
776
|
activeExecutionChildCount: activeExecutionChildren.length,
|
|
752
777
|
activeProcessCount: activeProcessRecords.length,
|
|
753
|
-
|
|
754
|
-
|
|
778
|
+
primaryWorkActivityCounts,
|
|
779
|
+
primaryWorkActivities,
|
|
755
780
|
activeContractCount: activeContracts.length,
|
|
781
|
+
...(detailLevel === 'detail' ? { repositoryDelivery: {
|
|
782
|
+
observation: 'work_handle_and_git_snapshot' as const,
|
|
783
|
+
diagnosticOnly: true,
|
|
784
|
+
checkoutId: repository.activeCheckoutId,
|
|
785
|
+
branch: liveGit.branch,
|
|
786
|
+
head: liveGit.head,
|
|
787
|
+
dirty: liveGit.dirty,
|
|
788
|
+
ownerCount: receivingOwners.length,
|
|
789
|
+
ownersTruncated: receivingOwners.length > 5,
|
|
790
|
+
owners: receivingOwners.slice(0, 5).map((handle) => ({
|
|
791
|
+
workId: handle.workId,
|
|
792
|
+
state: handle.state,
|
|
793
|
+
expectedHead: handle.expectedHead ?? null,
|
|
794
|
+
headDrift: Boolean(handle.expectedHead && handle.expectedHead !== liveGit.head),
|
|
795
|
+
})),
|
|
796
|
+
blockers: repositoryDeliveryBlockers,
|
|
797
|
+
nextSafeAction: repositoryDeliveryNextSafeAction,
|
|
798
|
+
limitations: 'Live leases, source validation, conflict preview and target CAS remain canonical delivery-time checks.',
|
|
799
|
+
} } : {}),
|
|
756
800
|
invalidActiveContractCount: activeWorkProjection.invalid.length,
|
|
757
801
|
invalidActiveContracts: activeWorkProjection.invalid.slice(0, 10).map(summarizeInvalidActiveWorkCandidate),
|
|
758
802
|
// Summary keeps the stable facade surface only; detail expands to the full registered schema.
|
|
@@ -792,10 +836,118 @@ export async function callStatusInboxAdapter(
|
|
|
792
836
|
return undefined;
|
|
793
837
|
}
|
|
794
838
|
|
|
839
|
+
function summarizeUserRequest(request: UserRequest) {
|
|
840
|
+
return {
|
|
841
|
+
requestId: request.requestId,
|
|
842
|
+
kind: request.kind,
|
|
843
|
+
title: request.title,
|
|
844
|
+
summary: request.summary,
|
|
845
|
+
actionRequired: request.actionRequired,
|
|
846
|
+
status: request.status,
|
|
847
|
+
targetScope: request.targetScope,
|
|
848
|
+
resolution: request.resolution,
|
|
849
|
+
updatedAt: request.updatedAt,
|
|
850
|
+
};
|
|
851
|
+
}
|
|
852
|
+
|
|
853
|
+
// `request_id` is Process Runtime idempotency/correlation only. UserRequest
|
|
854
|
+
// selection stays on `handoff_id` so retry identity can never change Inbox semantics.
|
|
855
|
+
export function findCanonicalUserRequest(controllerHome: string, args: Record<string, unknown>): UserRequest | undefined {
|
|
856
|
+
const handoffId = typeof args.handoff_id === 'string' ? args.handoff_id.trim() : '';
|
|
857
|
+
if (!handoffId) return undefined;
|
|
858
|
+
return getUserRequest(controllerHome, handoffId)
|
|
859
|
+
?? listUserRequests(controllerHome, 'all').find((request) => request.presentation?.legacyHandoffId === handoffId);
|
|
860
|
+
}
|
|
861
|
+
|
|
862
|
+
export function shouldUseCanonicalUserRequestInbox(
|
|
863
|
+
repositoryRepoId: string | undefined,
|
|
864
|
+
operation: string,
|
|
865
|
+
request: UserRequest | undefined,
|
|
866
|
+
): boolean {
|
|
867
|
+
if (!repositoryRepoId) return true;
|
|
868
|
+
if (operation === 'list' || operation === 'create') return false;
|
|
869
|
+
return Boolean(request && !request.targetScope?.repoId?.trim());
|
|
870
|
+
}
|
|
871
|
+
|
|
872
|
+
function callCanonicalUserRequestInbox(ctx: MultiRepositoryMcpToolContext, args: Record<string, unknown>, operation: string): CallToolResult {
|
|
873
|
+
const limit = Math.max(1, Math.min(Math.trunc(typeof args.limit === 'number' ? args.limit : 50), 100));
|
|
874
|
+
if (operation === 'list') {
|
|
875
|
+
const items = listUserRequests(ctx.controllerHome, 'pending').slice(0, limit);
|
|
876
|
+
return result(buildFacadeResult({
|
|
877
|
+
summary: items.length ? `${items.length} pending UserRequest item(s).` : 'No pending UserRequest items.',
|
|
878
|
+
data: { items: items.map(summarizeUserRequest) },
|
|
879
|
+
suggestedNextActions: items.slice(0, 1).map((item) => ({ label: `Read ${item.requestId}`, tool: 'rh_inbox', operation: 'get', payload: { handoff_id: item.requestId }, risk: 'readonly' as const })),
|
|
880
|
+
}) as unknown as Record<string, unknown>);
|
|
881
|
+
}
|
|
882
|
+
if (operation === 'create') {
|
|
883
|
+
const title = typeof args.title === 'string' ? args.title.trim() : '';
|
|
884
|
+
const summary = typeof args.summary === 'string' ? args.summary.trim() : typeof args.reason === 'string' ? args.reason.trim() : '';
|
|
885
|
+
if (!title || !summary) throw new Error('USER_REQUEST_TITLE_SUMMARY_REQUIRED');
|
|
886
|
+
const workId = typeof args.work_id === 'string' ? args.work_id.trim() : '';
|
|
887
|
+
const explicitId = typeof args.handoff_id === 'string' ? args.handoff_id.trim() : '';
|
|
888
|
+
const actionRequired = (typeof args.action_required === 'string' ? args.action_required : 'product_decision') as 'login' | 'grant_permission' | 'confirm_destructive' | 'product_decision';
|
|
889
|
+
const kind = (typeof args.request_kind === 'string' ? args.request_kind : actionRequired === 'product_decision' ? 'user_decision_request' : 'user_action_request') as 'user_action_request' | 'user_decision_request';
|
|
890
|
+
const rootCauseKey = typeof args.root_cause_key === 'string' && args.root_cause_key.trim()
|
|
891
|
+
? args.root_cause_key.trim()
|
|
892
|
+
: `rh_inbox:${explicitId || workId || title}:${summary}`;
|
|
893
|
+
const item = recordUserRequest(ctx.controllerHome, {
|
|
894
|
+
...(explicitId ? { requestId: explicitId } : {}),
|
|
895
|
+
kind,
|
|
896
|
+
rootCauseKey,
|
|
897
|
+
title,
|
|
898
|
+
summary,
|
|
899
|
+
actionRequired,
|
|
900
|
+
...(workId ? { targetScope: { scopeKind: 'work', scopeId: workId, workId } } : {}),
|
|
901
|
+
presentation: {
|
|
902
|
+
...(typeof args.handoff_id === 'string' && args.handoff_id.trim() ? { legacyHandoffId: args.handoff_id.trim() } : {}),
|
|
903
|
+
...(typeof args.reason === 'string' ? { reason: args.reason } : {}),
|
|
904
|
+
...(typeof args.recommended_decision === 'string' ? { recommendedDecision: args.recommended_decision } : {}),
|
|
905
|
+
...(typeof args.recommended_prompt === 'string' ? { recommendedPrompt: args.recommended_prompt } : {}),
|
|
906
|
+
},
|
|
907
|
+
});
|
|
908
|
+
return result(buildFacadeResult({ summary: `Created UserRequest ${item.requestId}.`, data: { item: summarizeUserRequest(item) } }) as unknown as Record<string, unknown>);
|
|
909
|
+
}
|
|
910
|
+
const current = findCanonicalUserRequest(ctx.controllerHome, args);
|
|
911
|
+
if (operation === 'get') {
|
|
912
|
+
const facade = buildFacadeResult({
|
|
913
|
+
status: current ? 'ok' : 'not_found',
|
|
914
|
+
summary: current ? `UserRequest ${current.requestId}.` : 'UserRequest not found.',
|
|
915
|
+
data: { item: current ? summarizeUserRequest(current) : undefined },
|
|
916
|
+
suggestedNextActions: current?.status === 'pending' ? [{ label: 'Resolve request', tool: 'rh_inbox', operation: 'resolve', payload: { request_id: current.requestId }, risk: 'workspace_write' }] : [],
|
|
917
|
+
});
|
|
918
|
+
return result(facade as unknown as Record<string, unknown>, facade.status === 'not_found');
|
|
919
|
+
}
|
|
920
|
+
if (!current) throw new Error('USER_REQUEST_NOT_FOUND');
|
|
921
|
+
if (operation === 'ack' || operation === 'accept') {
|
|
922
|
+
return result(buildFacadeResult({
|
|
923
|
+
summary: `${operation === 'accept' ? 'Accepted' : 'Acknowledged'} UserRequest ${current.requestId}; semantic state remains pending until resolve/dismiss.`,
|
|
924
|
+
data: { item: summarizeUserRequest(current), compatibilityNoop: true },
|
|
925
|
+
}) as unknown as Record<string, unknown>);
|
|
926
|
+
}
|
|
927
|
+
if (operation === 'resolve' || operation === 'dismiss') {
|
|
928
|
+
const decision = operation === 'dismiss'
|
|
929
|
+
? (typeof args.decision === 'string' && args.decision.trim() ? args.decision.trim() : 'dismissed')
|
|
930
|
+
: (typeof args.decision === 'string' ? args.decision.trim() : '');
|
|
931
|
+
if (!decision) throw new Error('USER_REQUEST_DECISION_REQUIRED');
|
|
932
|
+
const resolved = resolveUserRequest(ctx.controllerHome, {
|
|
933
|
+
requestId: current.requestId,
|
|
934
|
+
decision,
|
|
935
|
+
resolvedBy: typeof args.resolver === 'string' && args.resolver.trim() ? args.resolver.trim() : (ctx.principalId?.trim() || 'mcp-user'),
|
|
936
|
+
});
|
|
937
|
+
return result(buildFacadeResult({ summary: `Resolved UserRequest ${resolved.requestId}.`, data: { item: summarizeUserRequest(resolved) } }) as unknown as Record<string, unknown>);
|
|
938
|
+
}
|
|
939
|
+
throw new Error(`USER_REQUEST_OPERATION_UNSUPPORTED:${operation}`);
|
|
940
|
+
}
|
|
941
|
+
|
|
795
942
|
async function callInboxAdapter(ctx: MultiRepositoryMcpToolContext, args: Record<string, unknown>): Promise<CallToolResult> {
|
|
796
|
-
const repository =
|
|
943
|
+
const repository = selectedOptional(ctx, args);
|
|
797
944
|
const operation = String(args.operation ?? 'list');
|
|
798
945
|
if (!allowedFacadeOperations('rh_inbox').includes(operation)) return invalidFacadeOperation('rh_inbox', operation);
|
|
946
|
+
const canonicalRequest = findCanonicalUserRequest(ctx.controllerHome, args);
|
|
947
|
+
if (shouldUseCanonicalUserRequestInbox(repository?.repoId, operation, canonicalRequest)) {
|
|
948
|
+
return callCanonicalUserRequestInbox(ctx, args, operation);
|
|
949
|
+
}
|
|
950
|
+
if (!repository) throw new Error('REPOSITORY_CONTEXT_REQUIRED_FOR_HANDOFF');
|
|
799
951
|
const app = await runHandoffInboxApplication({
|
|
800
952
|
operation: operation as 'get' | 'list' | 'ack' | 'accept' | 'resolve' | 'dismiss' | 'create',
|
|
801
953
|
store: { controllerHome: ctx.controllerHome, repoId: repository.repoId },
|
|
@@ -814,13 +966,7 @@ async function callInboxAdapter(ctx: MultiRepositoryMcpToolContext, args: Record
|
|
|
814
966
|
resolver: typeof args.resolver === 'string' ? args.resolver : undefined,
|
|
815
967
|
controllerIdentity: { principalId: ctx.principalId, sessionId: ctx.sessionId },
|
|
816
968
|
}, {
|
|
817
|
-
triggerResolvedContinuation: (item) =>
|
|
818
|
-
ctx.controllerHome,
|
|
819
|
-
repository.repoId,
|
|
820
|
-
handoffResolvedContinuationEventName(item.id),
|
|
821
|
-
`handoff:${item.id}:${item.updatedAt}`,
|
|
822
|
-
{ workId: item.workId, data: { handoffId: item.id, status: item.status, decision: item.decision } },
|
|
823
|
-
),
|
|
969
|
+
triggerResolvedContinuation: (item) => triggerResolvedHandoffContinuation(ctx.controllerHome, repository.repoId, item),
|
|
824
970
|
});
|
|
825
971
|
if (operation === 'get') {
|
|
826
972
|
const item = 'item' in app ? app.item : undefined;
|