@vellumai/assistant 0.8.5 → 0.8.6
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 +33 -1
- package/ARCHITECTURE.md +1 -1
- package/bunfig.toml +6 -1
- package/docs/credential-execution-service.md +6 -6
- package/docs/plugins.md +4 -3
- package/node_modules/@vellumai/skill-host-contracts/src/client.ts +12 -13
- package/node_modules/@vellumai/skill-host-contracts/src/skill-host.ts +4 -1
- package/node_modules/@vellumai/skill-host-contracts/src/tool-types.ts +16 -14
- package/openapi.yaml +1900 -166
- package/package.json +1 -1
- package/src/__tests__/actor-token-service.test.ts +3 -2
- package/src/__tests__/agent-loop-exit-reason.test.ts +102 -9
- package/src/__tests__/agent-loop-override-profile.test.ts +2 -1
- package/src/__tests__/agent-wake-disk-pressure-callsite.test.ts +1 -0
- package/src/__tests__/agent-wake-override-profile.test.ts +1 -0
- package/src/__tests__/always-loaded-tools-guard.test.ts +2 -2
- package/src/__tests__/annotate-risk-options.test.ts +1 -0
- package/src/__tests__/approval-cascade.test.ts +1 -0
- package/src/__tests__/approval-routes-http.test.ts +9 -13
- package/src/__tests__/assert-not-live-db.ts +79 -0
- package/src/__tests__/assistant-feature-flags-integration.test.ts +9 -25
- package/src/__tests__/audit-log-rotation.test.ts +2 -2
- package/src/__tests__/auto-analysis-end-to-end.test.ts +6 -6
- package/src/__tests__/background-workers-disk-pressure.test.ts +5 -8
- package/src/__tests__/browser-skill-endstate.test.ts +3 -3
- package/src/__tests__/btw-routes.test.ts +3 -2
- package/src/__tests__/call-controller.test.ts +3 -2
- package/src/__tests__/channel-approval-routes.test.ts +3 -2
- package/src/__tests__/channel-guardian.test.ts +3 -2
- package/src/__tests__/channel-readiness-slack-remote.test.ts +175 -0
- package/src/__tests__/channel-reply-delivery.test.ts +35 -0
- package/src/__tests__/channel-retry-sweep.test.ts +320 -3
- package/src/__tests__/checker.test.ts +12 -12
- package/src/__tests__/compaction-events.test.ts +1 -0
- package/src/__tests__/compaction-trail-store.test.ts +264 -0
- package/src/__tests__/compactor-call-site-logging.test.ts +1 -0
- package/src/__tests__/compactor-preserved-tail-count.test.ts +1 -0
- package/src/__tests__/computer-use-skill-manifest-regression.test.ts +7 -5
- package/src/__tests__/computer-use-tools.test.ts +12 -14
- package/src/__tests__/config-loader-backfill.test.ts +13 -28
- package/src/__tests__/config-loader-corrupt.test.ts +5 -5
- package/src/__tests__/config-loader-platform-defaults.test.ts +93 -26
- package/src/__tests__/config-loader-quarantine-bulletin.test.ts +3 -3
- package/src/__tests__/config-managed-gemini-defaults.test.ts +3 -4
- package/src/__tests__/config-schema.test.ts +10 -10
- package/src/__tests__/connection-model-compat.test.ts +83 -0
- package/src/__tests__/contacts-tools.test.ts +3 -2
- package/src/__tests__/context-token-estimator.test.ts +22 -0
- package/src/__tests__/conversation-abort-tool-results.test.ts +5 -0
- package/src/__tests__/conversation-agent-loop-disk-pressure.test.ts +1 -0
- package/src/__tests__/conversation-agent-loop-handlers-max-tokens.test.ts +55 -0
- package/src/__tests__/conversation-agent-loop-inference-profile.test.ts +1 -0
- package/src/__tests__/conversation-agent-loop-overflow.test.ts +34 -0
- package/src/__tests__/conversation-agent-loop.test.ts +488 -2
- package/src/__tests__/conversation-analysis-routes.test.ts +1 -0
- package/src/__tests__/conversation-app-control-instantiation.test.ts +29 -19
- package/src/__tests__/conversation-app-control-lifecycle.test.ts +1 -0
- package/src/__tests__/conversation-attention-store.test.ts +101 -0
- package/src/__tests__/conversation-attention-telegram.test.ts +3 -2
- package/src/__tests__/conversation-confirmation-signals.test.ts +1 -0
- package/src/__tests__/conversation-error.test.ts +30 -0
- package/src/__tests__/conversation-fork-crud.test.ts +69 -8
- package/src/__tests__/conversation-fork-route.test.ts +3 -2
- package/src/__tests__/conversation-history-web-search.test.ts +1 -0
- package/src/__tests__/conversation-inference-profile-list.test.ts +3 -2
- package/src/__tests__/conversation-inference-profile-route.test.ts +3 -2
- package/src/__tests__/conversation-lifecycle.test.ts +1 -0
- package/src/__tests__/conversation-list-source.test.ts +3 -2
- package/src/__tests__/conversation-load-history-repair.test.ts +2 -1
- package/src/__tests__/conversation-load-history-stripped.test.ts +1 -0
- package/src/__tests__/conversation-pairing.test.ts +53 -0
- package/src/__tests__/conversation-process-app-control-preactivation.test.ts +26 -7
- package/src/__tests__/conversation-process-callsite.test.ts +1 -0
- package/src/__tests__/conversation-provider-retry-repair.test.ts +5 -0
- package/src/__tests__/conversation-queue.test.ts +333 -291
- package/src/__tests__/conversation-routes-disk-view.test.ts +3 -18
- package/src/__tests__/conversation-routes-guardian-reply.test.ts +33 -8
- package/src/__tests__/conversation-routes-slash-commands.test.ts +33 -2
- package/src/__tests__/conversation-runtime-assembly.test.ts +78 -0
- package/src/__tests__/conversation-skill-tools.test.ts +38 -142
- package/src/__tests__/conversation-slash-queue.test.ts +84 -32
- package/src/__tests__/conversation-slash-unknown.test.ts +5 -0
- package/src/__tests__/conversation-speed-override.test.ts +1 -0
- package/src/__tests__/conversation-surfaces-action-delivery.test.ts +46 -0
- package/src/__tests__/conversation-surfaces-data-persist.test.ts +1 -0
- package/src/__tests__/conversation-surfaces-standalone-payloads.test.ts +6 -3
- package/src/__tests__/conversation-surfaces-standalone.test.ts +6 -3
- package/src/__tests__/conversation-surfaces-state-update.test.ts +3 -3
- package/src/__tests__/conversation-surfaces-table-action.test.ts +7 -17
- package/src/__tests__/conversation-sync-tags.test.ts +128 -12
- package/src/__tests__/conversation-title-service.test.ts +1 -0
- package/src/__tests__/conversation-tool-setup-app-refresh.test.ts +30 -0
- package/src/__tests__/conversation-usage.test.ts +1 -0
- package/src/__tests__/conversation-workspace-cache-state.test.ts +1 -0
- package/src/__tests__/conversation-workspace-injection.test.ts +5 -0
- package/src/__tests__/conversation-workspace-tool-tracking.test.ts +5 -0
- package/src/__tests__/credential-broker-browser-fill.test.ts +3 -3
- package/src/__tests__/credential-broker-server-use.test.ts +5 -5
- package/src/__tests__/credential-execution-client.test.ts +72 -1
- package/src/__tests__/credential-execution-feature-gates.test.ts +10 -12
- package/src/__tests__/credential-health-service.test.ts +252 -3
- package/src/__tests__/credential-security-invariants.test.ts +5 -5
- package/src/__tests__/credential-vault-unit.test.ts +19 -19
- package/src/__tests__/credential-vault.test.ts +5 -5
- package/src/__tests__/cross-provider-web-search.test.ts +56 -2
- package/src/__tests__/db-connection-isolation.test.ts +7 -6
- package/src/__tests__/db-conversation-fork-lineage-migration.test.ts +8 -10
- package/src/__tests__/db-conversation-inference-profile-migration.test.ts +7 -10
- package/src/__tests__/db-llm-request-log-provider-migration.test.ts +9 -15
- package/src/__tests__/db-test-helpers.ts +58 -0
- package/src/__tests__/disk-pressure-guard.test.ts +58 -41
- package/src/__tests__/disk-pressure-lifecycle.test.ts +13 -10
- package/src/__tests__/disk-pressure-routes.test.ts +0 -33
- package/src/__tests__/disk-pressure-tools.test.ts +0 -4
- package/src/__tests__/dm-persistence.test.ts +26 -40
- package/src/__tests__/document-create-dedupe.test.ts +189 -0
- package/src/__tests__/document-find-replace.test.ts +3 -2
- package/src/__tests__/document-tool-security.test.ts +81 -2
- package/src/__tests__/dynamic-skill-workflow-prompt.test.ts +5 -4
- package/src/__tests__/encrypted-store-test-helpers.ts +56 -0
- package/src/__tests__/encrypted-store.test.ts +11 -9
- package/src/__tests__/feature-flag-test-helpers.ts +53 -0
- package/src/__tests__/filing-service.test.ts +1 -0
- package/src/__tests__/first-greeting.test.ts +62 -12
- package/src/__tests__/gateway-flag-listener.test.ts +0 -1
- package/src/__tests__/gemini-provider.test.ts +26 -0
- package/src/__tests__/guardian-action-sweep.test.ts +3 -2
- package/src/__tests__/guardian-outbound-http.test.ts +3 -2
- package/src/__tests__/handlers-skills-memory-v2-reseed.test.ts +48 -3
- package/src/__tests__/handlers-user-message-approval-consumption.test.ts +1 -0
- package/src/__tests__/heartbeat-disk-pressure.test.ts +1 -0
- package/src/__tests__/heartbeat-service.test.ts +1 -0
- package/src/__tests__/helpers/mock-logger.ts +26 -0
- package/src/__tests__/host-bash-routes.test.ts +1 -0
- package/src/__tests__/host-cu-routes-targeted.test.ts +1 -0
- package/src/__tests__/host-file-routes-targeted.test.ts +1 -0
- package/src/__tests__/host-shell-tool.test.ts +5 -4
- package/src/__tests__/host-transfer-routes-targeted.test.ts +1 -0
- package/src/__tests__/http-conversation-lineage.test.ts +3 -2
- package/src/__tests__/http-user-message-parity.test.ts +29 -7
- package/src/__tests__/identity-intro-cache.test.ts +133 -22
- package/src/__tests__/inbound-slack-persistence.test.ts +44 -72
- package/src/__tests__/inference-profile-reaper.test.ts +3 -2
- package/src/__tests__/inference-profile-session-ipc.test.ts +3 -2
- package/src/__tests__/injector-disk-pressure.test.ts +3 -17
- package/src/__tests__/inline-skill-load-permissions.test.ts +4 -4
- package/src/__tests__/list-messages-hidden-metadata.test.ts +80 -0
- package/src/__tests__/llm-context-normalization.test.ts +42 -0
- package/src/__tests__/llm-resolver.test.ts +331 -0
- package/src/__tests__/llm-schema.test.ts +1 -1
- package/src/__tests__/manual-token-reconciliation.test.ts +76 -1
- package/src/__tests__/mcp-abort-signal.test.ts +14 -0
- package/src/__tests__/mcp-client-auth.test.ts +14 -0
- package/src/__tests__/messaging-send-tool.test.ts +1 -0
- package/src/__tests__/migration-import-from-url.test.ts +3 -3
- package/src/__tests__/mock-gateway-ipc.ts +18 -2
- package/src/__tests__/model-intents.test.ts +3 -3
- package/src/__tests__/native-web-search.test.ts +30 -2
- package/src/__tests__/notification-deep-link.test.ts +62 -0
- package/src/__tests__/oauth-commands-routes.test.ts +37 -0
- package/src/__tests__/oauth-provider-visibility.test.ts +8 -8
- package/src/__tests__/oauth-store.test.ts +3 -2
- package/src/__tests__/onboarding-template-contract.test.ts +3 -2
- package/src/__tests__/openai-provider.test.ts +8 -9
- package/src/__tests__/openai-responses-provider.test.ts +70 -10
- package/src/__tests__/openrouter-provider-only.test.ts +27 -5
- package/src/__tests__/outbound-slack-persistence.test.ts +46 -1
- package/src/__tests__/persistence-pipeline.test.ts +139 -1
- package/src/__tests__/persistence-secret-redaction.test.ts +83 -12
- package/src/__tests__/plugin-bootstrap.test.ts +9 -11
- package/src/__tests__/plugin-tool-contribution.test.ts +41 -38
- package/src/__tests__/process-message-background-slack.test.ts +21 -16
- package/src/__tests__/process-message-display-content.test.ts +19 -22
- package/src/__tests__/provider-catalog-visibility.test.ts +9 -9
- package/src/__tests__/provider-platform-proxy-integration.test.ts +216 -4
- package/src/__tests__/provider-registry-ollama.test.ts +45 -22
- package/src/__tests__/recording-handler.test.ts +1 -0
- package/src/__tests__/regenerate-fire-and-forget-trace.test.ts +1 -0
- package/src/__tests__/registry.test.ts +82 -76
- package/src/__tests__/relay-server.test.ts +10 -10
- package/src/__tests__/runtime-attachment-metadata.test.ts +3 -2
- package/src/__tests__/schedule-store.test.ts +16 -1
- package/src/__tests__/scheduler-reuse-conversation.test.ts +48 -3
- package/src/__tests__/secret-ingress-http.test.ts +5 -1
- package/src/__tests__/secure-keys.test.ts +3 -3
- package/src/__tests__/send-endpoint-busy.test.ts +81 -42
- package/src/__tests__/server-history-render.test.ts +4 -1
- package/src/__tests__/skill-feature-flags-integration.test.ts +8 -10
- package/src/__tests__/skill-feature-flags.test.ts +14 -16
- package/src/__tests__/skill-load-feature-flag.test.ts +5 -5
- package/src/__tests__/skill-projection-feature-flag.test.ts +44 -30
- package/src/__tests__/skill-projection.benchmark.test.ts +5 -7
- package/src/__tests__/skill-tool-factory.test.ts +96 -95
- package/src/__tests__/slack-channel-config.test.ts +3 -3
- package/src/__tests__/subagent-call-site-routing.test.ts +11 -3
- package/src/__tests__/subagent-disposal.test.ts +27 -8
- package/src/__tests__/subagent-fork-notifications.test.ts +24 -9
- package/src/__tests__/subagent-fork-spawn.test.ts +13 -4
- package/src/__tests__/subagent-manager-notify.test.ts +20 -8
- package/src/__tests__/subagent-notify-parent.test.ts +5 -4
- package/src/__tests__/subagent-spawn-tool-fork.test.ts +58 -0
- package/src/__tests__/subagent-tools.test.ts +2 -1
- package/src/__tests__/suggestion-routes.test.ts +1 -0
- package/src/__tests__/system-prompt.test.ts +38 -0
- package/src/__tests__/test-preload-verifier.ts +68 -0
- package/src/__tests__/test-preload.ts +32 -39
- package/src/__tests__/tool-executor-lifecycle-events.test.ts +20 -7
- package/src/__tests__/tool-executor.test.ts +55 -10
- package/src/__tests__/tool-preview-lifecycle.test.ts +1 -0
- package/src/__tests__/tool-result-metadata-plumbing.test.ts +1 -0
- package/src/__tests__/twilio-routes.test.ts +3 -2
- package/src/__tests__/validate-input.test.ts +381 -0
- package/src/__tests__/verification-control-plane-policy.test.ts +1 -0
- package/src/__tests__/voice-scoped-grant-consumer.test.ts +2 -1
- package/src/__tests__/voice-session-bridge.test.ts +37 -28
- package/src/__tests__/workspace-migration-090-memory-router-cost-optimized-profile.test.ts +326 -0
- package/src/__tests__/workspace-migration-091-retighten-migration-onboarding-thread.test.ts +166 -0
- package/src/acp/session-manager.ts +5 -6
- package/src/agent/loop.ts +80 -0
- package/src/api/README.md +124 -2
- package/src/api/constants/call-sites.ts +27 -0
- package/src/api/events/assistant-outbound-attachment.ts +51 -0
- package/src/api/events/assistant-text-delta.ts +32 -0
- package/src/api/events/assistant-turn-start.ts +33 -0
- package/src/api/events/document-comment-created.ts +48 -0
- package/src/api/events/document-comment-deleted.ts +24 -0
- package/src/api/events/document-comment-reopened.ts +25 -0
- package/src/api/events/document-comment-resolved.ts +27 -0
- package/src/api/events/generation-cancelled.ts +24 -0
- package/src/api/events/generation-handoff.ts +41 -0
- package/src/api/events/message-complete.ts +42 -0
- package/src/api/events/open-url.ts +30 -0
- package/src/{events → api/events}/relationship-state-updated.ts +3 -3
- package/src/api/events/tool-use-start.ts +32 -0
- package/src/api/index.ts +128 -3
- package/src/api/responses/llm-context-response.ts +39 -0
- package/src/api/responses/llm-request-log-entry.ts +93 -0
- package/src/api/responses/memory-recall-log.ts +65 -0
- package/src/api/responses/memory-v2-activation-log.ts +78 -0
- package/src/background-wake/background-wake-routes.test.ts +687 -52
- package/src/background-wake/platform-client.test.ts +308 -0
- package/src/background-wake/platform-client.ts +167 -0
- package/src/background-wake/publisher.ts +91 -0
- package/src/background-wake/runtime-registry.ts +2 -2
- package/src/background-wake/wake-intent-hooks.test.ts +282 -0
- package/src/calls/guardian-dispatch.ts +1 -0
- package/src/calls/voice-session-bridge.ts +4 -4
- package/src/cli/commands/__tests__/conversations-slack.test.ts +16 -0
- package/src/cli/commands/__tests__/notifications.test.ts +184 -40
- package/src/cli/commands/channels/__tests__/channels.test.ts +143 -0
- package/src/cli/commands/channels/index.ts +229 -0
- package/src/cli/commands/memory-v3-render.ts +147 -0
- package/src/cli/commands/memory-v3.ts +255 -4
- package/src/cli/commands/notifications.ts +365 -55
- package/src/cli/lib/open-browser.ts +7 -2
- package/src/cli/program.ts +2 -0
- package/src/config/assistant-feature-flags.ts +23 -42
- package/src/config/bundled-skills/document-editor/SKILL.md +5 -1
- package/src/config/bundled-skills/schedule/SKILL.md +1 -1
- package/src/config/bundled-skills/schedule/TOOLS.json +2 -2
- package/src/config/bundled-skills/settings/tools/open-system-settings.ts +1 -0
- package/src/config/call-site-defaults.ts +1 -1
- package/src/config/feature-flag-cache.ts +86 -0
- package/src/config/feature-flag-registry.json +17 -17
- package/src/config/llm-context-resolution.ts +10 -1
- package/src/config/llm-resolver.ts +121 -15
- package/src/config/loader.ts +4 -5
- package/src/config/schemas/__tests__/memory-v2.test.ts +15 -0
- package/src/config/schemas/heartbeat.ts +1 -1
- package/src/config/schemas/llm.ts +90 -1
- package/src/config/schemas/memory-v2.ts +26 -0
- package/src/config/schemas/services.ts +6 -2
- package/src/config/seed-inference-profiles.ts +36 -16
- package/src/context/token-estimator.ts +10 -5
- package/src/credential-execution/executable-discovery.ts +40 -0
- package/src/credential-execution/process-manager.ts +6 -2
- package/src/credential-health/credential-health-service.ts +125 -40
- package/src/daemon/__tests__/conversation-lifecycle-auto-analyze.test.ts +3 -6
- package/src/daemon/__tests__/conversation-surfaces-launch.test.ts +13 -15
- package/src/daemon/__tests__/conversation-tool-setup-exclude.test.ts +1 -2
- package/src/daemon/__tests__/daemon-skill-host.test.ts +2 -0
- package/src/daemon/__tests__/meet-manifest-loader.test.ts +25 -12
- package/src/daemon/__tests__/native-web-search-metadata.test.ts +1 -0
- package/src/daemon/__tests__/switch-inference-profile-tool.test.ts +107 -0
- package/src/daemon/__tests__/web-search-status-text.test.ts +1 -0
- package/src/daemon/conversation-agent-loop-handlers.ts +389 -68
- package/src/daemon/conversation-agent-loop.ts +132 -28
- package/src/daemon/conversation-error.ts +33 -5
- package/src/daemon/conversation-messaging.ts +84 -43
- package/src/daemon/conversation-process.ts +74 -37
- package/src/daemon/conversation-runtime-assembly.ts +29 -9
- package/src/daemon/conversation-skill-tools.ts +14 -30
- package/src/daemon/conversation-surfaces.ts +69 -34
- package/src/daemon/conversation-tool-setup.ts +33 -48
- package/src/daemon/conversation.ts +26 -46
- package/src/daemon/daemon-control.ts +1 -1
- package/src/daemon/daemon-skill-host.ts +9 -2
- package/src/daemon/disk-pressure-guard.ts +27 -29
- package/src/daemon/first-greeting.ts +31 -13
- package/src/daemon/handlers/shared.ts +6 -1
- package/src/daemon/lifecycle.ts +12 -12
- package/src/daemon/mcp-reload-service.ts +1 -1
- package/src/daemon/meet-manifest-loader.ts +10 -17
- package/src/daemon/message-types/conversations.ts +20 -22
- package/src/daemon/message-types/document-comments.ts +8 -44
- package/src/daemon/message-types/home.ts +2 -2
- package/src/daemon/message-types/integrations.ts +2 -7
- package/src/daemon/message-types/messages.ts +23 -38
- package/src/daemon/message-types/subagents.ts +6 -0
- package/src/daemon/process-message.ts +9 -9
- package/src/daemon/providers-setup.ts +1 -1
- package/src/daemon/server.ts +16 -0
- package/src/daemon/switch-inference-profile-tool.ts +13 -3
- package/src/daemon/tool-setup-types.ts +0 -6
- package/src/daemon/wake-target-adapter.ts +10 -0
- package/src/documents/document-store.ts +38 -0
- package/src/export/__tests__/transcript-formatter.test.ts +1 -0
- package/src/heartbeat/__tests__/heartbeat-service.test.ts +29 -0
- package/src/heartbeat/heartbeat-service.ts +63 -0
- package/src/home/__tests__/feed-writer.test.ts +161 -0
- package/src/home/__tests__/post-connect-feed.test.ts +1 -0
- package/src/home/__tests__/suggested-prompts.test.ts +55 -59
- package/src/home/feed-writer.ts +146 -7
- package/src/home/suggested-prompts.ts +27 -145
- package/src/ipc/__tests__/cli-ipc.test.ts +1 -0
- package/src/ipc/gateway-client.test.ts +4 -1
- package/src/ipc/skill-routes/__tests__/memory.test.ts +1 -0
- package/src/ipc/skill-routes/__tests__/registries.test.ts +36 -7
- package/src/ipc/skill-routes/memory.ts +4 -3
- package/src/ipc/skill-routes/registries.ts +28 -29
- package/src/memory/__tests__/jobs-store-enqueue-gate.test.ts +1 -0
- package/src/memory/__tests__/jobs-worker-v2-schedule.test.ts +26 -5
- package/src/memory/__tests__/memory-retrospective-enqueue.test.ts +1 -0
- package/src/memory/__tests__/memory-retrospective-job.test.ts +1 -0
- package/src/memory/__tests__/memory-retrospective-startup-cleanup.test.ts +1 -0
- package/src/memory/__tests__/memory-v2-activation-log-store.test.ts +31 -0
- package/src/memory/conversation-attention-store.ts +17 -3
- package/src/memory/conversation-crud.ts +352 -112
- package/src/memory/db-connection.ts +29 -19
- package/src/memory/db-init.ts +4 -0
- package/src/memory/db-singleton.ts +77 -0
- package/src/memory/delivery-channels.ts +82 -0
- package/src/memory/graph/__tests__/conversation-graph-memory-v2-routing.test.ts +2 -4
- package/src/memory/graph/retriever.test.ts +3 -3
- package/src/memory/job-handlers/embedding.test.ts +3 -2
- package/src/memory/jobs/__tests__/embed-concept-page.test.ts +5 -2
- package/src/memory/jobs-worker.ts +12 -1
- package/src/memory/llm-request-log-source-clickhouse.ts +80 -0
- package/src/memory/llm-request-log-source-local.ts +24 -0
- package/src/memory/llm-request-log-source.ts +31 -0
- package/src/memory/llm-request-log-store.ts +188 -3
- package/src/memory/memory-v2-activation-log-store.ts +95 -1
- package/src/memory/migrations/265-drop-provider-connection-status.ts +26 -0
- package/src/memory/migrations/266-messages-client-message-id.ts +43 -0
- package/src/memory/migrations/index.ts +2 -0
- package/src/memory/schema/conversations.ts +9 -1
- package/src/memory/schema/inference.ts +0 -1
- package/src/memory/v2/__tests__/backfill-jobs.test.ts +5 -2
- package/src/memory/v2/__tests__/harness-metrics.test.ts +9 -0
- package/src/memory/v2/__tests__/harness-replay-input.test.ts +9 -4
- package/src/memory/v2/__tests__/harness-runner.test.ts +26 -0
- package/src/memory/v2/__tests__/sweep-job.test.ts +6 -3
- package/src/memory/v2/harness/metrics.ts +5 -1
- package/src/memory/v2/harness/replay-input.ts +19 -3
- package/src/memory/v2/harness/runner.ts +6 -0
- package/src/memory/v2/harness/trace.ts +6 -0
- package/src/memory/v3/__tests__/consolidation-job.test.ts +2 -4
- package/src/memory/v3/__tests__/coretrieval-seed.test.ts +270 -0
- package/src/memory/v3/__tests__/edges.test.ts +144 -1
- package/src/memory/v3/__tests__/filter.test.ts +48 -0
- package/src/memory/v3/__tests__/gate.test.ts +96 -33
- package/src/memory/v3/__tests__/index-composition.test.ts +58 -0
- package/src/memory/v3/__tests__/loop.test.ts +250 -5
- package/src/memory/v3/__tests__/scouts.test.ts +49 -0
- package/src/memory/v3/__tests__/shadow-diff.test.ts +225 -0
- package/src/memory/v3/__tests__/shadow-middleware.test.ts +88 -2
- package/src/memory/v3/__tests__/traversal.test.ts +39 -0
- package/src/memory/v3/__tests__/tree-walk.test.ts +77 -0
- package/src/memory/v3/__tests__/validate.test.ts +32 -0
- package/src/memory/v3/coretrieval-seed.ts +240 -0
- package/src/memory/v3/edges.ts +58 -21
- package/src/memory/v3/filter.ts +27 -22
- package/src/memory/v3/gate.ts +51 -36
- package/src/memory/v3/index-composition.ts +18 -5
- package/src/memory/v3/loop.ts +65 -17
- package/src/memory/v3/scouts.ts +15 -4
- package/src/memory/v3/shadow-diff.ts +287 -0
- package/src/memory/v3/shadow-middleware.ts +44 -2
- package/src/memory/v3/traversal.ts +6 -1
- package/src/memory/v3/tree-walk.ts +6 -1
- package/src/memory/v3/validate.ts +56 -33
- package/src/notifications/__tests__/emit-signal-home-feed.test.ts +1 -0
- package/src/notifications/__tests__/home-feed-side-effect.test.ts +1 -0
- package/src/notifications/adapters/slack.ts +45 -11
- package/src/notifications/broadcaster.ts +114 -63
- package/src/notifications/conversation-pairing.ts +23 -3
- package/src/notifications/decisions-store.ts +32 -1
- package/src/notifications/deliveries-store.ts +45 -0
- package/src/notifications/edit-notification.ts +201 -0
- package/src/notifications/emit-signal.ts +11 -1
- package/src/notifications/signal.ts +10 -0
- package/src/notifications/types.ts +37 -0
- package/src/oauth/byo-connection.test.ts +67 -3
- package/src/oauth/byo-connection.ts +32 -5
- package/src/oauth/connect-orchestrator.ts +9 -0
- package/src/oauth/connection-resolver.test.ts +76 -0
- package/src/oauth/connection-resolver.ts +49 -10
- package/src/oauth/manual-token-connection.ts +51 -3
- package/src/oauth/seed-providers.ts +3 -0
- package/src/permissions/approval-policy.test.ts +19 -5
- package/src/permissions/approval-policy.ts +14 -3
- package/src/permissions/checker.ts +21 -8
- package/src/platform/client.test.ts +24 -1
- package/src/platform/client.ts +8 -0
- package/src/platform/feature-gate.ts +15 -0
- package/src/plugins/defaults/injectors.ts +2 -8
- package/src/plugins/defaults/persistence.ts +25 -6
- package/src/plugins/types.ts +57 -13
- package/src/proactive-artifact/job.test.ts +1 -0
- package/src/prompts/__tests__/system-prompt.test.ts +4 -4
- package/src/prompts/system-prompt.ts +38 -40
- package/src/prompts/template-detection.ts +10 -4
- package/src/prompts/templates/BOOTSTRAP.md +7 -11
- package/src/prompts/templates/IDENTITY.md +0 -2
- package/src/providers/__tests__/connection-model-compat.test.ts +3 -4
- package/src/providers/__tests__/registry-native-web-search.test.ts +122 -0
- package/src/providers/call-site-routing.ts +33 -9
- package/src/providers/connection-model-compat.ts +23 -0
- package/src/providers/connection-resolution.ts +39 -20
- package/src/providers/fireworks/client.ts +1 -0
- package/src/providers/gemini/client.ts +24 -3
- package/src/providers/inference/__tests__/adapter-factory-openai-compatible.test.ts +0 -2
- package/src/providers/inference/__tests__/base-url-security.test.ts +2 -3
- package/src/providers/inference/__tests__/{connections-status-label.test.ts → connections-label.test.ts} +12 -111
- package/src/providers/inference/auth.ts +0 -8
- package/src/providers/inference/connections.ts +3 -66
- package/src/providers/inference/resolve-auth.ts +2 -3
- package/src/providers/model-catalog.ts +35 -1
- package/src/providers/model-intents.ts +3 -3
- package/src/providers/openai/__tests__/api-error-detail.test.ts +120 -0
- package/src/providers/openai/__tests__/chat-completions-provider-reasoning.test.ts +157 -5
- package/src/providers/openai/chat-completions-provider.ts +110 -12
- package/src/providers/openai/codex-models.ts +2 -0
- package/src/providers/openai/responses-provider.ts +53 -53
- package/src/providers/openrouter/client.ts +13 -8
- package/src/providers/provider-send-message.ts +18 -9
- package/src/providers/registry.ts +48 -8
- package/src/providers/retry.ts +16 -4
- package/src/providers/search-provider-catalog.ts +17 -9
- package/src/providers/types.ts +9 -0
- package/src/runtime/__tests__/agent-wake.test.ts +1 -0
- package/src/runtime/__tests__/background-job-runner.test.ts +1 -0
- package/src/runtime/access-request-helper.ts +1 -0
- package/src/runtime/auth/route-policy.ts +10 -0
- package/src/runtime/channel-readiness-service.ts +68 -0
- package/src/runtime/channel-reply-delivery.ts +23 -0
- package/src/runtime/channel-retry-sweep.ts +47 -14
- package/src/runtime/confirmation-request-guardian-bridge.ts +1 -1
- package/src/runtime/migrations/vbundle-builder.ts +3 -2
- package/src/runtime/routes/__tests__/bookmark-routes.test.ts +1 -0
- package/src/runtime/routes/__tests__/conversation-compaction-routes.test.ts +406 -0
- package/src/runtime/routes/__tests__/conversation-query-routes.test.ts +98 -0
- package/src/runtime/routes/__tests__/heartbeat-routes.test.ts +1 -1
- package/src/runtime/routes/__tests__/home-feed-routes.test.ts +209 -1
- package/src/runtime/routes/__tests__/inference-provider-connection-routes.test.ts +13 -50
- package/src/runtime/routes/__tests__/memory-v2-simulate-route.test.ts +51 -3
- package/src/runtime/routes/__tests__/memory-v3-simulate-params.test.ts +35 -0
- package/src/runtime/routes/__tests__/slack-channel-routes.test.ts +3 -2
- package/src/runtime/routes/__tests__/surface-content-routes.test.ts +294 -0
- package/src/runtime/routes/__tests__/task-routes.test.ts +48 -3
- package/src/runtime/routes/acp-routes-list.test.ts +3 -0
- package/src/runtime/routes/app-management-routes.ts +111 -4
- package/src/runtime/routes/background-wake-routes.ts +188 -20
- package/src/runtime/routes/btw-routes.ts +4 -4
- package/src/runtime/routes/conversation-analysis-routes.ts +6 -0
- package/src/runtime/routes/conversation-compaction-routes.ts +263 -0
- package/src/runtime/routes/conversation-list-routes.ts +147 -0
- package/src/runtime/routes/conversation-management-routes.ts +39 -14
- package/src/runtime/routes/conversation-query-routes.ts +60 -10
- package/src/runtime/routes/conversation-routes.ts +186 -140
- package/src/runtime/routes/conversations-import-routes.ts +19 -6
- package/src/runtime/routes/documents-routes.ts +10 -1
- package/src/runtime/routes/group-routes.ts +11 -0
- package/src/runtime/routes/home-feed-routes.ts +129 -0
- package/src/runtime/routes/identity-intro-cache.ts +61 -16
- package/src/runtime/routes/identity-routes.ts +30 -9
- package/src/runtime/routes/inbound-stages/background-dispatch.test.ts +530 -6
- package/src/runtime/routes/inbound-stages/background-dispatch.ts +57 -8
- package/src/runtime/routes/index.ts +2 -0
- package/src/runtime/routes/inference-provider-connection-routes.ts +5 -26
- package/src/runtime/routes/integrations/vercel.ts +15 -0
- package/src/runtime/routes/llm-context-normalization.ts +7 -2
- package/src/runtime/routes/memory-v3-routes.ts +160 -2
- package/src/runtime/routes/migration-routes.ts +20 -13
- package/src/runtime/routes/notification-routes.ts +63 -1
- package/src/runtime/routes/oauth-commands-routes.ts +6 -1
- package/src/runtime/routes/surface-action-routes.ts +1 -38
- package/src/runtime/routes/surface-content-routes.ts +12 -5
- package/src/runtime/routes/surface-conversation-resolver.ts +65 -0
- package/src/runtime/routes/wipe-conversation-routes.ts +3 -0
- package/src/runtime/services/__tests__/analyze-conversation.test.ts +2 -0
- package/src/runtime/slack-dm-text-delivery.ts +177 -0
- package/src/runtime/sync/resource-sync-events.ts +1 -1
- package/src/runtime/tool-grant-request-helper.ts +1 -0
- package/src/schedule/schedule-store.ts +8 -1
- package/src/schedule/scheduler.ts +111 -15
- package/src/security/__tests__/provider-key-env-fallback.test.ts +3 -3
- package/src/security/encrypted-store.ts +7 -16
- package/src/security/store-path-override.ts +61 -0
- package/src/signals/user-message.ts +5 -8
- package/src/skills/validate-input.ts +177 -0
- package/src/subagent/manager.ts +13 -13
- package/src/subagent/types.ts +6 -0
- package/src/tasks/tool-sanitizer.ts +2 -2
- package/src/tools/apps/definitions.ts +35 -21
- package/src/tools/browser/__tests__/browser-execution-acquire.test.ts +2 -8
- package/src/tools/computer-use/definitions.ts +268 -266
- package/src/tools/document/document-tool.ts +131 -8
- package/src/tools/execution-target.ts +2 -5
- package/src/tools/executor.ts +18 -55
- package/src/tools/host-filesystem/edit.test.ts +1 -0
- package/src/tools/host-filesystem/read.test.ts +1 -0
- package/src/tools/host-filesystem/transfer.test.ts +31 -6
- package/src/tools/host-filesystem/write.test.ts +1 -0
- package/src/tools/mcp/mcp-tool-factory.ts +0 -2
- package/src/tools/network/__tests__/managed-search-proxy.test.ts +282 -0
- package/src/tools/network/__tests__/web-search.test.ts +211 -3
- package/src/tools/network/managed-search-proxy.ts +183 -0
- package/src/tools/network/web-search.ts +199 -44
- package/src/tools/policy-context.ts +3 -1
- package/src/tools/registry.ts +146 -103
- package/src/tools/schedule/create.ts +1 -1
- package/src/tools/skills/skill-tool-factory.ts +17 -36
- package/src/tools/subagent/spawn.ts +3 -0
- package/src/tools/tool-approval-handler.ts +10 -4
- package/src/tools/tool-name-aliases.ts +72 -14
- package/src/tools/types.ts +17 -15
- package/src/tools/ui-surface/definitions.ts +98 -86
- package/src/types/onboarding-context.ts +6 -0
- package/src/usage/attribution.ts +32 -1
- package/src/util/browser.ts +7 -2
- package/src/workspace/migrations/090-memory-router-cost-optimized-profile.ts +109 -0
- package/src/workspace/migrations/091-retighten-migration-onboarding-thread.ts +41 -0
- package/src/workspace/migrations/registry.ts +4 -0
|
@@ -31,10 +31,7 @@ mock.module("../security/secure-keys.js", () => ({
|
|
|
31
31
|
getSecureKeyAsync: getSecureKeyAsyncMock,
|
|
32
32
|
}));
|
|
33
33
|
|
|
34
|
-
import {
|
|
35
|
-
_setOverridesForTesting,
|
|
36
|
-
clearFeatureFlagOverridesCache,
|
|
37
|
-
} from "../config/assistant-feature-flags.js";
|
|
34
|
+
import { clearFeatureFlagOverridesCache } from "../config/assistant-feature-flags.js";
|
|
38
35
|
import type { AssistantConfig } from "../config/schema.js";
|
|
39
36
|
import {
|
|
40
37
|
bootstrapPlugins,
|
|
@@ -54,6 +51,7 @@ import {
|
|
|
54
51
|
PluginExecutionError,
|
|
55
52
|
type PluginInitContext,
|
|
56
53
|
} from "../plugins/types.js";
|
|
54
|
+
import { setOverridesForTesting } from "./feature-flag-test-helpers.js";
|
|
57
55
|
|
|
58
56
|
// Redirect plugin storage directory creation into a per-process temp tree so
|
|
59
57
|
// the test doesn't touch the developer's real ~/.vellum.
|
|
@@ -125,7 +123,7 @@ describe("plugin bootstrap", () => {
|
|
|
125
123
|
getSecureKeyAsyncMock.mockReset();
|
|
126
124
|
getSecureKeyAsyncMock.mockImplementation(async () => undefined);
|
|
127
125
|
// Reset feature-flag cache so tests start from a known state. Individual
|
|
128
|
-
// tests that exercise `requiresFlag` use `
|
|
126
|
+
// tests that exercise `requiresFlag` use `setOverridesForTesting(...)`
|
|
129
127
|
// to install their own overrides.
|
|
130
128
|
clearFeatureFlagOverridesCache();
|
|
131
129
|
// Clean storage directory between runs so nothing leaks across cases.
|
|
@@ -335,11 +333,11 @@ describe("plugin bootstrap", () => {
|
|
|
335
333
|
// - no shutdown hook entry is installed (nothing to tear down later).
|
|
336
334
|
// Plugins without `requiresFlag` are unaffected.
|
|
337
335
|
//
|
|
338
|
-
// Uses `
|
|
336
|
+
// Uses `setOverridesForTesting` to control the resolver deterministically
|
|
339
337
|
// — no disk writes, no gateway IPC, no reliance on registry defaults.
|
|
340
338
|
|
|
341
339
|
test("requiresFlag enabled: plugin inits normally", async () => {
|
|
342
|
-
|
|
340
|
+
setOverridesForTesting({ "plugin-gated-enabled": true });
|
|
343
341
|
|
|
344
342
|
let initFired = false;
|
|
345
343
|
const plugin = buildPlugin(
|
|
@@ -359,7 +357,7 @@ describe("plugin bootstrap", () => {
|
|
|
359
357
|
});
|
|
360
358
|
|
|
361
359
|
test("requiresFlag disabled: init does not fire and no tools/routes/skills are registered", async () => {
|
|
362
|
-
|
|
360
|
+
setOverridesForTesting({ "plugin-gated-disabled": false });
|
|
363
361
|
|
|
364
362
|
let initFired = false;
|
|
365
363
|
// Attach tool/route/skill contributions alongside init. If gating works,
|
|
@@ -440,7 +438,7 @@ describe("plugin bootstrap", () => {
|
|
|
440
438
|
test("requiresFlag: one disabled flag out of several skips the plugin", async () => {
|
|
441
439
|
// When ANY listed flag is disabled, the plugin is skipped wholesale —
|
|
442
440
|
// this prevents sneaky partial activation on AND semantics.
|
|
443
|
-
|
|
441
|
+
setOverridesForTesting({
|
|
444
442
|
"plugin-multi-a": true,
|
|
445
443
|
"plugin-multi-b": false,
|
|
446
444
|
});
|
|
@@ -469,7 +467,7 @@ describe("plugin bootstrap", () => {
|
|
|
469
467
|
// injectors still ran on every pipeline invocation and system-prompt
|
|
470
468
|
// assembly even though `init()` had never fired to set up the state they
|
|
471
469
|
// depended on.
|
|
472
|
-
|
|
470
|
+
setOverridesForTesting({ "plugin-middleware-disabled": false });
|
|
473
471
|
|
|
474
472
|
const gatedMiddleware: PipelineMiddlewareMap["llmCall"] = async (
|
|
475
473
|
args,
|
|
@@ -506,7 +504,7 @@ describe("plugin bootstrap", () => {
|
|
|
506
504
|
});
|
|
507
505
|
|
|
508
506
|
test("requiresFlag disabled: no shutdown hook entry installed for the skipped plugin", async () => {
|
|
509
|
-
|
|
507
|
+
setOverridesForTesting({ "plugin-shutdown-flag": false });
|
|
510
508
|
|
|
511
509
|
let shutdownFired = false;
|
|
512
510
|
const plugin = buildPlugin(
|
|
@@ -6,9 +6,11 @@
|
|
|
6
6
|
*
|
|
7
7
|
* - Registering a plugin with `tools: Tool[]`, running `bootstrapPlugins`,
|
|
8
8
|
* and observing the contributed tool via `getAllTools()` / `getTool()`.
|
|
9
|
-
* - Tool ownership
|
|
10
|
-
*
|
|
11
|
-
*
|
|
9
|
+
* - Tool ownership (`owner: { kind: "plugin", id: <plugin> }`) recorded
|
|
10
|
+
* authoritatively by `registerPluginTools` into the registry's
|
|
11
|
+
* `ownersByName` map (queried via `getToolOwner(name)`), regardless of
|
|
12
|
+
* what the plugin author set on the incoming object. The `Tool` itself
|
|
13
|
+
* carries no ownership field — the bootstrap is the only writer.
|
|
12
14
|
* - Shutdown hook unregistering the contributed tools so the registry is
|
|
13
15
|
* clean again after teardown.
|
|
14
16
|
* - Direct `registerPluginTools` / `unregisterPluginTools` semantics,
|
|
@@ -55,6 +57,7 @@ import {
|
|
|
55
57
|
getAllTools,
|
|
56
58
|
getPluginRefCount,
|
|
57
59
|
getTool,
|
|
60
|
+
getToolOwner,
|
|
58
61
|
registerPluginTools,
|
|
59
62
|
unregisterPluginTools,
|
|
60
63
|
} from "../tools/registry.js";
|
|
@@ -164,13 +167,17 @@ describe("plugin tool contributions", () => {
|
|
|
164
167
|
|
|
165
168
|
const retrieved = getTool("plugin-contrib-tool");
|
|
166
169
|
expect(retrieved).toBeDefined();
|
|
167
|
-
// Ownership
|
|
168
|
-
//
|
|
169
|
-
// the
|
|
170
|
-
//
|
|
171
|
-
//
|
|
172
|
-
|
|
173
|
-
|
|
170
|
+
// Ownership is recorded authoritatively by the bootstrap into the
|
|
171
|
+
// registry's `ownersByName` map (keyed by tool name, accessed via
|
|
172
|
+
// `getToolOwner(name)`) — the registry uses it to drive ref-counting
|
|
173
|
+
// and conflict detection when the plugin shuts down or is hot-reloaded.
|
|
174
|
+
// Plugin tools live in their own namespace, disjoint from real skills,
|
|
175
|
+
// so a plugin name that happens to match a skill id cannot collide.
|
|
176
|
+
// Ownership is not stamped on the `Tool` object itself.
|
|
177
|
+
expect(getToolOwner("plugin-contrib-tool")).toEqual({
|
|
178
|
+
kind: "plugin",
|
|
179
|
+
id: "alpha-contributor",
|
|
180
|
+
});
|
|
174
181
|
|
|
175
182
|
// The tool surfaces in the global `getAllTools()` snapshot, which is
|
|
176
183
|
// what downstream consumers (tool-manifest, session projection) read.
|
|
@@ -248,22 +255,23 @@ describe("registerPluginTools / unregisterPluginTools helpers", () => {
|
|
|
248
255
|
__resetRegistryForTesting();
|
|
249
256
|
});
|
|
250
257
|
|
|
251
|
-
test("registerPluginTools stamps category
|
|
252
|
-
// Even if the plugin author hands in a tool with no category
|
|
253
|
-
//
|
|
254
|
-
//
|
|
258
|
+
test("registerPluginTools stamps category and records ownership in the registry", () => {
|
|
259
|
+
// Even if the plugin author hands in a tool with no category, the
|
|
260
|
+
// helper fills it in and records ownership in the registry's
|
|
261
|
+
// `ownersByName` map — the tool itself never carries an `owner` field,
|
|
262
|
+
// so plugin authors can't spoof ownership by forging one.
|
|
255
263
|
const accepted = registerPluginTools("my-plugin", [
|
|
256
264
|
makeFakeTool("pt_stamped"),
|
|
257
265
|
]);
|
|
258
266
|
expect(accepted).toHaveLength(1);
|
|
259
267
|
expect(accepted[0]?.category).toBe("plugin");
|
|
260
|
-
expect(
|
|
261
|
-
|
|
268
|
+
expect(getToolOwner("pt_stamped")).toEqual({
|
|
269
|
+
kind: "plugin",
|
|
270
|
+
id: "my-plugin",
|
|
271
|
+
});
|
|
262
272
|
|
|
263
273
|
const retrieved = getTool("pt_stamped");
|
|
264
274
|
expect(retrieved?.category).toBe("plugin");
|
|
265
|
-
expect(retrieved?.origin).toBe("plugin");
|
|
266
|
-
expect(retrieved?.ownerPluginId).toBe("my-plugin");
|
|
267
275
|
});
|
|
268
276
|
|
|
269
277
|
test("registerPluginTools exposes provider-safe aliases for unsafe plugin tool names", async () => {
|
|
@@ -313,33 +321,28 @@ describe("registerPluginTools / unregisterPluginTools helpers", () => {
|
|
|
313
321
|
expect(getTool(paddedAlias!)).toBeDefined();
|
|
314
322
|
});
|
|
315
323
|
|
|
316
|
-
test("registerPluginTools
|
|
324
|
+
test("registerPluginTools ignores forged ownership fields on the incoming tool", () => {
|
|
317
325
|
// A plugin author could (maliciously or mistakenly) hand in a tool
|
|
318
|
-
// pre-tagged with another skill's or plugin's ID. The
|
|
319
|
-
//
|
|
320
|
-
//
|
|
321
|
-
//
|
|
322
|
-
//
|
|
323
|
-
//
|
|
326
|
+
// pre-tagged with another skill's or plugin's ID. The `Tool` type now
|
|
327
|
+
// carries no ownership field at all, so any such forgery is purely
|
|
328
|
+
// inert extra data — the registry only populates `ownersByName` from
|
|
329
|
+
// the first argument to `register*Tools`, which is the single source
|
|
330
|
+
// of truth for ownership and cannot be spoofed by forging fields on
|
|
331
|
+
// the manifest.
|
|
324
332
|
//
|
|
325
|
-
//
|
|
326
|
-
//
|
|
327
|
-
// transpiled artifact that arrives with spoofed fields baked in —
|
|
328
|
-
// the bootstrap-side defense is the second layer that must hold.
|
|
333
|
+
// Cast through `unknown` to simulate a hostile or transpiled artifact
|
|
334
|
+
// arriving with extra fields baked in.
|
|
329
335
|
const spoofed = {
|
|
330
336
|
...makeFakeTool("pt_spoof"),
|
|
331
337
|
origin: "skill",
|
|
332
|
-
|
|
333
|
-
ownerSkillBundled: true,
|
|
334
|
-
ownerSkillVersionHash: "deadbeef",
|
|
338
|
+
owner: { kind: "skill", id: "some-other-skill" },
|
|
335
339
|
} as unknown as LoadedTool;
|
|
336
340
|
registerPluginTools("my-plugin", [spoofed]);
|
|
337
|
-
|
|
338
|
-
expect(
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
expect(retrieved?.ownerSkillVersionHash).toBeUndefined();
|
|
341
|
+
expect(getTool("pt_spoof")).toBeDefined();
|
|
342
|
+
expect(getToolOwner("pt_spoof")).toEqual({
|
|
343
|
+
kind: "plugin",
|
|
344
|
+
id: "my-plugin",
|
|
345
|
+
});
|
|
343
346
|
});
|
|
344
347
|
|
|
345
348
|
test("unregisterPluginTools removes the plugin's tools", () => {
|
|
@@ -24,6 +24,7 @@ mock.module("../memory/conversation-crud.js", () => ({
|
|
|
24
24
|
provenanceFromTrustContext: () => ({}),
|
|
25
25
|
setConversationOriginChannelIfUnset: () => {},
|
|
26
26
|
setConversationOriginInterfaceIfUnset: () => {},
|
|
27
|
+
reserveMessage: mock(async () => ({ id: "msg-reserve" })),
|
|
27
28
|
}));
|
|
28
29
|
|
|
29
30
|
mock.module("../memory/conversation-disk-view.js", () => ({
|
|
@@ -84,12 +85,14 @@ type Deferred<T> = {
|
|
|
84
85
|
};
|
|
85
86
|
type PersistUserMessageMock = ReturnType<
|
|
86
87
|
typeof mock<
|
|
87
|
-
(
|
|
88
|
-
content: string
|
|
89
|
-
attachments
|
|
90
|
-
requestId?: string
|
|
91
|
-
metadata?: Record<string, unknown
|
|
92
|
-
|
|
88
|
+
(options: {
|
|
89
|
+
content: string;
|
|
90
|
+
attachments?: unknown[];
|
|
91
|
+
requestId?: string;
|
|
92
|
+
metadata?: Record<string, unknown>;
|
|
93
|
+
displayContent?: string;
|
|
94
|
+
clientMessageId?: string;
|
|
95
|
+
}) => Promise<{ id: string; deduplicated: boolean }>
|
|
93
96
|
>
|
|
94
97
|
>;
|
|
95
98
|
type RunAgentLoopMock = ReturnType<
|
|
@@ -209,12 +212,14 @@ function makeConversation(): TestConversation {
|
|
|
209
212
|
estimatedCost: 0,
|
|
210
213
|
},
|
|
211
214
|
persistUserMessage: mock(
|
|
212
|
-
async (
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
215
|
+
async (_options: {
|
|
216
|
+
content: string;
|
|
217
|
+
attachments?: unknown[];
|
|
218
|
+
requestId?: string;
|
|
219
|
+
metadata?: Record<string, unknown>;
|
|
220
|
+
displayContent?: string;
|
|
221
|
+
clientMessageId?: string;
|
|
222
|
+
}) => ({ id: "persisted-user-message-id", deduplicated: false }),
|
|
218
223
|
),
|
|
219
224
|
runAgentLoop: mock(async (..._args: unknown[]) => {
|
|
220
225
|
await loopDeferred.promise;
|
|
@@ -259,9 +264,9 @@ describe("processMessageInBackground Slack option propagation", () => {
|
|
|
259
264
|
|
|
260
265
|
expect(result).toEqual({ messageId: "persisted-user-message-id" });
|
|
261
266
|
expect(activeConversation.persistUserMessage).toHaveBeenCalledTimes(1);
|
|
262
|
-
expect(
|
|
263
|
-
|
|
264
|
-
});
|
|
267
|
+
expect(
|
|
268
|
+
activeConversation.persistUserMessage.mock.calls[0][0].metadata,
|
|
269
|
+
).toEqual({ slackInbound });
|
|
265
270
|
expect(activeConversation.runAgentLoop).toHaveBeenCalledTimes(1);
|
|
266
271
|
|
|
267
272
|
activeConversation.__loopDeferred.resolve();
|
|
@@ -324,7 +329,7 @@ describe("processMessageInBackground Slack option propagation", () => {
|
|
|
324
329
|
|
|
325
330
|
expect(activeConversation.persistUserMessage).toHaveBeenCalledTimes(1);
|
|
326
331
|
expect(
|
|
327
|
-
activeConversation.persistUserMessage.mock.calls[0][
|
|
332
|
+
activeConversation.persistUserMessage.mock.calls[0][0].metadata,
|
|
328
333
|
).toBeUndefined();
|
|
329
334
|
expect(activeConversation.runAgentLoop.mock.calls[0][3]).toEqual({
|
|
330
335
|
isInteractive: false,
|
|
@@ -50,6 +50,7 @@ mock.module("../memory/conversation-crud.js", () => ({
|
|
|
50
50
|
provenanceFromTrustContext: () => ({}),
|
|
51
51
|
setConversationOriginChannelIfUnset: () => {},
|
|
52
52
|
setConversationOriginInterfaceIfUnset: () => {},
|
|
53
|
+
reserveMessage: mock(async () => ({ id: "msg-reserve" })),
|
|
53
54
|
}));
|
|
54
55
|
|
|
55
56
|
mock.module("../memory/conversation-disk-view.js", () => ({
|
|
@@ -181,21 +182,18 @@ function makeTestConversation() {
|
|
|
181
182
|
getTurnChannelContext: () => turnChannelContext,
|
|
182
183
|
getTurnInterfaceContext: () => turnInterfaceContext,
|
|
183
184
|
getMessages: () => messages,
|
|
184
|
-
persistUserMessage: async (
|
|
185
|
-
content: string
|
|
186
|
-
attachments
|
|
187
|
-
requestId?: string
|
|
188
|
-
metadata?: Record<string, unknown
|
|
189
|
-
displayContent?: string
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
metadata,
|
|
197
|
-
displayContent,
|
|
198
|
-
),
|
|
185
|
+
persistUserMessage: async (options: {
|
|
186
|
+
content: string;
|
|
187
|
+
attachments?: UserMessageAttachment[];
|
|
188
|
+
requestId?: string;
|
|
189
|
+
metadata?: Record<string, unknown>;
|
|
190
|
+
displayContent?: string;
|
|
191
|
+
clientMessageId?: string;
|
|
192
|
+
}) =>
|
|
193
|
+
persistQueuedMessageBody(messagingCtx, {
|
|
194
|
+
...options,
|
|
195
|
+
requestId: options.requestId ?? "req-display-content",
|
|
196
|
+
}),
|
|
199
197
|
runAgentLoop,
|
|
200
198
|
updateClient: () => {},
|
|
201
199
|
getCurrentSender: () => undefined,
|
|
@@ -340,9 +338,9 @@ describe("processMessage displayContent", () => {
|
|
|
340
338
|
const modelContent =
|
|
341
339
|
'<external_content source="slack">\n\n</external_content>';
|
|
342
340
|
|
|
343
|
-
await conversation.persistUserMessage(
|
|
344
|
-
modelContent,
|
|
345
|
-
[
|
|
341
|
+
await conversation.persistUserMessage({
|
|
342
|
+
content: modelContent,
|
|
343
|
+
attachments: [
|
|
346
344
|
{
|
|
347
345
|
id: "att-1",
|
|
348
346
|
filename: "attachment.pdf",
|
|
@@ -350,10 +348,9 @@ describe("processMessage displayContent", () => {
|
|
|
350
348
|
data: Buffer.from("pdf bytes").toString("base64"),
|
|
351
349
|
},
|
|
352
350
|
],
|
|
353
|
-
"req-display-content",
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
);
|
|
351
|
+
requestId: "req-display-content",
|
|
352
|
+
displayContent: "",
|
|
353
|
+
});
|
|
357
354
|
|
|
358
355
|
expect(addMessageCalls).toHaveLength(1);
|
|
359
356
|
const persistedBlocks = JSON.parse(addMessageCalls[0]!.content);
|
|
@@ -1,16 +1,16 @@
|
|
|
1
1
|
import { afterEach, beforeEach, describe, expect, test } from "bun:test";
|
|
2
2
|
|
|
3
|
-
import { _setOverridesForTesting } from "../config/assistant-feature-flags.js";
|
|
4
3
|
import type { AssistantConfig } from "../config/schema.js";
|
|
5
4
|
import { PROVIDER_CATALOG } from "../providers/model-catalog.js";
|
|
6
5
|
import { getVisibleProviderCatalog } from "../providers/provider-catalog-visibility.js";
|
|
6
|
+
import { setOverridesForTesting } from "./feature-flag-test-helpers.js";
|
|
7
7
|
|
|
8
8
|
beforeEach(() => {
|
|
9
|
-
|
|
9
|
+
setOverridesForTesting({});
|
|
10
10
|
});
|
|
11
11
|
|
|
12
12
|
afterEach(() => {
|
|
13
|
-
|
|
13
|
+
setOverridesForTesting({});
|
|
14
14
|
});
|
|
15
15
|
|
|
16
16
|
/** Minimal AssistantConfig stub for feature-flag resolution. */
|
|
@@ -20,7 +20,7 @@ function makeConfig(): AssistantConfig {
|
|
|
20
20
|
|
|
21
21
|
describe("getVisibleProviderCatalog", () => {
|
|
22
22
|
test("hides openai-compatible endpoints by default", () => {
|
|
23
|
-
|
|
23
|
+
setOverridesForTesting({});
|
|
24
24
|
|
|
25
25
|
const visible = getVisibleProviderCatalog(makeConfig());
|
|
26
26
|
|
|
@@ -28,7 +28,7 @@ describe("getVisibleProviderCatalog", () => {
|
|
|
28
28
|
});
|
|
29
29
|
|
|
30
30
|
test("shows openai-compatible endpoints when its flag is enabled", () => {
|
|
31
|
-
|
|
31
|
+
setOverridesForTesting({ "openai-compatible-endpoints": true });
|
|
32
32
|
|
|
33
33
|
const visible = getVisibleProviderCatalog(makeConfig());
|
|
34
34
|
|
|
@@ -43,7 +43,7 @@ describe("getVisibleProviderCatalog", () => {
|
|
|
43
43
|
if (model.featureFlag) allFlags[model.featureFlag] = true;
|
|
44
44
|
}
|
|
45
45
|
}
|
|
46
|
-
|
|
46
|
+
setOverridesForTesting(allFlags);
|
|
47
47
|
|
|
48
48
|
const visible = getVisibleProviderCatalog(makeConfig());
|
|
49
49
|
expect(visible.length).toBe(PROVIDER_CATALOG.length);
|
|
@@ -58,7 +58,7 @@ describe("getVisibleProviderCatalog", () => {
|
|
|
58
58
|
if (model.featureFlag) allFlags[model.featureFlag] = true;
|
|
59
59
|
}
|
|
60
60
|
}
|
|
61
|
-
|
|
61
|
+
setOverridesForTesting({ ...allFlags, "test-provider-flag": false });
|
|
62
62
|
|
|
63
63
|
const original = [...PROVIDER_CATALOG];
|
|
64
64
|
PROVIDER_CATALOG.push({
|
|
@@ -87,7 +87,7 @@ describe("getVisibleProviderCatalog", () => {
|
|
|
87
87
|
});
|
|
88
88
|
|
|
89
89
|
test("hides a model whose featureFlag is disabled but keeps the provider", () => {
|
|
90
|
-
|
|
90
|
+
setOverridesForTesting({ "test-model-flag": false });
|
|
91
91
|
|
|
92
92
|
const original = [...PROVIDER_CATALOG];
|
|
93
93
|
PROVIDER_CATALOG.push({
|
|
@@ -121,7 +121,7 @@ describe("getVisibleProviderCatalog", () => {
|
|
|
121
121
|
});
|
|
122
122
|
|
|
123
123
|
test("hides a provider entirely when all its models are flagged off", () => {
|
|
124
|
-
|
|
124
|
+
setOverridesForTesting({
|
|
125
125
|
"flag-a": false,
|
|
126
126
|
"flag-b": false,
|
|
127
127
|
});
|