@vellumai/assistant 0.10.12 → 0.11.0-staging.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +1 -1
- package/ARCHITECTURE.md +4 -5
- package/README.md +1 -1
- package/docs/architecture/memory.md +60 -23
- package/docs/error-handling.md +3 -3
- package/docs/guardian-request-flow.md +112 -0
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/package.json +1 -0
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/src/__tests__/channels.test.ts +9 -1
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/src/__tests__/secret-detection.test.ts +449 -0
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/src/channels.ts +1 -0
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/src/secret-detection.ts +468 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@slack/types/dist/events/app.d.ts +28 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@slack/types/dist/events/app.d.ts.map +1 -1
- package/node_modules/@vellumai/gateway-client/node_modules/@slack/types/dist/events/index.d.ts +2 -2
- package/node_modules/@vellumai/gateway-client/node_modules/@slack/types/dist/events/index.d.ts.map +1 -1
- package/node_modules/@vellumai/gateway-client/node_modules/@slack/types/dist/events/index.js.map +1 -1
- package/node_modules/@vellumai/gateway-client/node_modules/@slack/types/dist/events/message.d.ts +2 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@slack/types/dist/events/message.d.ts.map +1 -1
- package/node_modules/@vellumai/gateway-client/node_modules/@slack/types/package.json +1 -1
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/package.json +1 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/src/__tests__/channels.test.ts +9 -1
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/src/__tests__/secret-detection.test.ts +449 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/src/channels.ts +1 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/src/secret-detection.ts +468 -0
- package/node_modules/@vellumai/gateway-client/package.json +1 -1
- package/node_modules/@vellumai/gateway-client/src/admission-policy-contract.ts +6 -0
- package/node_modules/@vellumai/gateway-client/src/inbound-contract.ts +34 -0
- package/node_modules/@vellumai/service-contracts/package.json +1 -0
- package/node_modules/@vellumai/service-contracts/src/__tests__/channels.test.ts +9 -1
- package/node_modules/@vellumai/service-contracts/src/__tests__/secret-detection.test.ts +449 -0
- package/node_modules/@vellumai/service-contracts/src/channels.ts +1 -0
- package/node_modules/@vellumai/service-contracts/src/secret-detection.ts +468 -0
- package/openapi.yaml +246 -10
- package/package.json +2 -2
- package/src/__tests__/acp-session.test.ts +3 -3
- package/src/__tests__/agent-loop-mutable-latest-user-message.test.ts +3 -0
- package/src/__tests__/anthropic-provider.test.ts +40 -0
- package/src/__tests__/approval-cascade.test.ts +5 -5
- package/src/__tests__/approval-routes-http.test.ts +3 -3
- package/src/__tests__/ask-question-resolver.test.ts +207 -0
- package/src/__tests__/assistant-event-hub-self-exclusion.test.ts +16 -16
- package/src/__tests__/assistant-event-hub-targeted.test.ts +13 -11
- package/src/__tests__/assistant-event-hub.test.ts +13 -11
- package/src/__tests__/assistant-event.test.ts +12 -9
- package/src/__tests__/assistant-feature-flag-guard.test.ts +3 -3
- package/src/__tests__/assistant-feature-flag-guardrails.test.ts +1 -1
- package/src/__tests__/assistant-id-boundary-guard.test.ts +0 -58
- package/src/__tests__/assistant-stream-state.test.ts +17 -7
- package/src/__tests__/avatar-identity-sync.test.ts +3 -3
- package/src/__tests__/background-workers-disk-pressure.test.ts +1 -0
- package/src/__tests__/call-conversation-messages.test.ts +134 -18
- package/src/__tests__/call-start-guardian-guard.test.ts +27 -0
- package/src/__tests__/channel-approvals.test.ts +0 -27
- package/src/__tests__/channel-guardian.test.ts +85 -512
- package/src/__tests__/channel-readiness-slack-remote.test.ts +151 -3
- package/src/__tests__/channel-retry-sweep.test.ts +88 -1
- package/src/__tests__/channel-setup-panel-ack.test.ts +12 -9
- package/src/__tests__/chat-reveal-guard-priming.test.ts +31 -34
- package/src/__tests__/cli-memory-v2-reembed-skills.test.ts +2 -2
- package/src/__tests__/compaction-events.test.ts +8 -8
- package/src/__tests__/config-loader-platform-defaults.test.ts +54 -28
- package/src/__tests__/config-model-image-provider.test.ts +20 -0
- package/src/__tests__/config-schema-memory-substrate.test.ts +306 -0
- package/src/__tests__/config-schema.test.ts +14 -2
- package/src/__tests__/config-set-platform-guard.test.ts +11 -12
- package/src/__tests__/config-sounds-sync.test.ts +4 -4
- package/src/__tests__/confirmation-request-guardian-bridge.test.ts +5 -0
- package/src/__tests__/context-search-memory-source.test.ts +1 -1
- package/src/__tests__/context-search-memory-v2-source.test.ts +6 -6
- package/src/__tests__/context-token-estimator.test.ts +54 -1
- package/src/__tests__/conversation-agent-loop-disk-pressure.test.ts +12 -3
- package/src/__tests__/conversation-agent-loop-fatal-cleanup.test.ts +13 -4
- package/src/__tests__/conversation-agent-loop-handlers-max-tokens.test.ts +4 -4
- package/src/__tests__/conversation-agent-loop-inference-profile.test.ts +10 -1
- package/src/__tests__/conversation-agent-loop-overflow.test.ts +22 -13
- package/src/__tests__/conversation-agent-loop.test.ts +39 -30
- package/src/__tests__/conversation-confirmation-signals.test.ts +14 -14
- package/src/__tests__/conversation-evictor.test.ts +49 -0
- package/src/__tests__/conversation-fork-crud.test.ts +1 -1
- package/src/__tests__/conversation-history-web-search.test.ts +1 -1
- package/src/__tests__/conversation-key-store-disk-view.test.ts +5 -5
- package/src/__tests__/conversation-loop-db-lock-resilience.test.ts +5 -5
- package/src/__tests__/conversation-message-sync-tags.test.ts +4 -4
- package/src/__tests__/conversation-queue.test.ts +81 -81
- package/src/__tests__/conversation-routes-enabled-plugins.test.ts +8 -1
- package/src/__tests__/conversation-routes-hidden-queue.test.ts +8 -1
- package/src/__tests__/conversation-routes-slash-commands.test.ts +10 -1
- package/src/__tests__/conversation-runtime-assembly.test.ts +29 -2
- package/src/__tests__/conversation-slash-queue.test.ts +11 -11
- package/src/__tests__/conversation-slash-unknown.test.ts +2 -2
- package/src/__tests__/conversation-speed-override.test.ts +2 -2
- package/src/__tests__/conversation-summarize-route.test.ts +9 -0
- package/src/__tests__/conversation-surfaces-action-delivery.test.ts +18 -16
- package/src/__tests__/conversation-surfaces-activation-emit.test.ts +17 -17
- package/src/__tests__/conversation-surfaces-app-open.test.ts +7 -4
- package/src/__tests__/conversation-surfaces-data-persist.test.ts +7 -7
- package/src/__tests__/conversation-surfaces-standalone-payloads.test.ts +9 -9
- package/src/__tests__/conversation-surfaces-standalone.test.ts +12 -12
- package/src/__tests__/conversation-surfaces-state-update.test.ts +8 -5
- package/src/__tests__/conversation-surfaces-table-action.test.ts +6 -3
- package/src/__tests__/conversation-surfaces-task-progress.test.ts +46 -46
- package/src/__tests__/conversation-sync-tags.test.ts +5 -5
- package/src/__tests__/conversation-wait-for-idle.test.ts +2 -2
- package/src/__tests__/conversation-workspace-cache-state.test.ts +0 -4
- package/src/__tests__/conversation-workspace-injection.test.ts +0 -3
- package/src/__tests__/conversation-workspace-tool-tracking.test.ts +0 -3
- package/src/__tests__/copy-composer-tc-templates.test.ts +3 -131
- package/src/__tests__/credential-security-invariants.test.ts +1 -0
- package/src/__tests__/daemon-assistant-events.test.ts +14 -15
- package/src/__tests__/db-test-helpers.ts +13 -27
- package/src/__tests__/disk-pressure-routes.test.ts +12 -3
- package/src/__tests__/document-tool-security.test.ts +95 -0
- package/src/__tests__/drain-kick-guard.test.ts +232 -0
- package/src/__tests__/dynamic-skill-background-guard.test.ts +19 -6
- package/src/__tests__/emit-event-signal.test.ts +5 -6
- package/src/__tests__/encrypted-store-test-helpers.ts +10 -20
- package/src/__tests__/events-tail-route.test.ts +6 -4
- package/src/__tests__/feature-flag-test-helpers.ts +10 -20
- package/src/__tests__/file-edit-tool.test.ts +24 -4
- package/src/__tests__/file-list-tool.test.ts +2 -1
- package/src/__tests__/file-read-tool.test.ts +62 -10
- package/src/__tests__/file-write-tool.test.ts +24 -5
- package/src/__tests__/followup-tools.test.ts +58 -0
- package/src/__tests__/gateway-threshold-reader-mock.ts +99 -0
- package/src/__tests__/graph-extraction-event-date.test.ts +1 -1
- package/src/__tests__/guardian-question-mode.test.ts +42 -3
- package/src/__tests__/guardian-reply-router-answer-mode.test.ts +283 -0
- package/src/__tests__/guardian-vellum-destination-pinning.test.ts +221 -0
- package/src/__tests__/heartbeat-disk-pressure.test.ts +1 -0
- package/src/__tests__/heartbeat-service.test.ts +1 -0
- package/src/__tests__/helpers/native-web-search-harness.ts +10 -10
- package/src/__tests__/host-browser-proxy.test.ts +1 -1
- package/src/__tests__/host-file-edit-tool.test.ts +3 -3
- package/src/__tests__/host-file-read-tool.test.ts +2 -2
- package/src/__tests__/host-file-write-tool.test.ts +7 -3
- package/src/__tests__/host-shell-tool.test.ts +17 -5
- package/src/__tests__/host-transfer-pending-interactions.test.ts +8 -8
- package/src/__tests__/image-credentials.test.ts +65 -8
- package/src/__tests__/injection-block.test.ts +4 -4
- package/src/__tests__/injector-chain.test.ts +1 -1
- package/src/__tests__/injector-pkb-v2-silenced.test.ts +2 -2
- package/src/__tests__/injector-registry-order-guard.test.ts +4 -9
- package/src/__tests__/injector-v3-suppression.test.ts +6 -4
- package/src/__tests__/lifecycle-memory-v2-seed.test.ts +27 -28
- package/src/__tests__/list-messages-page-latest.test.ts +2 -2
- package/src/__tests__/llm-usage-store.test.ts +67 -4
- package/src/__tests__/log-redact.test.ts +18 -0
- package/src/__tests__/managed-profile-guard.test.ts +27 -0
- package/src/__tests__/managed-skill-lifecycle.test.ts +2 -2
- package/src/__tests__/media-generate-image.test.ts +62 -11
- package/src/__tests__/memory-identity-context-parity.test.ts +1 -1
- package/src/__tests__/memory-jobs-worker-lanes.test.ts +9 -1
- package/src/__tests__/memory-retrieval-hook.test.ts +4 -4
- package/src/__tests__/notification-decision-strategy.test.ts +115 -11
- package/src/__tests__/notification-deep-link.test.ts +12 -12
- package/src/__tests__/notification-vellum-adapter.test.ts +8 -8
- package/src/__tests__/outbound-slack-persistence.test.ts +8 -8
- package/src/__tests__/path-policy.test.ts +315 -0
- package/src/__tests__/pending-interactions-resolved-event.test.ts +6 -6
- package/src/__tests__/persistence-layering-guard.test.ts +2 -2
- package/src/__tests__/pkb-autoinject.test.ts +1 -1
- package/src/__tests__/platform-bash-auto-approve.test.ts +1 -0
- package/src/__tests__/plugin-event-hub-facade.test.ts +22 -15
- package/src/__tests__/plugin-import-boundary-guard.test.ts +15 -15
- package/src/__tests__/processing-flag-persist-failure.test.ts +0 -4
- package/src/__tests__/provider-platform-proxy-integration.test.ts +0 -1
- package/src/__tests__/rebuild-index-graph-nodes.test.ts +1 -1
- package/src/__tests__/request-secret-standalone-channel-gate.test.ts +5 -5
- package/src/__tests__/require-fresh-approval.test.ts +38 -38
- package/src/__tests__/run-due-schedules.test.ts +72 -1
- package/src/__tests__/runtime-events-sse-parity.test.ts +11 -10
- package/src/__tests__/runtime-events-sse.test.ts +1 -1
- package/src/__tests__/schedule-routes.test.ts +44 -5
- package/src/__tests__/schedule-store.test.ts +3 -3
- package/src/__tests__/schedule-tools.test.ts +176 -0
- package/src/__tests__/secret-prompt-log-hygiene.test.ts +3 -3
- package/src/__tests__/secret-prompter-channel-fallback.test.ts +3 -3
- package/src/__tests__/secret-response-routing.test.ts +3 -3
- package/src/__tests__/secret-routes-platform-proxy.test.ts +4 -7
- package/src/__tests__/secret-scanner.test.ts +36 -0
- package/src/__tests__/send-endpoint-busy.test.ts +7 -7
- package/src/__tests__/slack-required-scopes-mirror.test.ts +81 -0
- package/src/__tests__/starter-task-flow.test.ts +6 -3
- package/src/__tests__/subagent-call-site-routing.test.ts +2 -2
- package/src/__tests__/subagent-disposal.test.ts +40 -11
- package/src/__tests__/subagent-fork-notifications.test.ts +4 -4
- package/src/__tests__/subagent-fork-prompt-role.test.ts +3 -3
- package/src/__tests__/subagent-fork-spawn.test.ts +4 -4
- package/src/__tests__/subagent-manager-notify.test.ts +73 -14
- package/src/__tests__/subagent-notify-parent.test.ts +48 -4
- package/src/__tests__/subagent-spawn-and-await.test.ts +62 -14
- package/src/__tests__/subagent-tools.test.ts +64 -0
- package/src/__tests__/sync-message-contract.test.ts +3 -3
- package/src/__tests__/terminal-tools.test.ts +12 -3
- package/src/__tests__/test-preload.ts +9 -0
- package/src/__tests__/tool-approval-handler.test.ts +583 -43
- package/src/__tests__/tool-execution-pipeline.benchmark.test.ts +7 -4
- package/src/__tests__/tool-executor.test.ts +116 -0
- package/src/__tests__/tool-grant-request-escalation.test.ts +5 -0
- package/src/__tests__/tool-preview-lifecycle.test.ts +32 -29
- package/src/__tests__/tool-result-metadata-plumbing.test.ts +5 -5
- package/src/__tests__/tool-start-timestamp.test.ts +4 -4
- package/src/__tests__/trusted-contact-lifecycle-notifications.test.ts +9 -22
- package/src/__tests__/ui-choice-copy-surfaces.test.ts +13 -13
- package/src/__tests__/ui-work-result-surface.test.ts +3 -3
- package/src/__tests__/voice-scoped-grant-consumer.test.ts +6 -6
- package/src/__tests__/voice-session-bridge.test.ts +44 -44
- package/src/__tests__/workspace-migration-134-image-generation-mode-to-provider.test.ts +284 -0
- package/src/__tests__/workspace-policy.test.ts +399 -0
- package/src/acp/__tests__/client-handler.test.ts +3 -3
- package/src/acp/__tests__/session-manager-persistence.test.ts +10 -10
- package/src/acp/__tests__/session-manager-resume.test.ts +7 -7
- package/src/acp/client-handler.ts +3 -3
- package/src/acp/session-manager.ts +8 -8
- package/src/api/events/subagent-event.ts +2 -2
- package/src/api/responses/memory-v2-activation-log.ts +2 -2
- package/src/approvals/AGENTS.md +2 -0
- package/src/approvals/guardian-request-resolvers.ts +118 -24
- package/src/calls/__tests__/voice-control-protocol.test.ts +57 -0
- package/src/calls/__tests__/voice-session-bridge.test.ts +158 -4
- package/src/calls/__tests__/voice-triage-escalate.test.ts +3 -4
- package/src/calls/call-controller.ts +27 -27
- package/src/calls/call-conversation-messages.ts +58 -18
- package/src/calls/voice-control-protocol.ts +56 -0
- package/src/calls/voice-session-bridge.ts +156 -58
- package/src/calls/voice-triage-escalate.ts +2 -3
- package/src/channels/config.ts +8 -0
- package/src/channels/types.ts +1 -0
- package/src/cli/commands/config.ts +49 -13
- package/src/cli/commands/memory/index.help.ts +4 -2
- package/src/cli/commands/memory/memory-retrospective.ts +5 -0
- package/src/cli/lib/bundled-marketplace.json +12 -0
- package/src/cli.ts +2 -109
- package/src/config/__tests__/deployment-context-defaults.test.ts +9 -0
- package/src/config/__tests__/substrate-twin-shadowing.test.ts +191 -0
- package/src/config/assistant-feature-flags.ts +1 -1
- package/src/config/bundled-skills/image-studio/tools/media-generate-image.ts +13 -7
- package/src/config/feature-flag-cache.ts +6 -16
- package/src/config/feature-flag-registry.json +14 -30
- package/src/config/loader.ts +7 -1
- package/src/config/memory-tier.ts +15 -10
- package/src/config/memory-v3-gate.test.ts +278 -1
- package/src/config/memory-v3-gate.ts +88 -26
- package/src/config/raw-config-utils.ts +1 -1
- package/src/config/schemas/__tests__/live-voice.test.ts +27 -16
- package/src/config/schemas/__tests__/memory-v3.test.ts +1 -0
- package/src/config/schemas/live-voice.ts +33 -7
- package/src/config/schemas/llm.ts +1 -0
- package/src/config/schemas/memory-retrospective.ts +13 -0
- package/src/config/schemas/memory-substrate.ts +183 -0
- package/src/config/schemas/memory-v2.ts +3 -2
- package/src/config/schemas/memory-v3.ts +11 -4
- package/src/config/schemas/memory.ts +35 -1
- package/src/config/schemas/services.ts +10 -2
- package/src/config/substrate-twin-shadowing.ts +195 -0
- package/src/config/webhook-routing.ts +67 -0
- package/src/context/compactor.ts +10 -3
- package/src/context/token-estimator.ts +21 -0
- package/src/daemon/__tests__/channel-ui-capability.test.ts +85 -0
- package/src/daemon/__tests__/conversation-surfaces-launch.test.ts +3 -3
- package/src/daemon/__tests__/embedding-reconcile.test.ts +3 -3
- package/src/daemon/__tests__/inference-profile-notification.test.ts +3 -6
- package/src/daemon/__tests__/native-web-search-metadata.test.ts +5 -5
- package/src/daemon/__tests__/web-search-status-text.test.ts +2 -2
- package/src/daemon/channel-ui-capability.ts +70 -1
- package/src/daemon/conversation-agent-loop-handlers.ts +4 -4
- package/src/daemon/conversation-agent-loop.ts +12 -5
- package/src/daemon/conversation-evictor.ts +26 -4
- package/src/daemon/conversation-launch.ts +11 -14
- package/src/daemon/conversation-messaging.ts +14 -14
- package/src/daemon/conversation-notifiers.ts +2 -2
- package/src/daemon/conversation-process.ts +133 -21
- package/src/daemon/conversation-queue-manager.ts +7 -7
- package/src/daemon/conversation-runtime-assembly.ts +16 -0
- package/src/daemon/conversation-store.ts +11 -3
- package/src/daemon/conversation-surfaces.ts +4 -4
- package/src/daemon/conversation-tool-setup.ts +13 -7
- package/src/daemon/conversation-usage.ts +12 -11
- package/src/daemon/conversation.ts +38 -15
- package/src/daemon/disk-pressure-guard.ts +5 -12
- package/src/daemon/embedding-reconcile.ts +14 -9
- package/src/daemon/handlers/config-channels.ts +40 -134
- package/src/daemon/handlers/config-model.ts +15 -7
- package/src/daemon/handlers/conversations.ts +4 -2
- package/src/daemon/handlers/shared.ts +29 -0
- package/src/daemon/host-proxy-base.ts +4 -4
- package/src/daemon/lifecycle.ts +13 -0
- package/src/daemon/message-protocol.ts +8 -144
- package/src/daemon/message-types/computer-use.ts +0 -12
- package/src/daemon/message-types/conversations.ts +9 -345
- package/src/daemon/message-types/host-app-control.ts +0 -9
- package/src/daemon/message-types/host-browser.ts +0 -7
- package/src/daemon/message-types/host-ui-snapshot.ts +0 -7
- package/src/daemon/message-types/messages.ts +0 -48
- package/src/daemon/message-types/notifications.ts +0 -7
- package/src/daemon/message-types/skills.ts +0 -5
- package/src/daemon/message-types/surfaces.ts +0 -9
- package/src/daemon/message-types/sync.ts +0 -2
- package/src/daemon/process-message.ts +5 -5
- package/src/daemon/skill-memory-refresh.ts +5 -5
- package/src/daemon/tool-side-effects.ts +13 -13
- package/src/daemon/trust-context.ts +1 -1
- package/src/daemon/wake-conversation-ops.ts +4 -4
- package/src/heartbeat/__tests__/heartbeat-run-store.test.ts +100 -7
- package/src/heartbeat/__tests__/heartbeat-service.test.ts +67 -0
- package/src/heartbeat/heartbeat-run-store.ts +81 -4
- package/src/heartbeat/heartbeat-service.ts +32 -1
- package/src/home/__tests__/feed-writer.test.ts +7 -7
- package/src/home/__tests__/home-content-refresh.test.ts +3 -0
- package/src/home/__tests__/suggested-prompts.test.ts +1 -0
- package/src/home/feed-writer.ts +6 -13
- package/src/home/home-content-refresh.ts +6 -9
- package/src/home/relationship-state-writer.ts +5 -12
- package/src/home/suggested-prompts-cache.ts +6 -19
- package/src/ipc/__tests__/events-publish-client.test.ts +67 -0
- package/src/ipc/events-publish-client.ts +44 -0
- package/src/ipc/routes/__tests__/conversation-sync-ipc-routes.test.ts +2 -2
- package/src/ipc/routes/__tests__/events-ipc-routes.test.ts +38 -9
- package/src/ipc/routes/events-ipc-routes.ts +11 -31
- package/src/live-voice/__tests__/front-decision.test.ts +4 -176
- package/src/live-voice/__tests__/live-voice-agent-turn.test.ts +276 -68
- package/src/live-voice/__tests__/live-voice-events.test.ts +6 -3
- package/src/live-voice/__tests__/live-voice-progress.test.ts +185 -46
- package/src/live-voice/__tests__/live-voice-triage-escalate.test.ts +24 -59
- package/src/live-voice/__tests__/live-voice-tts-session.test.ts +38 -54
- package/src/live-voice/__tests__/live-voice-vad.test.ts +218 -422
- package/src/live-voice/front-decision.ts +5 -155
- package/src/live-voice/live-voice-metrics.ts +4 -1
- package/src/live-voice/live-voice-session.ts +650 -333
- package/src/live-voice/progress-phrases.ts +17 -0
- package/src/live-voice/protocol.ts +15 -0
- package/src/media/app-icon-generator.ts +15 -8
- package/src/media/avatar-router.ts +9 -5
- package/src/media/image-credentials.ts +42 -10
- package/src/media/image-service.ts +1 -13
- package/src/media/types.ts +26 -3
- package/src/notifications/AGENTS.md +2 -0
- package/src/notifications/__tests__/broadcaster.test.ts +95 -0
- package/src/notifications/adapters/macos.ts +3 -3
- package/src/notifications/broadcaster.ts +57 -0
- package/src/notifications/copy-composer.ts +0 -15
- package/src/notifications/decision-engine.ts +21 -22
- package/src/notifications/guardian-question-mode.ts +57 -2
- package/src/notifications/home-feed-side-effect.ts +4 -0
- package/src/notifications/signal.ts +6 -4
- package/src/notifications/trusted-contact-payloads.ts +3 -4
- package/src/notifications/vellum-card-affinity.ts +39 -0
- package/src/oauth/AGENTS.md +1 -1
- package/src/permissions/channel-permission-query.test.ts +69 -0
- package/src/permissions/channel-permission-query.ts +73 -1
- package/src/permissions/checker.test.ts +85 -9
- package/src/permissions/checker.ts +17 -22
- package/src/permissions/confirmation-guardian-request.test.ts +2 -2
- package/src/permissions/confirmation-guardian-request.ts +2 -2
- package/src/permissions/gateway-threshold-reader.test.ts +224 -17
- package/src/permissions/gateway-threshold-reader.ts +82 -10
- package/src/permissions/ipc-risk-types.ts +8 -0
- package/src/permissions/prompter.ts +5 -5
- package/src/permissions/question-guardian-request.test.ts +222 -0
- package/src/permissions/question-guardian-request.ts +179 -0
- package/src/permissions/question-prompter.test.ts +8 -8
- package/src/permissions/question-prompter.ts +18 -0
- package/src/permissions/secret-prompter.ts +2 -4
- package/src/permissions/workspace-policy.ts +236 -34
- package/src/persistence/__tests__/lifecycle-quiesce.test.ts +82 -0
- package/src/persistence/__tests__/message-content-file.test.ts +58 -3
- package/src/persistence/conversation-crud.ts +93 -0
- package/src/persistence/conversation-key-store.ts +63 -0
- package/src/persistence/db-async-query.ts +1 -1
- package/src/persistence/db-singleton.ts +14 -27
- package/src/persistence/delivery-crud.ts +45 -0
- package/src/persistence/embeddings/embedding-backend.ts +2 -1
- package/src/persistence/embeddings/embedding-identity.ts +7 -3
- package/src/persistence/job-utils.ts +32 -27
- package/src/persistence/jobs-store.ts +92 -3
- package/src/persistence/lifecycle-quiesce.ts +80 -0
- package/src/persistence/llm-usage-store.ts +45 -8
- package/src/persistence/message-content-file.ts +4 -4
- package/src/persistence/migrations/336-move-memory-v2-activation-logs-to-memory-db.ts +1 -1
- package/src/persistence/migrations/351-schedule-skill-script-handoff.ts +39 -0
- package/src/persistence/migrations/352-drop-schedule-skill-script-handoff.test.ts +83 -0
- package/src/persistence/migrations/352-drop-schedule-skill-script-handoff.ts +36 -0
- package/src/persistence/migrations/353-add-llm-usage-conversation-type.test.ts +110 -0
- package/src/persistence/migrations/353-add-llm-usage-conversation-type.ts +49 -0
- package/src/persistence/schema/infrastructure.ts +11 -0
- package/src/persistence/steps.ts +7 -1
- package/src/plugin-api/__tests__/publish-event-forwarding.test.ts +113 -0
- package/src/plugin-api/__tests__/publish-event.test.ts +57 -0
- package/src/plugin-api/conversation-turn.ts +4 -4
- package/src/plugin-api/event-hub-facade.ts +15 -6
- package/src/plugin-api/index.ts +10 -4
- package/src/plugin-api/publish-event.ts +36 -0
- package/src/plugins/AGENTS.md +2 -0
- package/src/plugins/defaults/compaction/window-manager.ts +9 -0
- package/src/plugins/defaults/index.ts +9 -13
- package/src/plugins/defaults/memory/AGENTS.md +775 -0
- package/src/plugins/defaults/memory/__tests__/capability-seed-embed-gate.test.ts +186 -0
- package/src/plugins/defaults/memory/__tests__/fixtures/memory-v2-activation-fixtures.ts +1 -1
- package/src/plugins/defaults/memory/__tests__/indexer-tier-dispatch.test.ts +129 -0
- package/src/plugins/defaults/memory/__tests__/jobs-worker-quiesce-gate.test.ts +91 -0
- package/src/plugins/defaults/memory/__tests__/jobs-worker-v1-graph-substrate-noop.test.ts +342 -0
- package/src/plugins/defaults/memory/__tests__/jobs-worker-v2-graph-trigger-embed.test.ts +9 -1
- package/src/plugins/defaults/memory/__tests__/jobs-worker-v2-schedule.test.ts +36 -1
- package/src/plugins/defaults/memory/__tests__/jobs-worker-v2-sweep-defer.test.ts +9 -1
- package/src/plugins/defaults/memory/__tests__/memory-log-stores-degraded.test.ts +2 -2
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-job.test.ts +44 -10
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-sweep.test.ts +151 -10
- package/src/plugins/defaults/memory/__tests__/memory-tier-boundary-guard.test.ts +1155 -0
- package/src/plugins/defaults/memory/__tests__/memory-v2-activation-log-store.test.ts +1 -1
- package/src/plugins/defaults/memory/__tests__/memory-v2-concept-frequency.test.ts +3 -3
- package/src/plugins/defaults/memory/__tests__/tools-delete-memory-page.test.ts +1 -1
- package/src/plugins/defaults/memory/context-search/sources/memory-v2.ts +71 -35
- package/src/plugins/defaults/memory/context-search/sources/memory.ts +5 -1
- package/src/plugins/defaults/memory/fork-conversation-memory.ts +4 -4
- package/src/plugins/defaults/memory/graph/__tests__/conversation-graph-memory-v2-routing.test.ts +80 -10
- package/src/plugins/defaults/memory/graph/__tests__/handle-remember-v2.test.ts +1 -1
- package/src/plugins/defaults/memory/graph/capability-seed.ts +24 -10
- package/src/plugins/defaults/memory/graph/conversation-graph-memory.ts +123 -49
- package/src/plugins/defaults/memory/graph/graph-search.ts +6 -118
- package/src/plugins/defaults/memory/graph/in-context-tracker.test.ts +173 -0
- package/src/plugins/defaults/memory/graph/in-context-tracker.ts +109 -0
- package/src/plugins/defaults/memory/graph/store.ts +1 -0
- package/src/plugins/defaults/memory/graph/tool-handlers.test.ts +1 -1
- package/src/plugins/defaults/memory/graph/tool-handlers.ts +5 -2
- package/src/plugins/defaults/memory/graph-topology/__tests__/build-memory-graph.test.ts +1 -1
- package/src/plugins/defaults/memory/graph-topology/build-memory-graph.ts +6 -9
- package/src/plugins/defaults/memory/hooks/__tests__/user-prompt-submit.test.ts +30 -16
- package/src/plugins/defaults/memory/hooks/user-prompt-submit.ts +18 -14
- package/src/plugins/defaults/memory/indexer.ts +146 -89
- package/src/plugins/defaults/memory/injectors.ts +86 -41
- package/src/plugins/defaults/memory/job-handlers.ts +130 -39
- package/src/plugins/defaults/memory/jobs/__tests__/embed-concept-page.test.ts +2 -2
- package/src/plugins/defaults/memory/jobs/embed-concept-page.ts +22 -10
- package/src/plugins/defaults/memory/jobs-worker.ts +279 -208
- package/src/plugins/defaults/memory/memory-retrospective-enqueue.ts +4 -2
- package/src/plugins/defaults/memory/memory-retrospective-job.ts +40 -3
- package/src/plugins/defaults/memory/memory-retrospective-sweep.ts +99 -11
- package/src/plugins/defaults/memory/src/__tests__/memory-v2-routes.test.ts +5 -3
- package/src/plugins/defaults/memory/src/__tests__/memory-v2-simulate-route.test.ts +3 -4
- package/src/plugins/defaults/memory/src/memory-graph-routes.ts +2 -1
- package/src/plugins/defaults/memory/src/memory-item-routes.test.ts +7 -5
- package/src/plugins/defaults/memory/src/memory-item-routes.ts +51 -19
- package/src/plugins/defaults/memory/src/memory-v2-routes.ts +31 -20
- package/src/plugins/defaults/memory/startup.ts +58 -21
- package/src/plugins/defaults/memory/substrate/__tests__/boot-maintenance.test.ts +335 -0
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/cli-command-store.test.ts +14 -8
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/consolidation-job.test.ts +51 -21
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/edge-index.test.ts +1 -1
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/frontmatter-sweep.test.ts +3 -3
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/page-index.test.ts +1 -1
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/page-store.test.ts +1 -1
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/prompts-consolidation.test.ts +2 -2
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/qdrant.test.ts +23 -14
- package/src/plugins/defaults/memory/substrate/__tests__/reembed-job.test.ts +262 -0
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/sim.test.ts +9 -12
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/skill-content.test.ts +2 -2
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/skill-store.test.ts +9 -9
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/sparse-bm25.test.ts +12 -5
- package/src/plugins/defaults/memory/substrate/__tests__/spread.test.ts +276 -0
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/static-context.test.ts +17 -8
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/sweep-job.test.ts +9 -9
- package/src/plugins/defaults/memory/{v3/substrate/memory-v2-startup.ts → substrate/boot-maintenance.ts} +43 -24
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/cli-command-store.ts +13 -8
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/consolidation-job.ts +51 -27
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/constants.ts +1 -0
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/edge-index.ts +28 -9
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/frontmatter-sweep.ts +14 -7
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/injected-block-slugs.ts +9 -3
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/page-index.ts +29 -10
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/page-store.ts +35 -12
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/prompts/consolidation.ts +14 -8
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/prompts/sweep.ts +4 -1
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/qdrant.ts +96 -36
- package/src/plugins/defaults/memory/substrate/reembed-job.ts +54 -0
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/sim.ts +26 -15
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/skill-content.ts +1 -1
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/skill-store.ts +13 -8
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/sparse-bm25.ts +27 -10
- package/src/plugins/defaults/memory/substrate/spread.ts +165 -0
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/static-context.ts +12 -7
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/sweep-job.ts +20 -15
- package/src/plugins/defaults/memory/substrate/tuning.ts +93 -0
- package/src/plugins/defaults/memory/{v3/substrate → substrate}/types.ts +7 -4
- package/src/plugins/defaults/memory/tools.test.ts +1 -1
- package/src/plugins/defaults/memory/tools.ts +1 -1
- package/src/plugins/defaults/memory/v1/README.md +5 -0
- package/src/plugins/defaults/memory/{__tests__ → v1/__tests__}/filing-jobs.test.ts +4 -4
- package/src/plugins/defaults/memory/{filing-jobs.ts → v1/filing-jobs.ts} +3 -3
- package/src/plugins/defaults/memory/{graph → v1/graph}/bootstrap.test.ts +68 -6
- package/src/plugins/defaults/memory/{graph → v1/graph}/bootstrap.ts +40 -21
- package/src/plugins/defaults/memory/{graph → v1/graph}/consolidation.ts +14 -14
- package/src/plugins/defaults/memory/{graph → v1/graph}/decay.test.ts +1 -1
- package/src/plugins/defaults/memory/{graph → v1/graph}/decay.ts +3 -3
- package/src/plugins/defaults/memory/{graph → v1/graph}/extraction-job.ts +5 -5
- package/src/plugins/defaults/memory/{graph → v1/graph}/extraction.test.ts +1 -1
- package/src/plugins/defaults/memory/{graph → v1/graph}/extraction.ts +20 -14
- package/src/plugins/defaults/memory/{graph → v1/graph}/graph-search.test.ts +3 -3
- package/src/plugins/defaults/memory/v1/graph/graph-search.ts +123 -0
- package/src/plugins/defaults/memory/{graph → v1/graph}/injection.test.ts +1 -118
- package/src/plugins/defaults/memory/{graph → v1/graph}/injection.ts +9 -111
- package/src/plugins/defaults/memory/{graph → v1/graph}/narrative.ts +6 -6
- package/src/plugins/defaults/memory/{graph → v1/graph}/pattern-scan.ts +5 -5
- package/src/plugins/defaults/memory/{graph → v1/graph}/retriever.test.ts +135 -42
- package/src/plugins/defaults/memory/{graph → v1/graph}/retriever.ts +40 -22
- package/src/plugins/defaults/memory/{graph → v1/graph}/scoring.test.ts +1 -1
- package/src/plugins/defaults/memory/{graph → v1/graph}/scoring.ts +1 -1
- package/src/plugins/defaults/memory/{graph → v1/graph}/serendipity.ts +1 -1
- package/src/plugins/defaults/memory/{graph → v1/graph}/triggers.test.ts +1 -1
- package/src/plugins/defaults/memory/{graph → v1/graph}/triggers.ts +1 -1
- package/src/plugins/defaults/memory/{identity-context.ts → v1/identity-context.ts} +4 -4
- package/src/plugins/defaults/memory/{job-handlers → v1/job-handlers}/backfill.ts +6 -6
- package/src/plugins/defaults/memory/{job-handlers → v1/job-handlers}/embedding.test.ts +6 -6
- package/src/plugins/defaults/memory/{job-handlers → v1/job-handlers}/embedding.ts +6 -6
- package/src/plugins/defaults/memory/{job-handlers → v1/job-handlers}/index-maintenance.ts +8 -8
- package/src/plugins/defaults/memory/{jobs → v1/jobs}/embed-pkb-file.test.ts +7 -7
- package/src/plugins/defaults/memory/{jobs → v1/jobs}/embed-pkb-file.ts +5 -5
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/autoinject.ts +1 -1
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/context.ts +2 -2
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/pkb-index.test.ts +3 -3
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/pkb-index.ts +2 -2
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/pkb-reconcile.test.ts +3 -3
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/pkb-reconcile.ts +2 -2
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/pkb-search.test.ts +3 -3
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/pkb-search.ts +6 -6
- package/src/plugins/defaults/memory/{pkb → v1/pkb}/types.ts +3 -5
- package/src/plugins/defaults/memory/{pkb-schedule.ts → v1/pkb-schedule.ts} +2 -2
- package/src/plugins/defaults/memory/{search/semantic.ts → v1/semantic-search.ts} +1 -1
- package/src/plugins/defaults/memory/v2/__tests__/activation-store.test.ts +1 -1
- package/src/plugins/defaults/memory/v2/__tests__/activation.test.ts +11 -274
- package/src/plugins/defaults/memory/v2/__tests__/backfill-jobs.test.ts +9 -131
- package/src/plugins/defaults/memory/v2/__tests__/harness-compare.test.ts +1 -1
- package/src/plugins/defaults/memory/v2/__tests__/harness-oracle.test.ts +1 -1
- package/src/plugins/defaults/memory/v2/__tests__/harness-replay-input.test.ts +1 -1
- package/src/plugins/defaults/memory/v2/__tests__/injection.test.ts +14 -10
- package/src/plugins/defaults/memory/v2/__tests__/reranker.test.ts +7 -5
- package/src/plugins/defaults/memory/v2/__tests__/router.test.ts +12 -6
- package/src/plugins/defaults/memory/{memory-v2-activation-log-store.ts → v2/activation-log-store.ts} +2 -2
- package/src/plugins/defaults/memory/v2/activation-store.ts +22 -8
- package/src/plugins/defaults/memory/v2/activation.ts +30 -163
- package/src/plugins/defaults/memory/v2/backfill-jobs.ts +7 -54
- package/src/plugins/defaults/memory/{memory-v2-concept-frequency.ts → v2/concept-frequency.ts} +3 -3
- package/src/plugins/defaults/memory/v2/harness/oracle.ts +1 -1
- package/src/plugins/defaults/memory/v2/harness/replay-input.ts +2 -2
- package/src/plugins/defaults/memory/v2/harness/retriever.ts +1 -1
- package/src/plugins/defaults/memory/v2/injection.ts +36 -26
- package/src/plugins/defaults/memory/v2/migration.ts +2 -2
- package/src/plugins/defaults/memory/{rerank-local.ts → v2/rerank-local.ts} +44 -18
- package/src/plugins/defaults/memory/v2/reranker.ts +29 -11
- package/src/plugins/defaults/memory/v2/router.ts +38 -15
- package/src/plugins/defaults/memory/v3/__tests__/candidate-match.test.ts +5 -3
- package/src/plugins/defaults/memory/v3/__tests__/carry-integration.test.ts +21 -8
- package/src/plugins/defaults/memory/v3/__tests__/edge.test.ts +1 -1
- package/src/plugins/defaults/memory/v3/__tests__/live-integration.test.ts +1 -1
- package/src/plugins/defaults/memory/v3/__tests__/maintain-job.test.ts +4 -1
- package/src/plugins/defaults/memory/v3/__tests__/orchestrate.test.ts +181 -3
- package/src/plugins/defaults/memory/v3/__tests__/selection-log-store.test.ts +3 -0
- package/src/plugins/defaults/memory/v3/__tests__/shadow-integration.test.ts +14 -5
- package/src/plugins/defaults/memory/v3/__tests__/shadow-plugin.test.ts +40 -50
- package/src/plugins/defaults/memory/v3/__tests__/tuning-profile.test.ts +1 -0
- package/src/plugins/defaults/memory/v3/candidate-match.ts +2 -2
- package/src/plugins/defaults/memory/v3/capabilities.ts +6 -4
- package/src/plugins/defaults/memory/v3/card.ts +25 -9
- package/src/plugins/defaults/memory/v3/edge.ts +52 -18
- package/src/plugins/defaults/memory/v3/gate.ts +4 -4
- package/src/plugins/defaults/memory/v3/injector.ts +10 -3
- package/src/plugins/defaults/memory/v3/maintain-job.ts +3 -3
- package/src/plugins/defaults/memory/v3/orchestrate.ts +100 -18
- package/src/plugins/defaults/memory/v3/page-content.ts +26 -10
- package/src/plugins/defaults/memory/v3/prune.ts +40 -16
- package/src/plugins/defaults/memory/v3/selection-log-store.ts +34 -12
- package/src/plugins/defaults/memory/v3/shadow-plugin.ts +9 -13
- package/src/plugins/defaults/memory/v3/span-query.test.ts +86 -0
- package/src/plugins/defaults/memory/v3/span-query.ts +71 -0
- package/src/plugins/defaults/memory/v3/tuning-profile.ts +3 -0
- package/src/plugins/defaults/memory/v3/types.ts +4 -1
- package/src/plugins/defaults/memory/v3-eval/eval-packets.ts +2 -2
- package/src/plugins/defaults/memory/validation.ts +1 -1
- package/src/plugins/defaults/memory/worker.ts +2 -1
- package/src/plugins/defaults/platform-hosted/__tests__/reengage.test.ts +104 -12
- package/src/plugins/defaults/platform-hosted/routes/reengage.ts +104 -12
- package/src/plugins/types.ts +2 -2
- package/src/providers/__tests__/registry-native-web-search.test.ts +47 -2
- package/src/providers/anthropic/client.ts +15 -6
- package/src/providers/content-block-schema.ts +26 -0
- package/src/providers/inference/__tests__/connections-credential-normalize.test.ts +87 -0
- package/src/providers/inference/adapter-factory.ts +6 -0
- package/src/providers/inference/connections.ts +30 -14
- package/src/providers/model-catalog.ts +77 -0
- package/src/providers/openai/__tests__/chat-completions-input-audio.test.ts +260 -0
- package/src/providers/openai/chat-completions-provider.ts +65 -17
- package/src/providers/openai/input-audio.ts +76 -0
- package/src/providers/openrouter/client.ts +0 -2
- package/src/providers/platform-proxy/constants.ts +4 -0
- package/src/providers/poolside/client.ts +42 -0
- package/src/providers/registry.ts +40 -8
- package/src/providers/retry.ts +2 -0
- package/src/providers/types.ts +39 -1
- package/src/providers/vercel-ai-gateway/client.ts +0 -2
- package/src/runtime/AGENTS.md +7 -5
- package/src/runtime/__tests__/question-request-guardian-bridge.test.ts +173 -0
- package/src/runtime/__tests__/question-resolution.test.ts +111 -0
- package/src/runtime/access-request-helper.ts +7 -15
- package/src/runtime/assistant-event-hub.ts +43 -31
- package/src/runtime/assistant-event-publish-options.ts +31 -0
- package/src/runtime/assistant-event.ts +19 -30
- package/src/runtime/assistant-stream-state.ts +4 -4
- package/src/runtime/channel-approvals.ts +0 -25
- package/src/runtime/channel-readiness-service.ts +99 -40
- package/src/runtime/channel-retry-sweep.ts +38 -15
- package/src/runtime/confirmation-request-guardian-bridge.ts +4 -0
- package/src/runtime/guardian-reply-router.ts +108 -0
- package/src/runtime/http-server.ts +8 -0
- package/src/runtime/http-types.ts +2 -2
- package/src/runtime/process-role.ts +42 -0
- package/src/runtime/question-request-guardian-bridge.ts +184 -0
- package/src/runtime/question-resolution.ts +153 -0
- package/src/runtime/routes/__tests__/bookmark-routes.test.ts +6 -2
- package/src/runtime/routes/__tests__/conversation-query-routes.test.ts +1 -1
- package/src/runtime/routes/acp-routes.ts +2 -2
- package/src/runtime/routes/bookmark-routes.ts +3 -15
- package/src/runtime/routes/canned-message-complete.ts +2 -2
- package/src/runtime/routes/consolidation-routes.ts +8 -2
- package/src/runtime/routes/conversation-list-routes.ts +3 -19
- package/src/runtime/routes/conversation-management-routes.ts +1 -5
- package/src/runtime/routes/conversation-query-routes.ts +52 -8
- package/src/runtime/routes/conversation-routes.ts +36 -22
- package/src/runtime/routes/credential-request-routes.ts +0 -1
- package/src/runtime/routes/filing-routes.ts +7 -7
- package/src/runtime/routes/global-search-routes.ts +1 -1
- package/src/runtime/routes/guardian-approval-prompt.ts +2 -2
- package/src/runtime/routes/image-generation-routes.ts +12 -9
- package/src/runtime/routes/inbound-message-handler.ts +17 -0
- package/src/runtime/routes/inbound-stages/acl-enforcement.test.ts +50 -0
- package/src/runtime/routes/inbound-stages/acl-enforcement.ts +19 -0
- package/src/runtime/routes/inbound-stages/background-dispatch.ts +4 -4
- package/src/runtime/routes/inbound-stages/inbound-content-prep.test.ts +129 -0
- package/src/runtime/routes/inbound-stages/inbound-content-prep.ts +141 -9
- package/src/runtime/routes/index.ts +2 -0
- package/src/runtime/routes/lifecycle-routes.ts +199 -0
- package/src/runtime/routes/platform-routes.ts +3 -8
- package/src/runtime/routes/playground/__tests__/inject-failures.test.ts +7 -7
- package/src/runtime/routes/playground/__tests__/reset-circuit.test.ts +5 -5
- package/src/runtime/routes/question-routes.ts +34 -87
- package/src/runtime/routes/secret-routes.ts +11 -1
- package/src/runtime/routes/settings-routes.ts +8 -18
- package/src/runtime/routes/upgrade-broadcast-routes.ts +4 -5
- package/src/runtime/routes/workspace-routes.test.ts +7 -4
- package/src/runtime/slack-reply-session.test.ts +12 -12
- package/src/runtime/slack-reply-session.ts +17 -17
- package/src/runtime/sync/sync-publisher.test.ts +7 -5
- package/src/runtime/tool-grant-request-helper.ts +4 -0
- package/src/schedule/schedule-store.ts +70 -0
- package/src/schedule/scheduler.ts +27 -0
- package/src/security/AGENTS.md +1 -1
- package/src/security/credential-key.ts +17 -0
- package/src/security/secret-ingress.ts +14 -105
- package/src/security/secret-patterns.ts +8 -139
- package/src/security/secret-scanner.ts +8 -3
- package/src/security/store-path-override.ts +6 -16
- package/src/sequence/store.ts +8 -0
- package/src/signals/emit-event.ts +5 -10
- package/src/signals/event-stream.ts +20 -10
- package/src/subagent/manager.ts +76 -25
- package/src/subagent/notify.ts +8 -0
- package/src/subagent/types.ts +13 -3
- package/src/telegram/__tests__/webhook-health.test.ts +442 -0
- package/src/telegram/webhook-health.ts +478 -0
- package/src/telemetry/AGENTS.md +6 -0
- package/src/telemetry/memory-corpus-size.test.ts +129 -0
- package/src/telemetry/memory-corpus-size.ts +184 -0
- package/src/telemetry/memory-tier-reporter.test.ts +67 -2
- package/src/telemetry/memory-tier-reporter.ts +30 -3
- package/src/tools/__tests__/document-tool-input-schemas.test.ts +103 -0
- package/src/tools/__tests__/followup-call-acp-tool-input-schemas.test.ts +125 -0
- package/src/tools/__tests__/schedule-tool-input-schemas.test.ts +83 -0
- package/src/tools/__tests__/subagent-workflow-tool-input-schemas.test.ts +116 -0
- package/src/tools/__tests__/tool-input-schemas.test.ts +192 -0
- package/src/tools/__tests__/tool-schema-drift-harness.ts +142 -0
- package/src/tools/acp/abort.ts +21 -1
- package/src/tools/acp/context.ts +5 -5
- package/src/tools/acp/spawn.test.ts +15 -5
- package/src/tools/acp/spawn.ts +26 -3
- package/src/tools/acp/status.ts +20 -1
- package/src/tools/acp/steer.test.ts +20 -0
- package/src/tools/acp/steer.ts +23 -2
- package/src/tools/ask-question/ask-question-tool.test.ts +65 -0
- package/src/tools/ask-question/ask-question-tool.ts +68 -92
- package/src/tools/browser/browser-screencast.ts +6 -6
- package/src/tools/calls/call-end.ts +24 -3
- package/src/tools/calls/call-start.ts +35 -11
- package/src/tools/calls/call-status.ts +20 -1
- package/src/tools/document/document-comment-tool.test.ts +49 -0
- package/src/tools/document/document-comment-tool.ts +45 -6
- package/src/tools/document/document-tool.ts +142 -24
- package/src/tools/executor.ts +27 -13
- package/src/tools/filesystem/edit.ts +62 -60
- package/src/tools/filesystem/list.ts +36 -29
- package/src/tools/filesystem/read.ts +56 -39
- package/src/tools/filesystem/write.ts +44 -38
- package/src/tools/followups/followup_create.ts +41 -12
- package/src/tools/followups/followup_list.ts +34 -6
- package/src/tools/followups/followup_resolve.ts +26 -4
- package/src/tools/host-filesystem/edit.ts +50 -60
- package/src/tools/host-filesystem/read.ts +45 -39
- package/src/tools/host-filesystem/write.ts +31 -36
- package/src/tools/host-terminal/host-shell.ts +76 -62
- package/src/tools/policy-context.ts +27 -10
- package/src/tools/schedule/create.ts +76 -33
- package/src/tools/schedule/delete.ts +21 -2
- package/src/tools/schedule/list.ts +25 -3
- package/src/tools/schedule/update.ts +105 -48
- package/src/tools/shared/filesystem/path-policy.ts +246 -40
- package/src/tools/shared/zod-tool-schema.ts +117 -0
- package/src/tools/subagent/abort.ts +12 -4
- package/src/tools/subagent/consult-deadline.ts +9 -3
- package/src/tools/subagent/message.ts +21 -5
- package/src/tools/subagent/notify-parent.ts +44 -23
- package/src/tools/subagent/read.ts +15 -4
- package/src/tools/subagent/resolve.ts +26 -4
- package/src/tools/subagent/spawn.ts +37 -13
- package/src/tools/subagent/status.ts +12 -4
- package/src/tools/system/request-permission.ts +35 -26
- package/src/tools/terminal/shell.ts +68 -55
- package/src/tools/tool-approval-handler.ts +327 -53
- package/src/tools/tool-input-schemas.ts +85 -0
- package/src/tools/tool-types.ts +7 -0
- package/src/tools/types.ts +8 -0
- package/src/tools/workflows/manage-workflows.ts +30 -2
- package/src/tools/workflows/run-workflow.test.ts +54 -2
- package/src/tools/workflows/run-workflow.ts +32 -4
- package/src/util/fs-symlinks.ts +30 -0
- package/src/util/log-redact.ts +7 -3
- package/src/vellum-assistant-namespace.d.ts +80 -0
- package/src/watcher/watcher-store.ts +8 -0
- package/src/workflows/leaf-runner.test.ts +104 -2
- package/src/workflows/leaf-runner.ts +31 -6
- package/src/workspace/migrations/070-memory-v2-summary-schema-rebuild.ts +2 -2
- package/src/workspace/migrations/134-image-generation-mode-to-provider.ts +128 -0
- package/src/workspace/migrations/135-copy-substrate-tunables.ts +248 -0
- package/src/workspace/migrations/__tests__/135-copy-substrate-tunables.test.ts +446 -0
- package/src/workspace/migrations/__tests__/backfill-v3-leaves.test.ts +2 -2
- package/src/workspace/migrations/registry.ts +4 -0
- package/src/__tests__/memory-retrieval-budget.test.ts +0 -49
- package/src/__tests__/secret-patterns.test.ts +0 -27
- package/src/config/__tests__/proc-to-skills.test.ts +0 -21
- package/src/config/memory-tier.test.ts +0 -44
- package/src/daemon/message-types/acp.ts +0 -20
- package/src/daemon/message-types/apps.ts +0 -11
- package/src/daemon/message-types/background-tools.ts +0 -14
- package/src/daemon/message-types/bookmarks.ts +0 -13
- package/src/daemon/message-types/contacts.ts +0 -13
- package/src/daemon/message-types/document-comments.ts +0 -14
- package/src/daemon/message-types/documents.ts +0 -13
- package/src/daemon/message-types/home.ts +0 -15
- package/src/daemon/message-types/host-bash.ts +0 -12
- package/src/daemon/message-types/host-cu.ts +0 -10
- package/src/daemon/message-types/host-file.ts +0 -12
- package/src/daemon/message-types/host-transfer.ts +0 -12
- package/src/daemon/message-types/integrations.ts +0 -90
- package/src/daemon/message-types/memory.ts +0 -10
- package/src/daemon/message-types/schedules.ts +0 -14
- package/src/daemon/message-types/settings.ts +0 -17
- package/src/daemon/message-types/subagents.ts +0 -63
- package/src/daemon/message-types/upgrades.ts +0 -14
- package/src/daemon/message-types/workflows.ts +0 -25
- package/src/daemon/message-types/workspace.ts +0 -137
- package/src/live-voice/ack-phrases.ts +0 -58
- package/src/plugins/defaults/memory/retrieval-budget.ts +0 -29
- package/src/plugins/defaults/memory/v3/__tests__/gate-flag.test.ts +0 -69
- package/src/plugins/defaults/memory/v3/gate-flag.ts +0 -20
- package/src/plugins/defaults/memory/v3/substrate/__tests__/memory-v2-startup.test.ts +0 -86
- package/src/plugins/defaults/memory/v3/substrate/memory-v2-startup.test.ts +0 -205
- /package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/concept-page-frontmatter-schema.test.ts +0 -0
- /package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/consolidation-prompt-flag-gating-guard.test.ts +0 -0
- /package/src/plugins/defaults/memory/{v3/substrate → substrate}/__tests__/injected-block-slugs.test.ts +0 -0
- /package/src/plugins/defaults/memory/{v3/substrate → substrate}/cli-command-content.ts +0 -0
|
@@ -11,6 +11,7 @@ import {
|
|
|
11
11
|
createAssistantMessage,
|
|
12
12
|
createUserMessage,
|
|
13
13
|
} from "../agent/message-types.js";
|
|
14
|
+
import type { AssistantEvent } from "../api/index.js";
|
|
14
15
|
import { listPendingRequestsByScopeOrEmpty } from "../channels/gateway-guardian-requests.js";
|
|
15
16
|
import {
|
|
16
17
|
parseChannelId,
|
|
@@ -56,10 +57,7 @@ import {
|
|
|
56
57
|
} from "./conversation-slash.js";
|
|
57
58
|
import { getModelInfo } from "./handlers/config-model.js";
|
|
58
59
|
import { preactivateHostProxySkills } from "./host-proxy-preactivation.js";
|
|
59
|
-
import type {
|
|
60
|
-
ServerMessage,
|
|
61
|
-
UserMessageAttachment,
|
|
62
|
-
} from "./message-protocol.js";
|
|
60
|
+
import type { UserMessageAttachment } from "./message-protocol.js";
|
|
63
61
|
import { buildTransportHints } from "./transport-hints.js";
|
|
64
62
|
import { resolveVerificationSessionIntent } from "./verification-session-intent.js";
|
|
65
63
|
|
|
@@ -192,7 +190,7 @@ export function formatCleanResult(result: CleanResult): string {
|
|
|
192
190
|
/** Build a model_info event with fresh config data. */
|
|
193
191
|
export async function buildModelInfoEvent(
|
|
194
192
|
conversationId?: string,
|
|
195
|
-
): Promise<
|
|
193
|
+
): Promise<AssistantEvent> {
|
|
196
194
|
return { type: "model_info", conversationId, ...(await getModelInfo()) };
|
|
197
195
|
}
|
|
198
196
|
|
|
@@ -438,13 +436,15 @@ function repairPendingToolUseBlocks(conversation: Conversation): void {
|
|
|
438
436
|
|
|
439
437
|
/**
|
|
440
438
|
* Restore drained messages to the front of the queue, in their original
|
|
441
|
-
* order, when another turn (e.g. a barged-in
|
|
442
|
-
* transition) owns the processing lock
|
|
443
|
-
*
|
|
444
|
-
*
|
|
445
|
-
*
|
|
439
|
+
* order, when the drain cannot run them: another turn (e.g. a barged-in
|
|
440
|
+
* voice turn woken by the idle transition) owns the processing lock, or the
|
|
441
|
+
* dispatch threw before the turn took over. The next drain trigger (the lock
|
|
442
|
+
* holder's own finally block, or `kickQueueDrain`'s retry) picks them back
|
|
443
|
+
* up. A steered drain also re-arms `pendingSteerRepair` so the re-drain
|
|
444
|
+
* promotes the steered head on its own instead of batching it with tails;
|
|
445
|
+
* the tool-use repair it re-triggers is idempotent.
|
|
446
446
|
*/
|
|
447
|
-
function
|
|
447
|
+
function requeueDrainedMessages(
|
|
448
448
|
conversation: Conversation,
|
|
449
449
|
messages: QueuedMessage[],
|
|
450
450
|
steered: boolean,
|
|
@@ -493,7 +493,9 @@ export async function drainQueue(
|
|
|
493
493
|
if (!next) {
|
|
494
494
|
return;
|
|
495
495
|
}
|
|
496
|
-
return
|
|
496
|
+
return dispatchDrainWithRestore(conversation, [next], true, () =>
|
|
497
|
+
drainSingleMessage(conversation, next, reason, true),
|
|
498
|
+
);
|
|
497
499
|
}
|
|
498
500
|
|
|
499
501
|
const batch = await buildPassthroughBatch(conversation);
|
|
@@ -505,12 +507,122 @@ export async function drainQueue(
|
|
|
505
507
|
if (!next) {
|
|
506
508
|
return;
|
|
507
509
|
}
|
|
508
|
-
return
|
|
510
|
+
return dispatchDrainWithRestore(conversation, [next], false, () =>
|
|
511
|
+
drainSingleMessage(conversation, next, reason),
|
|
512
|
+
);
|
|
509
513
|
}
|
|
510
514
|
if (batch.length === 1) {
|
|
511
|
-
return
|
|
515
|
+
return dispatchDrainWithRestore(conversation, batch, false, () =>
|
|
516
|
+
drainSingleMessage(conversation, batch[0], reason),
|
|
517
|
+
);
|
|
518
|
+
}
|
|
519
|
+
return dispatchDrainWithRestore(conversation, batch, false, () =>
|
|
520
|
+
drainBatch(conversation, batch, reason),
|
|
521
|
+
);
|
|
522
|
+
}
|
|
523
|
+
|
|
524
|
+
/**
|
|
525
|
+
* Errors that already triggered a queue restore on their way up. Drains
|
|
526
|
+
* recurse (a dropped message's error path re-drains the remaining queue), so
|
|
527
|
+
* without the marker an inner dispatch failure would also restore the outer
|
|
528
|
+
* dispatch's messages — resurrecting a message whose sender was already told
|
|
529
|
+
* it failed.
|
|
530
|
+
*/
|
|
531
|
+
const restoredDrainErrors = new WeakSet<object>();
|
|
532
|
+
|
|
533
|
+
/**
|
|
534
|
+
* Run a drain dispatch whose messages are already removed from the queue,
|
|
535
|
+
* restoring them to the front if the dispatch throws. `drainQueue` pops
|
|
536
|
+
* messages before the throw-prone turn-start steps (slash resolution,
|
|
537
|
+
* per-turn context application), so without the restore a retry would skip
|
|
538
|
+
* the failed message entirely: it drains the NEXT item, succeeds, and the
|
|
539
|
+
* removed message is silently lost with no `queue_drain_failed` event.
|
|
540
|
+
*/
|
|
541
|
+
async function dispatchDrainWithRestore(
|
|
542
|
+
conversation: Conversation,
|
|
543
|
+
messages: QueuedMessage[],
|
|
544
|
+
steered: boolean,
|
|
545
|
+
dispatch: () => Promise<void>,
|
|
546
|
+
): Promise<void> {
|
|
547
|
+
try {
|
|
548
|
+
return await dispatch();
|
|
549
|
+
} catch (err) {
|
|
550
|
+
const alreadyRestored =
|
|
551
|
+
typeof err === "object" && err !== null && restoredDrainErrors.has(err);
|
|
552
|
+
if (!alreadyRestored) {
|
|
553
|
+
if (typeof err === "object" && err !== null) {
|
|
554
|
+
restoredDrainErrors.add(err);
|
|
555
|
+
}
|
|
556
|
+
requeueDrainedMessages(
|
|
557
|
+
conversation,
|
|
558
|
+
messages,
|
|
559
|
+
steered,
|
|
560
|
+
"Requeueing drained messages: drain dispatch threw",
|
|
561
|
+
);
|
|
562
|
+
}
|
|
563
|
+
throw err;
|
|
564
|
+
}
|
|
565
|
+
}
|
|
566
|
+
|
|
567
|
+
/**
|
|
568
|
+
* Fire-and-forget entry point for drain triggers that sit outside the drain
|
|
569
|
+
* promise chain (the agent loop's `finally`, route handlers releasing the
|
|
570
|
+
* processing lock). `drainQueue` is async — batch building awaits slash
|
|
571
|
+
* resolution and can throw — and nothing re-triggers a drain whose promise
|
|
572
|
+
* rejects: the queued messages would sit stranded until an unrelated later
|
|
573
|
+
* turn completes. This wrapper never rejects. A failed drain is retried
|
|
574
|
+
* once — `dispatchDrainWithRestore` has already returned any popped
|
|
575
|
+
* messages to the queue head, so the retry retries the same messages. If
|
|
576
|
+
* the retry also fails, every queued sender is notified so the stall is
|
|
577
|
+
* visible to the user instead of silent, and the messages remain queued
|
|
578
|
+
* for the next drain trigger.
|
|
579
|
+
*
|
|
580
|
+
* `origin` names the triggering site for log correlation.
|
|
581
|
+
*/
|
|
582
|
+
export async function kickQueueDrain(
|
|
583
|
+
conversation: Conversation,
|
|
584
|
+
reason: QueueDrainReason = "loop_complete",
|
|
585
|
+
origin?: string,
|
|
586
|
+
): Promise<void> {
|
|
587
|
+
try {
|
|
588
|
+
await drainQueue(conversation, reason);
|
|
589
|
+
return;
|
|
590
|
+
} catch (err) {
|
|
591
|
+
log.error(
|
|
592
|
+
{
|
|
593
|
+
err,
|
|
594
|
+
conversationId: conversation.conversationId,
|
|
595
|
+
reason,
|
|
596
|
+
origin,
|
|
597
|
+
queueDepth: conversation.queue.length,
|
|
598
|
+
},
|
|
599
|
+
"drainQueue rejected; retrying once",
|
|
600
|
+
);
|
|
601
|
+
}
|
|
602
|
+
try {
|
|
603
|
+
await drainQueue(conversation, reason);
|
|
604
|
+
} catch (err) {
|
|
605
|
+
log.error(
|
|
606
|
+
{
|
|
607
|
+
err,
|
|
608
|
+
conversationId: conversation.conversationId,
|
|
609
|
+
reason,
|
|
610
|
+
origin,
|
|
611
|
+
queueDepth: conversation.queue.length,
|
|
612
|
+
},
|
|
613
|
+
"drainQueue retry rejected; queued messages remain stranded until the next drain trigger",
|
|
614
|
+
);
|
|
615
|
+
for (const queued of conversation.queue.snapshot()) {
|
|
616
|
+
queued.onEvent({
|
|
617
|
+
type: "error",
|
|
618
|
+
conversationId: conversation.conversationId,
|
|
619
|
+
requestId: queued.requestId,
|
|
620
|
+
message:
|
|
621
|
+
"The assistant couldn't start your queued message due to an internal error. The message is still queued and will be retried after the next reply; you can also cancel and resend it.",
|
|
622
|
+
category: "queue_drain_failed",
|
|
623
|
+
});
|
|
624
|
+
}
|
|
512
625
|
}
|
|
513
|
-
return drainBatch(conversation, batch, reason);
|
|
514
626
|
}
|
|
515
627
|
|
|
516
628
|
async function drainSingleMessage(
|
|
@@ -526,7 +638,7 @@ async function drainSingleMessage(
|
|
|
526
638
|
// requeue below stays as the TOCTOU backstop for a lock taken after
|
|
527
639
|
// this check.
|
|
528
640
|
if (conversation.isProcessing()) {
|
|
529
|
-
|
|
641
|
+
requeueDrainedMessages(
|
|
530
642
|
conversation,
|
|
531
643
|
[next],
|
|
532
644
|
steered,
|
|
@@ -952,7 +1064,7 @@ async function drainSingleMessage(
|
|
|
952
1064
|
// Another turn took the lock between this drain's dequeue and its
|
|
953
1065
|
// persist. The message is still valid — requeue it at the front and
|
|
954
1066
|
// stop; the lock holder's own finally re-drains the queue.
|
|
955
|
-
|
|
1067
|
+
requeueDrainedMessages(
|
|
956
1068
|
conversation,
|
|
957
1069
|
[next],
|
|
958
1070
|
steered,
|
|
@@ -1110,7 +1222,7 @@ async function drainBatch(
|
|
|
1110
1222
|
// The head persist-busy requeue below stays as the TOCTOU backstop.
|
|
1111
1223
|
// Steered drains never batch, so there is no steer promotion to restore.
|
|
1112
1224
|
if (conversation.isProcessing()) {
|
|
1113
|
-
|
|
1225
|
+
requeueDrainedMessages(
|
|
1114
1226
|
conversation,
|
|
1115
1227
|
batch,
|
|
1116
1228
|
false,
|
|
@@ -1329,7 +1441,7 @@ async function drainBatch(
|
|
|
1329
1441
|
// whole batch is still valid — requeue it at the front in order
|
|
1330
1442
|
// and stop; the lock holder's finally re-drains the queue.
|
|
1331
1443
|
conversation.preactivatedSkillIds = undefined;
|
|
1332
|
-
|
|
1444
|
+
requeueDrainedMessages(
|
|
1333
1445
|
conversation,
|
|
1334
1446
|
batch,
|
|
1335
1447
|
false,
|
|
@@ -1503,7 +1615,7 @@ async function drainBatch(
|
|
|
1503
1615
|
const successfulEventSinks = Array.from(
|
|
1504
1616
|
new Set(successfulBatch.map((qm) => qm.onEvent)),
|
|
1505
1617
|
);
|
|
1506
|
-
const fanOutOnEvent = (msg:
|
|
1618
|
+
const fanOutOnEvent = (msg: AssistantEvent) => {
|
|
1507
1619
|
for (const onEvent of successfulEventSinks) {
|
|
1508
1620
|
onEvent(msg);
|
|
1509
1621
|
}
|
|
@@ -1567,7 +1679,7 @@ async function drainBatch(
|
|
|
1567
1679
|
export interface ProcessMessageOptions {
|
|
1568
1680
|
content: string;
|
|
1569
1681
|
attachments: UserMessageAttachment[];
|
|
1570
|
-
onEvent?: (msg:
|
|
1682
|
+
onEvent?: (msg: AssistantEvent) => void;
|
|
1571
1683
|
requestId?: string;
|
|
1572
1684
|
activeSurfaceId?: string;
|
|
1573
1685
|
currentPage?: string;
|
|
@@ -5,6 +5,7 @@
|
|
|
5
5
|
* agent loop is in flight.
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
|
+
import type { AssistantEvent } from "../api/index.js";
|
|
8
9
|
import type {
|
|
9
10
|
TurnChannelContext,
|
|
10
11
|
TurnInterfaceContext,
|
|
@@ -12,7 +13,6 @@ import type {
|
|
|
12
13
|
import type { AuthContext } from "../runtime/auth/types.js";
|
|
13
14
|
import { getLogger } from "../util/logger.js";
|
|
14
15
|
import type {
|
|
15
|
-
ServerMessage,
|
|
16
16
|
UserMessageAttachment,
|
|
17
17
|
} from "./message-protocol.js";
|
|
18
18
|
import type { ConversationTransportMetadata } from "./message-types/conversations.js";
|
|
@@ -23,7 +23,7 @@ export interface QueuedMessage {
|
|
|
23
23
|
content: string;
|
|
24
24
|
attachments: UserMessageAttachment[];
|
|
25
25
|
requestId: string;
|
|
26
|
-
onEvent: (msg:
|
|
26
|
+
onEvent: (msg: AssistantEvent) => void;
|
|
27
27
|
activeSurfaceId?: string;
|
|
28
28
|
currentPage?: string;
|
|
29
29
|
metadata?: Record<string, unknown>;
|
|
@@ -156,7 +156,7 @@ export class MessageQueue {
|
|
|
156
156
|
*/
|
|
157
157
|
shiftN(count: number): QueuedMessage[] {
|
|
158
158
|
const n = Math.min(Math.max(0, count), this.items.length);
|
|
159
|
-
if (n === 0) return [];
|
|
159
|
+
if (n === 0) {return [];}
|
|
160
160
|
const removed = this.items.splice(0, n);
|
|
161
161
|
for (const item of removed) {
|
|
162
162
|
this.currentBytes -= estimateItemBytes(item);
|
|
@@ -188,8 +188,8 @@ export class MessageQueue {
|
|
|
188
188
|
*/
|
|
189
189
|
promoteToHead(requestId: string): QueuedMessage | undefined {
|
|
190
190
|
const idx = this.items.findIndex((m) => m.requestId === requestId);
|
|
191
|
-
if (idx === -1) return undefined;
|
|
192
|
-
if (idx === 0) return this.items[0]; // already at head
|
|
191
|
+
if (idx === -1) {return undefined;}
|
|
192
|
+
if (idx === 0) {return this.items[0];} // already at head
|
|
193
193
|
const [promoted] = this.items.splice(idx, 1);
|
|
194
194
|
this.items.unshift(promoted);
|
|
195
195
|
return promoted;
|
|
@@ -201,7 +201,7 @@ export class MessageQueue {
|
|
|
201
201
|
*/
|
|
202
202
|
removeByRequestId(requestId: string): QueuedMessage | undefined {
|
|
203
203
|
const idx = this.items.findIndex((m) => m.requestId === requestId);
|
|
204
|
-
if (idx === -1) return undefined;
|
|
204
|
+
if (idx === -1) {return undefined;}
|
|
205
205
|
const [removed] = this.items.splice(idx, 1);
|
|
206
206
|
this.currentBytes -= estimateItemBytes(removed);
|
|
207
207
|
return removed;
|
|
@@ -220,7 +220,7 @@ function estimateItemBytes(item: QueuedMessage): number {
|
|
|
220
220
|
let bytes = item.content.length * 2; // JS strings are UTF-16
|
|
221
221
|
for (const a of item.attachments) {
|
|
222
222
|
bytes += a.data.length * 2;
|
|
223
|
-
if (a.extractedText) bytes += a.extractedText.length * 2;
|
|
223
|
+
if (a.extractedText) {bytes += a.extractedText.length * 2;}
|
|
224
224
|
}
|
|
225
225
|
// Include transport metadata in the estimate so large transport
|
|
226
226
|
// payloads (e.g. hostHomeDir, hostUsername) count against the budget.
|
|
@@ -74,6 +74,7 @@ import { resolveCapabilities } from "../runtime/capabilities.js";
|
|
|
74
74
|
import type { SubagentState } from "../subagent/types.js";
|
|
75
75
|
import { TERMINAL_STATUSES } from "../subagent/types.js";
|
|
76
76
|
import { canonicalizeInboundIdentity } from "../util/canonicalize-identity.js";
|
|
77
|
+
import { channelSupportsInlineOptions } from "./channel-ui-capability.js";
|
|
77
78
|
import { findConversationOrSubagent } from "./conversation-registry.js";
|
|
78
79
|
import type { SurfaceShowPair } from "./conversation-surfaces.js";
|
|
79
80
|
import { canonicalizeTimeZone, formatTurnTimestamp } from "./date-context.js";
|
|
@@ -97,6 +98,13 @@ export interface ChannelCapabilities {
|
|
|
97
98
|
dashboardCapable: boolean;
|
|
98
99
|
/** Whether the channel supports dynamic UI surfaces (ui_show / ui_update). */
|
|
99
100
|
supportsDynamicUi: boolean;
|
|
101
|
+
/**
|
|
102
|
+
* Whether the channel's adapter can render inline tappable options — approval
|
|
103
|
+
* buttons and (next) question option pickers. Distinct from `supportsDynamicUi`:
|
|
104
|
+
* a text-only channel can render inline buttons without dynamic UI. Optional;
|
|
105
|
+
* absent is treated as `false`.
|
|
106
|
+
*/
|
|
107
|
+
supportsInlineOptions?: boolean;
|
|
100
108
|
/** Whether the channel supports voice/microphone input. */
|
|
101
109
|
supportsVoiceInput: boolean;
|
|
102
110
|
/** The client OS/interface identifier (e.g. "macos", "ios", "web"). */
|
|
@@ -282,6 +290,7 @@ export function resolveChannelCapabilities(
|
|
|
282
290
|
channel,
|
|
283
291
|
dashboardCapable: supportsDesktopUi,
|
|
284
292
|
supportsDynamicUi: supportsDesktopUi || iface === "web",
|
|
293
|
+
supportsInlineOptions: channelSupportsInlineOptions(channel),
|
|
285
294
|
supportsVoiceInput: supportsDesktopUi,
|
|
286
295
|
clientOS: iface ?? undefined,
|
|
287
296
|
chatType: resolvedChatType,
|
|
@@ -296,6 +305,7 @@ export function resolveChannelCapabilities(
|
|
|
296
305
|
channel,
|
|
297
306
|
dashboardCapable: false,
|
|
298
307
|
supportsDynamicUi: false,
|
|
308
|
+
supportsInlineOptions: channelSupportsInlineOptions(channel),
|
|
299
309
|
supportsVoiceInput: false,
|
|
300
310
|
chatType: resolvedChatType,
|
|
301
311
|
};
|
|
@@ -304,6 +314,7 @@ export function resolveChannelCapabilities(
|
|
|
304
314
|
channel,
|
|
305
315
|
dashboardCapable: false,
|
|
306
316
|
supportsDynamicUi: false,
|
|
317
|
+
supportsInlineOptions: channelSupportsInlineOptions(channel),
|
|
307
318
|
supportsVoiceInput: false,
|
|
308
319
|
chatType: resolvedChatType,
|
|
309
320
|
};
|
|
@@ -974,6 +985,11 @@ function placeholderForBlockType(type: ContentBlock["type"]): string | null {
|
|
|
974
985
|
case "tool_result":
|
|
975
986
|
case "web_search_tool_result":
|
|
976
987
|
return "[tool result]";
|
|
988
|
+
// Surfaces normally ride with a `_surfaceFallback` text sibling that
|
|
989
|
+
// supplies the line, so this label is reached only by legacy rows that
|
|
990
|
+
// carry a bare card — better than rendering an empty transcript line.
|
|
991
|
+
case "ui_surface":
|
|
992
|
+
return "[card]";
|
|
977
993
|
case "thinking":
|
|
978
994
|
case "redacted_thinking":
|
|
979
995
|
case "text":
|
|
@@ -118,6 +118,9 @@ export async function getOrCreateConversation(
|
|
|
118
118
|
(conversation.isStale() && !conversation.isProcessing())
|
|
119
119
|
) {
|
|
120
120
|
if (conversation) {
|
|
121
|
+
// Stale rebuild: the conversation id lives on, so abort in-flight
|
|
122
|
+
// children but keep terminal subagent results readable for the
|
|
123
|
+
// retention window.
|
|
121
124
|
getSubagentManager().abortAllForParent(conversationId);
|
|
122
125
|
conversation.dispose();
|
|
123
126
|
}
|
|
@@ -247,12 +250,15 @@ export async function getOrCreateConversation(
|
|
|
247
250
|
* deleted conversation and trip FK constraints.
|
|
248
251
|
*/
|
|
249
252
|
export function destroyActiveConversation(conversationId: string): void {
|
|
253
|
+
// Subagent teardown is keyed by parent id, not the live instance — an
|
|
254
|
+
// evicted parent still retains its terminal children, and deleting the
|
|
255
|
+
// conversation must take their records with it.
|
|
256
|
+
getSubagentManager().disposeAllForParent(conversationId);
|
|
250
257
|
const conversation = findConversation(conversationId);
|
|
251
258
|
if (!conversation) {
|
|
252
259
|
return;
|
|
253
260
|
}
|
|
254
261
|
removeFromEvictor(conversationId);
|
|
255
|
-
getSubagentManager().abortAllForParent(conversationId);
|
|
256
262
|
conversation.dispose();
|
|
257
263
|
deleteConversation(conversationId);
|
|
258
264
|
deleteConversationOptions(conversationId);
|
|
@@ -277,10 +283,12 @@ export function stopConversations(): void {
|
|
|
277
283
|
*/
|
|
278
284
|
export function clearAllActiveConversations(): number {
|
|
279
285
|
const count = conversationCount();
|
|
280
|
-
|
|
286
|
+
// Dispose subagents across ALL parents, not just the in-memory ones — an
|
|
287
|
+
// evicted parent still retains its terminal children, and clear-all must
|
|
288
|
+
// take their records with it.
|
|
289
|
+
getSubagentManager().disposeAllForAllParents();
|
|
281
290
|
for (const id of conversationIds()) {
|
|
282
291
|
removeFromEvictor(id);
|
|
283
|
-
subagentManager.abortAllForParent(id);
|
|
284
292
|
}
|
|
285
293
|
for (const conversation of allConversations()) {
|
|
286
294
|
conversation.dispose();
|
|
@@ -2,6 +2,7 @@ import { v4 as uuid, v7 as uuidv7 } from "uuid";
|
|
|
2
2
|
import { z } from "zod";
|
|
3
3
|
|
|
4
4
|
import { SurfaceActionSchema } from "../api/events/ui-surface-show.js";
|
|
5
|
+
import type { AssistantEvent } from "../api/index.js";
|
|
5
6
|
import {
|
|
6
7
|
CardSurfaceDataSchema,
|
|
7
8
|
ChoiceSurfaceDataSchema,
|
|
@@ -76,7 +77,6 @@ import type {
|
|
|
76
77
|
DynamicPagePreview,
|
|
77
78
|
DynamicPageSurfaceData,
|
|
78
79
|
FormSurfaceData,
|
|
79
|
-
ServerMessage,
|
|
80
80
|
SurfaceAction,
|
|
81
81
|
SurfaceData,
|
|
82
82
|
SurfaceType,
|
|
@@ -818,7 +818,7 @@ export interface SurfaceConversationContext {
|
|
|
818
818
|
channel: string;
|
|
819
819
|
supportsDynamicUi: boolean;
|
|
820
820
|
};
|
|
821
|
-
sendToClient(msg:
|
|
821
|
+
sendToClient(msg: AssistantEvent): void;
|
|
822
822
|
pendingSurfaceActions: Map<string, { surfaceType: SurfaceType }>;
|
|
823
823
|
lastSurfaceAction: Map<
|
|
824
824
|
string,
|
|
@@ -2001,7 +2001,7 @@ export async function handleSurfaceAction(
|
|
|
2001
2001
|
// Pass conversationId so events without an inline conversationId (e.g.
|
|
2002
2002
|
// text_delta) are published with the correct conversation scope and
|
|
2003
2003
|
// reach the SSE subscriber filtered to this conversation.
|
|
2004
|
-
const onEvent = (msg:
|
|
2004
|
+
const onEvent = (msg: AssistantEvent) =>
|
|
2005
2005
|
broadcastMessage(msg, ctx.conversationId);
|
|
2006
2006
|
|
|
2007
2007
|
const result = ctx.enqueueMessage({
|
|
@@ -2228,7 +2228,7 @@ export async function handleSurfaceAction(
|
|
|
2228
2228
|
// Pass conversationId so events without an inline conversationId (e.g.
|
|
2229
2229
|
// text_delta) are published with the correct conversation scope and
|
|
2230
2230
|
// reach the SSE subscriber filtered to this conversation.
|
|
2231
|
-
const onEvent = (msg:
|
|
2231
|
+
const onEvent = (msg: AssistantEvent) =>
|
|
2232
2232
|
broadcastMessage(msg, ctx.conversationId);
|
|
2233
2233
|
|
|
2234
2234
|
log.info(
|
|
@@ -6,12 +6,14 @@
|
|
|
6
6
|
* keeping the constructor body focused on wiring.
|
|
7
7
|
*/
|
|
8
8
|
|
|
9
|
+
import type { AssistantEvent } from "../api/index.js";
|
|
9
10
|
import {
|
|
10
11
|
type HostProxyCapability,
|
|
11
12
|
supportsHostProxy,
|
|
12
13
|
} from "../channels/types.js";
|
|
13
14
|
import { getIsPlatform } from "../config/env-registry.js";
|
|
14
15
|
import { getConfig } from "../config/loader.js";
|
|
16
|
+
import { isMemoryEnabled } from "../config/memory-v3-gate.js";
|
|
15
17
|
import type { PermissionPrompter } from "../permissions/prompter.js";
|
|
16
18
|
import type { SecretPrompter } from "../permissions/secret-prompter.js";
|
|
17
19
|
import { getBindingByConversation } from "../persistence/external-conversation-store.js";
|
|
@@ -62,7 +64,10 @@ import {
|
|
|
62
64
|
type UsageAttributionSnapshot,
|
|
63
65
|
} from "../usage/attribution.js";
|
|
64
66
|
import { getLogger } from "../util/logger.js";
|
|
65
|
-
import {
|
|
67
|
+
import {
|
|
68
|
+
conversationSupportsDynamicUi,
|
|
69
|
+
conversationSupportsGuardianQuestionCards,
|
|
70
|
+
} from "./channel-ui-capability.js";
|
|
66
71
|
import type { Conversation } from "./conversation.js";
|
|
67
72
|
import { projectSkillTools } from "./conversation-skill-tools.js";
|
|
68
73
|
import {
|
|
@@ -73,7 +78,6 @@ import {
|
|
|
73
78
|
isDoordashCommand,
|
|
74
79
|
markDoordashStepInProgress,
|
|
75
80
|
} from "./doordash-steps.js";
|
|
76
|
-
import type { ServerMessage } from "./message-protocol.js";
|
|
77
81
|
import { runPostExecutionSideEffects } from "./tool-side-effects.js";
|
|
78
82
|
import { FALLBACK_TURN_TRUST, resolveTrustClass } from "./trust-context.js";
|
|
79
83
|
|
|
@@ -176,8 +180,8 @@ export function getEffectiveEnabledPluginSet(conv: {
|
|
|
176
180
|
// ── read-only pass classification ────────────────────────────────────
|
|
177
181
|
|
|
178
182
|
/**
|
|
179
|
-
* The ONLY tools allowed in a read-only subagent pass
|
|
180
|
-
*
|
|
183
|
+
* The ONLY tools allowed in a read-only subagent pass
|
|
184
|
+
* (`subagentDenySideEffects`). This is a strict fail-safe allowlist
|
|
181
185
|
* of tools known to be read-only. Everything else is refused, because:
|
|
182
186
|
* - A side-effect denylist is inherently incomplete — low-risk core mutators
|
|
183
187
|
* (`remember`, `notify_parent`, `computer_use_*`, `delete_memory_page`, …) are
|
|
@@ -391,8 +395,8 @@ export function createToolExecutor(
|
|
|
391
395
|
enabledPluginSet: effectiveEnabledPluginSet,
|
|
392
396
|
sendToClient: (msg) => {
|
|
393
397
|
// Tool context's sendToClient uses a loose { type: string; [key: string]: unknown }
|
|
394
|
-
// signature, but at runtime these are always
|
|
395
|
-
ctx.sendToClient(msg as
|
|
398
|
+
// signature, but at runtime these are always AssistantEvent instances.
|
|
399
|
+
ctx.sendToClient(msg as AssistantEvent);
|
|
396
400
|
if (msg.type === "ui_surface_show") {
|
|
397
401
|
// The tool-context sendToClient signature is loose, so the show
|
|
398
402
|
// message's fields are untyped here; map them through the same
|
|
@@ -423,6 +427,8 @@ export function createToolExecutor(
|
|
|
423
427
|
// channels that can't render dynamic surfaces (Telegram, SMS) instead of
|
|
424
428
|
// emitting one the channel silently drops.
|
|
425
429
|
supportsDynamicUi: conversationSupportsDynamicUi(ctx),
|
|
430
|
+
supportsGuardianQuestionCards:
|
|
431
|
+
conversationSupportsGuardianQuestionCards(ctx),
|
|
426
432
|
proxyToolResolver: (
|
|
427
433
|
toolName: string,
|
|
428
434
|
proxyInput: Record<string, unknown>,
|
|
@@ -717,7 +723,7 @@ export function isToolActiveForContext(
|
|
|
717
723
|
}
|
|
718
724
|
if (name === "remember") {
|
|
719
725
|
try {
|
|
720
|
-
return getConfig()
|
|
726
|
+
return isMemoryEnabled(getConfig());
|
|
721
727
|
} catch {
|
|
722
728
|
return true;
|
|
723
729
|
}
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { AssistantEvent } from "../api/index.js";
|
|
1
2
|
import { getConfig } from "../config/loader.js";
|
|
2
3
|
import { updateConversationUsage } from "../persistence/conversation-crud.js";
|
|
3
4
|
import { recordUsageEvent } from "../persistence/llm-usage-store.js";
|
|
@@ -16,7 +17,7 @@ import {
|
|
|
16
17
|
resolvePricingForUsageWithOverrides,
|
|
17
18
|
usesAnthropicPricingRules,
|
|
18
19
|
} from "../util/pricing.js";
|
|
19
|
-
import type {
|
|
20
|
+
import type { UsageStats } from "./message-protocol.js";
|
|
20
21
|
|
|
21
22
|
const log = getLogger("conversation-usage");
|
|
22
23
|
|
|
@@ -27,12 +28,12 @@ export interface UsageContext {
|
|
|
27
28
|
}
|
|
28
29
|
|
|
29
30
|
function normalizeTokenCount(value: number | null | undefined): number {
|
|
30
|
-
if (typeof value !== "number" || !Number.isFinite(value)) return 0;
|
|
31
|
+
if (typeof value !== "number" || !Number.isFinite(value)) {return 0;}
|
|
31
32
|
return Math.max(value, 0);
|
|
32
33
|
}
|
|
33
34
|
|
|
34
35
|
function asRecord(value: unknown): Record<string, unknown> | null {
|
|
35
|
-
if (typeof value !== "object" || value == null) return null;
|
|
36
|
+
if (typeof value !== "object" || value == null) {return null;}
|
|
36
37
|
return value as Record<string, unknown>;
|
|
37
38
|
}
|
|
38
39
|
|
|
@@ -42,7 +43,7 @@ function extractAnthropicCacheCreationFromResponse(
|
|
|
42
43
|
const rawResponse = asRecord(response);
|
|
43
44
|
const usage = asRecord(rawResponse?.usage);
|
|
44
45
|
const cacheCreation = asRecord(usage?.cache_creation);
|
|
45
|
-
if (!cacheCreation) return null;
|
|
46
|
+
if (!cacheCreation) {return null;}
|
|
46
47
|
|
|
47
48
|
return {
|
|
48
49
|
ephemeral_5m_input_tokens: normalizeTokenCount(
|
|
@@ -64,7 +65,7 @@ function extractAnthropicCacheCreation(
|
|
|
64
65
|
|
|
65
66
|
for (const response of responses) {
|
|
66
67
|
const details = extractAnthropicCacheCreationFromResponse(response);
|
|
67
|
-
if (!details) continue;
|
|
68
|
+
if (!details) {continue;}
|
|
68
69
|
foundDetails = true;
|
|
69
70
|
ephemeral5mInputTokens += normalizeTokenCount(
|
|
70
71
|
details.ephemeral_5m_input_tokens,
|
|
@@ -74,7 +75,7 @@ function extractAnthropicCacheCreation(
|
|
|
74
75
|
);
|
|
75
76
|
}
|
|
76
77
|
|
|
77
|
-
if (!foundDetails) return null;
|
|
78
|
+
if (!foundDetails) {return null;}
|
|
78
79
|
|
|
79
80
|
return {
|
|
80
81
|
ephemeral_5m_input_tokens: ephemeral5mInputTokens,
|
|
@@ -96,8 +97,8 @@ function extractAnthropicSpeed(
|
|
|
96
97
|
for (const response of responses) {
|
|
97
98
|
const rec = asRecord(response);
|
|
98
99
|
const usage = asRecord(rec?.usage);
|
|
99
|
-
if (usage?.speed === "fast") return "fast";
|
|
100
|
-
if (usage?.speed === "standard") foundStandard = true;
|
|
100
|
+
if (usage?.speed === "fast") {return "fast";}
|
|
101
|
+
if (usage?.speed === "standard") {foundStandard = true;}
|
|
101
102
|
}
|
|
102
103
|
return foundStandard ? "standard" : null;
|
|
103
104
|
}
|
|
@@ -143,7 +144,7 @@ function resolveAttribution(
|
|
|
143
144
|
| null
|
|
144
145
|
| undefined,
|
|
145
146
|
): UsageAttributionSnapshot | null {
|
|
146
|
-
if (attribution == null) return null;
|
|
147
|
+
if (attribution == null) {return null;}
|
|
147
148
|
return isUsageAttributionSnapshot(attribution)
|
|
148
149
|
? attribution
|
|
149
150
|
: resolveUsageAttribution(attribution);
|
|
@@ -154,7 +155,7 @@ export function recordUsage(
|
|
|
154
155
|
inputTokens: number,
|
|
155
156
|
outputTokens: number,
|
|
156
157
|
model: string,
|
|
157
|
-
onEvent: (msg:
|
|
158
|
+
onEvent: (msg: AssistantEvent) => void,
|
|
158
159
|
actor: UsageActor,
|
|
159
160
|
requestId: string | null = null,
|
|
160
161
|
cacheCreationInputTokens = 0,
|
|
@@ -165,7 +166,7 @@ export function recordUsage(
|
|
|
165
166
|
attribution?: UsageAttributionInput | UsageAttributionSnapshot | null,
|
|
166
167
|
cronRunId: string | null = null,
|
|
167
168
|
): void {
|
|
168
|
-
if (inputTokens <= 0 && outputTokens <= 0) return;
|
|
169
|
+
if (inputTokens <= 0 && outputTokens <= 0) {return;}
|
|
169
170
|
|
|
170
171
|
const normalizedCacheCreationInputTokens = normalizeTokenCount(
|
|
171
172
|
cacheCreationInputTokens,
|