@timurproko/a1 0.1.8-dev.21b95d6 → 0.1.8-dev.226
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +107 -67
- package/bin/cli.js +28 -10
- package/bin/guardian.js +4 -1
- package/bin/module-identity.js +69 -35
- package/bin/pi-tui.d.ts +6 -0
- package/bin/pi-tui.js +28 -0
- package/bin/release-cleanup.js +8 -0
- package/bin/supervisor.js +1 -1
- package/bin/sync-pi-tui-proxy.js +97 -0
- package/bin/ui.js +25 -6
- package/bin/warmup.js +18 -0
- package/dist/cli/capabilities.d.ts +6 -0
- package/dist/{src/cli → cli}/capabilities.js +1 -1
- package/dist/{src/cli → cli}/dispatch.d.ts +6 -0
- package/dist/cli/dispatch.js +202 -0
- package/dist/{src/cli → cli}/packages.d.ts +10 -2
- package/dist/{src/cli → cli}/packages.js +24 -20
- package/dist/{src/cli → cli}/version-stats.d.ts +6 -0
- package/dist/cli/version-stats.js +112 -0
- package/dist/composition/agent-engine-bridge.d.ts +3 -0
- package/dist/composition/agent-engine-bridge.js +108 -0
- package/dist/composition/index.d.ts +3 -0
- package/dist/composition/index.js +3 -0
- package/dist/composition/owned-ui.d.ts +28 -0
- package/dist/composition/owned-ui.js +64 -0
- package/dist/composition/process.d.ts +16 -0
- package/dist/composition/process.js +45 -0
- package/dist/composition/settings-route-host.d.ts +8 -0
- package/dist/composition/settings-route-host.js +75 -0
- package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/capability-ports.d.ts +2 -2
- package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/domain-validation.js +22 -4
- package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/domain.d.ts +17 -0
- package/dist/{src/foundation/owned-ui-contracts → contracts/owned-ui}/model.d.ts +36 -0
- package/dist/{src/foundation/owned-ui-contracts → contracts/owned-ui}/validation.js +25 -0
- package/dist/{src/features → features}/launch/development-launch.js +11 -3
- package/dist/{src/features → features}/launch/index.d.ts +0 -1
- package/dist/{src/features → features}/launch/index.js +0 -1
- package/dist/{src/features → features}/launch/intent.d.ts +3 -2
- package/dist/features/launch/intent.js +3 -0
- package/dist/{src/features → features}/launch/prepare-launch.d.ts +0 -2
- package/dist/{src/features → features}/launch/prepare-launch.js +2 -9
- package/dist/{src/features → features}/launch/profile-paths.d.ts +1 -2
- package/dist/{src/features → features}/launch/profile-paths.js +2 -8
- package/dist/{src/features → features}/launch/runtime-selection.d.ts +2 -5
- package/dist/{src/features → features}/owned-ui/customization.d.ts +3 -1
- package/dist/{src/features → features}/owned-ui/customization.js +3 -1
- package/dist/{src/features → features}/owned-ui/diagnostics.d.ts +2 -1
- package/dist/{src/features → features}/owned-ui/diagnostics.js +1 -0
- package/dist/{src/features → features}/owned-ui/index.d.ts +1 -0
- package/dist/{src/features → features}/owned-ui/index.js +1 -0
- package/dist/features/owned-ui/project-trust-prompt.d.ts +25 -0
- package/dist/features/owned-ui/project-trust-prompt.js +149 -0
- package/dist/{src/features → features}/owned-ui/run.d.ts +2 -2
- package/dist/{src/features → features}/owned-ui/run.js +2 -0
- package/dist/{src/features → features}/owned-ui/settings-app.d.ts +3 -3
- package/dist/{src/features → features}/owned-ui/settings-app.js +103 -54
- package/dist/{src/features → features}/workspace/capabilities.d.ts +1 -1
- package/dist/{src/features → features}/workspace/reducer.d.ts +2 -1
- package/dist/{src/features → features}/workspace/reducer.js +2 -1
- package/dist/{src/features → features}/workspace/router.d.ts +2 -1
- package/dist/{src/features → features}/workspace/router.js +1 -0
- package/dist/{src/features → features}/workspace/store.d.ts +2 -1
- package/dist/{src/features → features}/workspace/store.js +1 -0
- package/dist/{src/foundation → foundation}/launch-guardian/main.js +10 -2
- package/dist/{src/foundation → foundation}/lifecycle/model.d.ts +1 -1
- package/dist/{src/foundation → foundation}/lifecycle/model.js +1 -1
- package/dist/foundation/lifecycle/paths.d.ts +28 -0
- package/dist/{src/foundation → foundation}/lifecycle/paths.js +21 -0
- package/dist/{src/foundation → foundation}/native-host-protocol/codec.d.ts +2 -0
- package/dist/{src/foundation → foundation}/native-host-protocol/codec.js +2 -0
- package/dist/{src/foundation → foundation}/native-host-protocol/messages.d.ts +1 -1
- package/dist/{src/foundation → foundation}/native-host-protocol/messages.js +1 -1
- package/dist/{src/foundation → foundation}/process-containment/linux-process-inspector.d.ts +1 -0
- package/dist/{src/foundation → foundation}/process-containment/linux-process-inspector.js +1 -0
- package/dist/{src/foundation → foundation}/process-containment/native-guardian-containment.d.ts +1 -0
- package/dist/{src/foundation → foundation}/process-containment/native-guardian-containment.js +1 -0
- package/dist/{src/foundation → foundation}/process-containment/windows-process-inspector.d.ts +1 -0
- package/dist/{src/foundation → foundation}/process-containment/windows-process-inspector.js +1 -0
- package/dist/{src/foundation → foundation}/protocol/client.d.ts +1 -0
- package/dist/{src/foundation → foundation}/protocol/client.js +1 -0
- package/dist/{src/foundation → foundation}/protocol/messages.d.ts +1 -0
- package/dist/{src/foundation → foundation}/protocol/messages.js +1 -0
- package/dist/{src/foundation → foundation}/release/bootstrap.d.ts +14 -4
- package/dist/{src/foundation → foundation}/release/bootstrap.js +66 -13
- package/dist/foundation/release/cohort-state.d.ts +156 -0
- package/dist/foundation/release/cohort-state.js +471 -0
- package/dist/foundation/release/dependency-layer.d.ts +78 -0
- package/dist/foundation/release/dependency-layer.js +487 -0
- package/dist/foundation/release/endpoints.d.ts +20 -0
- package/dist/foundation/release/endpoints.js +50 -0
- package/dist/{src/foundation → foundation}/release/index.d.ts +3 -0
- package/dist/{src/foundation → foundation}/release/index.js +3 -0
- package/dist/foundation/release/release-gc.d.ts +71 -0
- package/dist/foundation/release/release-gc.js +734 -0
- package/dist/{src/foundation → foundation}/release/release-store.d.ts +3 -1
- package/dist/{src/foundation → foundation}/release/release-store.js +60 -10
- package/dist/{src/foundation → foundation}/release/release.d.ts +4 -1
- package/dist/{src/foundation → foundation}/release/release.js +10 -3
- package/dist/{src/foundation → foundation}/release/update-transaction.d.ts +1 -0
- package/dist/{src/foundation → foundation}/release/update-transaction.js +1 -0
- package/dist/{src/foundation → foundation}/release/update.d.ts +19 -3
- package/dist/{src/foundation → foundation}/release/update.js +114 -54
- package/dist/foundation/release/warmup.d.ts +3 -0
- package/dist/foundation/release/warmup.js +35 -0
- package/dist/foundation/startup/index.d.ts +1 -0
- package/dist/foundation/startup/index.js +1 -0
- package/dist/foundation/startup/startup-runtime.d.ts +36 -0
- package/dist/foundation/startup/startup-runtime.js +140 -0
- package/dist/{src/foundation → foundation}/storage/control-store.d.ts +2 -1
- package/dist/{src/foundation → foundation}/storage/control-store.js +39 -4
- package/dist/{src/foundation → foundation}/structured-agent-runtime/backpressure.d.ts +2 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/backpressure.js +2 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/commands.d.ts +2 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/commands.js +2 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/handshake.d.ts +1 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/handshake.js +1 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/reconnection.d.ts +2 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/reconnection.js +2 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/state.d.ts +2 -1
- package/dist/{src/foundation → foundation}/structured-agent-runtime/state.js +2 -1
- package/dist/foundation/supervision/index.d.ts +3 -0
- package/dist/foundation/supervision/index.js +3 -0
- package/dist/{src/foundation → foundation}/supervision/main.js +11 -5
- package/dist/foundation/supervision/paths.d.ts +1 -0
- package/dist/foundation/supervision/paths.js +1 -0
- package/dist/{src/foundation → foundation}/supervision/server.d.ts +19 -1
- package/dist/{src/foundation → foundation}/supervision/server.js +51 -2
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/components.d.ts +1 -1
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/conformance.d.ts +1 -0
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/conformance.js +3 -2
- package/dist/integrations/pi/components/owned-editor-ux.d.ts +55 -0
- package/dist/integrations/pi/components/owned-editor-ux.js +778 -0
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-components.d.ts +1 -0
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-components.js +1 -0
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-editor-autocomplete.js +54 -6
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-extension-ui.d.ts +1 -1
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-footer-status.d.ts +3 -3
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-footer-status.js +32 -17
- package/dist/integrations/pi/components/shell-presenters-info.d.ts +36 -0
- package/dist/integrations/pi/components/shell-presenters-info.js +78 -0
- package/dist/integrations/pi/components/shell-presenters-transcript.d.ts +25 -0
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-presenters-transcript.js +92 -131
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-selectors-dialogs.d.ts +1 -1
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-shared-facade.d.ts +52 -8
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-shared-facade.js +4 -2
- package/dist/integrations/pi/components/submitted-prompt-adapter.d.ts +13 -0
- package/dist/integrations/pi/components/submitted-prompt-adapter.js +27 -0
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/adjacent/core/keybindings.d.ts +10 -2
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/adjacent/core/keybindings.js +36 -3
- package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/session-footer.d.ts +1 -1
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/adapter.d.ts +22 -4
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/adapter.js +289 -68
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/conformance.d.ts +2 -0
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/conformance.js +4 -2
- package/dist/integrations/pi/engine/http-dispatcher.d.ts +4 -0
- package/dist/integrations/pi/engine/http-dispatcher.js +25 -0
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/index.d.ts +3 -0
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/index.js +3 -0
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/model-auth-integration.d.ts +2 -1
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/model-auth-integration.js +1 -0
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/package-integration.d.ts +1 -1
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/package-integration.js +2 -2
- package/dist/integrations/pi/engine/project-trust-preflight.d.ts +22 -0
- package/dist/integrations/pi/engine/project-trust-preflight.js +50 -0
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/resource-extension-integration.d.ts +2 -1
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/resource-extension-integration.js +1 -0
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/runtime-integration.d.ts +16 -1
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/runtime-integration.js +39 -4
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/session-integration.d.ts +4 -2
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/session-integration.js +19 -4
- package/dist/integrations/pi/engine/settings-effects.d.ts +66 -0
- package/dist/integrations/pi/engine/settings-effects.js +249 -0
- package/dist/integrations/pi/engine/settings-integration.d.ts +43 -0
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/settings-integration.js +102 -108
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/workflow-controllers.d.ts +3 -2
- package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/workflow-controllers.js +1 -0
- package/dist/integrations/pi/session-ui/clipboard-image.d.ts +11 -0
- package/dist/integrations/pi/session-ui/clipboard-image.js +29 -0
- package/dist/{src/foundation/pi-owned-ui-integration → integrations/pi/session-ui}/index.d.ts +1 -0
- package/dist/{src/foundation/pi-owned-ui-integration → integrations/pi/session-ui}/index.js +1 -0
- package/dist/integrations/pi/session-ui/prompt-chips.d.ts +23 -0
- package/dist/integrations/pi/session-ui/prompt-chips.js +246 -0
- package/dist/integrations/pi/session-ui/route-host.d.ts +5 -0
- package/dist/integrations/pi/session-ui/session-shell-root.d.ts +137 -0
- package/dist/integrations/pi/session-ui/session-shell-root.js +1106 -0
- package/dist/integrations/pi/session-ui/session-shell.d.ts +55 -0
- package/dist/{src/foundation/pi-owned-ui-integration → integrations/pi/session-ui}/session-shell.js +415 -775
- package/dist/integrations/pi/session-ui/session-viewport-controller.d.ts +44 -0
- package/dist/integrations/pi/session-ui/session-viewport-controller.js +434 -0
- package/dist/integrations/pi/session-ui/stream-presentation-coalescer.d.ts +29 -0
- package/dist/integrations/pi/session-ui/stream-presentation-coalescer.js +79 -0
- package/dist/integrations/pi/session-ui/system-clipboard.d.ts +20 -0
- package/dist/integrations/pi/session-ui/system-clipboard.js +130 -0
- package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/adapter.d.ts +8 -1
- package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/adapter.js +216 -9
- package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/contracts.d.ts +29 -6
- package/dist/integrations/pi/tui-runtime/damage-aware-terminal.d.ts +63 -0
- package/dist/integrations/pi/tui-runtime/damage-aware-terminal.js +240 -0
- package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/index.d.ts +2 -0
- package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/index.js +2 -0
- package/dist/integrations/pi/tui-runtime/input-presentation-coordinator.d.ts +39 -0
- package/dist/integrations/pi/tui-runtime/input-presentation-coordinator.js +139 -0
- package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/presentation-adapter.d.ts +1 -1
- package/dist/native/darwin-arm64/manifest.json +1 -1
- package/dist/native/linux-x64/manifest.json +3 -3
- package/dist/native/linux-x64/process-guardian +0 -0
- package/dist/native/win32-x64/manifest.json +3 -3
- package/dist/native/win32-x64/process-guardian.exe +0 -0
- package/dist/{src/product-identity.d.ts → product-identity.d.ts} +3 -3
- package/dist/{src/product-identity.js → product-identity.js} +7 -5
- package/dist/{src/product-identity.json → product-identity.json} +11 -6
- package/dist/runtime-payload-inventory.json +122328 -0
- package/dist/{src/foundation/ui-apps → ui/apps}/contracts.d.ts +23 -1
- package/dist/{src/foundation/ui-apps → ui/apps}/host.d.ts +1 -1
- package/dist/{src/foundation/ui-apps → ui/apps}/host.js +14 -10
- package/dist/{src/foundation/ui-apps → ui/apps}/registry.d.ts +1 -0
- package/dist/{src/foundation/ui-apps → ui/apps}/registry.js +1 -0
- package/dist/{src/foundation/ui-components → ui/components}/dialog-panel.js +5 -3
- package/dist/{src/foundation/ui-components → ui/components}/frame.d.ts +1 -0
- package/dist/{src/foundation/ui-components → ui/components}/frame.js +1 -0
- package/dist/{src/foundation/ui-components → ui/components}/index.d.ts +4 -0
- package/dist/{src/foundation/ui-components → ui/components}/index.js +4 -0
- package/dist/{src/foundation/ui-components → ui/components}/line-input.d.ts +1 -6
- package/dist/{src/foundation/ui-components → ui/components}/line-input.js +4 -9
- package/dist/{src/foundation/ui-components → ui/components}/list-view.d.ts +0 -6
- package/dist/{src/foundation/ui-components → ui/components}/list-view.js +14 -7
- package/dist/{src/foundation/ui-components → ui/components}/mouse.d.ts +10 -0
- package/dist/{src/foundation/ui-components → ui/components}/mouse.js +23 -0
- package/dist/ui/components/progress-status.d.ts +2 -0
- package/dist/ui/components/progress-status.js +4 -0
- package/dist/ui/components/prompt-row.d.ts +14 -0
- package/dist/ui/components/prompt-row.js +20 -0
- package/dist/{src/foundation/ui-components → ui/components}/scrollbar.d.ts +26 -0
- package/dist/{src/foundation/ui-components → ui/components}/scrollbar.js +35 -0
- package/dist/{src/foundation/ui-components → ui/components}/shortcuts.d.ts +1 -0
- package/dist/{src/foundation/ui-components → ui/components}/shortcuts.js +1 -0
- package/dist/ui/components/spans.d.ts +25 -0
- package/dist/ui/components/spans.js +257 -0
- package/dist/ui/components/submitted-prompt.d.ts +23 -0
- package/dist/ui/components/submitted-prompt.js +50 -0
- package/dist/{src/foundation/ui-components → ui/components}/surface.d.ts +0 -5
- package/dist/{src/foundation/ui-components → ui/components}/surface.js +1 -5
- package/dist/ui/components/text-selection.d.ts +62 -0
- package/dist/ui/components/text-selection.js +235 -0
- package/dist/{src/foundation/ui-components → ui/components}/text.d.ts +14 -0
- package/dist/{src/foundation/ui-components → ui/components}/text.js +66 -4
- package/dist/ui/components/transcript-viewport.d.ts +146 -0
- package/dist/ui/components/transcript-viewport.js +629 -0
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/declarations.d.ts +8 -1
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/declarations.js +33 -5
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/migrations.d.ts +1 -1
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/migrations.js +21 -2
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/sections.d.ts +6 -19
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/sections.js +32 -23
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/session.d.ts +9 -17
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/session.js +65 -55
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/store.d.ts +1 -0
- package/dist/{src/foundation/owned-ui-settings → ui/settings}/store.js +2 -1
- package/docs/architecture/boundaries.md +9 -9
- package/docs/architecture/code-documentation.md +77 -0
- package/docs/architecture/project-structure.md +67 -30
- package/docs/architecture/resource-and-data-policy.md +1 -1
- package/docs/architecture/toolchain.md +10 -10
- package/docs/architecture/ui-reference-provenance.md +34 -5
- package/docs/ci-release-runbook.md +186 -79
- package/docs/features/launch-profiles.md +10 -19
- package/docs/manual-launch-instance-acceptance.md +12 -35
- package/docs/manual-owned-ui-checkpoint.md +78 -0
- package/docs/manual-pi-boundary-candidate.md +4 -5
- package/docs/manual-terminal-colour-check.md +4 -3
- package/docs/repository-governance-live-acceptance.md +77 -0
- package/package.json +37 -27
- package/dist/src/cli/capabilities.d.ts +0 -15
- package/dist/src/cli/dispatch.js +0 -177
- package/dist/src/cli/version-stats.js +0 -72
- package/dist/src/composition/index.d.ts +0 -48
- package/dist/src/composition/index.js +0 -258
- package/dist/src/features/launch/intent.js +0 -4
- package/dist/src/features/launch/profiles.d.ts +0 -12
- package/dist/src/features/launch/profiles.js +0 -26
- package/dist/src/foundation/lifecycle/paths.d.ts +0 -10
- package/dist/src/foundation/pi-component-adapter/shell-presenters-transcript.d.ts +0 -57
- package/dist/src/foundation/pi-engine-adapter/settings-integration.d.ts +0 -55
- package/dist/src/foundation/pi-owned-ui-integration/route-host.d.ts +0 -29
- package/dist/src/foundation/pi-owned-ui-integration/session-shell.d.ts +0 -112
- package/dist/src/foundation/release/cohort-state.d.ts +0 -70
- package/dist/src/foundation/release/cohort-state.js +0 -202
- package/dist/src/foundation/release/release-gc.d.ts +0 -5
- package/dist/src/foundation/release/release-gc.js +0 -16
- package/dist/src/foundation/supervision/index.d.ts +0 -3
- package/dist/src/foundation/supervision/index.js +0 -3
- package/dist/src/foundation/supervision/paths.d.ts +0 -1
- package/dist/src/foundation/supervision/paths.js +0 -1
- package/dist/src/foundation/ui-components/spans.d.ts +0 -7
- package/dist/src/foundation/ui-components/spans.js +0 -59
- package/docs/manual-transparent-checkpoint.md +0 -53
- /package/dist/{src/cli → cli}/index.d.ts +0 -0
- /package/dist/{src/cli → cli}/index.js +0 -0
- /package/dist/{src/cli → cli}/version.d.ts +0 -0
- /package/dist/{src/cli → cli}/version.js +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/capability-ports.js +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/domain-validation.d.ts +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/domain.js +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/index.d.ts +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/index.js +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/model.d.ts +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/model.js +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/package-ports.d.ts +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/package-ports.js +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/ports.d.ts +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/ports.js +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/serialization.d.ts +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/serialization.js +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/validation.d.ts +0 -0
- /package/dist/{src/foundation/agent-engine-contracts → contracts/agent-engine}/validation.js +0 -0
- /package/dist/{src/foundation/owned-ui-contracts → contracts/owned-ui}/extension-ui.d.ts +0 -0
- /package/dist/{src/foundation/owned-ui-contracts → contracts/owned-ui}/extension-ui.js +0 -0
- /package/dist/{src/foundation/owned-ui-contracts → contracts/owned-ui}/index.d.ts +0 -0
- /package/dist/{src/foundation/owned-ui-contracts → contracts/owned-ui}/index.js +0 -0
- /package/dist/{src/foundation/owned-ui-contracts → contracts/owned-ui}/model.js +0 -0
- /package/dist/{src/foundation/owned-ui-contracts → contracts/owned-ui}/validation.d.ts +0 -0
- /package/dist/{src/foundation/presentation-contracts → contracts/presentation}/index.d.ts +0 -0
- /package/dist/{src/foundation/presentation-contracts → contracts/presentation}/index.js +0 -0
- /package/dist/{src/foundation/workspace-contracts → contracts/workspace}/index.d.ts +0 -0
- /package/dist/{src/foundation/workspace-contracts → contracts/workspace}/index.js +0 -0
- /package/dist/{src/foundation/workspace-contracts → contracts/workspace}/model.d.ts +0 -0
- /package/dist/{src/foundation/workspace-contracts → contracts/workspace}/model.js +0 -0
- /package/dist/{src/foundation/workspace-contracts → contracts/workspace}/validation.d.ts +0 -0
- /package/dist/{src/foundation/workspace-contracts → contracts/workspace}/validation.js +0 -0
- /package/dist/{src/features → features}/launch/development-launch.d.ts +0 -0
- /package/dist/{src/features → features}/launch/initialize-profile.d.ts +0 -0
- /package/dist/{src/features → features}/launch/initialize-profile.js +0 -0
- /package/dist/{src/features → features}/launch/runtime-selection.js +0 -0
- /package/dist/{src/features → features}/workspace/capabilities.js +0 -0
- /package/dist/{src/features → features}/workspace/index.d.ts +0 -0
- /package/dist/{src/features → features}/workspace/index.js +0 -0
- /package/dist/{src/features → features}/workspace/presentation.d.ts +0 -0
- /package/dist/{src/features → features}/workspace/presentation.js +0 -0
- /package/dist/{src/features → features}/workspace/reconciliation.d.ts +0 -0
- /package/dist/{src/features → features}/workspace/reconciliation.js +0 -0
- /package/dist/{src/foundation → foundation}/launch-guardian/index.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/launch-guardian/index.js +0 -0
- /package/dist/{src/foundation → foundation}/launch-guardian/main.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/lifecycle/commands.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/lifecycle/commands.js +0 -0
- /package/dist/{src/foundation → foundation}/lifecycle/index.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/lifecycle/index.js +0 -0
- /package/dist/{src/foundation → foundation}/lifecycle/launch-instance.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/lifecycle/launch-instance.js +0 -0
- /package/dist/{src/foundation → foundation}/native-host-protocol/evidence.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/native-host-protocol/evidence.js +0 -0
- /package/dist/{src/foundation → foundation}/native-host-protocol/index.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/native-host-protocol/index.js +0 -0
- /package/dist/{src/foundation → foundation}/native-host-protocol/proof-gate.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/native-host-protocol/proof-gate.js +0 -0
- /package/dist/{src/foundation → foundation}/process-containment/artifact.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/process-containment/artifact.js +0 -0
- /package/dist/{src/foundation → foundation}/process-containment/contracts.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/process-containment/contracts.js +0 -0
- /package/dist/{src/foundation → foundation}/process-containment/index.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/process-containment/index.js +0 -0
- /package/dist/{src/foundation → foundation}/protocol/index.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/protocol/index.js +0 -0
- /package/dist/{src/foundation → foundation}/release/cohort-selection.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/release/cohort-selection.js +0 -0
- /package/dist/{src/foundation → foundation}/release/concurrency.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/release/concurrency.js +0 -0
- /package/dist/{src/foundation → foundation}/release/process-cleanup.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/release/process-cleanup.js +0 -0
- /package/dist/{src/foundation → foundation}/release/stable-release.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/release/stable-release.js +0 -0
- /package/dist/{src/foundation → foundation}/storage/index.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/storage/index.js +0 -0
- /package/dist/{src/foundation → foundation}/structured-agent-runtime/index.d.ts +0 -0
- /package/dist/{src/foundation → foundation}/structured-agent-runtime/index.js +0 -0
- /package/dist/{src/foundation → foundation}/supervision/main.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/components.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/index.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/index.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/resources/builtin-themes.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/resources/builtin-themes.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-editor-autocomplete.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-extension-ui.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/shell-selectors-dialogs.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/theme.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/theme.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/countdown-timer.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/countdown-timer.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/custom-entry.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/custom-entry.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/daxnuts.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/daxnuts.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/earendil-announcement.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/earendil-announcement.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/extension-editor.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/extension-editor.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/first-time-setup.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/first-time-setup.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/markdown-transform.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/markdown-transform.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/mermaid.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/mermaid.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/owned-editor.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/owned-editor.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/scoped-models-selector.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/scoped-models-selector.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/session-footer.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/session-selector-search.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/session-selector-search.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/session-selector.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/session-selector.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/skill-invocation-message.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/skill-invocation-message.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/status-indicator.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/status-indicator.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/tree-selector.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/tree-selector.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/trust-selector.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/components/trust-selector.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/external-editor.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/external-editor.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/model-search.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/model-search.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/theme/theme-controller.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/theme/theme-controller.js +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/theme/theme.d.ts +0 -0
- /package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/upstream/theme/theme.js +0 -0
- /package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/pi-settings-metadata.json +0 -0
- /package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/public-main-entry.d.ts +0 -0
- /package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/public-main-entry.js +0 -0
- /package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/workflows.d.ts +0 -0
- /package/dist/{src/foundation/pi-engine-adapter → integrations/pi/engine}/workflows.js +0 -0
- /package/dist/{src/foundation/pi-owned-ui-integration → integrations/pi/session-ui}/route-host.js +0 -0
- /package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/conformance.d.ts +0 -0
- /package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/conformance.js +0 -0
- /package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/contracts.js +0 -0
- /package/dist/{src/foundation/pi-tui-runtime-adapter → integrations/pi/tui-runtime}/presentation-adapter.js +0 -0
- /package/dist/{src/foundation/ui-apps → ui/apps}/contracts.js +0 -0
- /package/dist/{src/foundation/ui-apps → ui/apps}/index.d.ts +0 -0
- /package/dist/{src/foundation/ui-apps → ui/apps}/index.js +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/dialog-panel.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/label.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/label.js +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/list-block.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/list-block.js +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/pane.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/pane.js +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/revision.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/revision.js +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/status-line.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/status-line.js +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/stepper.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/stepper.js +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/theme.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/theme.js +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/value-menu.d.ts +0 -0
- /package/dist/{src/foundation/ui-components → ui/components}/value-menu.js +0 -0
- /package/dist/{src/foundation/owned-ui-settings → ui/settings}/index.d.ts +0 -0
- /package/dist/{src/foundation/owned-ui-settings → ui/settings}/index.js +0 -0
- /package/dist/{src/foundation/owned-ui-settings → ui/settings}/resolution.d.ts +0 -0
- /package/dist/{src/foundation/owned-ui-settings → ui/settings}/resolution.js +0 -0
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import { spawn } from "node:child_process";
|
|
2
|
+
import { resolve } from "node:path";
|
|
3
|
+
import { releaseEnvironment } from "./bootstrap.js";
|
|
4
|
+
import { PRODUCT_IDENTITY } from "../../product-identity.js";
|
|
5
|
+
/** Import the exact immutable startup graph in a terminal-free bounded child process. */
|
|
6
|
+
export async function warmMaterializedRelease(release, environment, timeoutMs = 15_000) {
|
|
7
|
+
const entry = resolve(release.releaseRoot, "bin", "warmup.js");
|
|
8
|
+
await new Promise((resolvePromise, rejectPromise) => {
|
|
9
|
+
const child = spawn(process.execPath, [entry], {
|
|
10
|
+
env: { ...releaseEnvironment(environment, release), [PRODUCT_IDENTITY.environment.immutableWarmup]: "1" },
|
|
11
|
+
stdio: "ignore",
|
|
12
|
+
windowsHide: true,
|
|
13
|
+
});
|
|
14
|
+
let settled = false;
|
|
15
|
+
const finish = (error) => {
|
|
16
|
+
if (settled)
|
|
17
|
+
return;
|
|
18
|
+
settled = true;
|
|
19
|
+
clearTimeout(timer);
|
|
20
|
+
if (error)
|
|
21
|
+
rejectPromise(error);
|
|
22
|
+
else
|
|
23
|
+
resolvePromise();
|
|
24
|
+
};
|
|
25
|
+
child.once("error", error => finish(error));
|
|
26
|
+
child.once("close", (code, signal) => finish(code === 0
|
|
27
|
+
? undefined
|
|
28
|
+
: new Error(`immutable startup warmup exited with ${code === null ? signal ?? "unknown status" : `status ${code}`}`)));
|
|
29
|
+
const timer = setTimeout(() => {
|
|
30
|
+
child.kill();
|
|
31
|
+
finish(new Error(`immutable startup warmup exceeded ${timeoutMs}ms`));
|
|
32
|
+
}, timeoutMs);
|
|
33
|
+
timer.unref?.();
|
|
34
|
+
});
|
|
35
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./startup-runtime.js";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./startup-runtime.js";
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import { PRODUCT_IDENTITY } from "../../product-identity.js";
|
|
2
|
+
export type StartupPhase = "command-invoked" | "bootstrap-start" | "bootstrap-selected" | "guardian-start" | "guardian-connected" | "ui-entry" | "ui-modules-loaded" | "pi-services" | "resource-discovery" | "session-created" | "settings-loaded" | "first-input-ready-render";
|
|
3
|
+
export interface StartupPerformanceEvidence {
|
|
4
|
+
readonly profileId: "a1" | "pi";
|
|
5
|
+
readonly launchKind: "post-update" | "warm";
|
|
6
|
+
readonly events: readonly StartupTraceEvent[];
|
|
7
|
+
}
|
|
8
|
+
export interface StartupTraceEvent {
|
|
9
|
+
readonly schema: typeof PRODUCT_IDENTITY.evidence.startupTraceSchema;
|
|
10
|
+
readonly traceId: string;
|
|
11
|
+
readonly phase: StartupPhase;
|
|
12
|
+
readonly elapsedMs: number;
|
|
13
|
+
readonly processId: number;
|
|
14
|
+
readonly profileId: string;
|
|
15
|
+
readonly releaseId: string | null;
|
|
16
|
+
readonly dependencyLayerIds: readonly string[];
|
|
17
|
+
readonly nodeVersion: string;
|
|
18
|
+
readonly fileReadOperations: number;
|
|
19
|
+
}
|
|
20
|
+
/** Initialize opt-in startup tracing from a caller-provided evidence path. */
|
|
21
|
+
export declare function initializeStartupTrace(environment: NodeJS.ProcessEnv, profileId: string, startedAtMs?: number): void;
|
|
22
|
+
/** Append one redacted phase event; ordinary launches without trace context perform no I/O. */
|
|
23
|
+
export declare function markStartupPhase(environment: NodeJS.ProcessEnv, phase: StartupPhase): Promise<void>;
|
|
24
|
+
export declare function assertImmutableWarmupEnvironment(environment: NodeJS.ProcessEnv): void;
|
|
25
|
+
/** Enable the compile cache directly from launch environment without loading profile services. */
|
|
26
|
+
export declare function enableEnvironmentCompileCache(environment: NodeJS.ProcessEnv): string | null;
|
|
27
|
+
/** Enable Node's supported persistent compile cache in an immutable-identity namespace. */
|
|
28
|
+
export declare function enableStartupCompileCache(dataDir: string, releaseId: string | null, dependencyLayerIds: readonly string[]): string | null;
|
|
29
|
+
export declare function startupCompileCachePath(dataDir: string, releaseId: string | null, dependencyLayerIds: readonly string[]): string;
|
|
30
|
+
/** Retain current compile namespaces plus a bounded number of recent fallbacks. */
|
|
31
|
+
export declare function collectCompileCaches(dataDir: string, protectedPaths: readonly string[], keepRecent?: number): Promise<void>;
|
|
32
|
+
export declare function assertStartupPerformanceBudget(evidence: StartupPerformanceEvidence, budgets?: {
|
|
33
|
+
readonly postUpdateMs: number;
|
|
34
|
+
readonly warmMs: number;
|
|
35
|
+
}): void;
|
|
36
|
+
export declare function parseStartupTrace(source: string): readonly StartupTraceEvent[];
|
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
import { createHash, randomUUID } from "node:crypto";
|
|
2
|
+
import { appendFile, mkdir, readdir, rm } from "node:fs/promises";
|
|
3
|
+
import { constants as moduleConstants, enableCompileCache } from "node:module";
|
|
4
|
+
import { dirname, resolve } from "node:path";
|
|
5
|
+
import { homedir, platform } from "node:os";
|
|
6
|
+
import { performance } from "node:perf_hooks";
|
|
7
|
+
import { PRODUCT_IDENTITY } from "../../product-identity.js";
|
|
8
|
+
/** Initialize opt-in startup tracing from a caller-provided evidence path. */
|
|
9
|
+
export function initializeStartupTrace(environment, profileId, startedAtMs = performance.timeOrigin + performance.now()) {
|
|
10
|
+
const configured = environment[PRODUCT_IDENTITY.environment.startupTrace];
|
|
11
|
+
if (!configured || parseContext(configured) !== null)
|
|
12
|
+
return;
|
|
13
|
+
const context = {
|
|
14
|
+
path: resolve(configured),
|
|
15
|
+
traceId: randomUUID(),
|
|
16
|
+
startedAtMs,
|
|
17
|
+
profileId,
|
|
18
|
+
releaseId: environment[PRODUCT_IDENTITY.environment.releaseId] ?? null,
|
|
19
|
+
dependencyLayerIds: parseLayerIds(environment[PRODUCT_IDENTITY.environment.releaseLayers]),
|
|
20
|
+
};
|
|
21
|
+
environment[PRODUCT_IDENTITY.environment.startupTrace] = JSON.stringify(context);
|
|
22
|
+
}
|
|
23
|
+
/** Append one redacted phase event; ordinary launches without trace context perform no I/O. */
|
|
24
|
+
export async function markStartupPhase(environment, phase) {
|
|
25
|
+
const context = parseContext(environment[PRODUCT_IDENTITY.environment.startupTrace]);
|
|
26
|
+
if (context === null)
|
|
27
|
+
return;
|
|
28
|
+
const event = {
|
|
29
|
+
schema: PRODUCT_IDENTITY.evidence.startupTraceSchema,
|
|
30
|
+
traceId: context.traceId,
|
|
31
|
+
phase,
|
|
32
|
+
elapsedMs: Math.max(0, performance.timeOrigin + performance.now() - context.startedAtMs),
|
|
33
|
+
processId: process.pid,
|
|
34
|
+
profileId: context.profileId,
|
|
35
|
+
releaseId: environment[PRODUCT_IDENTITY.environment.releaseId] ?? context.releaseId,
|
|
36
|
+
dependencyLayerIds: parseLayerIds(environment[PRODUCT_IDENTITY.environment.releaseLayers]).length > 0
|
|
37
|
+
? parseLayerIds(environment[PRODUCT_IDENTITY.environment.releaseLayers])
|
|
38
|
+
: context.dependencyLayerIds,
|
|
39
|
+
nodeVersion: process.version,
|
|
40
|
+
fileReadOperations: process.resourceUsage().fsRead,
|
|
41
|
+
};
|
|
42
|
+
await mkdir(dirname(context.path), { recursive: true, mode: 0o700 });
|
|
43
|
+
await appendFile(context.path, `${JSON.stringify(event)}\n`, { encoding: "utf8", mode: 0o600 });
|
|
44
|
+
}
|
|
45
|
+
export function assertImmutableWarmupEnvironment(environment) {
|
|
46
|
+
if (environment[PRODUCT_IDENTITY.environment.immutableWarmup] !== "1") {
|
|
47
|
+
throw new Error("warmup entry is private to verified update activation");
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
/** Enable the compile cache directly from launch environment without loading profile services. */
|
|
51
|
+
export function enableEnvironmentCompileCache(environment) {
|
|
52
|
+
const home = environment.HOME ?? environment.USERPROFILE ?? homedir();
|
|
53
|
+
const dataDir = resolve(environment[PRODUCT_IDENTITY.environment.dataDir]
|
|
54
|
+
?? (platform() === "win32"
|
|
55
|
+
? resolve(environment.LOCALAPPDATA ?? home, PRODUCT_IDENTITY.state.windowsControlDirectory)
|
|
56
|
+
: resolve(environment.XDG_DATA_HOME ?? resolve(home, ".local", "share"), PRODUCT_IDENTITY.state.unixControlDirectory)));
|
|
57
|
+
return enableStartupCompileCache(dataDir, environment[PRODUCT_IDENTITY.environment.releaseId] ?? null, parseLayerIds(environment[PRODUCT_IDENTITY.environment.releaseLayers]));
|
|
58
|
+
}
|
|
59
|
+
/** Enable Node's supported persistent compile cache in an immutable-identity namespace. */
|
|
60
|
+
export function enableStartupCompileCache(dataDir, releaseId, dependencyLayerIds) {
|
|
61
|
+
try {
|
|
62
|
+
const path = startupCompileCachePath(dataDir, releaseId, dependencyLayerIds);
|
|
63
|
+
const result = enableCompileCache(path);
|
|
64
|
+
return result.status === moduleConstants.compileCacheStatus.FAILED ? null : result.directory ?? path;
|
|
65
|
+
}
|
|
66
|
+
catch {
|
|
67
|
+
return null;
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
export function startupCompileCachePath(dataDir, releaseId, dependencyLayerIds) {
|
|
71
|
+
const layers = createHash("sha256").update(dependencyLayerIds.join("\0")).digest("hex").slice(0, 20);
|
|
72
|
+
const content = dependencyLayerIds.length > 0
|
|
73
|
+
? `layers-${layers}`
|
|
74
|
+
: `release-${(releaseId ?? "mutable").replace(/[^0-9A-Za-z.+_-]/g, "_")}`;
|
|
75
|
+
// Performance: stable layer paths share compiled dependency entries across product releases;
|
|
76
|
+
// Node's own cache key still isolates each release-specific module path and source bytes.
|
|
77
|
+
return resolve(dataDir, "cache", "compile", `${process.versions.modules ?? "node"}-${process.version.replace(/[^0-9A-Za-z.-]/g, "_")}-${content}`);
|
|
78
|
+
}
|
|
79
|
+
/** Retain current compile namespaces plus a bounded number of recent fallbacks. */
|
|
80
|
+
export async function collectCompileCaches(dataDir, protectedPaths, keepRecent = 2) {
|
|
81
|
+
const root = resolve(dataDir, "cache", "compile");
|
|
82
|
+
const protectedSet = new Set(protectedPaths.map(path => resolve(path)));
|
|
83
|
+
const entries = await readdir(root, { withFileTypes: true }).catch(() => []);
|
|
84
|
+
const candidates = await Promise.all(entries.filter(entry => entry.isDirectory()).map(async (entry) => {
|
|
85
|
+
const path = resolve(root, entry.name);
|
|
86
|
+
const metadata = await import("node:fs/promises").then(fs => fs.stat(path));
|
|
87
|
+
return { path, mtimeMs: metadata.mtimeMs };
|
|
88
|
+
}));
|
|
89
|
+
const retainedRecent = new Set(candidates.filter(item => !protectedSet.has(item.path))
|
|
90
|
+
.sort((left, right) => right.mtimeMs - left.mtimeMs)
|
|
91
|
+
.slice(0, keepRecent)
|
|
92
|
+
.map(item => item.path));
|
|
93
|
+
for (const candidate of candidates) {
|
|
94
|
+
if (!protectedSet.has(candidate.path) && !retainedRecent.has(candidate.path))
|
|
95
|
+
await rm(candidate.path, { recursive: true, force: true });
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
export function assertStartupPerformanceBudget(evidence, budgets = { postUpdateMs: 5_000, warmMs: 3_000 }) {
|
|
99
|
+
const events = [...evidence.events].sort((left, right) => left.elapsedMs - right.elapsedMs);
|
|
100
|
+
const ready = events.findLast(event => event.phase === "first-input-ready-render");
|
|
101
|
+
if (!ready)
|
|
102
|
+
throw new Error(`startup budget failed for ${evidence.profileId}: first input-ready render was not recorded`);
|
|
103
|
+
const budget = evidence.launchKind === "post-update" ? budgets.postUpdateMs : budgets.warmMs;
|
|
104
|
+
if (ready.elapsedMs <= budget)
|
|
105
|
+
return;
|
|
106
|
+
const intervals = events.map((event, index) => ({
|
|
107
|
+
phase: event.phase,
|
|
108
|
+
durationMs: event.elapsedMs - (events[index - 1]?.elapsedMs ?? 0),
|
|
109
|
+
})).sort((left, right) => right.durationMs - left.durationMs);
|
|
110
|
+
throw new Error(`startup budget failed for ${evidence.profileId} ${evidence.launchKind}: ${Math.round(ready.elapsedMs)}ms exceeds ${budget}ms; dominant phases: ${intervals.slice(0, 3).map(item => `${item.phase} ${Math.round(item.durationMs)}ms`).join(", ")}`);
|
|
111
|
+
}
|
|
112
|
+
export function parseStartupTrace(source) {
|
|
113
|
+
const events = source.split(/\r?\n/).filter(Boolean).map(line => JSON.parse(line));
|
|
114
|
+
for (const event of events) {
|
|
115
|
+
if (event.schema !== PRODUCT_IDENTITY.evidence.startupTraceSchema || typeof event.traceId !== "string"
|
|
116
|
+
|| typeof event.phase !== "string" || !Number.isFinite(event.elapsedMs) || !Array.isArray(event.dependencyLayerIds)) {
|
|
117
|
+
throw new Error("startup trace contains an invalid event");
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
return events.sort((left, right) => left.elapsedMs - right.elapsedMs);
|
|
121
|
+
}
|
|
122
|
+
function parseContext(value) {
|
|
123
|
+
if (!value?.startsWith("{"))
|
|
124
|
+
return null;
|
|
125
|
+
try {
|
|
126
|
+
const context = JSON.parse(value);
|
|
127
|
+
if (typeof context.path !== "string" || typeof context.traceId !== "string" || !Number.isFinite(context.startedAtMs)
|
|
128
|
+
|| typeof context.profileId !== "string" || !Array.isArray(context.dependencyLayerIds))
|
|
129
|
+
return null;
|
|
130
|
+
return context;
|
|
131
|
+
}
|
|
132
|
+
catch {
|
|
133
|
+
return null;
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
function parseLayerIds(value) {
|
|
137
|
+
if (!value)
|
|
138
|
+
return [];
|
|
139
|
+
return [...new Set(value.split(",").filter(id => /^dependencies-[a-f0-9]{32}$/.test(id)))].sort();
|
|
140
|
+
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { DatabaseSync } from "node:sqlite";
|
|
2
|
-
import type { ManagedAgentDescriptor, PaneId, AgentRecoveryAuthority, RecoveryReferenceId, TerminalSessionLaunch, TerminalTopologySnapshot } from "
|
|
2
|
+
import type { ManagedAgentDescriptor, PaneId, AgentRecoveryAuthority, RecoveryReferenceId, TerminalSessionLaunch, TerminalTopologySnapshot } from "../../contracts/workspace/index.js";
|
|
3
3
|
import type { LaunchInstance, LaunchInstanceId, LaunchInstanceOutcome, NativeProcessIdentity, ProcessContainmentIdentity } from "../lifecycle/index.js";
|
|
4
4
|
export declare const DEFAULT_WORKSPACE_ID = "workspace-default";
|
|
5
5
|
export interface WorkspaceAgentPresentation {
|
|
@@ -14,6 +14,7 @@ export interface StoredWorkspaceAgent {
|
|
|
14
14
|
readonly agent: ManagedAgentDescriptor;
|
|
15
15
|
readonly presentation: WorkspaceAgentPresentation;
|
|
16
16
|
}
|
|
17
|
+
/** Owns WAL-backed control persistence and reconciles prior-boot records before current use. */
|
|
17
18
|
export declare class ControlStore {
|
|
18
19
|
#private;
|
|
19
20
|
readonly bootNonce: string | null;
|
|
@@ -2,10 +2,11 @@ import { DatabaseSync } from "node:sqlite";
|
|
|
2
2
|
import { mkdirSync } from "node:fs";
|
|
3
3
|
import { dirname } from "node:path";
|
|
4
4
|
import { PRODUCT_IDENTITY } from "../../product-identity.js";
|
|
5
|
-
import { assertManagedAgentDescriptor, assertRecoveryAuthority, assertTerminalSessionLaunch, assertTerminalTopologySnapshot, } from "
|
|
5
|
+
import { assertManagedAgentDescriptor, assertRecoveryAuthority, assertTerminalSessionLaunch, assertTerminalTopologySnapshot, } from "../../contracts/workspace/index.js";
|
|
6
6
|
import { assertLaunchInstance, assertLaunchInstanceOutcome, assertNativeProcessIdentity, assertProcessContainmentIdentity, } from "../lifecycle/index.js";
|
|
7
7
|
export const DEFAULT_WORKSPACE_ID = "workspace-default";
|
|
8
8
|
const INITIAL_WORKSPACE_ID = DEFAULT_WORKSPACE_ID;
|
|
9
|
+
/** Owns WAL-backed control persistence and reconciles prior-boot records before current use. */
|
|
9
10
|
export class ControlStore {
|
|
10
11
|
bootNonce;
|
|
11
12
|
database;
|
|
@@ -30,8 +31,8 @@ export class ControlStore {
|
|
|
30
31
|
migrate() {
|
|
31
32
|
const versionRow = this.database.prepare("PRAGMA user_version").get();
|
|
32
33
|
const version = versionRow.user_version;
|
|
33
|
-
if (version >
|
|
34
|
-
throw new Error(`control database version ${version} is newer than supported version
|
|
34
|
+
if (version > 6)
|
|
35
|
+
throw new Error(`control database version ${version} is newer than supported version 6`);
|
|
35
36
|
if (version !== 0)
|
|
36
37
|
this.#assertCurrentControlSchema();
|
|
37
38
|
if (version === 0) {
|
|
@@ -187,7 +188,7 @@ export class ControlStore {
|
|
|
187
188
|
CREATE TABLE launch_instances (
|
|
188
189
|
id TEXT PRIMARY KEY,
|
|
189
190
|
owner_client_id TEXT NOT NULL,
|
|
190
|
-
profile_id TEXT NOT NULL CHECK (profile_id IN ('a1', 'pi'
|
|
191
|
+
profile_id TEXT NOT NULL CHECK (profile_id IN ('a1', 'pi')),
|
|
191
192
|
state TEXT NOT NULL CHECK (state IN ('requested', 'active', 'stopping', 'completed', 'interrupted')),
|
|
192
193
|
shutdown_policy TEXT NOT NULL CHECK (shutdown_policy = 'terminate-tree-on-close'),
|
|
193
194
|
guardian_identity_json TEXT NOT NULL CHECK (json_valid(guardian_identity_json)),
|
|
@@ -208,6 +209,40 @@ export class ControlStore {
|
|
|
208
209
|
CREATE INDEX idx_launch_instances_boot ON launch_instances(owner_boot_nonce, state);
|
|
209
210
|
PRAGMA user_version = 5;
|
|
210
211
|
COMMIT;
|
|
212
|
+
`);
|
|
213
|
+
}
|
|
214
|
+
if (version <= 5) {
|
|
215
|
+
this.database.exec(`
|
|
216
|
+
BEGIN IMMEDIATE;
|
|
217
|
+
ALTER TABLE launch_instances RENAME TO launch_instances_v5;
|
|
218
|
+
DROP INDEX idx_launch_instances_owner;
|
|
219
|
+
DROP INDEX idx_launch_instances_boot;
|
|
220
|
+
CREATE TABLE launch_instances (
|
|
221
|
+
id TEXT PRIMARY KEY,
|
|
222
|
+
owner_client_id TEXT NOT NULL,
|
|
223
|
+
profile_id TEXT NOT NULL CHECK (profile_id IN ('a1', 'pi')),
|
|
224
|
+
state TEXT NOT NULL CHECK (state IN ('requested', 'active', 'stopping', 'completed', 'interrupted')),
|
|
225
|
+
shutdown_policy TEXT NOT NULL CHECK (shutdown_policy = 'terminate-tree-on-close'),
|
|
226
|
+
guardian_identity_json TEXT NOT NULL CHECK (json_valid(guardian_identity_json)),
|
|
227
|
+
root_identity_json TEXT CHECK (root_identity_json IS NULL OR json_valid(root_identity_json)),
|
|
228
|
+
containment_identity_json TEXT CHECK (containment_identity_json IS NULL OR json_valid(containment_identity_json)),
|
|
229
|
+
created_at TEXT NOT NULL,
|
|
230
|
+
activated_at TEXT,
|
|
231
|
+
stopping_at TEXT,
|
|
232
|
+
completed_at TEXT,
|
|
233
|
+
outcome_json TEXT CHECK (outcome_json IS NULL OR json_valid(outcome_json)),
|
|
234
|
+
owner_boot_nonce TEXT NOT NULL,
|
|
235
|
+
CHECK ((state = 'requested' AND root_identity_json IS NULL AND containment_identity_json IS NULL AND activated_at IS NULL AND stopping_at IS NULL AND completed_at IS NULL AND outcome_json IS NULL)
|
|
236
|
+
OR (state = 'active' AND root_identity_json IS NOT NULL AND containment_identity_json IS NOT NULL AND activated_at IS NOT NULL AND stopping_at IS NULL AND completed_at IS NULL AND outcome_json IS NULL)
|
|
237
|
+
OR (state = 'stopping' AND root_identity_json IS NOT NULL AND containment_identity_json IS NOT NULL AND activated_at IS NOT NULL AND stopping_at IS NOT NULL AND completed_at IS NULL AND outcome_json IS NULL)
|
|
238
|
+
OR (state IN ('completed', 'interrupted') AND completed_at IS NOT NULL AND outcome_json IS NOT NULL))
|
|
239
|
+
);
|
|
240
|
+
INSERT INTO launch_instances SELECT * FROM launch_instances_v5 WHERE profile_id IN ('a1', 'pi');
|
|
241
|
+
DROP TABLE launch_instances_v5;
|
|
242
|
+
CREATE INDEX idx_launch_instances_owner ON launch_instances(owner_client_id, state);
|
|
243
|
+
CREATE INDEX idx_launch_instances_boot ON launch_instances(owner_boot_nonce, state);
|
|
244
|
+
PRAGMA user_version = 6;
|
|
245
|
+
COMMIT;
|
|
211
246
|
`);
|
|
212
247
|
}
|
|
213
248
|
if (version === 0) {
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type StructuredCapabilityContract } from "
|
|
1
|
+
import { type StructuredCapabilityContract } from "../../contracts/workspace/index.js";
|
|
2
2
|
export type StructuredBackpressureResource = "events" | "commands" | "snapshots" | "attachments" | "reconnect-replay";
|
|
3
3
|
export type StructuredBackpressureAction = "none" | "reject-payload" | "pause-adapter" | "reject-request" | "disconnect-adapter";
|
|
4
4
|
export interface StructuredResourceLease {
|
|
@@ -33,6 +33,7 @@ export type StructuredBackpressureReleaseResult = {
|
|
|
33
33
|
readonly code: "unknown-lease" | "invalid-request";
|
|
34
34
|
readonly diagnostic: string;
|
|
35
35
|
};
|
|
36
|
+
/** Issues bounded resource leases and selects the negotiated backpressure action on exhaustion. */
|
|
36
37
|
export declare class StructuredBackpressureController {
|
|
37
38
|
#private;
|
|
38
39
|
readonly adapterId: string;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import { assertStructuredCapability, } from "
|
|
1
|
+
import { assertStructuredCapability, } from "../../contracts/workspace/index.js";
|
|
2
|
+
/** Issues bounded resource leases and selects the negotiated backpressure action on exhaustion. */
|
|
2
3
|
export class StructuredBackpressureController {
|
|
3
4
|
adapterId;
|
|
4
5
|
#budgets;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type StructuredCapabilityContract, type WorkspaceCommand } from "
|
|
1
|
+
import { type StructuredCapabilityContract, type WorkspaceCommand } from "../../contracts/workspace/index.js";
|
|
2
2
|
export type StructuredCommandRequest = Extract<WorkspaceCommand, {
|
|
3
3
|
readonly type: "structured-command";
|
|
4
4
|
}>;
|
|
@@ -38,6 +38,7 @@ export type StructuredCommandOutcomeResult = {
|
|
|
38
38
|
readonly code: string;
|
|
39
39
|
readonly diagnostic: string;
|
|
40
40
|
};
|
|
41
|
+
/** Tracks structured commands by correlation identity through one idempotent terminal outcome. */
|
|
41
42
|
export declare class StructuredCommandTracker {
|
|
42
43
|
#private;
|
|
43
44
|
readonly agentId: string;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import { assertStructuredCapability, assertWorkspaceCommand, } from "
|
|
1
|
+
import { assertStructuredCapability, assertWorkspaceCommand, } from "../../contracts/workspace/index.js";
|
|
2
|
+
/** Tracks structured commands by correlation identity through one idempotent terminal outcome. */
|
|
2
3
|
export class StructuredCommandTracker {
|
|
3
4
|
agentId;
|
|
4
5
|
#capability;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type AdapterId, type StructuredCapabilityContract, type StructuredFlowLimits } from "
|
|
1
|
+
import { type AdapterId, type StructuredCapabilityContract, type StructuredFlowLimits } from "../../contracts/workspace/index.js";
|
|
2
2
|
export declare const STRUCTURED_ADAPTER_ENVELOPE: string;
|
|
3
3
|
export declare const STRUCTURED_ADAPTER_ENVELOPE_REVISION: 1;
|
|
4
4
|
export declare const REQUIRED_STRUCTURED_FEATURES: readonly ["identity.adapter.v1", "commands.correlated.v1", "events.typed.v1", "flow-control.limits.v1"];
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { WORKSPACE_CONTRACT_VERSION, assertStructuredCapability, } from "
|
|
1
|
+
import { WORKSPACE_CONTRACT_VERSION, assertStructuredCapability, } from "../../contracts/workspace/index.js";
|
|
2
2
|
import { PRODUCT_IDENTITY, PRODUCT_TEXT } from "../../product-identity.js";
|
|
3
3
|
export const STRUCTURED_ADAPTER_ENVELOPE = PRODUCT_IDENTITY.protocol.structuredAgentSchema;
|
|
4
4
|
export const STRUCTURED_ADAPTER_ENVELOPE_REVISION = 1;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type AgentRecoveryAuthority, type StructuredAgentSnapshot, type StructuredCapabilityContract, type StructuredRecoveryAuthority } from "
|
|
1
|
+
import { type AgentRecoveryAuthority, type StructuredAgentSnapshot, type StructuredCapabilityContract, type StructuredRecoveryAuthority } from "../../contracts/workspace/index.js";
|
|
2
2
|
import { StructuredEventReducer, type StructuredRuntimeView } from "./state.js";
|
|
3
3
|
export interface StructuredResumeProof {
|
|
4
4
|
readonly protocolVersion: number;
|
|
@@ -30,6 +30,7 @@ export type StructuredReconnectionResult = {
|
|
|
30
30
|
readonly code: string;
|
|
31
31
|
readonly diagnostic: string;
|
|
32
32
|
};
|
|
33
|
+
/** Accepts a recovery boundary once after validating negotiated identity, proof, and protocol continuity. */
|
|
33
34
|
export declare class StructuredReconnectionManager {
|
|
34
35
|
#private;
|
|
35
36
|
constructor(capability: StructuredCapabilityContract);
|
|
@@ -1,5 +1,6 @@
|
|
|
1
|
-
import { WORKSPACE_CONTRACT_VERSION, assertRecoveryAuthority, assertStructuredAgentSnapshot, assertStructuredCapability, } from "
|
|
1
|
+
import { WORKSPACE_CONTRACT_VERSION, assertRecoveryAuthority, assertStructuredAgentSnapshot, assertStructuredCapability, } from "../../contracts/workspace/index.js";
|
|
2
2
|
import { StructuredEventReducer } from "./state.js";
|
|
3
|
+
/** Accepts a recovery boundary once after validating negotiated identity, proof, and protocol continuity. */
|
|
3
4
|
export class StructuredReconnectionManager {
|
|
4
5
|
#capability;
|
|
5
6
|
#acceptedBoundaries = new Set();
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { type StructuredAgentSnapshot, type StructuredCapabilityContract, type WorkspaceEvent } from "
|
|
1
|
+
import { type StructuredAgentSnapshot, type StructuredCapabilityContract, type WorkspaceEvent } from "../../contracts/workspace/index.js";
|
|
2
2
|
export type StructuredAgentEvent = Extract<WorkspaceEvent, {
|
|
3
3
|
readonly type: "structured-event";
|
|
4
4
|
}>;
|
|
@@ -44,6 +44,7 @@ export type StructuredSnapshotApplyResult = {
|
|
|
44
44
|
readonly code: string;
|
|
45
45
|
readonly diagnostic: string;
|
|
46
46
|
};
|
|
47
|
+
/** Applies ordered structured events and snapshots while exposing gaps as explicit resynchronization. */
|
|
47
48
|
export declare class StructuredEventReducer {
|
|
48
49
|
#private;
|
|
49
50
|
readonly agentId: string;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import { assertStructuredAgentSnapshot, assertStructuredCapability, assertWorkspaceEvent, } from "
|
|
1
|
+
import { assertStructuredAgentSnapshot, assertStructuredCapability, assertWorkspaceEvent, } from "../../contracts/workspace/index.js";
|
|
2
|
+
/** Applies ordered structured events and snapshots while exposing gaps as explicit resynchronization. */
|
|
2
3
|
export class StructuredEventReducer {
|
|
3
4
|
agentId;
|
|
4
5
|
#capability;
|
|
@@ -1,14 +1,16 @@
|
|
|
1
1
|
import { randomUUID } from "node:crypto";
|
|
2
2
|
import { appendFileSync, mkdirSync } from "node:fs";
|
|
3
3
|
import { resolve } from "node:path";
|
|
4
|
-
import { assertImmutableExecutionRoot, readCertifiedReleaseManifest } from "../release/index.js";
|
|
4
|
+
import { assertImmutableExecutionRoot, CohortStateStore, readCertifiedReleaseManifest } from "../release/index.js";
|
|
5
5
|
import { ControlStore } from "../storage/index.js";
|
|
6
|
-
import { resolveProductPaths } from "./paths.js";
|
|
6
|
+
import { resolveCohortEndpoint, resolveProductPaths } from "./paths.js";
|
|
7
7
|
import { SupervisorServer } from "./server.js";
|
|
8
8
|
import { PRODUCT_IDENTITY, PRODUCT_TEXT } from "../../product-identity.js";
|
|
9
9
|
export async function runSupervisor() {
|
|
10
|
-
const
|
|
11
|
-
mkdirSync(
|
|
10
|
+
const productPaths = resolveProductPaths();
|
|
11
|
+
mkdirSync(productPaths.runtimeDir, { recursive: true, mode: 0o700 });
|
|
12
|
+
mkdirSync(productPaths.endpointsDir, { recursive: true, mode: 0o700 });
|
|
13
|
+
let paths = productPaths;
|
|
12
14
|
const log = (message) => appendFileSync(paths.supervisorLogPath, `${new Date().toISOString()} ${message}\n`);
|
|
13
15
|
const releaseRoot = process.env[PRODUCT_IDENTITY.environment.releaseRoot];
|
|
14
16
|
const releaseId = process.env[PRODUCT_IDENTITY.environment.releaseId];
|
|
@@ -17,9 +19,13 @@ export async function runSupervisor() {
|
|
|
17
19
|
throw new Error(PRODUCT_TEXT.diagnostic("supervisor must be launched from a verified immutable release"));
|
|
18
20
|
const release = await readCertifiedReleaseManifest({ releaseRoot, releaseId, contentDigest }, resolve(paths.dataDir, "releases"));
|
|
19
21
|
await assertImmutableExecutionRoot(release, paths.dataDir);
|
|
22
|
+
// Protocol: one endpoint per cohort: a superseded cohort keeps serving what it already has while the
|
|
23
|
+
// installed release listens on its own address.
|
|
24
|
+
paths = { ...productPaths, ...resolveCohortEndpoint(productPaths, release.releaseId) };
|
|
20
25
|
const bootNonce = randomUUID();
|
|
21
26
|
const store = new ControlStore(paths.databasePath, bootNonce);
|
|
22
|
-
const
|
|
27
|
+
const cohortState = new CohortStateStore(paths.dataDir);
|
|
28
|
+
const server = new SupervisorServer(store, paths, release, bootNonce, undefined, undefined, undefined, async () => (await cohortState.read()).references.active);
|
|
23
29
|
await server.listen();
|
|
24
30
|
log(`supervisor ${server.id} listening at ${paths.endpoint} (pid ${process.pid})`);
|
|
25
31
|
let closing = false;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { resolveCohortEndpoint, resolveProductPaths, type CohortEndpointPaths, type ProductPaths, } from "../lifecycle/index.js";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { resolveCohortEndpoint, resolveProductPaths, } from "../lifecycle/index.js";
|
|
@@ -2,6 +2,7 @@ import { type SupervisorSnapshot } from "../lifecycle/index.js";
|
|
|
2
2
|
import { type MaterializedRelease } from "../release/index.js";
|
|
3
3
|
import { ControlStore } from "../storage/index.js";
|
|
4
4
|
import { type ProductPaths } from "./paths.js";
|
|
5
|
+
/** Owns one release-cohort endpoint and the authenticated launch instances registered through it. */
|
|
5
6
|
export declare class SupervisorServer {
|
|
6
7
|
#private;
|
|
7
8
|
readonly store: ControlStore;
|
|
@@ -9,14 +10,31 @@ export declare class SupervisorServer {
|
|
|
9
10
|
readonly terminateProcess: (code: number) => void;
|
|
10
11
|
readonly reconciliationDeadlineMs: number;
|
|
11
12
|
readonly shutdownDeadlineMs: number;
|
|
13
|
+
/**
|
|
14
|
+
* Which release new sessions start on. A cohort that is no longer that release keeps
|
|
15
|
+
* serving the instances it already has, takes no new ones, and exits when its last one
|
|
16
|
+
* leaves. Absent, this supervisor never considers itself superseded.
|
|
17
|
+
*/
|
|
18
|
+
readonly readActiveReleaseId: (() => Promise<string | null>) | null;
|
|
19
|
+
readonly supersededPollMs: number;
|
|
12
20
|
readonly id: `${string}-${string}-${string}-${string}-${string}`;
|
|
13
21
|
readonly bootNonce: string;
|
|
14
22
|
readonly pidStartIdentity: string;
|
|
15
23
|
readonly startedAt: string;
|
|
16
24
|
readonly paths: ProductPaths;
|
|
17
|
-
constructor(store: ControlStore, paths: ProductPaths | undefined, release: MaterializedRelease, bootNonce?: string, terminateProcess?: (code: number) => void, reconciliationDeadlineMs?: number, shutdownDeadlineMs?: number
|
|
25
|
+
constructor(store: ControlStore, paths: ProductPaths | undefined, release: MaterializedRelease, bootNonce?: string, terminateProcess?: (code: number) => void, reconciliationDeadlineMs?: number, shutdownDeadlineMs?: number,
|
|
26
|
+
/**
|
|
27
|
+
* Which release new sessions start on. A cohort that is no longer that release keeps
|
|
28
|
+
* serving the instances it already has, takes no new ones, and exits when its last one
|
|
29
|
+
* leaves. Absent, this supervisor never considers itself superseded.
|
|
30
|
+
*/
|
|
31
|
+
readActiveReleaseId?: (() => Promise<string | null>) | null, supersededPollMs?: number);
|
|
18
32
|
snapshot(): SupervisorSnapshot;
|
|
19
33
|
listen(): Promise<void>;
|
|
34
|
+
/** Whether new sessions start on some other release. */
|
|
35
|
+
get superseded(): boolean;
|
|
36
|
+
/** Leaves, taking this cohort's own endpoint artifacts with it. */
|
|
37
|
+
retire(): Promise<void>;
|
|
20
38
|
close(stopAgents?: boolean): Promise<void>;
|
|
21
39
|
closeForReleaseReplacement(stopAgents: boolean): Promise<void>;
|
|
22
40
|
}
|
|
@@ -8,12 +8,15 @@ import { processIsAlive } from "../release/index.js";
|
|
|
8
8
|
import { ControlStore } from "../storage/index.js";
|
|
9
9
|
import { resolveProductPaths } from "./paths.js";
|
|
10
10
|
import { PRODUCT_IDENTITY, PRODUCT_TEXT } from "../../product-identity.js";
|
|
11
|
+
/** Owns one release-cohort endpoint and the authenticated launch instances registered through it. */
|
|
11
12
|
export class SupervisorServer {
|
|
12
13
|
store;
|
|
13
14
|
release;
|
|
14
15
|
terminateProcess;
|
|
15
16
|
reconciliationDeadlineMs;
|
|
16
17
|
shutdownDeadlineMs;
|
|
18
|
+
readActiveReleaseId;
|
|
19
|
+
supersededPollMs;
|
|
17
20
|
id = randomUUID();
|
|
18
21
|
bootNonce;
|
|
19
22
|
pidStartIdentity = `${process.pid}:${Math.floor(Date.now() - process.uptime() * 1_000)}`;
|
|
@@ -31,12 +34,22 @@ export class SupervisorServer {
|
|
|
31
34
|
#results = new Map();
|
|
32
35
|
#metadataWrites = Promise.resolve();
|
|
33
36
|
#closing = false;
|
|
34
|
-
|
|
37
|
+
#superseded = false;
|
|
38
|
+
#supersededPoll = null;
|
|
39
|
+
constructor(store, paths = resolveProductPaths(), release, bootNonce = randomUUID(), terminateProcess = code => process.exit(code), reconciliationDeadlineMs = 3_000, shutdownDeadlineMs = 1_500,
|
|
40
|
+
/**
|
|
41
|
+
* Which release new sessions start on. A cohort that is no longer that release keeps
|
|
42
|
+
* serving the instances it already has, takes no new ones, and exits when its last one
|
|
43
|
+
* leaves. Absent, this supervisor never considers itself superseded.
|
|
44
|
+
*/
|
|
45
|
+
readActiveReleaseId = null, supersededPollMs = 1_000) {
|
|
35
46
|
this.store = store;
|
|
36
47
|
this.release = release;
|
|
37
48
|
this.terminateProcess = terminateProcess;
|
|
38
49
|
this.reconciliationDeadlineMs = reconciliationDeadlineMs;
|
|
39
50
|
this.shutdownDeadlineMs = shutdownDeadlineMs;
|
|
51
|
+
this.readActiveReleaseId = readActiveReleaseId;
|
|
52
|
+
this.supersededPollMs = supersededPollMs;
|
|
40
53
|
this.bootNonce = bootNonce;
|
|
41
54
|
this.paths = paths;
|
|
42
55
|
for (const instance of store.loadActiveLaunchInstances())
|
|
@@ -56,6 +69,7 @@ export class SupervisorServer {
|
|
|
56
69
|
if (this.#server)
|
|
57
70
|
throw new Error("supervisor is already listening");
|
|
58
71
|
await mkdir(this.paths.runtimeDir, { recursive: true, mode: 0o700 });
|
|
72
|
+
await mkdir(this.paths.endpointsDir, { recursive: true, mode: 0o700 });
|
|
59
73
|
if (platform() !== "win32") {
|
|
60
74
|
if (await endpointIsLive(this.paths.endpoint))
|
|
61
75
|
throw new Error(PRODUCT_TEXT.diagnostic(`supervisor already owns ${this.paths.endpoint}`));
|
|
@@ -71,12 +85,41 @@ export class SupervisorServer {
|
|
|
71
85
|
});
|
|
72
86
|
});
|
|
73
87
|
await this.#writeEndpointMetadata();
|
|
88
|
+
if (this.readActiveReleaseId) {
|
|
89
|
+
const poll = setInterval(() => void this.#refreshCohortRole(), this.supersededPollMs);
|
|
90
|
+
poll.unref();
|
|
91
|
+
this.#supersededPoll = poll;
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
// Invariant: superseding a cohort never interrupts its held instances; it retires only when empty.
|
|
95
|
+
async #refreshCohortRole() {
|
|
96
|
+
if (this.#closing || !this.readActiveReleaseId)
|
|
97
|
+
return;
|
|
98
|
+
const active = await this.readActiveReleaseId().catch(() => null);
|
|
99
|
+
if (active === null)
|
|
100
|
+
return;
|
|
101
|
+
this.#superseded = active !== this.release.releaseId;
|
|
102
|
+
if (this.#superseded && this.#instances.size === 0)
|
|
103
|
+
await this.retire();
|
|
104
|
+
}
|
|
105
|
+
/** Whether new sessions start on some other release. */
|
|
106
|
+
get superseded() {
|
|
107
|
+
return this.#superseded;
|
|
108
|
+
}
|
|
109
|
+
/** Leaves, taking this cohort's own endpoint artifacts with it. */
|
|
110
|
+
async retire() {
|
|
111
|
+
if (this.#closing)
|
|
112
|
+
return;
|
|
113
|
+
await this.close(false);
|
|
74
114
|
}
|
|
75
115
|
async close(stopAgents = false) {
|
|
76
116
|
if (stopAgents && !await this.#drainInstances("update", this.shutdownDeadlineMs)) {
|
|
77
117
|
throw new Error("active launch instances did not release ownership within the shutdown deadline");
|
|
78
118
|
}
|
|
79
119
|
this.#closing = true;
|
|
120
|
+
if (this.#supersededPoll)
|
|
121
|
+
clearInterval(this.#supersededPoll);
|
|
122
|
+
this.#supersededPoll = null;
|
|
80
123
|
for (const client of this.#clients)
|
|
81
124
|
client.destroy();
|
|
82
125
|
if (this.#server)
|
|
@@ -197,6 +240,9 @@ export class SupervisorServer {
|
|
|
197
240
|
#createLaunchInstance(command, socket, clientId) {
|
|
198
241
|
assertNativeProcessIdentity(command.guardianIdentity);
|
|
199
242
|
const existing = this.store.loadLaunchInstance(command.instanceId);
|
|
243
|
+
if (this.#superseded && !existing) {
|
|
244
|
+
throw new Error(PRODUCT_TEXT.diagnostic(`release ${this.release.releaseId} is no longer the release new sessions start on`));
|
|
245
|
+
}
|
|
200
246
|
if (existing) {
|
|
201
247
|
if (existing.ownerClientId !== clientId
|
|
202
248
|
|| existing.profileId !== command.profileId
|
|
@@ -279,6 +325,9 @@ export class SupervisorServer {
|
|
|
279
325
|
this.#uncertainInstances.delete(stored.id);
|
|
280
326
|
this.#unbindOwner(stored.id, socket);
|
|
281
327
|
this.#mutated();
|
|
328
|
+
// Invariant: the last session on a superseded cohort has left; there is nothing here to keep.
|
|
329
|
+
if (this.#superseded && this.#instances.size === 0)
|
|
330
|
+
void this.retire();
|
|
282
331
|
}
|
|
283
332
|
#ownedInstance(instanceId, socket, clientId) {
|
|
284
333
|
const instance = this.#instances.get(instanceId) ?? this.store.loadLaunchInstance(instanceId);
|
|
@@ -370,7 +419,7 @@ export class SupervisorServer {
|
|
|
370
419
|
const deadline = Date.now() + timeoutMs;
|
|
371
420
|
while (Date.now() < deadline) {
|
|
372
421
|
if (this.#instances.size === 0) {
|
|
373
|
-
//
|
|
422
|
+
// Concurrency: allow the terminal command result to flush before closing owner sockets.
|
|
374
423
|
await new Promise(resolvePromise => setTimeout(resolvePromise, 25));
|
|
375
424
|
return this.#instances.size === 0;
|
|
376
425
|
}
|
package/dist/{src/foundation/pi-component-adapter → integrations/pi/components}/components.d.ts
RENAMED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { OwnedUiTranscriptBlock } from "
|
|
1
|
+
import type { OwnedUiTranscriptBlock } from "../../../contracts/owned-ui/index.js";
|
|
2
2
|
export declare function adaptPiUserMessage(block: OwnedUiTranscriptBlock, width: number): readonly string[];
|
|
3
3
|
export declare function adaptPiAssistantMessage(block: OwnedUiTranscriptBlock, width: number): readonly string[];
|
|
4
4
|
export declare function adaptPiToolExecution(block: OwnedUiTranscriptBlock, width: number, cwd: string): readonly string[];
|