@adhdev/daemon-core 0.9.82-rc.49 → 0.9.82-rc.490
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/boot/daemon-lifecycle.d.ts +9 -0
- package/dist/boot/process-hardening.d.ts +50 -0
- package/dist/build-info.d.ts +37 -0
- package/dist/chat/source-machine.d.ts +166 -0
- package/dist/chat/source-resolver.d.ts +104 -0
- package/dist/chat/subscription-updates.d.ts +1 -0
- package/dist/cli-adapter-types.d.ts +68 -2
- package/dist/cli-adapters/cli-script-runner.d.ts +117 -0
- package/dist/cli-adapters/cli-state-engine.d.ts +220 -0
- package/dist/cli-adapters/provider-cli-adapter.d.ts +137 -64
- package/dist/cli-adapters/provider-cli-parse.d.ts +5 -0
- package/dist/cli-adapters/provider-cli-runtime.d.ts +34 -0
- package/dist/cli-adapters/provider-cli-shared.d.ts +74 -0
- package/dist/cli-adapters/pty-write-chunking.d.ts +34 -0
- package/dist/cli-adapters/raw-terminal-io.d.ts +37 -0
- package/dist/cli-adapters/resolve-executable.d.ts +69 -0
- package/dist/cli-adapters/terminal-backends/ghostty-vt-backend.d.ts +6 -3
- package/dist/cli-adapters/terminal-backends/types.d.ts +10 -2
- package/dist/cli-adapters/terminal-screen.d.ts +4 -11
- package/dist/commands/chat-commands-debug-bundle.d.ts +14 -0
- package/dist/commands/chat-commands-read.d.ts +23 -0
- package/dist/commands/chat-commands-scope.d.ts +39 -0
- package/dist/commands/chat-commands-shared.d.ts +33 -0
- package/dist/commands/chat-commands-write.d.ts +14 -0
- package/dist/commands/chat-commands.d.ts +10 -23
- package/dist/commands/cli-manager.d.ts +71 -1
- package/dist/commands/handler.d.ts +125 -0
- package/dist/commands/high-family/index.d.ts +3 -0
- package/dist/commands/high-family/mesh-coordinator-launch.d.ts +2 -0
- package/dist/commands/high-family/mesh-events.d.ts +2 -0
- package/dist/commands/high-family/mesh-status.d.ts +2 -0
- package/dist/commands/high-family/types.d.ts +64 -0
- package/dist/commands/low-family/coordinator-prompt.d.ts +9 -0
- package/dist/commands/low-family/daemon-lifecycle.d.ts +2 -0
- package/dist/commands/low-family/diagnostics.d.ts +2 -0
- package/dist/commands/low-family/index.d.ts +3 -0
- package/dist/commands/low-family/mesh-ledger.d.ts +10 -0
- package/dist/commands/low-family/mesh-node-logs.d.ts +2 -0
- package/dist/commands/low-family/notification.d.ts +2 -0
- package/dist/commands/low-family/refine-config.d.ts +2 -0
- package/dist/commands/low-family/session-host.d.ts +2 -0
- package/dist/commands/low-family/spec-providerdev.d.ts +11 -0
- package/dist/commands/low-family/status-meta.d.ts +2 -0
- package/dist/commands/low-family/types.d.ts +33 -0
- package/dist/commands/med-family/cli-agent.d.ts +2 -0
- package/dist/commands/med-family/fast-forward.d.ts +2 -0
- package/dist/commands/med-family/ide.d.ts +10 -0
- package/dist/commands/med-family/index.d.ts +3 -0
- package/dist/commands/med-family/mesh-crud.d.ts +48 -0
- package/dist/commands/med-family/mesh-host-pairing.d.ts +2 -0
- package/dist/commands/med-family/mesh-queue.d.ts +2 -0
- package/dist/commands/med-family/mesh-restart.d.ts +2 -0
- package/dist/commands/med-family/types.d.ts +152 -0
- package/dist/commands/mesh-coordinator.d.ts +85 -1
- package/dist/commands/router-aggregate-status.d.ts +24 -0
- package/dist/commands/router-mesh-session-owner.d.ts +59 -0
- package/dist/commands/router-refine.d.ts +151 -0
- package/dist/commands/router-worktree-cleanup.d.ts +133 -0
- package/dist/commands/router.d.ts +203 -15
- package/dist/commands/upgrade-helper.d.ts +41 -1
- package/dist/config/chat-history.d.ts +11 -0
- package/dist/config/config.d.ts +19 -0
- package/dist/config/mesh-config.d.ts +65 -0
- package/dist/config/mesh-json-config.d.ts +199 -0
- package/dist/config/registry-resolver.d.ts +54 -0
- package/dist/config/repo-settings.d.ts +77 -0
- package/dist/config/state-store.d.ts +30 -0
- package/dist/daemon/dev-server.d.ts +0 -2
- package/dist/detection/cli-detector.d.ts +17 -0
- package/dist/detection/ide-detector.d.ts +13 -0
- package/dist/detection/win32-ide-version.d.ts +37 -0
- package/dist/git/change-impact-config.d.ts +159 -0
- package/dist/git/git-commands.d.ts +26 -2
- package/dist/git/git-diff.d.ts +6 -0
- package/dist/git/git-executor.d.ts +11 -0
- package/dist/git/git-status.d.ts +80 -0
- package/dist/git/git-types.d.ts +2 -50
- package/dist/git/git-worktree.d.ts +71 -1
- package/dist/git/index.d.ts +3 -1
- package/dist/index.d.ts +70 -17
- package/dist/index.js +53532 -19073
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +53283 -18989
- package/dist/index.mjs.map +1 -1
- package/dist/installer.d.ts +1 -4
- package/dist/ipc/local-ipc-server.d.ts +91 -0
- package/dist/launch.d.ts +1 -1
- package/dist/logging/async-batch-writer.d.ts +10 -0
- package/dist/logging/debug-config.d.ts +16 -0
- package/dist/logging/log-redactor.d.ts +24 -0
- package/dist/logging/log-tail-reader.d.ts +81 -0
- package/dist/logging/logger.d.ts +1 -1
- package/dist/mesh/contracts.d.ts +256 -0
- package/dist/mesh/coordinator-prompt.d.ts +76 -0
- package/dist/mesh/coordinator-registry.d.ts +59 -0
- package/dist/mesh/mesh-active-work.d.ts +203 -0
- package/dist/mesh/mesh-clone-grace.d.ts +8 -0
- package/dist/mesh/mesh-completion-synthesis.d.ts +4 -0
- package/dist/mesh/mesh-coordinator-config.d.ts +21 -0
- package/dist/mesh/mesh-delivery-policy.d.ts +104 -0
- package/dist/mesh/mesh-event-classify.d.ts +7 -0
- package/dist/mesh/mesh-event-forwarding.d.ts +58 -0
- package/dist/mesh/mesh-event-trace.d.ts +21 -0
- package/dist/mesh/mesh-events-coordinator.d.ts +4 -0
- package/dist/mesh/mesh-events-pending.d.ts +258 -0
- package/dist/mesh/mesh-events-stale.d.ts +61 -0
- package/dist/mesh/mesh-events-utils.d.ts +75 -0
- package/dist/mesh/mesh-events.d.ts +6 -49
- package/dist/mesh/mesh-fast-forward.d.ts +81 -0
- package/dist/mesh/mesh-host-ownership.d.ts +21 -1
- package/dist/mesh/mesh-init.d.ts +128 -0
- package/dist/mesh/mesh-ledger-reconciliation.d.ts +23 -4
- package/dist/mesh/mesh-ledger.d.ts +139 -1
- package/dist/mesh/mesh-magi-status.d.ts +63 -0
- package/dist/mesh/mesh-missions.d.ts +281 -0
- package/dist/mesh/mesh-node-identity.d.ts +310 -0
- package/dist/mesh/mesh-queue-assignment.d.ts +162 -0
- package/dist/mesh/mesh-reconcile-acked-hold.d.ts +17 -0
- package/dist/mesh/mesh-reconcile-config.d.ts +6 -0
- package/dist/mesh/mesh-reconcile-identity.d.ts +6 -0
- package/dist/mesh/mesh-reconcile-loop.d.ts +84 -0
- package/dist/mesh/mesh-reconcile-v2-backstop.d.ts +16 -0
- package/dist/mesh/mesh-refine-batch.d.ts +68 -0
- package/dist/mesh/mesh-refine-gates.d.ts +457 -0
- package/dist/mesh/mesh-refine-status.d.ts +62 -0
- package/dist/mesh/mesh-remote-event-pull.d.ts +15 -0
- package/dist/mesh/mesh-review-inbox.d.ts +90 -0
- package/dist/mesh/mesh-routing.d.ts +70 -0
- package/dist/mesh/mesh-runtime-store.d.ts +567 -0
- package/dist/mesh/mesh-scheduling-runtime.d.ts +78 -0
- package/dist/mesh/mesh-task-inflight.d.ts +46 -0
- package/dist/mesh/mesh-task-stats.d.ts +49 -0
- package/dist/mesh/mesh-unresolved-forward-outbox.d.ts +34 -0
- package/dist/mesh/mesh-warmup-deadline.d.ts +68 -0
- package/dist/mesh/mesh-work-queue.d.ts +392 -1
- package/dist/mesh/preview-freshness.d.ts +28 -0
- package/dist/mesh/refine-config.d.ts +97 -0
- package/dist/mesh/worktree-bootstrap-config.d.ts +219 -0
- package/dist/providers/acp-provider-instance.d.ts +5 -0
- package/dist/providers/approval-utils.d.ts +46 -0
- package/dist/providers/chat-message-normalization.d.ts +58 -1
- package/dist/providers/cli-provider-effect-format.d.ts +30 -0
- package/dist/providers/cli-provider-history-dedup.d.ts +17 -0
- package/dist/providers/cli-provider-input-prompt.d.ts +12 -0
- package/dist/providers/cli-provider-instance-types.d.ts +45 -0
- package/dist/providers/cli-provider-instance.d.ts +426 -30
- package/dist/providers/cli-provider-status-helpers.d.ts +46 -0
- package/dist/providers/cli-provider-transcript-merge.d.ts +7 -0
- package/dist/providers/contracts.d.ts +196 -6
- package/dist/providers/external-sources.d.ts +71 -0
- package/dist/providers/manual-attendance.d.ts +79 -0
- package/dist/providers/native-history/antigravity-claim-registry.d.ts +39 -0
- package/dist/providers/native-history/antigravity-cli-transcript.d.ts +137 -0
- package/dist/providers/native-history/claude-cli-transcript.d.ts +70 -0
- package/dist/providers/native-history/codex-cli-transcript.d.ts +73 -0
- package/dist/providers/native-history/constants.d.ts +12 -0
- package/dist/providers/native-history/dispatcher.d.ts +44 -0
- package/dist/providers/native-history/hermes-cli-transcript.d.ts +30 -0
- package/dist/providers/native-history/index.d.ts +13 -0
- package/dist/providers/provider-instance-manager.d.ts +30 -0
- package/dist/providers/provider-instance.d.ts +31 -1
- package/dist/providers/provider-loader.d.ts +42 -5
- package/dist/providers/provider-trust.d.ts +31 -0
- package/dist/providers/read-chat-contract.d.ts +29 -0
- package/dist/providers/sdk/v1/builders/acp/detect-status.d.ts +68 -0
- package/dist/providers/sdk/v1/builders/cli/detect-status.d.ts +86 -0
- package/dist/providers/sdk/v1/builders/cli/parse-approval-squash.d.ts +59 -0
- package/dist/providers/sdk/v1/builders/cli/parse-approval.d.ts +65 -0
- package/dist/providers/sdk/v1/builders/cli/parse-session.d.ts +91 -0
- package/dist/providers/sdk/v1/builders/cli/visible-region.d.ts +42 -0
- package/dist/providers/sdk/v1/fixture-tooling/format.d.ts +126 -0
- package/dist/providers/sdk/v1/fixture-tooling/index.d.ts +8 -0
- package/dist/providers/sdk/v1/fixture-tooling/replay.d.ts +38 -0
- package/dist/providers/sdk/v1/index.d.ts +30 -0
- package/dist/providers/sdk/v1/sandbox/README-design.d.ts +193 -0
- package/dist/providers/sdk/v1/sandbox/require-whitelist.d.ts +74 -0
- package/dist/providers/sdk/v1/sandbox/script-runner.d.ts +98 -0
- package/dist/providers/sdk/v1/types/cli/index.d.ts +277 -0
- package/dist/providers/sdk/v1/types/common/index.d.ts +203 -0
- package/dist/providers/sdk/v1/validators/index.d.ts +5 -0
- package/dist/providers/sdk/v1/validators/manifest.d.ts +40 -0
- package/dist/providers/sdk/v1/validators/taint.d.ts +52 -0
- package/dist/providers/spec/adapter.d.ts +98 -0
- package/dist/providers/spec/cli-adapter.d.ts +223 -0
- package/dist/providers/spec/evaluator.d.ts +45 -0
- package/dist/providers/spec/fsm-driver.d.ts +449 -0
- package/dist/providers/spec/fsm-evaluator.d.ts +93 -0
- package/dist/providers/spec/fsm-loader.d.ts +14 -0
- package/dist/providers/spec/fsm-types.d.ts +202 -0
- package/dist/providers/spec/native-history-executor.d.ts +41 -0
- package/dist/providers/spec/pre-launch-trust.d.ts +16 -0
- package/dist/providers/spec/route.d.ts +4 -0
- package/dist/providers/spec/types.d.ts +244 -0
- package/dist/providers/status-monitor.d.ts +7 -7
- package/dist/providers/transcript-v2.d.ts +176 -0
- package/dist/providers/types/interactive-prompt.d.ts +84 -0
- package/dist/providers/working-dir.d.ts +17 -0
- package/dist/repo-mesh-types.d.ts +616 -12
- package/dist/runtime-defaults.d.ts +2 -0
- package/dist/session-host/managed-host.d.ts +64 -0
- package/dist/session-host/runtime-surface.d.ts +10 -16
- package/dist/sessions/registry.d.ts +26 -0
- package/dist/shared-types-extra.d.ts +2 -4
- package/dist/shared-types.d.ts +110 -55
- package/dist/status/chat-tail-hot-sessions.d.ts +40 -0
- package/dist/status/normalize.d.ts +1 -1
- package/dist/status/normalize.js +1 -0
- package/dist/status/normalize.js.map +1 -1
- package/dist/status/normalize.mjs +1 -0
- package/dist/status/normalize.mjs.map +1 -1
- package/dist/status/reporter.d.ts +2 -0
- package/dist/status/snapshot.d.ts +27 -0
- package/dist/system/hash.d.ts +8 -0
- package/dist/system/load-better-sqlite3.d.ts +21 -0
- package/dist/types.d.ts +20 -6
- package/package.json +11 -4
- package/src/agent-stream/poller.ts +2 -3
- package/src/agent-stream/provider-adapter.ts +1 -1
- package/src/boot/daemon-lifecycle.ts +80 -14
- package/src/boot/process-hardening.ts +89 -0
- package/src/build-info.ts +73 -0
- package/src/chat/source-machine.ts +534 -0
- package/src/chat/source-resolver.ts +0 -0
- package/src/chat/subscription-updates.ts +20 -1
- package/src/cli-adapter-types.d.ts +3 -1
- package/src/cli-adapter-types.ts +68 -2
- package/src/cli-adapters/cli-script-runner.ts +421 -0
- package/src/cli-adapters/cli-state-engine.ts +1282 -0
- package/src/cli-adapters/provider-cli-adapter.d.ts +1 -1
- package/src/cli-adapters/provider-cli-adapter.ts +1048 -1143
- package/src/cli-adapters/provider-cli-parse.d.ts +2 -0
- package/src/cli-adapters/provider-cli-parse.ts +19 -0
- package/src/cli-adapters/provider-cli-runtime.ts +56 -7
- package/src/cli-adapters/provider-cli-shared.d.ts +4 -0
- package/src/cli-adapters/provider-cli-shared.ts +121 -11
- package/src/cli-adapters/pty-transport.ts +2 -1
- package/src/cli-adapters/pty-write-chunking.ts +106 -0
- package/src/cli-adapters/raw-terminal-io.ts +252 -0
- package/src/cli-adapters/resolve-executable.ts +204 -0
- package/src/cli-adapters/session-host-transport.ts +2 -1
- package/src/cli-adapters/terminal-backends/ghostty-vt-backend.ts +63 -29
- package/src/cli-adapters/terminal-backends/types.ts +10 -3
- package/src/cli-adapters/terminal-screen.ts +16 -81
- package/src/commands/chat-commands-debug-bundle.ts +398 -0
- package/src/commands/chat-commands-read.ts +2788 -0
- package/src/commands/chat-commands-scope.ts +54 -0
- package/src/commands/chat-commands-shared.ts +114 -0
- package/src/commands/chat-commands-write.ts +891 -0
- package/src/commands/chat-commands.ts +19 -1841
- package/src/commands/cli-manager.d.ts +2 -0
- package/src/commands/cli-manager.ts +724 -27
- package/src/commands/handler.ts +865 -2
- package/src/commands/high-family/index.ts +28 -0
- package/src/commands/high-family/mesh-coordinator-launch.ts +696 -0
- package/src/commands/high-family/mesh-events.ts +102 -0
- package/src/commands/high-family/mesh-status.ts +857 -0
- package/src/commands/high-family/types.ts +80 -0
- package/src/commands/low-family/coordinator-prompt.ts +125 -0
- package/src/commands/low-family/daemon-lifecycle.ts +120 -0
- package/src/commands/low-family/diagnostics.ts +57 -0
- package/src/commands/low-family/index.ts +37 -0
- package/src/commands/low-family/mesh-ledger.ts +62 -0
- package/src/commands/low-family/mesh-node-logs.ts +87 -0
- package/src/commands/low-family/notification.ts +116 -0
- package/src/commands/low-family/refine-config.ts +106 -0
- package/src/commands/low-family/session-host.ts +282 -0
- package/src/commands/low-family/spec-providerdev.ts +217 -0
- package/src/commands/low-family/status-meta.ts +112 -0
- package/src/commands/low-family/types.ts +39 -0
- package/src/commands/med-family/cli-agent.ts +270 -0
- package/src/commands/med-family/fast-forward.ts +230 -0
- package/src/commands/med-family/ide.ts +163 -0
- package/src/commands/med-family/index.ts +37 -0
- package/src/commands/med-family/mesh-crud.ts +1268 -0
- package/src/commands/med-family/mesh-host-pairing.ts +234 -0
- package/src/commands/med-family/mesh-queue.ts +167 -0
- package/src/commands/med-family/mesh-restart.ts +92 -0
- package/src/commands/med-family/types.ts +153 -0
- package/src/commands/mesh-coordinator.ts +334 -124
- package/src/commands/router-aggregate-status.ts +209 -0
- package/src/commands/router-mesh-session-owner.ts +114 -0
- package/src/commands/router-refine.ts +1794 -0
- package/src/commands/router-worktree-cleanup.ts +870 -0
- package/src/commands/router.ts +567 -4149
- package/src/commands/stream-commands.ts +8 -0
- package/src/commands/upgrade-helper.ts +310 -45
- package/src/config/chat-history.ts +517 -24
- package/src/config/config.ts +30 -0
- package/src/config/mesh-config.ts +300 -24
- package/src/config/mesh-json-config.ts +376 -0
- package/src/config/recent-activity.ts +8 -2
- package/src/config/registry-resolver.ts +100 -0
- package/src/config/repo-settings.ts +111 -0
- package/src/config/state-store.ts +55 -0
- package/src/daemon/dev-auto-implement.ts +3 -2
- package/src/daemon/dev-cli-debug.ts +10 -1
- package/src/daemon/dev-server.ts +0 -541
- package/src/detection/cli-detector.ts +94 -9
- package/src/detection/ide-detector.ts +55 -16
- package/src/detection/win32-ide-version.ts +106 -0
- package/src/git/change-impact-config.ts +354 -0
- package/src/git/git-commands.ts +112 -16
- package/src/git/git-diff.ts +81 -11
- package/src/git/git-executor.ts +12 -0
- package/src/git/git-status.ts +822 -48
- package/src/git/git-types.ts +14 -62
- package/src/git/git-worktree.ts +261 -4
- package/src/git/index.ts +17 -0
- package/src/index.ts +190 -13
- package/src/installer.d.ts +1 -1
- package/src/installer.ts +8 -6
- package/src/ipc/local-ipc-server.ts +278 -0
- package/src/launch.d.ts +1 -1
- package/src/launch.ts +37 -28
- package/src/logging/async-batch-writer.ts +55 -0
- package/src/logging/command-log.ts +7 -5
- package/src/logging/debug-config.ts +25 -0
- package/src/logging/debug-trace.ts +7 -2
- package/src/logging/log-redactor.ts +100 -0
- package/src/logging/log-tail-reader.ts +341 -0
- package/src/logging/logger.ts +14 -7
- package/src/mesh/contracts.ts +510 -0
- package/src/mesh/coordinator-prompt.ts +627 -34
- package/src/mesh/coordinator-registry.ts +121 -0
- package/src/mesh/mesh-active-work.ts +706 -0
- package/src/mesh/mesh-clone-grace.ts +68 -0
- package/src/mesh/mesh-completion-synthesis.ts +416 -0
- package/src/mesh/mesh-coordinator-config.ts +97 -0
- package/src/mesh/mesh-delivery-policy.ts +284 -0
- package/src/mesh/mesh-event-classify.ts +78 -0
- package/src/mesh/mesh-event-forwarding.ts +2030 -0
- package/src/mesh/mesh-event-trace.ts +67 -0
- package/src/mesh/mesh-events-coordinator.ts +32 -0
- package/src/mesh/mesh-events-pending.ts +1548 -0
- package/src/mesh/mesh-events-stale.ts +452 -0
- package/src/mesh/mesh-events-utils.ts +443 -0
- package/src/mesh/mesh-events.ts +43 -1035
- package/src/mesh/mesh-fast-forward.ts +856 -0
- package/src/mesh/mesh-host-ownership.ts +41 -3
- package/src/mesh/mesh-init.ts +350 -0
- package/src/mesh/mesh-ledger-reconciliation.ts +12 -7
- package/src/mesh/mesh-ledger.ts +897 -102
- package/src/mesh/mesh-magi-status.ts +223 -0
- package/src/mesh/mesh-missions.ts +695 -0
- package/src/mesh/mesh-node-identity.ts +2065 -0
- package/src/mesh/mesh-queue-assignment.ts +2498 -0
- package/src/mesh/mesh-reconcile-acked-hold.ts +230 -0
- package/src/mesh/mesh-reconcile-config.ts +66 -0
- package/src/mesh/mesh-reconcile-identity.ts +103 -0
- package/src/mesh/mesh-reconcile-loop.ts +1696 -0
- package/src/mesh/mesh-reconcile-v2-backstop.ts +62 -0
- package/src/mesh/mesh-refine-batch.ts +205 -0
- package/src/mesh/mesh-refine-gates.ts +1792 -0
- package/src/mesh/mesh-refine-status.ts +231 -0
- package/src/mesh/mesh-remote-event-pull.ts +279 -0
- package/src/mesh/mesh-review-inbox.ts +308 -0
- package/src/mesh/mesh-routing.ts +291 -0
- package/src/mesh/mesh-runtime-store.ts +2292 -0
- package/src/mesh/mesh-scheduling-runtime.ts +198 -0
- package/src/mesh/mesh-task-inflight.ts +70 -0
- package/src/mesh/mesh-task-stats.ts +161 -0
- package/src/mesh/mesh-unresolved-forward-outbox.ts +215 -0
- package/src/mesh/mesh-warmup-deadline.ts +152 -0
- package/src/mesh/mesh-work-queue.ts +1489 -145
- package/src/mesh/preview-freshness.ts +163 -0
- package/src/mesh/refine-config.ts +129 -12
- package/src/mesh/worktree-bootstrap-config.ts +599 -0
- package/src/providers/acp-provider-instance.ts +43 -10
- package/src/providers/approval-utils.d.ts +5 -0
- package/src/providers/approval-utils.ts +100 -6
- package/src/providers/chat-message-normalization.ts +126 -4
- package/src/providers/cli-provider-effect-format.ts +53 -0
- package/src/providers/cli-provider-history-dedup.ts +75 -0
- package/src/providers/cli-provider-input-prompt.ts +133 -0
- package/src/providers/cli-provider-instance-types.ts +131 -0
- package/src/providers/cli-provider-instance.ts +2771 -499
- package/src/providers/cli-provider-status-helpers.ts +123 -0
- package/src/providers/cli-provider-transcript-merge.ts +114 -0
- package/src/providers/contracts.d.ts +55 -0
- package/src/providers/contracts.ts +207 -6
- package/src/providers/extension-provider-instance.ts +12 -7
- package/src/providers/external-sources.ts +218 -0
- package/src/providers/ide-provider-instance.ts +35 -12
- package/src/providers/manual-attendance.ts +105 -0
- package/src/providers/native-history/antigravity-claim-registry.ts +138 -0
- package/src/providers/native-history/antigravity-cli-transcript.ts +1275 -0
- package/src/providers/native-history/claude-cli-transcript.ts +396 -0
- package/src/providers/native-history/codex-cli-transcript.ts +479 -0
- package/src/providers/native-history/constants.ts +19 -0
- package/src/providers/native-history/dispatcher.ts +617 -0
- package/src/providers/native-history/hermes-cli-transcript.ts +312 -0
- package/src/providers/native-history/index.ts +30 -0
- package/src/providers/provider-instance-manager.ts +71 -0
- package/src/providers/provider-instance.ts +24 -1
- package/src/providers/provider-loader.ts +700 -55
- package/src/providers/provider-schema.ts +93 -14
- package/src/providers/provider-trust.ts +114 -0
- package/src/providers/read-chat-contract.ts +76 -16
- package/src/providers/sdk/README.md +49 -0
- package/src/providers/sdk/v1/builders/acp/detect-status.ts +144 -0
- package/src/providers/sdk/v1/builders/cli/detect-status.ts +313 -0
- package/src/providers/sdk/v1/builders/cli/parse-approval-squash.ts +158 -0
- package/src/providers/sdk/v1/builders/cli/parse-approval.ts +261 -0
- package/src/providers/sdk/v1/builders/cli/parse-session.ts +276 -0
- package/src/providers/sdk/v1/builders/cli/visible-region.ts +143 -0
- package/src/providers/sdk/v1/fixture-tooling/format.ts +130 -0
- package/src/providers/sdk/v1/fixture-tooling/index.ts +22 -0
- package/src/providers/sdk/v1/fixture-tooling/replay.ts +352 -0
- package/src/providers/sdk/v1/index.ts +152 -0
- package/src/providers/sdk/v1/sandbox/README-design.ts +195 -0
- package/src/providers/sdk/v1/sandbox/require-whitelist.ts +472 -0
- package/src/providers/sdk/v1/sandbox/script-runner.ts +150 -0
- package/src/providers/sdk/v1/schemas/cli/provider.schema.json +538 -0
- package/src/providers/sdk/v1/schemas/primitives/acp-session-protocol-v1.json +131 -0
- package/src/providers/sdk/v1/schemas/primitives/native-history-codex-rollout-v1.json +66 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-approval-squash-v1.json +91 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-assistant-block-v1.json +91 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-cue-ordering-v1.json +47 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-dispatch-order-v1.json +32 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-footer-chrome-v1.json +42 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-index-finder-v1.json +27 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-modal-v1.json +125 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-prompt-marker-v1.json +45 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-session-id-extraction-v1.json +46 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-settled-prompt-v1.json +71 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-spinner-v1.json +83 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-transcript-pty-v1.json +83 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-visible-region-v1.json +57 -0
- package/src/providers/sdk/v1/schemas/primitives/tui-welcome-screen-v1.json +35 -0
- package/src/providers/sdk/v1/types/cli/index.ts +365 -0
- package/src/providers/sdk/v1/types/common/index.ts +229 -0
- package/src/providers/sdk/v1/validators/index.ts +19 -0
- package/src/providers/sdk/v1/validators/manifest.ts +110 -0
- package/src/providers/sdk/v1/validators/taint.ts +309 -0
- package/src/providers/spec/adapter.ts +246 -0
- package/src/providers/spec/cli-adapter.ts +1064 -0
- package/src/providers/spec/evaluator.ts +407 -0
- package/src/providers/spec/fsm-driver.ts +1528 -0
- package/src/providers/spec/fsm-evaluator.ts +290 -0
- package/src/providers/spec/fsm-loader.ts +128 -0
- package/src/providers/spec/fsm-types.ts +301 -0
- package/src/providers/spec/native-history-executor.ts +1241 -0
- package/src/providers/spec/pre-launch-trust.ts +104 -0
- package/src/providers/spec/route.ts +51 -0
- package/src/providers/spec/types.ts +284 -0
- package/src/providers/status-monitor.d.ts +7 -7
- package/src/providers/status-monitor.ts +37 -22
- package/src/providers/transcript-v2.ts +567 -0
- package/src/providers/types/interactive-prompt.ts +536 -0
- package/src/providers/version-archive.ts +64 -24
- package/src/providers/working-dir.ts +23 -0
- package/src/repo-mesh-types.ts +861 -14
- package/src/runtime-defaults.ts +39 -0
- package/src/session-host/managed-host.ts +218 -0
- package/src/session-host/runtime-surface.ts +20 -80
- package/src/sessions/registry.ts +44 -0
- package/src/shared-types-extra.ts +2 -4
- package/src/shared-types.d.ts +8 -0
- package/src/shared-types.ts +148 -55
- package/src/status/builders.ts +69 -6
- package/src/status/chat-tail-hot-sessions.ts +117 -2
- package/src/status/normalize.ts +2 -0
- package/src/status/reporter.ts +19 -1
- package/src/status/snapshot.ts +100 -27
- package/src/system/hash.ts +23 -0
- package/src/system/host-memory.ts +29 -12
- package/src/system/load-better-sqlite3.ts +68 -0
- package/src/types.ts +26 -6
- package/dist/cli-adapters/terminal-backends/xterm-backend.d.ts +0 -17
- package/dist/mesh/mesh-sync.d.ts +0 -53
- package/src/cli-adapters/terminal-backends/ghostty-vt-backend.d.ts +0 -16
- package/src/cli-adapters/terminal-backends/xterm-backend.ts +0 -97
- package/src/mesh/mesh-sync.ts +0 -111
|
@@ -58,6 +58,40 @@ const savedHistoryFileSummaryCache = new Map<string, SavedHistoryFileSummaryCach
|
|
|
58
58
|
const savedHistoryBackgroundRefresh = new Set<string>();
|
|
59
59
|
const savedHistoryRollupInFlight = new Set<string>();
|
|
60
60
|
|
|
61
|
+
// Bounded-tail read cache. The dashboard re-subscribes and polls hot sessions
|
|
62
|
+
// every ~2.5s; without a cache each poll re-reads/parses/sorts the whole
|
|
63
|
+
// conversation just to slice a small tail. We key on (type, sessionId,
|
|
64
|
+
// pagination args) plus the on-disk size+mtime signature so an UNCHANGED
|
|
65
|
+
// session returns the previously computed tail in O(1) and only re-reads when a
|
|
66
|
+
// new message is appended (signature changes). The map is bounded by a small
|
|
67
|
+
// LRU to keep memory flat regardless of how many sessions are touched.
|
|
68
|
+
interface BoundedTailCacheEntry {
|
|
69
|
+
signature: string;
|
|
70
|
+
result: { messages: HistoryMessage[]; hasMore: boolean };
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
const BOUNDED_TAIL_CACHE_MAX_ENTRIES = 64;
|
|
74
|
+
const boundedTailReadCache = new Map<string, BoundedTailCacheEntry>();
|
|
75
|
+
|
|
76
|
+
function readBoundedTailCache(key: string, signature: string): { messages: HistoryMessage[]; hasMore: boolean } | null {
|
|
77
|
+
const cached = boundedTailReadCache.get(key);
|
|
78
|
+
if (!cached || cached.signature !== signature) return null;
|
|
79
|
+
// Refresh LRU recency.
|
|
80
|
+
boundedTailReadCache.delete(key);
|
|
81
|
+
boundedTailReadCache.set(key, cached);
|
|
82
|
+
return cached.result;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
function writeBoundedTailCache(key: string, signature: string, result: { messages: HistoryMessage[]; hasMore: boolean }): void {
|
|
86
|
+
boundedTailReadCache.delete(key);
|
|
87
|
+
boundedTailReadCache.set(key, { signature, result });
|
|
88
|
+
while (boundedTailReadCache.size > BOUNDED_TAIL_CACHE_MAX_ENTRIES) {
|
|
89
|
+
const oldest = boundedTailReadCache.keys().next().value;
|
|
90
|
+
if (oldest === undefined) break;
|
|
91
|
+
boundedTailReadCache.delete(oldest);
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
|
|
61
95
|
interface HistoryMessage {
|
|
62
96
|
ts: string; // ISO timestamp
|
|
63
97
|
receivedAt: number; // epoch ms
|
|
@@ -138,6 +172,15 @@ function collapseReplayAssistantTurns(messages: HistoryMessage[], historyBehavio
|
|
|
138
172
|
}
|
|
139
173
|
|
|
140
174
|
if (message.role === 'assistant') {
|
|
175
|
+
// Tool / activity bubbles are distinct events, not replayed prose —
|
|
176
|
+
// collapsing them would erase every tool call and result after the
|
|
177
|
+
// turn's first assistant message. Only consecutive *prose* assistant
|
|
178
|
+
// turns are the replay-dedup target this collapse exists for.
|
|
179
|
+
const isActivity = message.kind === 'tool' || message.kind === 'terminal' || message.kind === 'thought';
|
|
180
|
+
if (isActivity) {
|
|
181
|
+
collapsed.push(message);
|
|
182
|
+
continue;
|
|
183
|
+
}
|
|
141
184
|
if (sawAssistantSinceLastUser) continue;
|
|
142
185
|
sawAssistantSinceLastUser = true;
|
|
143
186
|
collapsed.push(message);
|
|
@@ -1180,6 +1223,324 @@ function pageHistoryRecords(
|
|
|
1180
1223
|
return { messages: sliced, hasMore: startInclusive > 0 };
|
|
1181
1224
|
}
|
|
1182
1225
|
|
|
1226
|
+
// A finite tail request can be served by reading only the newest files instead
|
|
1227
|
+
// of the whole conversation. Treat very large limits (e.g. MAX_SAFE_INTEGER, or
|
|
1228
|
+
// anything past a generous ceiling) as a full-history request so restore/seed
|
|
1229
|
+
// callers keep their existing behavior.
|
|
1230
|
+
const BOUNDED_TAIL_MAX_LIMIT = 5_000;
|
|
1231
|
+
// Slack added to the requested window before sorting/dedup/collapse so the
|
|
1232
|
+
// boundary message at the top of the tail dedupes/collapses identically to a
|
|
1233
|
+
// full read. Modest and bounded — it only widens the parse window, not output.
|
|
1234
|
+
const BOUNDED_TAIL_SLACK = 50;
|
|
1235
|
+
|
|
1236
|
+
function isBoundedTailRequest(limit: number, offset: number, excludeRecentCount: number): boolean {
|
|
1237
|
+
const numericLimit = Number(limit);
|
|
1238
|
+
if (!Number.isFinite(numericLimit) || numericLimit <= 0) return false;
|
|
1239
|
+
if (numericLimit > BOUNDED_TAIL_MAX_LIMIT) return false;
|
|
1240
|
+
const numericOffset = Number(offset);
|
|
1241
|
+
const numericExclude = Number(excludeRecentCount);
|
|
1242
|
+
if (!Number.isFinite(numericOffset) || !Number.isFinite(numericExclude)) return false;
|
|
1243
|
+
return true;
|
|
1244
|
+
}
|
|
1245
|
+
|
|
1246
|
+
// Byte threshold below which a file is small enough that reading the whole
|
|
1247
|
+
// thing is cheaper than seeking. Reverse-seek pays off only on large files.
|
|
1248
|
+
const REVERSE_TAIL_SMALL_FILE_BYTES = 64 * 1024;
|
|
1249
|
+
// Chunk size for backward reads. We read the file tail one chunk at a time
|
|
1250
|
+
// (newest bytes first) until we have collected enough complete lines.
|
|
1251
|
+
const REVERSE_TAIL_CHUNK_BYTES = 64 * 1024;
|
|
1252
|
+
|
|
1253
|
+
// Per-(file path) incremental tail cache. A hot session's daily JSONL file grows
|
|
1254
|
+
// append-only while it generates; the size+mtime signature on the bounded-tail
|
|
1255
|
+
// read cache therefore invalidates on every append and forces a full re-read.
|
|
1256
|
+
// Here we keep the most recently decoded tail LINES for a file plus the byte
|
|
1257
|
+
// length we read them from. When the file has only grown (append-only: size
|
|
1258
|
+
// increased, the previously-read prefix is unchanged) we read just the new bytes
|
|
1259
|
+
// from `size` onward and splice them onto the retained tail — no full re-parse.
|
|
1260
|
+
// Truncation/rotation (size shrank, or a fresh inode) drops the entry and falls
|
|
1261
|
+
// back to a full reverse-seek.
|
|
1262
|
+
interface IncrementalTailCacheEntry {
|
|
1263
|
+
// File length (bytes) we have already consumed into `lines`.
|
|
1264
|
+
size: number;
|
|
1265
|
+
mtimeMs: number;
|
|
1266
|
+
// Decoded complete lines (oldest-first) covering at least the tail window.
|
|
1267
|
+
// Bounded to TAIL_LINES_RETAINED so memory stays flat for huge files.
|
|
1268
|
+
lines: string[];
|
|
1269
|
+
// True when `lines` is the entire file (head reached), so older pages can
|
|
1270
|
+
// trust that nothing precedes the retained window.
|
|
1271
|
+
coversWholeFile: boolean;
|
|
1272
|
+
}
|
|
1273
|
+
|
|
1274
|
+
// How many trailing lines we retain per file. The bounded-tail caller never
|
|
1275
|
+
// asks for more than BOUNDED_TAIL_MAX_LIMIT + slack; keep a generous multiple so
|
|
1276
|
+
// repeated reads at the same window are served incrementally.
|
|
1277
|
+
const TAIL_LINES_RETAINED = BOUNDED_TAIL_MAX_LIMIT + 2 * BOUNDED_TAIL_SLACK;
|
|
1278
|
+
const INCREMENTAL_TAIL_CACHE_MAX_ENTRIES = 64;
|
|
1279
|
+
const incrementalTailCache = new Map<string, IncrementalTailCacheEntry>();
|
|
1280
|
+
|
|
1281
|
+
function evictIncrementalTailCache(): void {
|
|
1282
|
+
while (incrementalTailCache.size > INCREMENTAL_TAIL_CACHE_MAX_ENTRIES) {
|
|
1283
|
+
const oldest = incrementalTailCache.keys().next().value;
|
|
1284
|
+
if (oldest === undefined) break;
|
|
1285
|
+
incrementalTailCache.delete(oldest);
|
|
1286
|
+
}
|
|
1287
|
+
}
|
|
1288
|
+
|
|
1289
|
+
// Split a Buffer into complete lines plus a leftover head fragment, partitioning
|
|
1290
|
+
// only on the newline byte (0x0A). 0x0A never appears inside a multibyte UTF-8
|
|
1291
|
+
// sequence, so decoding each complete byte segment is boundary-safe. The leftover
|
|
1292
|
+
// (bytes before the first newline) is returned undecoded so a caller stitching
|
|
1293
|
+
// chunks together never splits a multibyte char.
|
|
1294
|
+
function splitBufferLines(buf: Buffer): { head: Buffer; lines: string[] } {
|
|
1295
|
+
const lines: string[] = [];
|
|
1296
|
+
let lineEnd = buf.length;
|
|
1297
|
+
let firstNewline = -1;
|
|
1298
|
+
for (let i = buf.length - 1; i >= 0; i--) {
|
|
1299
|
+
if (buf[i] !== 0x0a) continue;
|
|
1300
|
+
if (i + 1 < lineEnd) {
|
|
1301
|
+
lines.push(buf.toString('utf-8', i + 1, lineEnd));
|
|
1302
|
+
}
|
|
1303
|
+
lineEnd = i;
|
|
1304
|
+
firstNewline = i;
|
|
1305
|
+
}
|
|
1306
|
+
// Lines were collected newest-first; restore oldest-first for the segment
|
|
1307
|
+
// that follows the first (lowest-index) newline.
|
|
1308
|
+
lines.reverse();
|
|
1309
|
+
const head = firstNewline >= 0 ? buf.subarray(0, firstNewline) : buf;
|
|
1310
|
+
return { head, lines };
|
|
1311
|
+
}
|
|
1312
|
+
|
|
1313
|
+
// Read the last bytes of a file, newest-first, until we have at least `needed`
|
|
1314
|
+
// complete lines (or reach the start of the file). Returns lines oldest-first and
|
|
1315
|
+
// whether the whole file was consumed. Boundary-safe: lines are cut on the
|
|
1316
|
+
// newline byte only, so multibyte UTF-8 chars are never split, and a trailing
|
|
1317
|
+
// partial line (no terminating newline) is preserved as a complete final line.
|
|
1318
|
+
function readReverseTailLines(filePath: string, needed: number): { lines: string[]; coversWholeFile: boolean; size: number; mtimeMs: number } {
|
|
1319
|
+
const fd = fs.openSync(filePath, 'r');
|
|
1320
|
+
try {
|
|
1321
|
+
const stat = fs.fstatSync(fd);
|
|
1322
|
+
const size = stat.size;
|
|
1323
|
+
let position = size;
|
|
1324
|
+
// `carry` holds bytes belonging to a line that straddles the current
|
|
1325
|
+
// chunk boundary (its start is in an older, not-yet-read chunk).
|
|
1326
|
+
let carry: Buffer = Buffer.alloc(0);
|
|
1327
|
+
const collected: string[] = [];
|
|
1328
|
+
|
|
1329
|
+
while (position > 0 && collected.length < needed) {
|
|
1330
|
+
const chunkSize = Math.min(REVERSE_TAIL_CHUNK_BYTES, position);
|
|
1331
|
+
position -= chunkSize;
|
|
1332
|
+
const chunk = Buffer.alloc(chunkSize);
|
|
1333
|
+
fs.readSync(fd, chunk, 0, chunkSize, position);
|
|
1334
|
+
const combined = carry.length ? Buffer.concat([chunk, carry]) : chunk;
|
|
1335
|
+
const { head, lines } = splitBufferLines(combined);
|
|
1336
|
+
// `head` is the (possibly partial) line whose start lies further back;
|
|
1337
|
+
// hold it for the next (older) chunk to complete.
|
|
1338
|
+
carry = head;
|
|
1339
|
+
// `lines` are oldest-first within this combined buffer; prepend them
|
|
1340
|
+
// ahead of what we already collected (which is strictly newer).
|
|
1341
|
+
for (let i = lines.length - 1; i >= 0; i--) {
|
|
1342
|
+
collected.push(lines[i]);
|
|
1343
|
+
}
|
|
1344
|
+
}
|
|
1345
|
+
|
|
1346
|
+
const reachedStart = position <= 0;
|
|
1347
|
+
if (reachedStart && carry.length) {
|
|
1348
|
+
// Leftover head at the start of the file is itself a complete line.
|
|
1349
|
+
collected.push(carry.toString('utf-8'));
|
|
1350
|
+
}
|
|
1351
|
+
// `collected` is newest-first; restore oldest-first.
|
|
1352
|
+
collected.reverse();
|
|
1353
|
+
return { lines: collected, coversWholeFile: reachedStart, size, mtimeMs: stat.mtimeMs };
|
|
1354
|
+
} finally {
|
|
1355
|
+
fs.closeSync(fd);
|
|
1356
|
+
}
|
|
1357
|
+
}
|
|
1358
|
+
|
|
1359
|
+
// Return the tail lines (oldest-first) for a single history file, reading as
|
|
1360
|
+
// little of the file as possible. Strategy:
|
|
1361
|
+
// - Small files: one readFileSync (seeking is not worth the syscalls).
|
|
1362
|
+
// - Large files: reverse byte-seek for the newest `needed` lines.
|
|
1363
|
+
// - Append-only growth since the last read: read only the appended bytes and
|
|
1364
|
+
// splice them onto the retained tail (no full re-parse) — this is what keeps
|
|
1365
|
+
// a hot, still-generating session cheap to poll.
|
|
1366
|
+
// `needed` is a soft floor; we may return more (whole small files / retained
|
|
1367
|
+
// window). Lines include any trailing partial (unterminated) final line.
|
|
1368
|
+
function readFileTailLines(filePath: string, needed: number): { lines: string[]; coversWholeFile: boolean } {
|
|
1369
|
+
let stat: fs.Stats;
|
|
1370
|
+
try {
|
|
1371
|
+
stat = fs.statSync(filePath);
|
|
1372
|
+
} catch {
|
|
1373
|
+
return { lines: [], coversWholeFile: true };
|
|
1374
|
+
}
|
|
1375
|
+
const size = stat.size;
|
|
1376
|
+
const mtimeMs = stat.mtimeMs;
|
|
1377
|
+
if (size === 0) {
|
|
1378
|
+
incrementalTailCache.delete(filePath);
|
|
1379
|
+
return { lines: [], coversWholeFile: true };
|
|
1380
|
+
}
|
|
1381
|
+
|
|
1382
|
+
const cached = incrementalTailCache.get(filePath);
|
|
1383
|
+
if (cached) {
|
|
1384
|
+
if (cached.size === size && cached.mtimeMs === mtimeMs) {
|
|
1385
|
+
// Unchanged since last read — reuse retained tail. Refresh LRU.
|
|
1386
|
+
incrementalTailCache.delete(filePath);
|
|
1387
|
+
incrementalTailCache.set(filePath, cached);
|
|
1388
|
+
if (cached.coversWholeFile || cached.lines.length >= needed) {
|
|
1389
|
+
return { lines: cached.lines, coversWholeFile: cached.coversWholeFile };
|
|
1390
|
+
}
|
|
1391
|
+
// Retained window is smaller than this request needs; fall through
|
|
1392
|
+
// to a fresh reverse-seek for the larger window.
|
|
1393
|
+
} else if (size > cached.size) {
|
|
1394
|
+
// Append-only growth: the prefix [0, cached.size) is assumed
|
|
1395
|
+
// unchanged (JSONL is append-only). Read just the new bytes and
|
|
1396
|
+
// stitch them — but verify the byte at cached.size-1 is still the
|
|
1397
|
+
// newline that terminated our last retained line, so a rewrite that
|
|
1398
|
+
// happens to grow the file (compaction) is detected and rejected.
|
|
1399
|
+
const incremental = tryIncrementalTailGrowth(filePath, cached, size, mtimeMs, needed);
|
|
1400
|
+
if (incremental) return { lines: incremental.lines, coversWholeFile: incremental.coversWholeFile };
|
|
1401
|
+
}
|
|
1402
|
+
// size shrank (truncation/rotation) or incremental failed → drop & reload.
|
|
1403
|
+
incrementalTailCache.delete(filePath);
|
|
1404
|
+
}
|
|
1405
|
+
|
|
1406
|
+
if (size <= REVERSE_TAIL_SMALL_FILE_BYTES) {
|
|
1407
|
+
let content: string;
|
|
1408
|
+
try {
|
|
1409
|
+
content = fs.readFileSync(filePath, 'utf-8');
|
|
1410
|
+
} catch {
|
|
1411
|
+
return { lines: [], coversWholeFile: true };
|
|
1412
|
+
}
|
|
1413
|
+
const lines = content.split('\n');
|
|
1414
|
+
// A trailing newline yields a final empty element; drop only that one so
|
|
1415
|
+
// an unterminated partial last line is still preserved.
|
|
1416
|
+
if (lines.length && lines[lines.length - 1] === '') lines.pop();
|
|
1417
|
+
storeIncrementalTailCache(filePath, size, mtimeMs, lines, true);
|
|
1418
|
+
return { lines, coversWholeFile: true };
|
|
1419
|
+
}
|
|
1420
|
+
|
|
1421
|
+
let result: { lines: string[]; coversWholeFile: boolean; size: number; mtimeMs: number };
|
|
1422
|
+
try {
|
|
1423
|
+
result = readReverseTailLines(filePath, needed);
|
|
1424
|
+
} catch {
|
|
1425
|
+
return { lines: [], coversWholeFile: true };
|
|
1426
|
+
}
|
|
1427
|
+
storeIncrementalTailCache(filePath, result.size, result.mtimeMs, result.lines, result.coversWholeFile);
|
|
1428
|
+
return { lines: result.lines, coversWholeFile: result.coversWholeFile };
|
|
1429
|
+
}
|
|
1430
|
+
|
|
1431
|
+
// Read appended bytes [cached.size, size) and splice them onto the retained tail.
|
|
1432
|
+
// Returns null if the prior byte is not a newline (the retained tail did not end
|
|
1433
|
+
// on a record boundary, e.g. the file was rewritten) so the caller can full-reload.
|
|
1434
|
+
function tryIncrementalTailGrowth(
|
|
1435
|
+
filePath: string,
|
|
1436
|
+
cached: IncrementalTailCacheEntry,
|
|
1437
|
+
size: number,
|
|
1438
|
+
mtimeMs: number,
|
|
1439
|
+
needed: number,
|
|
1440
|
+
): { lines: string[]; coversWholeFile: boolean } | null {
|
|
1441
|
+
const fd = fs.openSync(filePath, 'r');
|
|
1442
|
+
try {
|
|
1443
|
+
// Confirm the byte ending the previously-read prefix is still a newline.
|
|
1444
|
+
if (cached.size > 0) {
|
|
1445
|
+
const boundary = Buffer.alloc(1);
|
|
1446
|
+
fs.readSync(fd, boundary, 0, 1, cached.size - 1);
|
|
1447
|
+
if (boundary[0] !== 0x0a) return null;
|
|
1448
|
+
}
|
|
1449
|
+
const appendedLength = size - cached.size;
|
|
1450
|
+
const appended = Buffer.alloc(appendedLength);
|
|
1451
|
+
fs.readSync(fd, appended, 0, appendedLength, cached.size);
|
|
1452
|
+
const newLines = appended.toString('utf-8').split('\n');
|
|
1453
|
+
if (newLines.length && newLines[newLines.length - 1] === '') newLines.pop();
|
|
1454
|
+
const merged = cached.lines.concat(newLines);
|
|
1455
|
+
// Keep memory flat: retain only the trailing window.
|
|
1456
|
+
const trimmed = merged.length > TAIL_LINES_RETAINED
|
|
1457
|
+
? merged.slice(merged.length - TAIL_LINES_RETAINED)
|
|
1458
|
+
: merged;
|
|
1459
|
+
const coversWholeFile = cached.coversWholeFile && trimmed.length === merged.length;
|
|
1460
|
+
storeIncrementalTailCache(filePath, size, mtimeMs, trimmed, coversWholeFile);
|
|
1461
|
+
if (coversWholeFile || trimmed.length >= needed) {
|
|
1462
|
+
return { lines: trimmed, coversWholeFile };
|
|
1463
|
+
}
|
|
1464
|
+
// Should not happen (we only grew), but be safe.
|
|
1465
|
+
return { lines: trimmed, coversWholeFile };
|
|
1466
|
+
} catch {
|
|
1467
|
+
return null;
|
|
1468
|
+
} finally {
|
|
1469
|
+
fs.closeSync(fd);
|
|
1470
|
+
}
|
|
1471
|
+
}
|
|
1472
|
+
|
|
1473
|
+
function storeIncrementalTailCache(filePath: string, size: number, mtimeMs: number, lines: string[], coversWholeFile: boolean): void {
|
|
1474
|
+
const retained = lines.length > TAIL_LINES_RETAINED ? lines.slice(lines.length - TAIL_LINES_RETAINED) : lines;
|
|
1475
|
+
const covers = coversWholeFile && retained.length === lines.length;
|
|
1476
|
+
incrementalTailCache.delete(filePath);
|
|
1477
|
+
incrementalTailCache.set(filePath, { size, mtimeMs, lines: retained, coversWholeFile: covers });
|
|
1478
|
+
evictIncrementalTailCache();
|
|
1479
|
+
}
|
|
1480
|
+
|
|
1481
|
+
// Read newest-first only as many files as needed to cover the requested window
|
|
1482
|
+
// plus slack. listHistoryFiles already returns files reversed (newest-first), so
|
|
1483
|
+
// we accumulate (de-duped) candidates from the end and stop once we have enough,
|
|
1484
|
+
// then hand the bounded window to pageHistoryRecords in chronological order.
|
|
1485
|
+
function readBoundedTailRecords(
|
|
1486
|
+
agentType: string,
|
|
1487
|
+
dir: string,
|
|
1488
|
+
files: string[],
|
|
1489
|
+
needed: number,
|
|
1490
|
+
): { records: HistoryMessage[]; readAllFiles: boolean } {
|
|
1491
|
+
const collected: HistoryMessage[] = [];
|
|
1492
|
+
const seen = new Set<string>();
|
|
1493
|
+
let readAllFiles = true;
|
|
1494
|
+
|
|
1495
|
+
for (let f = 0; f < files.length; f++) {
|
|
1496
|
+
const filePath = path.join(dir, files[f]);
|
|
1497
|
+
// Read only the file tail needed to top up the window — for a large
|
|
1498
|
+
// single-day file this seeks the last `needed` lines instead of parsing
|
|
1499
|
+
// the whole file. We re-derive the per-file floor each iteration from how
|
|
1500
|
+
// many records are still missing (plus slack so dedup at the boundary is
|
|
1501
|
+
// stable), capped at `needed`.
|
|
1502
|
+
const remaining = Math.max(0, needed - collected.length);
|
|
1503
|
+
const perFileNeeded = Math.min(needed, remaining + BOUNDED_TAIL_SLACK);
|
|
1504
|
+
const { lines, coversWholeFile } = readFileTailLines(filePath, perFileNeeded);
|
|
1505
|
+
// Walk this file's tail lines newest-first so we fill the tail window from
|
|
1506
|
+
// the bottom. seen-dedup keeps the same first-wins-by-newest semantics the
|
|
1507
|
+
// full read produced (files are processed newest-first there too).
|
|
1508
|
+
for (let i = lines.length - 1; i >= 0; i--) {
|
|
1509
|
+
const line = lines[i];
|
|
1510
|
+
if (!line) continue;
|
|
1511
|
+
try {
|
|
1512
|
+
const parsed = JSON.parse(line) as HistoryMessage;
|
|
1513
|
+
const sanitizedMessage = sanitizeHistoryMessage(agentType, parsed);
|
|
1514
|
+
if (!sanitizedMessage) continue;
|
|
1515
|
+
const hash = buildHistoryMessageHash(agentType, sanitizedMessage);
|
|
1516
|
+
if (seen.has(hash)) continue;
|
|
1517
|
+
seen.add(hash);
|
|
1518
|
+
collected.push(sanitizedMessage);
|
|
1519
|
+
} catch { /* skip invalid lines */ }
|
|
1520
|
+
}
|
|
1521
|
+
// If we only read this file's tail (its head was not reached), older
|
|
1522
|
+
// messages remain within this very file — the conversation is NOT fully
|
|
1523
|
+
// represented even if this is the last file, so hasMore must stay true.
|
|
1524
|
+
if (!coversWholeFile) {
|
|
1525
|
+
readAllFiles = false;
|
|
1526
|
+
break;
|
|
1527
|
+
}
|
|
1528
|
+
// Stop once we have the window AND there is at least one more file (so a
|
|
1529
|
+
// potential older boundary message exists). If this is the last file we
|
|
1530
|
+
// fall through and mark the whole history as read.
|
|
1531
|
+
if (collected.length >= needed && f < files.length - 1) {
|
|
1532
|
+
readAllFiles = false;
|
|
1533
|
+
break;
|
|
1534
|
+
}
|
|
1535
|
+
}
|
|
1536
|
+
|
|
1537
|
+
// collected is newest-first across the bounded window; restore chronological
|
|
1538
|
+
// (oldest-first) order before paging. pageHistoryRecords re-sorts by
|
|
1539
|
+
// receivedAt regardless, so this is purely for stable input ordering.
|
|
1540
|
+
collected.reverse();
|
|
1541
|
+
return { records: collected, readAllFiles };
|
|
1542
|
+
}
|
|
1543
|
+
|
|
1183
1544
|
export function readChatHistory(
|
|
1184
1545
|
agentType: string,
|
|
1185
1546
|
offset: number = 0,
|
|
@@ -1196,6 +1557,33 @@ export function readChatHistory(
|
|
|
1196
1557
|
// JSONL file list — filter by persistent history key when specified
|
|
1197
1558
|
const files = listHistoryFiles(dir, historySessionId);
|
|
1198
1559
|
|
|
1560
|
+
const bounded = isBoundedTailRequest(limit, offset, excludeRecentCount);
|
|
1561
|
+
|
|
1562
|
+
if (bounded) {
|
|
1563
|
+
const fileSignatures = buildSavedHistoryFileSignatureMap(dir, files);
|
|
1564
|
+
const cacheKey = `${sanitized}\0${historySessionId || ''}\0${offset}\0${limit}\0${excludeRecentCount}\0${historyBehavior?.collapseConsecutiveAssistantTurns ? '1' : '0'}`;
|
|
1565
|
+
const signature = buildSavedHistoryCacheSignature(files, fileSignatures);
|
|
1566
|
+
const cached = readBoundedTailCache(cacheKey, signature);
|
|
1567
|
+
if (cached) return cached;
|
|
1568
|
+
|
|
1569
|
+
// Window large enough that the top boundary dedupes/collapses the same
|
|
1570
|
+
// as a full read. hasMore reflects whether older messages exist beyond
|
|
1571
|
+
// the window we actually read.
|
|
1572
|
+
const numericLimit = Math.max(1, Number(limit));
|
|
1573
|
+
const numericOffset = Math.max(0, Number(offset));
|
|
1574
|
+
const numericExclude = Math.max(0, Number(excludeRecentCount));
|
|
1575
|
+
const needed = numericLimit + numericOffset + numericExclude + Math.max(BOUNDED_TAIL_SLACK, numericLimit);
|
|
1576
|
+
const { records, readAllFiles } = readBoundedTailRecords(agentType, dir, files, needed);
|
|
1577
|
+
const result = pageHistoryRecords(agentType, records, offset, limit, excludeRecentCount, historyBehavior);
|
|
1578
|
+
// If we read every file, the conversation is fully represented in the
|
|
1579
|
+
// window and pageHistoryRecords' hasMore is authoritative. If we
|
|
1580
|
+
// stopped early there are older messages we never read, so hasMore
|
|
1581
|
+
// must stay true regardless of the in-window slice position.
|
|
1582
|
+
const boundedResult = readAllFiles ? result : { messages: result.messages, hasMore: true };
|
|
1583
|
+
writeBoundedTailCache(cacheKey, signature, boundedResult);
|
|
1584
|
+
return boundedResult;
|
|
1585
|
+
}
|
|
1586
|
+
|
|
1199
1587
|
const allMessages: HistoryMessage[] = [];
|
|
1200
1588
|
const seen = new Set<string>();
|
|
1201
1589
|
|
|
@@ -1345,7 +1733,21 @@ function rewriteCanonicalSavedHistory(agentType: string, historySessionId: strin
|
|
|
1345
1733
|
|
|
1346
1734
|
export type ProviderNativeHistoryScripts = Record<string, ((input: any) => any) | undefined>;
|
|
1347
1735
|
|
|
1348
|
-
type ProviderNativeHistoryReadResult = {
|
|
1736
|
+
type ProviderNativeHistoryReadResult = {
|
|
1737
|
+
records: HistoryMessage[];
|
|
1738
|
+
sourcePath: string;
|
|
1739
|
+
sourceMtimeMs: number;
|
|
1740
|
+
providerSessionId?: string;
|
|
1741
|
+
workspace?: string;
|
|
1742
|
+
nativeHistoryCoverage?: string;
|
|
1743
|
+
partialReason?: string;
|
|
1744
|
+
unavailableReason?: string;
|
|
1745
|
+
// Antigravity: whether the resolved conversation was owner-token-confirmed as
|
|
1746
|
+
// this session's own (vs a bare recency pick). Threaded to the read-path so
|
|
1747
|
+
// the workspace-latest pin + first-read safe-mapping trust only fire for a
|
|
1748
|
+
// confirmed uuid. See dispatcher NativeHistoryResult.ownerConfirmed.
|
|
1749
|
+
ownerConfirmed?: boolean;
|
|
1750
|
+
};
|
|
1349
1751
|
|
|
1350
1752
|
function getNativeHistoryScriptName(canonicalHistory: ProviderCanonicalHistoryConfig | undefined, key: 'readSession' | 'listSessions'): string {
|
|
1351
1753
|
const configured = canonicalHistory?.scripts?.[key];
|
|
@@ -1367,19 +1769,42 @@ function normalizeProviderNativeHistoryRecords(agentType: string, historySession
|
|
|
1367
1769
|
if (!Array.isArray(records)) return [];
|
|
1368
1770
|
const normalizedSessionId = normalizeSavedHistorySessionId(historySessionId);
|
|
1369
1771
|
return records
|
|
1370
|
-
.map((record: any) =>
|
|
1371
|
-
|
|
1372
|
-
|
|
1373
|
-
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
|
|
1379
|
-
|
|
1380
|
-
|
|
1381
|
-
|
|
1382
|
-
|
|
1772
|
+
.map((record: any) => {
|
|
1773
|
+
const base: HistoryMessage = {
|
|
1774
|
+
ts: typeof record?.ts === 'string' ? record.ts : new Date(Number(record?.receivedAt) || Date.now()).toISOString(),
|
|
1775
|
+
receivedAt: Number(record?.receivedAt) || Date.parse(record?.ts || '') || Date.now(),
|
|
1776
|
+
role: record?.role,
|
|
1777
|
+
content: String(record?.content || ''),
|
|
1778
|
+
kind: record?.kind || (record?.role === 'system' ? 'session_start' : 'standard'),
|
|
1779
|
+
senderName: record?.senderName,
|
|
1780
|
+
agent: agentType,
|
|
1781
|
+
instanceId: record?.instanceId,
|
|
1782
|
+
historySessionId: normalizeSavedHistorySessionId(record?.historySessionId || normalizedSessionId),
|
|
1783
|
+
sessionTitle: record?.sessionTitle,
|
|
1784
|
+
workspace: record?.workspace,
|
|
1785
|
+
} as HistoryMessage;
|
|
1786
|
+
// (A2.3 v2 identity passthrough) — if the producer (native_history.js)
|
|
1787
|
+
// emitted v2 stable identity, keep it across the sanitize layer so
|
|
1788
|
+
// downstream (chat-commands.ts normalizeNativeHistoryMessages) sees
|
|
1789
|
+
// the producer's contract output instead of recomputing from index
|
|
1790
|
+
// and content hash. v1 producers without these fields are unaffected.
|
|
1791
|
+
if (typeof record?.providerUnitKey === 'string' && record.providerUnitKey) {
|
|
1792
|
+
(base as any).providerUnitKey = record.providerUnitKey;
|
|
1793
|
+
}
|
|
1794
|
+
if (typeof record?.bubbleId === 'string' && record.bubbleId) {
|
|
1795
|
+
(base as any).bubbleId = record.bubbleId;
|
|
1796
|
+
}
|
|
1797
|
+
if (typeof record?.sequence === 'number' && Number.isFinite(record.sequence)) {
|
|
1798
|
+
(base as any).sequence = record.sequence;
|
|
1799
|
+
}
|
|
1800
|
+
if (typeof record?._turnKey === 'string' && record._turnKey) {
|
|
1801
|
+
(base as any)._turnKey = record._turnKey;
|
|
1802
|
+
}
|
|
1803
|
+
if (typeof record?.bubbleState === 'string' && record.bubbleState) {
|
|
1804
|
+
(base as any).bubbleState = record.bubbleState;
|
|
1805
|
+
}
|
|
1806
|
+
return sanitizeHistoryMessage(agentType, base);
|
|
1807
|
+
})
|
|
1383
1808
|
.filter(Boolean) as HistoryMessage[];
|
|
1384
1809
|
}
|
|
1385
1810
|
|
|
@@ -1387,27 +1812,60 @@ function callProviderNativeHistoryRead(
|
|
|
1387
1812
|
agentType: string,
|
|
1388
1813
|
canonicalHistory: ProviderCanonicalHistoryConfig | undefined,
|
|
1389
1814
|
scripts: ProviderNativeHistoryScripts | undefined,
|
|
1390
|
-
historySessionId: string,
|
|
1815
|
+
historySessionId: string | undefined,
|
|
1391
1816
|
workspace?: string,
|
|
1817
|
+
excludeInProgressTurn?: boolean,
|
|
1818
|
+
sessionStartedAtMs?: number,
|
|
1819
|
+
envOverrides?: Record<string, string>,
|
|
1820
|
+
forceRefresh?: boolean,
|
|
1821
|
+
instanceId?: string,
|
|
1392
1822
|
): ProviderNativeHistoryReadResult | null {
|
|
1393
1823
|
const fn = getProviderNativeHistoryScript(scripts, canonicalHistory, 'readSession');
|
|
1394
1824
|
if (!fn) return null;
|
|
1825
|
+
const normalizedSessionId = normalizeSavedHistorySessionId(historySessionId || '');
|
|
1826
|
+
const normalizedInstanceId = typeof instanceId === 'string' ? instanceId.trim() : '';
|
|
1395
1827
|
const result = fn({
|
|
1396
1828
|
agentType,
|
|
1397
|
-
sessionId:
|
|
1398
|
-
|
|
1829
|
+
sessionId: normalizedSessionId,
|
|
1830
|
+
// Arm the native-history executor's session pin guard. When the
|
|
1831
|
+
// instance is already bound to a provider session, pass that id as
|
|
1832
|
+
// `providerSessionId` so the executor rejects any *other* newest
|
|
1833
|
+
// session it would otherwise pick (hermes ≥0.14 creates a fresh
|
|
1834
|
+
// `sessions` row per internal sub-session, so an unpinned
|
|
1835
|
+
// newest-wins query drifts to a different id on every read →
|
|
1836
|
+
// re-bind churn + unbounded history re-hydration). When there is no
|
|
1837
|
+
// bound id yet (first-bind / workspace-only discovery) this is '',
|
|
1838
|
+
// which leaves the guard disarmed so discovery still works.
|
|
1839
|
+
providerSessionId: normalizedSessionId,
|
|
1840
|
+
historySessionId: normalizedSessionId,
|
|
1841
|
+
// Stable per-session owner key for the antigravity conversation-claim
|
|
1842
|
+
// registry (see dispatcher.resolveAntigravityPath / antigravityOwnerToken).
|
|
1843
|
+
// Equals the session registry's sessionId and the provider instance's
|
|
1844
|
+
// instanceId, so read side and instance side derive the identical claim
|
|
1845
|
+
// owner token and two concurrent antigravity sessions never cross-bind.
|
|
1846
|
+
instanceId: normalizedInstanceId || undefined,
|
|
1399
1847
|
workspace,
|
|
1400
1848
|
format: canonicalHistory?.format,
|
|
1401
1849
|
watchPath: canonicalHistory?.watchPath,
|
|
1402
|
-
|
|
1850
|
+
excludeInProgressTurn: excludeInProgressTurn === true,
|
|
1851
|
+
sessionStartedAtMs,
|
|
1852
|
+
envOverrides,
|
|
1853
|
+
forceRefresh: forceRefresh === true,
|
|
1854
|
+
args: { sessionId: normalizedSessionId, historySessionId: normalizedSessionId, instanceId: normalizedInstanceId || undefined, workspace, excludeInProgressTurn: excludeInProgressTurn === true, sessionStartedAtMs, envOverrides, forceRefresh: forceRefresh === true },
|
|
1403
1855
|
});
|
|
1404
1856
|
if (!result || typeof result !== 'object') return null;
|
|
1405
|
-
const records = normalizeProviderNativeHistoryRecords(agentType,
|
|
1857
|
+
const records = normalizeProviderNativeHistoryRecords(agentType, normalizedSessionId, (result as any).messages || (result as any).records);
|
|
1406
1858
|
if (records.length === 0) return null;
|
|
1407
1859
|
return {
|
|
1408
1860
|
records,
|
|
1409
1861
|
sourcePath: typeof (result as any).sourcePath === 'string' ? (result as any).sourcePath : '',
|
|
1410
1862
|
sourceMtimeMs: Number((result as any).sourceMtimeMs) || 0,
|
|
1863
|
+
providerSessionId: typeof (result as any).providerSessionId === 'string' ? (result as any).providerSessionId.trim() : undefined,
|
|
1864
|
+
workspace: typeof (result as any).workspace === 'string' ? (result as any).workspace.trim() : undefined,
|
|
1865
|
+
nativeHistoryCoverage: typeof (result as any).nativeHistoryCoverage === 'string' ? (result as any).nativeHistoryCoverage.trim() : undefined,
|
|
1866
|
+
partialReason: typeof (result as any).partialReason === 'string' ? (result as any).partialReason.trim() : undefined,
|
|
1867
|
+
unavailableReason: typeof (result as any).unavailableReason === 'string' ? (result as any).unavailableReason.trim() : undefined,
|
|
1868
|
+
ownerConfirmed: typeof (result as any).ownerConfirmed === 'boolean' ? (result as any).ownerConfirmed : undefined,
|
|
1411
1869
|
};
|
|
1412
1870
|
}
|
|
1413
1871
|
|
|
@@ -1417,10 +1875,16 @@ function buildNativeHistoryReadResult(
|
|
|
1417
1875
|
scripts: ProviderNativeHistoryScripts | undefined,
|
|
1418
1876
|
historySessionId: string | undefined,
|
|
1419
1877
|
workspace?: string,
|
|
1878
|
+
excludeInProgressTurn?: boolean,
|
|
1879
|
+
sessionStartedAtMs?: number,
|
|
1880
|
+
envOverrides?: Record<string, string>,
|
|
1881
|
+
forceRefresh?: boolean,
|
|
1882
|
+
instanceId?: string,
|
|
1420
1883
|
): ProviderNativeHistoryReadResult | null {
|
|
1421
1884
|
const normalizedSessionId = normalizeSavedHistorySessionId(historySessionId || '');
|
|
1422
|
-
|
|
1423
|
-
|
|
1885
|
+
const normalizedWorkspace = typeof workspace === 'string' ? workspace.trim() : '';
|
|
1886
|
+
if (!canonicalHistory || (!normalizedSessionId && !normalizedWorkspace) || !isNativeSourceCanonicalHistory(canonicalHistory)) return null;
|
|
1887
|
+
return callProviderNativeHistoryRead(agentType, canonicalHistory, scripts, normalizedSessionId, workspace, excludeInProgressTurn, sessionStartedAtMs, envOverrides, forceRefresh, instanceId);
|
|
1424
1888
|
}
|
|
1425
1889
|
|
|
1426
1890
|
function materializeNativeHistoryToMirror(
|
|
@@ -1476,16 +1940,45 @@ export function readProviderChatHistory(
|
|
|
1476
1940
|
excludeRecentCount?: number;
|
|
1477
1941
|
historyBehavior?: ProviderHistoryBehavior;
|
|
1478
1942
|
scripts?: ProviderNativeHistoryScripts;
|
|
1943
|
+
excludeInProgressTurn?: boolean;
|
|
1944
|
+
sessionStartedAtMs?: number;
|
|
1945
|
+
envOverrides?: Record<string, string>;
|
|
1946
|
+
forceRefresh?: boolean;
|
|
1947
|
+
// Daemon instance id of the reading session (== the session registry's
|
|
1948
|
+
// sessionId). Threaded to the native-history dispatcher so the
|
|
1949
|
+
// antigravity conversation-claim owner token is keyed on this stable
|
|
1950
|
+
// per-session identity — identical to the token the provider instance
|
|
1951
|
+
// derives — instead of a spawn timestamp that differs across sample
|
|
1952
|
+
// sites and silently breaks claim isolation.
|
|
1953
|
+
instanceId?: string;
|
|
1479
1954
|
} = {},
|
|
1480
|
-
): {
|
|
1481
|
-
|
|
1482
|
-
|
|
1955
|
+
): {
|
|
1956
|
+
messages: HistoryMessage[];
|
|
1957
|
+
hasMore: boolean;
|
|
1958
|
+
source: 'provider-native' | 'adhdev-mirror' | 'native-unavailable';
|
|
1959
|
+
sourcePath?: string;
|
|
1960
|
+
sourceMtimeMs?: number;
|
|
1961
|
+
providerSessionId?: string;
|
|
1962
|
+
workspace?: string;
|
|
1963
|
+
nativeHistoryCoverage?: string;
|
|
1964
|
+
partialReason?: string;
|
|
1965
|
+
unavailableReason?: string;
|
|
1966
|
+
ownerConfirmed?: boolean;
|
|
1967
|
+
} {
|
|
1968
|
+
if (isNativeSourceCanonicalHistory(options.canonicalHistory) && (options.historySessionId || options.workspace)) {
|
|
1969
|
+
const nativeResult = buildNativeHistoryReadResult(agentType, options.canonicalHistory, options.scripts, options.historySessionId, options.workspace, options.excludeInProgressTurn, options.sessionStartedAtMs, options.envOverrides, options.forceRefresh, options.instanceId);
|
|
1483
1970
|
if (!nativeResult) return { messages: [], hasMore: false, source: 'native-unavailable' };
|
|
1484
1971
|
return {
|
|
1485
1972
|
...pageHistoryRecords(agentType, nativeResult.records, options.offset || 0, options.limit || 30, options.excludeRecentCount || 0, options.historyBehavior),
|
|
1486
1973
|
source: 'provider-native',
|
|
1487
1974
|
sourcePath: nativeResult.sourcePath,
|
|
1488
1975
|
sourceMtimeMs: nativeResult.sourceMtimeMs,
|
|
1976
|
+
providerSessionId: nativeResult.providerSessionId,
|
|
1977
|
+
workspace: nativeResult.workspace,
|
|
1978
|
+
nativeHistoryCoverage: nativeResult.nativeHistoryCoverage,
|
|
1979
|
+
partialReason: nativeResult.partialReason,
|
|
1980
|
+
unavailableReason: nativeResult.unavailableReason,
|
|
1981
|
+
ownerConfirmed: nativeResult.ownerConfirmed,
|
|
1489
1982
|
};
|
|
1490
1983
|
}
|
|
1491
1984
|
return {
|