@vellumai/assistant 0.7.2 → 0.8.0
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/ARCHITECTURE.md +45 -29
- package/Dockerfile +1 -0
- package/__tests__/permissions/gateway-threshold-reader.test.ts +236 -9
- package/bun.lock +3 -0
- package/docs/architecture/memory.md +5 -2
- package/knip.json +1 -0
- package/node_modules/@vellumai/gateway-client/src/ipc-client.ts +13 -4
- package/node_modules/@vellumai/ipc-server-utils/bun.lock +24 -0
- package/node_modules/@vellumai/ipc-server-utils/package.json +18 -0
- package/node_modules/@vellumai/ipc-server-utils/src/index.ts +6 -0
- package/node_modules/@vellumai/ipc-server-utils/src/socket-watchdog.test.ts +430 -0
- package/node_modules/@vellumai/ipc-server-utils/src/socket-watchdog.ts +221 -0
- package/node_modules/@vellumai/ipc-server-utils/tsconfig.json +20 -0
- package/node_modules/@vellumai/skill-host-contracts/src/assistant-event.ts +0 -9
- package/node_modules/@vellumai/slack-text/src/index.test.ts +18 -35
- package/node_modules/@vellumai/slack-text/src/index.ts +2 -48
- package/openapi.yaml +470 -25
- package/package.json +3 -1
- package/src/__tests__/annotate-risk-options.test.ts +291 -0
- package/src/__tests__/app-control-flow.test.ts +21 -11
- package/src/__tests__/approval-cascade.test.ts +8 -16
- package/src/__tests__/approval-routes-http.test.ts +6 -0
- package/src/__tests__/assistant-event-hub.test.ts +48 -0
- package/src/__tests__/assistant-event.test.ts +0 -10
- package/src/__tests__/assistant-events-sse-hardening.test.ts +2 -7
- package/src/__tests__/assistant-feature-flags-integration.test.ts +18 -0
- package/src/__tests__/auto-analysis-end-to-end.test.ts +48 -0
- package/src/__tests__/background-workers-disk-pressure.test.ts +268 -0
- package/src/__tests__/call-constants.test.ts +10 -1
- package/src/__tests__/call-controller.test.ts +127 -0
- package/src/__tests__/call-conversation-messages.test.ts +8 -2
- package/src/__tests__/channel-inbound-disk-pressure.test.ts +537 -0
- package/src/__tests__/channel-readiness-service.test.ts +4 -2
- package/src/__tests__/cli-memory-v2-reembed-skills.test.ts +58 -28
- package/src/__tests__/config-loader-backfill.test.ts +379 -0
- package/src/__tests__/config-loader-platform-defaults.test.ts +284 -1
- package/src/__tests__/config-schema.test.ts +1 -0
- package/src/__tests__/config-watcher-cleanup-throttle.test.ts +18 -9
- package/src/__tests__/config-watcher.test.ts +140 -69
- package/src/__tests__/context-search-agent-runner.test.ts +61 -3
- package/src/__tests__/context-search-conversations-source.test.ts +0 -24
- package/src/__tests__/context-search-fanout.test.ts +0 -1
- package/src/__tests__/context-search-memory-source.test.ts +6 -33
- package/src/__tests__/context-search-memory-v2-source.test.ts +0 -2
- package/src/__tests__/context-search-pkb-source.test.ts +12 -7
- package/src/__tests__/context-search-workspace-source.test.ts +0 -1
- package/src/__tests__/conversation-abort-tool-results.test.ts +1 -0
- package/src/__tests__/conversation-agent-loop-disk-pressure.test.ts +223 -0
- package/src/__tests__/conversation-agent-loop-inference-profile.test.ts +1 -1
- package/src/__tests__/conversation-agent-loop-overflow.test.ts +1 -1
- package/src/__tests__/conversation-agent-loop.test.ts +457 -8
- package/src/__tests__/conversation-confirmation-signals.test.ts +5 -13
- package/src/__tests__/conversation-error.test.ts +150 -3
- package/src/__tests__/conversation-init.benchmark.test.ts +1 -1
- package/src/__tests__/conversation-process-callsite.test.ts +38 -0
- package/src/__tests__/conversation-provider-retry-repair.test.ts +1 -0
- package/src/__tests__/conversation-runtime-assembly.test.ts +74 -0
- package/src/__tests__/conversation-slash-unknown.test.ts +1 -0
- package/src/__tests__/conversation-speed-override.test.ts +0 -3
- package/src/__tests__/conversation-store.test.ts +0 -18
- package/src/__tests__/conversation-surfaces-action-delivery.test.ts +170 -9
- package/src/__tests__/conversation-surfaces-app-control.test.ts +15 -4
- package/src/__tests__/conversation-surfaces-data-persist.test.ts +476 -0
- package/src/__tests__/conversation-tool-setup-app-refresh.test.ts +61 -5
- package/src/__tests__/conversation-workspace-injection.test.ts +1 -1
- package/src/__tests__/conversation-workspace-tool-tracking.test.ts +1 -1
- package/src/__tests__/credentials-cli.test.ts +7 -0
- package/src/__tests__/cu-unified-flow.test.ts +176 -10
- package/src/__tests__/date-context.test.ts +164 -2
- package/src/__tests__/disk-pressure-guard.test.ts +262 -0
- package/src/__tests__/disk-pressure-lifecycle.test.ts +168 -0
- package/src/__tests__/disk-pressure-policy.test.ts +241 -0
- package/src/__tests__/disk-pressure-routes.test.ts +379 -0
- package/src/__tests__/disk-pressure-tools.test.ts +277 -0
- package/src/__tests__/disk-usage.test.ts +150 -0
- package/src/__tests__/events-client-registration.test.ts +52 -0
- package/src/__tests__/events-dev-bypass-actor.test.ts +162 -0
- package/src/__tests__/file-write-tool.test.ts +4 -10
- package/src/__tests__/filing-service.test.ts +2 -20
- package/src/__tests__/handlers-skills-memory-v2-reseed.test.ts +10 -26
- package/src/__tests__/heartbeat-disk-pressure.test.ts +183 -0
- package/src/__tests__/heartbeat-service.test.ts +260 -11
- package/src/__tests__/host-app-control-proxy.test.ts +195 -25
- package/src/__tests__/host-bash-proxy.test.ts +227 -34
- package/src/__tests__/host-bash-routes.test.ts +178 -13
- package/src/__tests__/host-cu-proxy.test.ts +210 -3
- package/src/__tests__/host-cu-routes-targeted.test.ts +141 -12
- package/src/__tests__/host-file-proxy-targeted.test.ts +48 -9
- package/src/__tests__/host-file-proxy.test.ts +268 -6
- package/src/__tests__/host-file-routes-targeted.test.ts +175 -17
- package/src/__tests__/host-transfer-proxy-targeted.test.ts +408 -59
- package/src/__tests__/host-transfer-routes-targeted.test.ts +232 -17
- package/src/__tests__/http-user-message-parity.test.ts +107 -1
- package/src/__tests__/injector-chain.test.ts +36 -16
- package/src/__tests__/injector-disk-pressure.test.ts +224 -0
- package/src/__tests__/injector-pkb-v2-silenced.test.ts +10 -7
- package/src/__tests__/lifecycle-memory-v2-seed.test.ts +154 -67
- package/src/__tests__/managed-profile-guard.test.ts +18 -0
- package/src/__tests__/mcp-abort-signal.test.ts +130 -0
- package/src/__tests__/memory-admin-recall.test.ts +3 -11
- package/src/__tests__/memory-retrieval-pipeline.test.ts +22 -1
- package/src/__tests__/normalize-onboarding.test.ts +180 -0
- package/src/__tests__/notification-decision-fallback.test.ts +91 -0
- package/src/__tests__/notification-decision-strategy.test.ts +22 -0
- package/src/__tests__/oauth-cli.test.ts +121 -0
- package/src/__tests__/oauth-connect-routes.test.ts +316 -0
- package/src/__tests__/oauth-provider-seed-logos.test.ts +24 -2
- package/src/__tests__/onboarding-persona-write.test.ts +308 -0
- package/src/__tests__/openai-provider.test.ts +45 -8
- package/src/__tests__/persist-onboarding-artifacts.test.ts +44 -64
- package/src/__tests__/platform-callback-registration.test.ts +21 -4
- package/src/__tests__/platform.test.ts +2 -1
- package/src/__tests__/playbook-execution.test.ts +0 -43
- package/src/__tests__/plugin-tool-contribution.test.ts +47 -0
- package/src/__tests__/prechat-onboarding-contract.test.ts +214 -27
- package/src/__tests__/provider-tool-name.test.ts +23 -0
- package/src/__tests__/relay-server.test.ts +60 -5
- package/src/__tests__/runtime-events-sse.test.ts +4 -8
- package/src/__tests__/scheduler-disk-pressure.test.ts +148 -0
- package/src/__tests__/secret-ingress-http.test.ts +0 -1
- package/src/__tests__/secret-prompt-log-hygiene.test.ts +7 -5
- package/src/__tests__/secret-prompter-channel-fallback.test.ts +7 -5
- package/src/__tests__/secret-response-routing.test.ts +7 -5
- package/src/__tests__/server-history-render.test.ts +82 -0
- package/src/__tests__/skill-include-graph.test.ts +31 -0
- package/src/__tests__/skill-load-tool.test.ts +44 -16
- package/src/__tests__/skills.test.ts +39 -0
- package/src/__tests__/suggestion-routes.test.ts +46 -0
- package/src/__tests__/tool-execution-pipeline.benchmark.test.ts +0 -42
- package/src/__tests__/tool-executor.test.ts +155 -0
- package/src/__tests__/twilio-validation.test.ts +2 -2
- package/src/__tests__/voice-session-bridge.test.ts +3 -0
- package/src/__tests__/workspace-migration-065-bump-stale-heartbeat-interval.test.ts +122 -0
- package/src/__tests__/workspace-migration-066-seed-heartbeat-callsite-cost-default.test.ts +285 -0
- package/src/__tests__/workspace-migration-068-release-notes-local-timezone.test.ts +90 -0
- package/src/__tests__/workspace-migration-069-seed-onboarding-threads.test.ts +120 -0
- package/src/__tests__/workspace-migration-071-remove-safe-storage-release-note.test.ts +206 -0
- package/src/__tests__/workspace-migration-safe-storage-limits-release.test.ts +78 -0
- package/src/agent/loop.ts +11 -0
- package/src/approvals/guardian-request-resolvers.ts +3 -32
- package/src/backup/snapshot-lock.ts +2 -27
- package/src/bundler/compiler-tools.ts +3 -2
- package/src/calls/call-constants.ts +5 -8
- package/src/calls/call-controller.ts +130 -67
- package/src/calls/call-conversation-messages.ts +46 -10
- package/src/calls/relay-server.ts +7 -1
- package/src/calls/voice-session-bridge.ts +1 -1
- package/src/cli/commands/__tests__/webhooks.test.ts +0 -4
- package/src/cli/commands/bash.ts +35 -108
- package/src/cli/commands/contacts.ts +64 -25
- package/src/cli/commands/credentials.ts +56 -0
- package/src/cli/commands/memory-v2.ts +11 -10
- package/src/cli/commands/oauth/__tests__/connect.test.ts +401 -219
- package/src/cli/commands/oauth/connect.ts +124 -40
- package/src/cli/commands/platform/__tests__/callback-routes-list.test.ts +0 -3
- package/src/cli/commands/platform/__tests__/connect.test.ts +7 -1
- package/src/cli/commands/platform/__tests__/disconnect.test.ts +7 -1
- package/src/cli/commands/platform/__tests__/status.test.ts +103 -6
- package/src/cli/commands/platform/index.ts +16 -7
- package/src/cli/commands/status.ts +57 -0
- package/src/cli/program.ts +4 -2
- package/src/config/assistant-feature-flags.ts +13 -3
- package/src/config/bundled-skills/app-builder/SKILL.md +1 -3
- package/src/config/bundled-skills/messaging/tools/messaging-analyze-style.ts +4 -3
- package/src/config/bundled-skills/phone-calls/references/TROUBLESHOOTING.md +13 -7
- package/src/config/bundled-skills/playbooks/tools/playbook-create.ts +2 -2
- package/src/config/bundled-skills/playbooks/tools/playbook-delete.ts +2 -2
- package/src/config/bundled-skills/playbooks/tools/playbook-list.ts +2 -2
- package/src/config/bundled-skills/playbooks/tools/playbook-update.ts +2 -2
- package/src/config/env.ts +0 -8
- package/src/config/feature-flag-registry.json +13 -5
- package/src/config/loader.ts +199 -27
- package/src/config/schemas/__tests__/memory-v2.test.ts +10 -5
- package/src/config/schemas/call-site-catalog.ts +14 -0
- package/src/config/schemas/channels.ts +0 -5
- package/src/config/schemas/heartbeat.ts +1 -1
- package/src/config/schemas/llm.ts +2 -0
- package/src/config/schemas/memory-lifecycle.ts +13 -0
- package/src/config/schemas/memory-v2.ts +76 -12
- package/src/config/schemas/platform.ts +43 -3
- package/src/config/schemas/services.ts +28 -0
- package/src/config/seed-inference-profiles.ts +230 -33
- package/src/contacts/contact-store.ts +0 -25
- package/src/daemon/__tests__/conversation-lifecycle-auto-analyze.test.ts +32 -0
- package/src/daemon/__tests__/conversation-tool-setup.test.ts +86 -25
- package/src/daemon/assistant-attachments.ts +4 -4
- package/src/daemon/config-watcher.ts +85 -57
- package/src/daemon/conversation-agent-loop-handlers.ts +38 -0
- package/src/daemon/conversation-agent-loop.ts +183 -43
- package/src/daemon/conversation-error.ts +87 -15
- package/src/daemon/conversation-lifecycle.ts +22 -10
- package/src/daemon/conversation-process.ts +8 -0
- package/src/daemon/conversation-runtime-assembly.ts +26 -0
- package/src/daemon/conversation-store.ts +2 -2
- package/src/daemon/conversation-surfaces.ts +211 -29
- package/src/daemon/conversation-tool-setup.ts +66 -19
- package/src/daemon/conversation.ts +18 -23
- package/src/daemon/date-context.ts +71 -22
- package/src/daemon/disk-pressure-background-gate.ts +73 -0
- package/src/daemon/disk-pressure-guard.ts +343 -0
- package/src/daemon/disk-pressure-policy.ts +163 -0
- package/src/daemon/handlers/shared.ts +26 -1
- package/src/daemon/handlers/skills.ts +3 -4
- package/src/daemon/host-app-control-proxy.ts +137 -41
- package/src/daemon/host-bash-proxy.ts +47 -22
- package/src/daemon/host-browser-proxy.ts +1 -1
- package/src/daemon/host-cu-proxy.ts +50 -4
- package/src/daemon/host-file-proxy.ts +44 -8
- package/src/daemon/host-transfer-proxy.ts +97 -6
- package/src/daemon/lifecycle.ts +167 -101
- package/src/daemon/meet-host-supervisor.ts +4 -4
- package/src/daemon/meet-manifest-loader.ts +0 -1
- package/src/daemon/memory-v2-startup.ts +66 -15
- package/src/daemon/message-protocol.ts +3 -0
- package/src/daemon/message-types/conversations.ts +4 -0
- package/src/daemon/message-types/disk-pressure.ts +9 -0
- package/src/daemon/message-types/messages.ts +22 -1
- package/src/daemon/profiler-run-store.ts +5 -5
- package/src/daemon/tool-setup-types.ts +2 -2
- package/src/documents/document-store.ts +119 -0
- package/src/filing/filing-service.ts +29 -5
- package/src/heartbeat/__tests__/heartbeat-feed-event.test.ts +9 -16
- package/src/heartbeat/__tests__/heartbeat-run-store.test.ts +36 -0
- package/src/heartbeat/heartbeat-run-store.ts +13 -0
- package/src/heartbeat/heartbeat-service.ts +205 -31
- package/src/home/feed-scheduler.ts +18 -0
- package/src/inbound/platform-callback-registration.ts +8 -15
- package/src/ipc/__tests__/clients-list-ipc.test.ts +169 -0
- package/src/ipc/assistant-server.ts +149 -38
- package/src/ipc/gateway-client.ts +37 -3
- package/src/ipc/skill-server.ts +99 -42
- package/src/live-voice/live-voice-archive.ts +4 -4
- package/src/live-voice/protocol.ts +5 -7
- package/src/media/image-service.ts +1 -7
- package/src/memory/__tests__/fixtures/memory-v2-activation-fixtures.ts +21 -13
- package/src/memory/__tests__/jobs-worker-v2-schedule.test.ts +34 -51
- package/src/memory/__tests__/memory-v2-activation-log-store.test.ts +0 -6
- package/src/memory/__tests__/memory-v2-concept-frequency.test.ts +272 -0
- package/src/memory/admin.ts +5 -9
- package/src/memory/context-search/agent-runner.ts +19 -2
- package/src/memory/context-search/sources/conversations.ts +2 -11
- package/src/memory/context-search/sources/memory-v2.ts +1 -16
- package/src/memory/context-search/sources/memory.ts +2 -3
- package/src/memory/context-search/sources/pkb.ts +2 -3
- package/src/memory/context-search/types.ts +0 -1
- package/src/memory/conversation-crud.ts +4 -12
- package/src/memory/db-init.ts +2 -0
- package/src/memory/embedding-runtime-manager.ts +119 -5
- package/src/memory/graph/__tests__/conversation-graph-memory-v2-routing.test.ts +136 -82
- package/src/memory/graph/__tests__/handle-remember-v2.test.ts +11 -26
- package/src/memory/graph/conversation-graph-memory.ts +72 -61
- package/src/memory/graph/extraction.ts +1 -3
- package/src/memory/graph/graph-search.test.ts +11 -67
- package/src/memory/graph/graph-search.ts +4 -24
- package/src/memory/graph/retriever.test.ts +12 -1
- package/src/memory/graph/retriever.ts +10 -15
- package/src/memory/graph/tool-handlers.ts +3 -4
- package/src/memory/graph/tools.ts +4 -4
- package/src/memory/indexer.ts +53 -45
- package/src/memory/job-handlers/backfill.ts +2 -11
- package/src/memory/job-handlers/cleanup.ts +43 -0
- package/src/memory/job-handlers/embedding.ts +6 -8
- package/src/memory/job-handlers/summarization.ts +2 -7
- package/src/memory/jobs/__tests__/embed-concept-page.test.ts +116 -0
- package/src/memory/jobs/embed-concept-page.ts +223 -87
- package/src/memory/jobs-store.ts +48 -0
- package/src/memory/jobs-worker.ts +85 -43
- package/src/memory/memory-v2-activation-log-store.ts +32 -14
- package/src/memory/memory-v2-concept-frequency.ts +169 -0
- package/src/memory/migrations/239-trace-events-created-at-index.ts +18 -0
- package/src/memory/migrations/index.ts +1 -0
- package/src/memory/pkb/pkb-search.test.ts +7 -0
- package/src/memory/pkb/pkb-search.ts +4 -5
- package/src/memory/qdrant-client.ts +3 -13
- package/src/memory/rerank-local.ts +374 -0
- package/src/memory/search/semantic.ts +10 -72
- package/src/memory/trace-event-store.ts +1 -17
- package/src/memory/v2/__tests__/activation.test.ts +346 -255
- package/src/memory/v2/__tests__/consolidation-job.test.ts +61 -40
- package/src/memory/v2/__tests__/injection.test.ts +297 -190
- package/src/memory/v2/__tests__/prompts-consolidation.test.ts +61 -2
- package/src/memory/v2/__tests__/qdrant.test.ts +326 -9
- package/src/memory/v2/__tests__/reranker.test.ts +338 -0
- package/src/memory/v2/__tests__/sim.test.ts +113 -196
- package/src/memory/v2/__tests__/skill-store.test.ts +71 -65
- package/src/memory/v2/__tests__/static-context.test.ts +77 -14
- package/src/memory/v2/__tests__/sweep-job.test.ts +19 -33
- package/src/memory/v2/activation.ts +149 -156
- package/src/memory/v2/consolidation-job.ts +69 -20
- package/src/memory/v2/injection.ts +75 -68
- package/src/memory/v2/page-store.ts +39 -0
- package/src/memory/v2/prompts/consolidation.ts +41 -1
- package/src/memory/v2/qdrant.ts +306 -46
- package/src/memory/v2/reranker.ts +177 -0
- package/src/memory/v2/sim.ts +77 -110
- package/src/memory/v2/skill-content.ts +4 -3
- package/src/memory/v2/skill-store.ts +82 -59
- package/src/memory/v2/static-context.ts +26 -8
- package/src/memory/v2/sweep-job.ts +5 -6
- package/src/memory/v2/types.ts +17 -10
- package/src/notifications/copy-composer.ts +47 -0
- package/src/notifications/decision-engine.ts +46 -0
- package/src/notifications/signal.ts +4 -0
- package/src/oauth/AGENTS.md +3 -1
- package/src/oauth/__tests__/oauth-connect-state.test.ts +137 -0
- package/src/oauth/connect-orchestrator.ts +2 -0
- package/src/oauth/connection-resolver.test.ts +66 -1
- package/src/oauth/connection-resolver.ts +55 -1
- package/src/oauth/oauth-connect-state.ts +77 -0
- package/src/oauth/seed-providers.ts +58 -1
- package/src/permissions/gateway-threshold-reader.ts +116 -8
- package/src/permissions/prompter.ts +86 -96
- package/src/permissions/secret-prompter.ts +31 -31
- package/src/plugins/defaults/injectors.ts +36 -4
- package/src/plugins/defaults/memory-retrieval.ts +5 -6
- package/src/plugins/types.ts +7 -0
- package/src/proactive-artifact/aux-message-injector.ts +74 -0
- package/src/proactive-artifact/decision.test.ts +226 -0
- package/src/proactive-artifact/decision.ts +165 -0
- package/src/proactive-artifact/index.ts +7 -0
- package/src/proactive-artifact/job.test.ts +914 -0
- package/src/proactive-artifact/job.ts +366 -0
- package/src/proactive-artifact/message-copy.ts +58 -0
- package/src/proactive-artifact/trigger-state.test.ts +277 -0
- package/src/proactive-artifact/trigger-state.ts +119 -0
- package/src/prompts/normalize-onboarding.ts +80 -0
- package/src/prompts/persona-resolver.ts +101 -9
- package/src/prompts/system-prompt.ts +21 -7
- package/src/prompts/templates/BOOTSTRAP.md +13 -5
- package/src/prompts/templates/SOUL.md +13 -28
- package/src/providers/__tests__/retry-callsite.test.ts +222 -1
- package/src/providers/model-intents.ts +7 -0
- package/src/providers/openrouter/client.ts +8 -0
- package/src/providers/retry.ts +50 -0
- package/src/providers/types.ts +1 -0
- package/src/runtime/__tests__/agent-wake.test.ts +456 -3
- package/src/runtime/agent-wake.ts +238 -100
- package/src/runtime/assistant-event-hub.ts +36 -6
- package/src/runtime/assistant-event.ts +0 -1
- package/src/runtime/auth/__tests__/route-policy.test.ts +64 -0
- package/src/runtime/auth/route-policy.ts +15 -1
- package/src/runtime/auth/same-actor.ts +216 -0
- package/src/runtime/channel-approvals.ts +3 -2
- package/src/runtime/channel-retry-sweep.ts +65 -1
- package/src/runtime/local-actor-identity.ts +52 -11
- package/src/runtime/pending-interactions.ts +27 -15
- package/src/runtime/routes/__tests__/client-routes.test.ts +155 -0
- package/src/runtime/routes/__tests__/conversation-query-routes.test.ts +0 -5
- package/src/runtime/routes/__tests__/heartbeat-routes.test.ts +1 -1
- package/src/runtime/routes/__tests__/memory-v2-routes.test.ts +147 -0
- package/src/runtime/routes/approval-routes.ts +7 -3
- package/src/runtime/routes/client-routes.ts +20 -2
- package/src/runtime/routes/consolidation-routes.ts +8 -9
- package/src/runtime/routes/contact-routes.ts +0 -25
- package/src/runtime/routes/conversation-query-routes.ts +44 -1
- package/src/runtime/routes/conversation-routes.ts +35 -26
- package/src/runtime/routes/debug-bash-routes.ts +165 -0
- package/src/runtime/routes/disk-pressure-routes.ts +121 -0
- package/src/runtime/routes/document-pdf-renderer.ts +6 -2
- package/src/runtime/routes/documents-routes.ts +2 -75
- package/src/runtime/routes/events-routes.ts +41 -9
- package/src/runtime/routes/filing-routes.ts +2 -3
- package/src/runtime/routes/host-bash-routes.ts +23 -3
- package/src/runtime/routes/host-cu-routes.ts +33 -6
- package/src/runtime/routes/host-file-routes.ts +32 -6
- package/src/runtime/routes/host-transfer-routes.ts +79 -16
- package/src/runtime/routes/identity-routes.ts +7 -138
- package/src/runtime/routes/inbound-message-handler.ts +77 -12
- package/src/runtime/routes/index.ts +6 -0
- package/src/runtime/routes/memory-item-routes.test.ts +37 -17
- package/src/runtime/routes/memory-item-routes.ts +5 -6
- package/src/runtime/routes/memory-v2-routes.ts +136 -17
- package/src/runtime/routes/oauth-connect-routes.ts +153 -0
- package/src/runtime/verification-outbound-actions.ts +4 -4
- package/src/schedule/run-script.ts +37 -5
- package/src/schedule/scheduler.ts +20 -1
- package/src/security/encrypted-store.ts +2 -0
- package/src/security/secure-keys.ts +55 -0
- package/src/skills/include-graph.ts +35 -13
- package/src/skills/remote-skill-policy.ts +4 -10
- package/src/subagent/index.ts +1 -7
- package/src/subagent/manager.ts +1 -15
- package/src/tasks/task-runner.ts +0 -1
- package/src/tasks/task-store.ts +0 -3
- package/src/tools/background-tool-registry.ts +17 -3
- package/src/tools/document/document-tool.ts +20 -0
- package/src/tools/executor.ts +18 -2
- package/src/tools/host-filesystem/edit.test.ts +151 -0
- package/src/tools/host-filesystem/edit.ts +43 -1
- package/src/tools/host-filesystem/read.test.ts +129 -0
- package/src/tools/host-filesystem/read.ts +43 -1
- package/src/tools/host-filesystem/transfer.test.ts +127 -2
- package/src/tools/host-filesystem/transfer.ts +56 -11
- package/src/tools/host-filesystem/write.test.ts +134 -0
- package/src/tools/host-filesystem/write.ts +43 -1
- package/src/tools/host-terminal/host-shell.ts +13 -6
- package/src/tools/mcp/mcp-tool-factory.ts +2 -1
- package/src/tools/memory/register.test.ts +14 -9
- package/src/tools/memory/register.ts +1 -2
- package/src/tools/permission-checker.ts +15 -0
- package/src/tools/provider-tool-name.ts +28 -0
- package/src/tools/registry.ts +30 -9
- package/src/tools/skills/load.ts +24 -20
- package/src/tools/terminal/shell.ts +9 -1
- package/src/tools/tool-approval-handler.ts +31 -6
- package/src/tools/tool-name-aliases.ts +19 -0
- package/src/tools/types.ts +43 -3
- package/src/tts/provider-catalog.ts +3 -5
- package/src/util/disk-usage.ts +138 -0
- package/src/util/platform.ts +21 -11
- package/src/util/process-liveness.ts +26 -0
- package/src/workspace/heartbeat-service.ts +19 -0
- package/src/workspace/migrations/065-bump-stale-heartbeat-interval.ts +60 -0
- package/src/workspace/migrations/066-seed-heartbeat-callsite-cost-default.ts +146 -0
- package/src/workspace/migrations/067-release-notes-safe-storage-limits.ts +14 -0
- package/src/workspace/migrations/068-release-notes-local-timezone.ts +65 -0
- package/src/workspace/migrations/069-seed-onboarding-threads.ts +28 -0
- package/src/workspace/migrations/070-memory-v2-summary-schema-rebuild.ts +31 -0
- package/src/workspace/migrations/071-remove-safe-storage-release-note.ts +111 -0
- package/src/workspace/migrations/registry.ts +14 -0
- package/src/__tests__/conversation-tool-setup-memory-scope.test.ts +0 -167
- package/src/memory/v2/__tests__/skill-qdrant.test.ts +0 -657
- package/src/memory/v2/skill-qdrant.ts +0 -404
- package/src/signals/bash.ts +0 -198
package/src/daemon/lifecycle.ts
CHANGED
|
@@ -7,10 +7,7 @@ import { reconcileCallsOnStartup } from "../calls/call-recovery.js";
|
|
|
7
7
|
import { setRelayBroadcast } from "../calls/relay-server.js";
|
|
8
8
|
import { TwilioConversationRelayProvider } from "../calls/twilio-provider.js";
|
|
9
9
|
import { setVoiceBridgeDeps } from "../calls/voice-session-bridge.js";
|
|
10
|
-
import {
|
|
11
|
-
initFeatureFlagOverrides,
|
|
12
|
-
isAssistantFeatureFlagEnabled,
|
|
13
|
-
} from "../config/assistant-feature-flags.js";
|
|
10
|
+
import { initFeatureFlagOverrides } from "../config/assistant-feature-flags.js";
|
|
14
11
|
import {
|
|
15
12
|
getPlatformAssistantId,
|
|
16
13
|
getRuntimeHttpHost,
|
|
@@ -54,7 +51,6 @@ import { startMemoryJobsWorker } from "../memory/jobs-worker.js";
|
|
|
54
51
|
import { initQdrantClient, resolveQdrantUrl } from "../memory/qdrant-client.js";
|
|
55
52
|
import { QdrantManager } from "../memory/qdrant-manager.js";
|
|
56
53
|
import { rotateToolInvocations } from "../memory/tool-usage-store.js";
|
|
57
|
-
import { deleteOldTraceEvents } from "../memory/trace-event-store.js";
|
|
58
54
|
import {
|
|
59
55
|
emitNotificationSignal,
|
|
60
56
|
registerBroadcastFn,
|
|
@@ -62,6 +58,7 @@ import {
|
|
|
62
58
|
import { backfillManualTokenConnections } from "../oauth/manual-token-connection.js";
|
|
63
59
|
import { seedOAuthProviders } from "../oauth/seed-providers.js";
|
|
64
60
|
import { loadUserPlugins } from "../plugins/user-loader.js";
|
|
61
|
+
import { backfillGuardIfNeeded } from "../proactive-artifact/index.js";
|
|
65
62
|
import { ensurePromptFiles } from "../prompts/system-prompt.js";
|
|
66
63
|
import { resolveManagedProxyContext } from "../providers/managed-proxy/context.js";
|
|
67
64
|
import { broadcastMessage } from "../runtime/assistant-event-hub.js";
|
|
@@ -105,6 +102,11 @@ import {
|
|
|
105
102
|
cleanupPidFileIfOwner,
|
|
106
103
|
writePid,
|
|
107
104
|
} from "./daemon-control.js";
|
|
105
|
+
import {
|
|
106
|
+
evaluateDiskPressureNow,
|
|
107
|
+
startDiskPressureGuard,
|
|
108
|
+
stopDiskPressureGuard,
|
|
109
|
+
} from "./disk-pressure-guard.js";
|
|
108
110
|
import { bootstrapPlugins } from "./external-plugins-bootstrap.js";
|
|
109
111
|
import {
|
|
110
112
|
createGuardianActionCopyGenerator,
|
|
@@ -112,7 +114,10 @@ import {
|
|
|
112
114
|
} from "./guardian-action-generators.js";
|
|
113
115
|
import { backfillSlackInjectionTemplates } from "./handlers/config-slack-channel.js";
|
|
114
116
|
import { installAssistantSymlink } from "./install-symlink.js";
|
|
115
|
-
import {
|
|
117
|
+
import {
|
|
118
|
+
maybeRebuildMemoryV2Concepts,
|
|
119
|
+
maybeSeedMemoryV2Skills,
|
|
120
|
+
} from "./memory-v2-startup.js";
|
|
116
121
|
import { processMessage } from "./process-message.js";
|
|
117
122
|
import { runProfilerSweep } from "./profiler-run-store.js";
|
|
118
123
|
import {
|
|
@@ -125,11 +130,57 @@ import { DaemonServer } from "./server.js";
|
|
|
125
130
|
import { installShutdownHandlers } from "./shutdown-handlers.js";
|
|
126
131
|
|
|
127
132
|
const log = getLogger("lifecycle");
|
|
133
|
+
let diskPressureStartupSampleTimer: ReturnType<typeof setTimeout> | null = null;
|
|
128
134
|
|
|
129
135
|
function loadDotEnv(): void {
|
|
130
136
|
dotenvConfig({ path: getDotEnvPath(), quiet: true });
|
|
131
137
|
}
|
|
132
138
|
|
|
139
|
+
function runDeferredDiskPressureStartupSample(): void {
|
|
140
|
+
diskPressureStartupSampleTimer = null;
|
|
141
|
+
try {
|
|
142
|
+
const status = evaluateDiskPressureNow();
|
|
143
|
+
if (status.error) {
|
|
144
|
+
log.warn(
|
|
145
|
+
{ error: status.error },
|
|
146
|
+
"Disk pressure guard sample failed during startup — continuing unlocked",
|
|
147
|
+
);
|
|
148
|
+
}
|
|
149
|
+
} catch (err) {
|
|
150
|
+
log.warn(
|
|
151
|
+
{ err },
|
|
152
|
+
"Disk pressure guard failed during startup — continuing unlocked",
|
|
153
|
+
);
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
export function startDiskPressureGuardForLifecycle(): void {
|
|
158
|
+
try {
|
|
159
|
+
const startedStatus = startDiskPressureGuard();
|
|
160
|
+
if (!startedStatus.enabled) return;
|
|
161
|
+
if (!diskPressureStartupSampleTimer) {
|
|
162
|
+
diskPressureStartupSampleTimer = setTimeout(
|
|
163
|
+
runDeferredDiskPressureStartupSample,
|
|
164
|
+
0,
|
|
165
|
+
);
|
|
166
|
+
(diskPressureStartupSampleTimer as { unref?: () => void }).unref?.();
|
|
167
|
+
}
|
|
168
|
+
} catch (err) {
|
|
169
|
+
log.warn(
|
|
170
|
+
{ err },
|
|
171
|
+
"Disk pressure guard failed during startup — continuing unlocked",
|
|
172
|
+
);
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
export function stopDiskPressureGuardForLifecycle(): void {
|
|
177
|
+
if (diskPressureStartupSampleTimer) {
|
|
178
|
+
clearTimeout(diskPressureStartupSampleTimer);
|
|
179
|
+
diskPressureStartupSampleTimer = null;
|
|
180
|
+
}
|
|
181
|
+
stopDiskPressureGuard();
|
|
182
|
+
}
|
|
183
|
+
|
|
133
184
|
export interface CesStartupResult {
|
|
134
185
|
client: CesClient | undefined;
|
|
135
186
|
processManager: CesProcessManager | undefined;
|
|
@@ -267,21 +318,16 @@ export async function runDaemon(): Promise<void> {
|
|
|
267
318
|
const signingKey = resolveSigningKey();
|
|
268
319
|
initAuthSigningKey(signingKey);
|
|
269
320
|
|
|
270
|
-
// Pre-populate
|
|
271
|
-
//
|
|
272
|
-
//
|
|
273
|
-
//
|
|
274
|
-
//
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
// the daemon. seedV2SkillEntries is idempotent, so re-running after
|
|
281
|
-
// overrides land is safe.
|
|
282
|
-
void initFeatureFlagOverrides()
|
|
283
|
-
.then(() => maybeSeedMemoryV2Skills(loadConfig()))
|
|
284
|
-
.catch((err) => log.warn({ err }, "Background feature flag init failed"));
|
|
321
|
+
// Pre-populate feature flag overrides so subsequent sync
|
|
322
|
+
// isAssistantFeatureFlagEnabled() calls have data. Fired non-blocking
|
|
323
|
+
// so a slow or unreachable gateway doesn't delay daemon startup (the
|
|
324
|
+
// IPC call has a 3s connect + 5s call timeout that would otherwise
|
|
325
|
+
// stall the critical path).
|
|
326
|
+
void initFeatureFlagOverrides().catch((err) =>
|
|
327
|
+
log.warn({ err }, "Background feature flag init failed"),
|
|
328
|
+
);
|
|
329
|
+
|
|
330
|
+
maybeSeedMemoryV2Skills(loadConfig());
|
|
285
331
|
|
|
286
332
|
seedInterfaceFiles();
|
|
287
333
|
|
|
@@ -448,12 +494,22 @@ export async function runDaemon(): Promise<void> {
|
|
|
448
494
|
}
|
|
449
495
|
} // end if (dbReady)
|
|
450
496
|
|
|
451
|
-
//
|
|
452
|
-
//
|
|
453
|
-
//
|
|
454
|
-
//
|
|
497
|
+
// Merge CLI-provided default config (from VELLUM_DEFAULT_WORKSPACE_CONFIG_PATH)
|
|
498
|
+
// into the workspace config file before profile seeding and the first
|
|
499
|
+
// loadConfig() call so onboarding/platform preferences are visible to the
|
|
500
|
+
// seeder and persisted alongside schema defaults.
|
|
501
|
+
const defaultConfigMerge = mergeDefaultWorkspaceConfig();
|
|
502
|
+
|
|
503
|
+
// Seed managed inference profiles into the workspace config. Runs after
|
|
504
|
+
// workspace migrations and default-config merge, but before loadConfig() so
|
|
505
|
+
// fresh hatches have profiles on disk before the first config load. Any
|
|
506
|
+
// profile fields explicitly supplied by the default overlay stay
|
|
507
|
+
// authoritative for this startup.
|
|
455
508
|
try {
|
|
456
|
-
seedInferenceProfiles(
|
|
509
|
+
seedInferenceProfiles({
|
|
510
|
+
preserveProfileNames: defaultConfigMerge.providedLlmProfileNames,
|
|
511
|
+
preserveActiveProfile: defaultConfigMerge.providedLlmActiveProfile,
|
|
512
|
+
});
|
|
457
513
|
log.info("Inference profile seeding complete");
|
|
458
514
|
} catch (err) {
|
|
459
515
|
log.warn(
|
|
@@ -462,11 +518,6 @@ export async function runDaemon(): Promise<void> {
|
|
|
462
518
|
);
|
|
463
519
|
}
|
|
464
520
|
|
|
465
|
-
// Merge CLI-provided default config (from VELLUM_DEFAULT_WORKSPACE_CONFIG_PATH)
|
|
466
|
-
// into the workspace config file before the first loadConfig() call so
|
|
467
|
-
// onboarding preferences are persisted alongside schema defaults.
|
|
468
|
-
mergeDefaultWorkspaceConfig();
|
|
469
|
-
|
|
470
521
|
log.info("Daemon startup: loading config");
|
|
471
522
|
const config = loadConfig();
|
|
472
523
|
|
|
@@ -625,6 +676,7 @@ export async function runDaemon(): Promise<void> {
|
|
|
625
676
|
|
|
626
677
|
await server.start();
|
|
627
678
|
log.info("Daemon startup: DaemonServer started");
|
|
679
|
+
startDiskPressureGuardForLifecycle();
|
|
628
680
|
|
|
629
681
|
// Kick off the update bulletin background job AFTER `server.start()`
|
|
630
682
|
// resolves. The conversation store must be initialized before wake
|
|
@@ -684,64 +736,87 @@ export async function runDaemon(): Promise<void> {
|
|
|
684
736
|
}
|
|
685
737
|
|
|
686
738
|
if (qdrantStarted) {
|
|
687
|
-
|
|
688
|
-
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
692
|
-
|
|
693
|
-
|
|
694
|
-
|
|
695
|
-
|
|
696
|
-
|
|
697
|
-
collection
|
|
698
|
-
|
|
699
|
-
|
|
700
|
-
|
|
701
|
-
|
|
702
|
-
|
|
739
|
+
// Skip the v1 Qdrant collection lifecycle when memory v2 is active —
|
|
740
|
+
// the v1 collection has no writers (handleRemember returns early) or
|
|
741
|
+
// readers (graph search is bypassed) under v2, so ensuring/migrating
|
|
742
|
+
// it just maintains a dead-on-arrival collection. Existing on-disk
|
|
743
|
+
// collections are left intact so flipping v2 off restores v1 cleanly.
|
|
744
|
+
if (!config.memory.v2.enabled) {
|
|
745
|
+
try {
|
|
746
|
+
const embeddingSelection = await selectEmbeddingBackend(config);
|
|
747
|
+
// Sentinel only encodes the dense provider+model identity; sparse
|
|
748
|
+
// encoder changes never require collection recreation, so they
|
|
749
|
+
// intentionally do not contribute to the v1 collection identity.
|
|
750
|
+
const embeddingModel = embeddingSelection.backend
|
|
751
|
+
? `${embeddingSelection.backend.provider}:${embeddingSelection.backend.model}`
|
|
752
|
+
: undefined;
|
|
753
|
+
const qdrantClient = initQdrantClient({
|
|
754
|
+
url: qdrantUrl,
|
|
755
|
+
collection: config.memory.qdrant.collection,
|
|
756
|
+
vectorSize: config.memory.qdrant.vectorSize,
|
|
757
|
+
onDisk: config.memory.qdrant.onDisk,
|
|
758
|
+
quantization: config.memory.qdrant.quantization,
|
|
759
|
+
embeddingModel,
|
|
760
|
+
});
|
|
761
|
+
|
|
762
|
+
// Eagerly ensure the collection exists so we detect migrations
|
|
763
|
+
// (unnamed→named vectors, dimension/model changes) at startup.
|
|
764
|
+
// If a destructive migration occurred, enqueue a rebuild_index job
|
|
765
|
+
// to re-embed all memory items from the SQLite cache.
|
|
766
|
+
const { migrated } = await qdrantClient.ensureCollection();
|
|
767
|
+
if (migrated) {
|
|
768
|
+
enqueueMemoryJob("rebuild_index", {});
|
|
769
|
+
log.info(
|
|
770
|
+
"Qdrant collection was migrated — enqueued rebuild_index job",
|
|
771
|
+
);
|
|
772
|
+
}
|
|
703
773
|
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
if (migrated) {
|
|
710
|
-
enqueueMemoryJob("rebuild_index", {});
|
|
711
|
-
log.info(
|
|
712
|
-
"Qdrant collection was migrated — enqueued rebuild_index job",
|
|
774
|
+
log.info("Qdrant vector store initialized");
|
|
775
|
+
} catch (err) {
|
|
776
|
+
log.warn(
|
|
777
|
+
{ err },
|
|
778
|
+
"Qdrant client initialization failed — memory features will be degraded",
|
|
713
779
|
);
|
|
714
780
|
}
|
|
781
|
+
}
|
|
715
782
|
|
|
716
|
-
|
|
783
|
+
// Detect schema drift on the v2 concept-page collection (e.g.
|
|
784
|
+
// pre-#29823 collections lacking summary_dense / summary_sparse) and
|
|
785
|
+
// recreate + enqueue a reembed when needed. Awaited inline so the
|
|
786
|
+
// reembed enqueue happens before the memory worker drains its first
|
|
787
|
+
// batch; the call's own try/catch keeps any v2-side failure from
|
|
788
|
+
// blocking the v1 PKB reconcile or BM25 build below.
|
|
789
|
+
try {
|
|
790
|
+
await maybeRebuildMemoryV2Concepts(config);
|
|
717
791
|
} catch (err) {
|
|
718
792
|
log.warn(
|
|
719
793
|
{ err },
|
|
720
|
-
"
|
|
794
|
+
"Memory v2 collection schema check threw — continuing startup",
|
|
721
795
|
);
|
|
722
796
|
}
|
|
723
797
|
|
|
724
|
-
// Reconcile the PKB Qdrant index against the on-disk tree.
|
|
725
|
-
//
|
|
726
|
-
// `getQdrantClient()`
|
|
727
|
-
//
|
|
728
|
-
//
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
|
|
798
|
+
// Reconcile the PKB Qdrant index against the on-disk tree. Gated on
|
|
799
|
+
// !v2 because PKB is the v1 storage layer; under v2 the v1 collection
|
|
800
|
+
// is not initialized, so calling `getQdrantClient()` here would throw.
|
|
801
|
+
// Fire-and-forget so enqueued re-index jobs drain in the background
|
|
802
|
+
// and first-turn latency stays unaffected.
|
|
803
|
+
if (!config.memory.v2.enabled) {
|
|
804
|
+
void (async () => {
|
|
805
|
+
try {
|
|
806
|
+
const { reconcilePkbIndex } =
|
|
807
|
+
await import("../memory/pkb/pkb-reconcile.js");
|
|
808
|
+
const { PKB_WORKSPACE_SCOPE } =
|
|
809
|
+
await import("../memory/pkb/types.js");
|
|
810
|
+
const pkbRoot = join(getWorkspaceDir(), "pkb");
|
|
811
|
+
await reconcilePkbIndex(pkbRoot, PKB_WORKSPACE_SCOPE);
|
|
812
|
+
} catch (err) {
|
|
813
|
+
log.warn(
|
|
814
|
+
{ err },
|
|
815
|
+
"PKB index reconciliation failed — continuing startup",
|
|
816
|
+
);
|
|
817
|
+
}
|
|
818
|
+
})();
|
|
819
|
+
}
|
|
745
820
|
|
|
746
821
|
// Build the BM25 corpus stats (per-token document frequencies and
|
|
747
822
|
// average document length) used by the v2 sparse channel. Without
|
|
@@ -1198,22 +1273,6 @@ export async function runDaemon(): Promise<void> {
|
|
|
1198
1273
|
}
|
|
1199
1274
|
}
|
|
1200
1275
|
|
|
1201
|
-
// Prune trace events older than 7 days to keep the database lean.
|
|
1202
|
-
// Deferred so synchronous cleanup doesn't block the startup path.
|
|
1203
|
-
setTimeout(() => {
|
|
1204
|
-
try {
|
|
1205
|
-
const deletedTraceEvents = deleteOldTraceEvents(7);
|
|
1206
|
-
if (deletedTraceEvents > 0) {
|
|
1207
|
-
log.debug(
|
|
1208
|
-
{ deletedTraceEvents },
|
|
1209
|
-
`Pruned ${deletedTraceEvents} trace event(s) older than 7 days`,
|
|
1210
|
-
);
|
|
1211
|
-
}
|
|
1212
|
-
} catch (err) {
|
|
1213
|
-
log.warn({ err }, "Trace event cleanup failed");
|
|
1214
|
-
}
|
|
1215
|
-
}, 0);
|
|
1216
|
-
|
|
1217
1276
|
const workspaceHeartbeat = new WorkspaceHeartbeatService();
|
|
1218
1277
|
workspaceHeartbeat.start();
|
|
1219
1278
|
|
|
@@ -1236,14 +1295,17 @@ export async function runDaemon(): Promise<void> {
|
|
|
1236
1295
|
"Heartbeat service configured",
|
|
1237
1296
|
);
|
|
1238
1297
|
|
|
1239
|
-
|
|
1298
|
+
try {
|
|
1299
|
+
backfillGuardIfNeeded();
|
|
1300
|
+
} catch (err) {
|
|
1301
|
+
log.warn({ err }, "Proactive artifact backfill failed");
|
|
1302
|
+
}
|
|
1303
|
+
|
|
1304
|
+
// Filing yields to the memory v2 consolidation job when v2 is enabled —
|
|
1240
1305
|
// both serve the same role (periodic background memory processing) and
|
|
1241
1306
|
// running both is redundant. The consolidation job runs through the
|
|
1242
1307
|
// memory jobs worker (see `maybeEnqueueGraphMaintenanceJobs`).
|
|
1243
|
-
const memoryV2Enabled =
|
|
1244
|
-
"memory-v2-enabled",
|
|
1245
|
-
config,
|
|
1246
|
-
);
|
|
1308
|
+
const memoryV2Enabled = config.memory.v2.enabled;
|
|
1247
1309
|
let filing: FilingService | null = null;
|
|
1248
1310
|
if (!memoryV2Enabled) {
|
|
1249
1311
|
const filingConfig = config.filing;
|
|
@@ -1281,10 +1343,14 @@ export async function runDaemon(): Promise<void> {
|
|
|
1281
1343
|
getQdrantManager: () => bgRefs.qdrantManager,
|
|
1282
1344
|
mcpManager,
|
|
1283
1345
|
telemetryReporter,
|
|
1284
|
-
cleanupPidFile
|
|
1346
|
+
cleanupPidFile: () => {
|
|
1347
|
+
stopDiskPressureGuardForLifecycle();
|
|
1348
|
+
cleanupPidFile();
|
|
1349
|
+
},
|
|
1285
1350
|
});
|
|
1286
1351
|
} catch (err) {
|
|
1287
1352
|
log.error({ err }, "Daemon startup failed — cleaning up");
|
|
1353
|
+
stopDiskPressureGuardForLifecycle();
|
|
1288
1354
|
cleanupPidFileIfOwner(process.pid);
|
|
1289
1355
|
throw err;
|
|
1290
1356
|
}
|
|
@@ -72,7 +72,7 @@ import { getLogger } from "../util/logger.js";
|
|
|
72
72
|
* keeps the supervisor free of path assumptions and simplifies
|
|
73
73
|
* tests.
|
|
74
74
|
*/
|
|
75
|
-
|
|
75
|
+
interface MeetHostManifest {
|
|
76
76
|
/** SHA-256 of the shipped skill source tree. */
|
|
77
77
|
sourceHash: string;
|
|
78
78
|
}
|
|
@@ -84,7 +84,7 @@ export interface MeetHostManifest {
|
|
|
84
84
|
* protocol version) can be threaded through later without a
|
|
85
85
|
* signature break.
|
|
86
86
|
*/
|
|
87
|
-
|
|
87
|
+
interface MeetHostHandshakePayload {
|
|
88
88
|
sourceHash: string;
|
|
89
89
|
}
|
|
90
90
|
|
|
@@ -97,7 +97,7 @@ export interface MeetHostHandshakePayload {
|
|
|
97
97
|
* supervisor unaware of the rest of the IPC server's surface and avoids a
|
|
98
98
|
* circular import in tests that already stub `skill-server.js`.
|
|
99
99
|
*/
|
|
100
|
-
|
|
100
|
+
interface SkillRequestSender {
|
|
101
101
|
sendRequest(
|
|
102
102
|
connection: SkillIpcConnection,
|
|
103
103
|
method: string,
|
|
@@ -111,7 +111,7 @@ export interface SkillRequestSender {
|
|
|
111
111
|
* child. All are optional on construction — production callers
|
|
112
112
|
* rely on the defaults and tests override one or two at a time.
|
|
113
113
|
*/
|
|
114
|
-
|
|
114
|
+
interface MeetHostSupervisorDeps {
|
|
115
115
|
/** Absolute path to the shipped `meet-join` skill dir, containing `register.ts`. */
|
|
116
116
|
skillRuntimePath: string;
|
|
117
117
|
/** Absolute path to a standalone bun binary, or `"bun"` for PATH lookup. */
|
|
@@ -6,30 +6,81 @@
|
|
|
6
6
|
// startup work invoked from `lifecycle.ts`. Lives in its own file so the unit
|
|
7
7
|
// test for the gate does not have to mount the entire lifecycle import graph.
|
|
8
8
|
|
|
9
|
-
import { isAssistantFeatureFlagEnabled } from "../config/assistant-feature-flags.js";
|
|
10
9
|
import type { AssistantConfig } from "../config/schema.js";
|
|
11
10
|
import { getLogger } from "../util/logger.js";
|
|
11
|
+
import { getWorkspaceDir } from "../util/platform.js";
|
|
12
12
|
|
|
13
13
|
const log = getLogger("memory-v2-startup");
|
|
14
14
|
|
|
15
15
|
/**
|
|
16
|
-
* Fire-and-forget seed of the v2
|
|
17
|
-
*
|
|
18
|
-
*
|
|
19
|
-
*
|
|
20
|
-
*
|
|
21
|
-
*
|
|
22
|
-
* Never awaits — startup must not block on this (see `assistant/CLAUDE.md`
|
|
23
|
-
* daemon startup philosophy).
|
|
16
|
+
* Fire-and-forget seed of the v2 skill entries (now indexed alongside concept
|
|
17
|
+
* pages in `memory_v2_concept_pages` under the `skills/<id>` slug prefix), and
|
|
18
|
+
* a one-shot best-effort cleanup of the legacy `memory_v2_skills` Qdrant
|
|
19
|
+
* collection. Uses a dynamic import so v2 code does not load unless the gate
|
|
20
|
+
* passes. Never awaits — startup must not block on this (see
|
|
21
|
+
* `assistant/CLAUDE.md` daemon startup philosophy).
|
|
24
22
|
*/
|
|
25
23
|
export function maybeSeedMemoryV2Skills(config: AssistantConfig): void {
|
|
26
|
-
if (
|
|
27
|
-
!isAssistantFeatureFlagEnabled("memory-v2-enabled", config) ||
|
|
28
|
-
!config.memory.v2.enabled
|
|
29
|
-
) {
|
|
30
|
-
return;
|
|
31
|
-
}
|
|
24
|
+
if (!config.memory.v2.enabled) return;
|
|
32
25
|
void import("../memory/v2/skill-store.js")
|
|
33
26
|
.then(({ seedV2SkillEntries }) => seedV2SkillEntries())
|
|
34
27
|
.catch((err) => log.warn({ err }, "Failed to seed v2 skill entries"));
|
|
28
|
+
void import("../memory/v2/qdrant.js")
|
|
29
|
+
.then(({ dropLegacySkillsCollection }) => dropLegacySkillsCollection())
|
|
30
|
+
.catch((err) =>
|
|
31
|
+
log.warn(
|
|
32
|
+
{ err },
|
|
33
|
+
"Failed to drop legacy memory_v2_skills collection — non-fatal",
|
|
34
|
+
),
|
|
35
|
+
);
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* Reconcile the v2 concept-page Qdrant collection with the expected schema
|
|
40
|
+
* and enqueue `memory_v2_reembed` when the collection is missing data.
|
|
41
|
+
* Triggers reembed in two cases:
|
|
42
|
+
* - Drift: `ensureConceptPageCollection` returned `{ migrated: true }`
|
|
43
|
+
* after destructively recreating the collection (e.g. pre-#29823
|
|
44
|
+
* schemas lacking `summary_*` named vectors).
|
|
45
|
+
* - Empty-after-create: the collection has zero points but pages exist on
|
|
46
|
+
* disk — covers crash-mid-rebuild and external Qdrant wipes.
|
|
47
|
+
*
|
|
48
|
+
* Awaited inline by `lifecycle.ts` so the enqueue happens before the memory
|
|
49
|
+
* worker drains its first batch; the body is wrapped in try/catch so a v2
|
|
50
|
+
* failure never blocks startup.
|
|
51
|
+
*/
|
|
52
|
+
export async function maybeRebuildMemoryV2Concepts(
|
|
53
|
+
config: AssistantConfig,
|
|
54
|
+
): Promise<void> {
|
|
55
|
+
if (!config.memory.v2.enabled) return;
|
|
56
|
+
|
|
57
|
+
try {
|
|
58
|
+
const { ensureConceptPageCollection, countConceptPagePoints } =
|
|
59
|
+
await import("../memory/v2/qdrant.js");
|
|
60
|
+
const { hasConceptPages } = await import("../memory/v2/page-store.js");
|
|
61
|
+
const { enqueueMemoryJob } = await import("../memory/jobs-store.js");
|
|
62
|
+
|
|
63
|
+
const { migrated } = await ensureConceptPageCollection();
|
|
64
|
+
|
|
65
|
+
let shouldReembed = migrated;
|
|
66
|
+
if (!shouldReembed) {
|
|
67
|
+
const points = await countConceptPagePoints();
|
|
68
|
+
if (points === 0 && (await hasConceptPages(getWorkspaceDir()))) {
|
|
69
|
+
shouldReembed = true;
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
if (shouldReembed) {
|
|
74
|
+
const jobId = enqueueMemoryJob("memory_v2_reembed", {});
|
|
75
|
+
log.info(
|
|
76
|
+
{ jobId, collectionMigrated: migrated },
|
|
77
|
+
"Memory v2 collection rebuild required — enqueued reembed job",
|
|
78
|
+
);
|
|
79
|
+
}
|
|
80
|
+
} catch (err) {
|
|
81
|
+
log.warn(
|
|
82
|
+
{ err },
|
|
83
|
+
"Memory v2 collection schema check failed — continuing startup; v2 retrieval may be degraded",
|
|
84
|
+
);
|
|
85
|
+
}
|
|
35
86
|
}
|
|
@@ -20,6 +20,7 @@ export * from "./message-types/computer-use.js";
|
|
|
20
20
|
export * from "./message-types/contacts.js";
|
|
21
21
|
export * from "./message-types/conversations.js";
|
|
22
22
|
export * from "./message-types/diagnostics.js";
|
|
23
|
+
export * from "./message-types/disk-pressure.js";
|
|
23
24
|
export * from "./message-types/documents.js";
|
|
24
25
|
export * from "./message-types/guardian-actions.js";
|
|
25
26
|
export * from "./message-types/home.js";
|
|
@@ -71,6 +72,7 @@ import type {
|
|
|
71
72
|
_DiagnosticsClientMessages,
|
|
72
73
|
_DiagnosticsServerMessages,
|
|
73
74
|
} from "./message-types/diagnostics.js";
|
|
75
|
+
import type { _DiskPressureServerMessages } from "./message-types/disk-pressure.js";
|
|
74
76
|
import type {
|
|
75
77
|
_DocumentsClientMessages,
|
|
76
78
|
_DocumentsServerMessages,
|
|
@@ -203,6 +205,7 @@ export type ServerMessage =
|
|
|
203
205
|
| _NotificationsServerMessages
|
|
204
206
|
| _UpgradesServerMessages
|
|
205
207
|
| _AcpServerMessages
|
|
208
|
+
| _DiskPressureServerMessages
|
|
206
209
|
| SubagentEvent;
|
|
207
210
|
|
|
208
211
|
// === Contract schema ===
|
|
@@ -29,6 +29,8 @@ interface BaseTransportMetadata {
|
|
|
29
29
|
uxBrief?: string;
|
|
30
30
|
/** Chat type from the gateway (e.g. "private", "group", "supergroup", "channel"). */
|
|
31
31
|
chatType?: string;
|
|
32
|
+
/** IANA timezone reported by the active client for the current turn. */
|
|
33
|
+
clientTimezone?: string;
|
|
32
34
|
}
|
|
33
35
|
|
|
34
36
|
/**
|
|
@@ -522,6 +524,7 @@ export interface CompactionCircuitClosed {
|
|
|
522
524
|
export type ConversationErrorCode =
|
|
523
525
|
| "PROVIDER_NETWORK"
|
|
524
526
|
| "PROVIDER_RATE_LIMIT"
|
|
527
|
+
| "MANAGED_USAGE_LIMIT"
|
|
525
528
|
| "PROVIDER_OVERLOADED"
|
|
526
529
|
| "PROVIDER_API"
|
|
527
530
|
| "PROVIDER_BILLING"
|
|
@@ -532,6 +535,7 @@ export type ConversationErrorCode =
|
|
|
532
535
|
| "CONTEXT_TOO_LARGE"
|
|
533
536
|
| "CONVERSATION_ABORTED"
|
|
534
537
|
| "CONVERSATION_PROCESSING_FAILED"
|
|
538
|
+
| "DISK_SPACE_CRITICAL"
|
|
535
539
|
| "REGENERATE_FAILED"
|
|
536
540
|
| "UNKNOWN";
|
|
537
541
|
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { DiskPressureStatus } from "../disk-pressure-guard.js";
|
|
2
|
+
|
|
3
|
+
/** Server push when the disk pressure status snapshot changes. */
|
|
4
|
+
export interface DiskPressureStatusChanged {
|
|
5
|
+
type: "disk_pressure_status_changed";
|
|
6
|
+
status: DiskPressureStatus;
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
export type _DiskPressureServerMessages = DiskPressureStatusChanged;
|
|
@@ -147,8 +147,26 @@ export interface ToolResult {
|
|
|
147
147
|
matchedTrustRuleId?: string;
|
|
148
148
|
/** Whether the daemon is running in a containerized (Docker) environment. */
|
|
149
149
|
isContainerized?: boolean;
|
|
150
|
-
/**
|
|
150
|
+
/**
|
|
151
|
+
* Display-only ladder of scope option labels for the rule editor
|
|
152
|
+
* (narrowest to broadest). The `pattern` here is regex-style and is
|
|
153
|
+
* NOT a valid trust rule pattern. Clients must use
|
|
154
|
+
* `riskAllowlistOptions` for the pattern that gets saved.
|
|
155
|
+
*/
|
|
151
156
|
riskScopeOptions?: Array<{ pattern: string; label: string }>;
|
|
157
|
+
/**
|
|
158
|
+
* Allowlist options for the rule editor save path (narrowest to
|
|
159
|
+
* broadest). Each `pattern` is a Minimatch-glob compatible string —
|
|
160
|
+
* what the gateway actually matches against. Mirrors the
|
|
161
|
+
* `allowlistOptions` field on `ConfirmationRequest`. May be absent
|
|
162
|
+
* for tools whose classifier does not produce an allowlist (e.g.
|
|
163
|
+
* web-risk classifier, MCP tools without classifier coverage).
|
|
164
|
+
*/
|
|
165
|
+
riskAllowlistOptions?: Array<{
|
|
166
|
+
label: string;
|
|
167
|
+
description: string;
|
|
168
|
+
pattern: string;
|
|
169
|
+
}>;
|
|
152
170
|
/** Directory scope ladder for the rule editor modal (narrowest to broadest). */
|
|
153
171
|
riskDirectoryScopeOptions?: Array<{ scope: string; label: string }>;
|
|
154
172
|
/** How the approval decision was reached: prompted, auto, blocked, or unknown (legacy). */
|
|
@@ -236,10 +254,13 @@ export interface MessageComplete {
|
|
|
236
254
|
export interface ErrorMessage {
|
|
237
255
|
type: "error";
|
|
238
256
|
conversationId?: string;
|
|
257
|
+
requestId?: string;
|
|
239
258
|
code?: string;
|
|
240
259
|
message: string;
|
|
241
260
|
/** Categorizes the error so the client can offer contextual actions (e.g. "Send Anyway" for secret_blocked). */
|
|
242
261
|
category?: string;
|
|
262
|
+
/** Machine-readable conversation error category for clients that need source-aware recovery UI. */
|
|
263
|
+
errorCategory?: string;
|
|
243
264
|
}
|
|
244
265
|
|
|
245
266
|
export interface MessageQueued {
|