@vellumai/assistant 0.12.1-staging.1 → 0.12.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +0 -4
- package/ARCHITECTURE.md +12 -11
- package/docs/architecture/turn-actor.md +8 -15
- package/openapi.yaml +1 -291
- package/package.json +1 -1
- package/src/__tests__/always-loaded-tools-guard.test.ts +10 -18
- package/src/__tests__/app-compiler.test.ts +0 -6
- package/src/__tests__/app-control-tool-schemas.test.ts +2 -5
- package/src/__tests__/app-dir-path-guard.test.ts +3 -1
- package/src/__tests__/app-source-watcher.test.ts +218 -0
- package/src/{calls/__tests__ → __tests__}/call-controller.test.ts +82 -503
- package/src/__tests__/computer-use-skill-proxy-bridge.test.ts +2 -5
- package/src/__tests__/computer-use-tools.test.ts +5 -17
- package/src/__tests__/config-schema-cmd.test.ts +2 -2
- package/src/__tests__/config-schema.test.ts +29 -28
- package/src/__tests__/config-watcher-skill-reseed.test.ts +359 -0
- package/src/__tests__/config-watcher.test.ts +8 -23
- package/src/__tests__/connection-model-compat.test.ts +2 -2
- package/src/__tests__/conversation-key-store-disk-view.test.ts +1 -1
- package/src/__tests__/conversation-pairing.test.ts +0 -26
- package/src/__tests__/conversation-process-app-control-preactivation.test.ts +10 -4
- package/src/__tests__/conversation-queue.test.ts +207 -48
- package/src/__tests__/conversation-retry-discard.test.ts +1 -54
- package/src/__tests__/conversation-skill-tools.test.ts +0 -27
- package/src/__tests__/conversation-surfaces-app-control.test.ts +3 -8
- package/src/__tests__/conversation-surfaces-task-progress.test.ts +0 -67
- package/src/__tests__/conversation-title-service.test.ts +10 -14
- package/src/__tests__/conversation-tool-setup-app-refresh.test.ts +5 -3
- package/src/__tests__/conversation-tool-setup-attribution.test.ts +0 -51
- package/src/__tests__/credential-record-retire.test.ts +1 -171
- package/src/__tests__/credential-routes.test.ts +3 -212
- package/src/__tests__/credential-security-invariants.test.ts +1 -2
- package/src/__tests__/cu-unified-flow.test.ts +2 -8
- package/src/__tests__/drain-kick-guard.test.ts +2 -0
- package/src/__tests__/drain-requeue-on-contention.test.ts +6 -0
- package/src/__tests__/evict-conversations-for-reload.test.ts +1 -1
- package/src/__tests__/host-bash-proxy.test.ts +45 -26
- package/src/__tests__/host-browser-proxy.test.ts +17 -6
- package/src/__tests__/host-file-proxy-targeted.test.ts +0 -23
- package/src/__tests__/host-file-proxy.test.ts +23 -11
- package/src/__tests__/host-transfer-proxy-targeted.test.ts +9 -30
- package/src/__tests__/llm-catalog-parity.test.ts +0 -25
- package/src/__tests__/mcp-auth-routes.test.ts +9 -6
- package/src/__tests__/mcp-config-secret-boundary.test.ts +136 -78
- package/src/__tests__/mcp-health-check.test.ts +11 -8
- package/src/__tests__/mcp-list-plugin-servers.test.ts +10 -8
- package/src/{calls/__tests__ → __tests__}/media-stream-audio-transcode.test.ts +1 -1
- package/src/{calls/__tests__ → __tests__}/media-stream-output.test.ts +8 -37
- package/src/{calls/__tests__ → __tests__}/media-stream-parser.test.ts +1 -1
- package/src/{calls/__tests__ → __tests__}/media-stream-server-integration.test.ts +57 -150
- package/src/{calls/__tests__ → __tests__}/media-stream-stt-session.test.ts +5 -5
- package/src/{calls/__tests__ → __tests__}/media-turn-detector.test.ts +1 -1
- package/src/__tests__/messages-after-tiebreaker.test.ts +0 -91
- package/src/__tests__/messages-read-boundary-guard.test.ts +1 -1
- package/src/__tests__/messaging-send-tool.test.ts +548 -355
- package/src/__tests__/model-intents.test.ts +0 -3
- package/src/__tests__/outlook-messaging-provider.test.ts +6 -6
- package/src/__tests__/platform-client-verify-credential.test.ts +0 -2
- package/src/__tests__/plugin-import-boundary-guard.test.ts +0 -13
- package/src/__tests__/script-proxy-certs.test.ts +0 -35
- package/src/__tests__/skill-feature-flags-integration.test.ts +1 -1
- package/src/__tests__/skill-feature-flags.test.ts +2 -2
- package/src/__tests__/speaker-identification.test.ts +56 -0
- package/src/__tests__/subagent-tool-gate-mode.test.ts +3 -19
- package/src/__tests__/subagent-tools.test.ts +2 -3
- package/src/__tests__/telephony-tts-guard.test.ts +3 -38
- package/src/__tests__/vellum-self-knowledge-inline-command.test.ts +0 -4
- package/src/{calls/__tests__/voice-session-bridge-turn-flow.test.ts → __tests__/voice-session-bridge.test.ts} +12 -20
- package/src/__tests__/watch-retro-tool-availability.test.ts +17 -8
- package/src/__tests__/workspace-git-service.test.ts +0 -26
- package/src/acp/__tests__/agent-process.test.ts +4 -258
- package/src/acp/__tests__/auth-required.test.ts +0 -96
- package/src/acp/__tests__/client-handler.test.ts +2 -90
- package/src/acp/__tests__/session-manager-persistence.test.ts +1 -5
- package/src/acp/__tests__/session-manager-resume.test.ts +6 -270
- package/src/acp/__tests__/session-manager-usage.test.ts +2 -4
- package/src/acp/__tests__/session-manager.test.ts +4 -895
- package/src/acp/agent-process.test.ts +1 -4
- package/src/acp/agent-process.ts +9 -94
- package/src/acp/auth-required.ts +1 -50
- package/src/acp/auto-install.test.ts +7 -9
- package/src/acp/client-handler.ts +3 -16
- package/src/acp/resolve-agent.test.ts +6 -220
- package/src/acp/resolve-agent.ts +23 -88
- package/src/acp/session-manager.test.ts +3 -196
- package/src/acp/session-manager.ts +18 -441
- package/src/acp/types.ts +5 -50
- package/src/api/events/app-files-changed.ts +3 -4
- package/src/api/index.ts +0 -6
- package/src/apps/app-store.ts +1 -1
- package/src/bundler/app-compiler.ts +0 -15
- package/src/calls/__tests__/voice-control-protocol.test.ts +25 -58
- package/src/calls/__tests__/voice-session-bridge.test.ts +1 -37
- package/src/calls/__tests__/voice-triage-escalate.test.ts +0 -105
- package/src/calls/call-constants.ts +4 -24
- package/src/calls/call-controller.ts +199 -499
- package/src/calls/call-transport.ts +0 -16
- package/src/calls/media-stream-output.ts +0 -32
- package/src/calls/media-stream-server.ts +30 -82
- package/src/calls/media-stream-stt-session.ts +0 -15
- package/src/calls/resolve-call-tts-provider.ts +2 -33
- package/src/calls/speaker-identification.ts +233 -0
- package/src/calls/tts-call-strategy.ts +5 -9
- package/src/calls/types.ts +0 -2
- package/src/calls/voice-control-protocol.ts +21 -53
- package/src/calls/voice-session-bridge.ts +46 -59
- package/src/calls/voice-triage-escalate.ts +56 -175
- package/src/cli/commands/apps.help.ts +13 -67
- package/src/cli/commands/apps.ts +0 -183
- package/src/cli/commands/channels/index.help.ts +2 -70
- package/src/cli/commands/channels/index.ts +3 -16
- package/src/cli/commands/credentials.help.ts +2 -6
- package/src/cli/commands/credentials.ts +2 -2
- package/src/cli/commands/mcp.help.ts +8 -8
- package/src/cli/commands/mcp.ts +1 -1
- package/src/cli/commands/roadmap.help.ts +1 -5
- package/src/cli/commands/roadmap.ts +1 -1
- package/src/cli/lib/bundled-marketplace.json +90 -103
- package/src/config/__tests__/default-profile-catalog.test.ts +0 -22
- package/src/config/__tests__/memory-retrospective-schema.test.ts +1 -15
- package/src/config/__tests__/platform-rehydration.test.ts +0 -93
- package/src/config/acp-defaults.test.ts +3 -13
- package/src/config/acp-defaults.ts +6 -23
- package/src/config/acp-schema.ts +2 -30
- package/src/config/bundled-skills/acp/SKILL.md +14 -22
- package/src/config/bundled-skills/acp/TOOLS.json +1 -5
- package/src/config/bundled-skills/app-builder/SKILL.md +9 -12
- package/src/config/bundled-skills/app-builder/references/CUSTOM_ROUTES.md +1 -1
- package/src/config/bundled-skills/messaging/TOOLS.json +3 -3
- package/src/config/bundled-skills/messaging/tools/messaging-send.ts +139 -67
- package/src/config/bundled-skills/phone-calls/references/TRANSCRIPTS.md +1 -1
- package/src/config/bundled-skills/screen-annotation/SKILL.md +1 -8
- package/src/config/bundled-skills/screen-annotation/tools/screen-annotation.test.ts +1 -4
- package/src/config/bundled-skills/skill-management/TOOLS.json +2 -2
- package/src/config/default-profile-catalog.ts +1 -1
- package/src/config/env.ts +2 -2
- package/src/config/feature-flag-registry.json +12 -8
- package/src/config/memory-v3-gate.test.ts +0 -31
- package/src/config/memory-v3-gate.ts +16 -20
- package/src/config/platform-rehydration.ts +21 -75
- package/src/config/schema.ts +2 -2
- package/src/config/schemas/__tests__/live-voice.test.ts +158 -8
- package/src/config/schemas/calls.ts +28 -1
- package/src/config/schemas/live-voice.ts +173 -1
- package/src/config/schemas/mcp.ts +1 -1
- package/src/config/schemas/memory-retrospective.ts +0 -10
- package/src/config/schemas/skills.ts +14 -0
- package/src/credential-execution/process-manager.test.ts +19 -18
- package/src/daemon/__tests__/conversation-tool-setup.test.ts +121 -66
- package/src/daemon/__tests__/plugin-mcp-reconcile.test.ts +1 -4
- package/src/daemon/app-source-watcher.ts +218 -0
- package/src/daemon/config-watcher.ts +194 -13
- package/src/daemon/conversation-process.ts +64 -35
- package/src/daemon/conversation-skill-tools.ts +31 -13
- package/src/daemon/conversation-store.ts +1 -1
- package/src/daemon/conversation-surfaces.ts +8 -10
- package/src/daemon/conversation-tool-setup.ts +43 -37
- package/src/daemon/conversation.ts +3 -0
- package/src/daemon/host-bash-proxy.ts +12 -8
- package/src/daemon/host-browser-proxy.ts +1 -15
- package/src/daemon/host-file-proxy.ts +10 -8
- package/src/daemon/host-transfer-proxy.ts +18 -14
- package/src/daemon/lifecycle.ts +5 -0
- package/src/daemon/mcp-reload-service.ts +5 -5
- package/src/daemon/message-types/sync.ts +0 -1
- package/src/daemon/providers-setup.ts +1 -1
- package/src/daemon/shutdown-handlers.ts +9 -1
- package/src/daemon/skill-memory-refresh.ts +0 -64
- package/src/daemon/tool-side-effects.ts +18 -7
- package/src/hooks/types.ts +0 -33
- package/src/inbound/platform-callback-registration.ts +5 -4
- package/src/live-voice/__tests__/live-voice-metrics.test.ts +3 -0
- package/src/live-voice/__tests__/live-voice-progress.test.ts +15 -15
- package/src/live-voice/__tests__/live-voice-vad.test.ts +2 -2
- package/src/{calls → live-voice}/__tests__/progress-narration.test.ts +4 -4
- package/src/{calls → live-voice}/__tests__/progress-phrases.test.ts +1 -1
- package/src/live-voice/__tests__/runtime-websocket-shell.test.ts +69 -13
- package/src/live-voice/live-voice-session.ts +693 -213
- package/src/{calls → live-voice}/progress-narration.ts +2 -2
- package/src/live-voice/protocol.ts +2 -0
- package/src/mcp/__tests__/effective-config.test.ts +2 -2
- package/src/mcp/effective-config.ts +3 -3
- package/src/mcp/mcp-header-store.ts +45 -29
- package/src/mcp/startup.ts +4 -8
- package/src/messaging/provider.ts +3 -10
- package/src/messaging/providers/callback-routing.ts +0 -18
- package/src/messaging/providers/channel-transport.ts +0 -56
- package/src/messaging/providers/discord/transport.ts +0 -17
- package/src/messaging/providers/slack/__tests__/adapter-token-routing.test.ts +17 -6
- package/src/messaging/providers/slack/adapter.ts +44 -7
- package/src/messaging/providers/slack/transport.ts +0 -16
- package/src/messaging/providers/telegram-bot/adapter.ts +48 -1
- package/src/messaging/providers/telegram-bot/client.ts +26 -0
- package/src/messaging/providers/telegram-bot/transport.ts +0 -20
- package/src/messaging/providers/whatsapp/adapter.ts +48 -1
- package/src/messaging/providers/whatsapp/client.ts +29 -0
- package/src/messaging/providers/whatsapp/transport.ts +0 -18
- package/src/monitoring/__tests__/workspace-git-heartbeat.test.ts +0 -8
- package/src/notifications/__tests__/assistant-reply-producer.test.ts +0 -55
- package/src/notifications/__tests__/home-feed-side-effect.test.ts +3 -153
- package/src/notifications/assistant-reply-producer.ts +3 -8
- package/src/notifications/conversation-pairing.ts +16 -36
- package/src/notifications/delivered-post-record.ts +1 -11
- package/src/notifications/home-feed-side-effect.ts +7 -55
- package/src/outbound-proxy/certs.ts +5 -3
- package/src/permissions/checker.test.ts +6 -11
- package/src/persistence/compaction-log-store-clickhouse.ts +3 -3
- package/src/persistence/conversation-crud.ts +63 -71
- package/src/persistence/conversation-lineage.ts +4 -12
- package/src/persistence/conversation-title-service.ts +26 -9
- package/src/persistence/llm-request-log-sink-clickhouse.ts +3 -3
- package/src/persistence/llm-request-log-source-clickhouse.ts +3 -3
- package/src/persistence/message-reads.ts +0 -30
- package/src/persistence/migrations/157-invite-contact-id.ts +6 -18
- package/src/persistence/schema/memory-core.ts +0 -5
- package/src/platform/client.test.ts +0 -2
- package/src/platform/client.ts +10 -2
- package/src/plugin-api/constants.ts +0 -2
- package/src/plugin-api/index.ts +0 -1
- package/src/plugin-api/types.ts +0 -2
- package/src/plugins/defaults/index.ts +0 -2
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-accounting.test.ts +0 -46
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-enqueue.test.ts +5 -9
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-job.test.ts +10 -20
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-state.test.ts +0 -219
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-sweep.test.ts +0 -31
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-trigger-check.test.ts +0 -63
- package/src/plugins/defaults/memory/__tests__/shutdown-hook.test.ts +0 -4
- package/src/plugins/defaults/memory/graph/capability-seed.ts +6 -4
- package/src/plugins/defaults/memory/hooks/init.ts +0 -10
- package/src/plugins/defaults/memory/hooks/shutdown.ts +0 -2
- package/src/plugins/defaults/memory/jobs-worker.ts +0 -13
- package/src/plugins/defaults/memory/memory-retrospective-accounting.ts +60 -34
- package/src/plugins/defaults/memory/memory-retrospective-enqueue.ts +5 -3
- package/src/plugins/defaults/memory/memory-retrospective-job.ts +3 -12
- package/src/plugins/defaults/memory/memory-retrospective-state.ts +71 -312
- package/src/plugins/defaults/memory/memory-retrospective-sweep.ts +1 -2
- package/src/plugins/defaults/memory/memory-retrospective-trigger-check.ts +3 -5
- package/src/plugins/defaults/memory/startup.ts +1 -6
- package/src/plugins/defaults/memory/substrate/__tests__/skill-content.test.ts +9 -7
- package/src/plugins/defaults/memory/substrate/skill-content.ts +2 -2
- package/src/plugins/defaults/memory/v3/__tests__/pool-select.test.ts +0 -89
- package/src/plugins/defaults/memory/worker.ts +0 -6
- package/src/plugins/mcp-servers.ts +75 -15
- package/src/providers/__tests__/connection-model-compat.test.ts +3 -3
- package/src/providers/gemini/client.ts +23 -9
- package/src/providers/model-catalog.ts +0 -34
- package/src/providers/model-intents.ts +5 -10
- package/src/providers/openai/__tests__/chat-completions-provider-reasoning.test.ts +18 -146
- package/src/providers/openai/__tests__/tool-choice-mapping.test.ts +1 -83
- package/src/providers/openai/chat-completions-provider.ts +78 -192
- package/src/providers/openai/codex-models.ts +4 -0
- package/src/runtime/AGENTS.md +0 -2
- package/src/runtime/auth/same-actor.ts +3 -38
- package/src/runtime/http-server.ts +151 -160
- package/src/runtime/routes/__tests__/acp-routes.test.ts +4 -159
- package/src/runtime/routes/__tests__/conversation-query-routes.test.ts +1 -108
- package/src/runtime/routes/__tests__/mcp-add-default-risk.test.ts +12 -16
- package/src/runtime/routes/acp-routes.test.ts +0 -15
- package/src/runtime/routes/acp-routes.ts +9 -72
- package/src/runtime/routes/app-management-routes.ts +0 -73
- package/src/runtime/routes/app-routes.ts +1 -1
- package/src/runtime/routes/conversation-list-routes.ts +3 -14
- package/src/runtime/routes/conversation-query-routes.ts +0 -40
- package/src/runtime/routes/credential-routes.ts +10 -19
- package/src/runtime/routes/diagnostics-routes.ts +3 -55
- package/src/runtime/routes/index.ts +0 -4
- package/src/runtime/routes/log-export-routes.ts +0 -2
- package/src/runtime/routes/mcp-auth-routes.ts +47 -39
- package/src/runtime/routes/migration-routes.ts +21 -8
- package/src/runtime/routes/platform-routes.ts +15 -18
- package/src/runtime/services/__tests__/conversation-serializer.test.ts +0 -28
- package/src/runtime/services/conversation-serializer.ts +3 -16
- package/src/runtime/sync/resource-sync-events.ts +1 -2
- package/src/schedule/worker.ts +1 -1
- package/src/security/ces-rpc-record-backend.ts +0 -7
- package/src/subagent/consult-context.ts +25 -12
- package/src/tools/acp/list-agents.test.ts +1 -3
- package/src/tools/acp/spawn.test.ts +11 -146
- package/src/tools/acp/spawn.ts +3 -21
- package/src/tools/acp/status.ts +3 -40
- package/src/tools/app-control/skill-proxy-bridge.ts +1 -2
- package/src/tools/capability-offer.test.ts +2 -22
- package/src/tools/capability-offer.ts +1 -16
- package/src/tools/computer-use/definitions.ts +2 -4
- package/src/tools/computer-use/skill-proxy-bridge.ts +1 -2
- package/src/tools/credentials/metadata-store.ts +0 -100
- package/src/tools/host-filesystem/edit.test.ts +1 -2
- package/src/tools/host-filesystem/edit.ts +2 -2
- package/src/tools/host-filesystem/read.test.ts +1 -2
- package/src/tools/host-filesystem/read.ts +2 -2
- package/src/tools/host-filesystem/transfer.test.ts +1 -2
- package/src/tools/host-filesystem/transfer.ts +2 -2
- package/src/tools/host-filesystem/write.test.ts +1 -2
- package/src/tools/host-filesystem/write.ts +2 -2
- package/src/tools/host-terminal/host-shell.test.ts +0 -16
- package/src/tools/host-terminal/host-shell.ts +20 -4
- package/src/tools/policy-context.ts +7 -6
- package/src/tools/subagent/spawn.ts +8 -5
- package/src/tools/watch/watch-retro-report.ts +8 -0
- package/src/util/__tests__/language-subtag.test.ts +1 -23
- package/src/util/fs-watcher-error.ts +36 -0
- package/src/util/language-subtag.ts +0 -16
- package/src/util/platform.ts +0 -8
- package/src/workspace/git-service.ts +54 -5
- package/src/workspace/migrations/registry.ts +0 -6
- package/scripts/smoke-desktop-window-theme.ts +0 -186
- package/src/__tests__/git-porcelain.test.ts +0 -47
- package/src/__tests__/helpers/set-workspace-mcp.ts +0 -11
- package/src/__tests__/message-deleted-hook-dispatch.test.ts +0 -119
- package/src/__tests__/resolve-app.test.ts +0 -135
- package/src/__tests__/source-fingerprint.test.ts +0 -184
- package/src/__tests__/workspace-migration-154-repair-retired-codex-gpt-5-4-model-ids.test.ts +0 -336
- package/src/acp/__tests__/helpers/acp-model-option.ts +0 -51
- package/src/acp/model-config.test.ts +0 -166
- package/src/acp/model-config.ts +0 -138
- package/src/api/events/acp-session-model-update.test.ts +0 -88
- package/src/api/events/acp-session-model-update.ts +0 -46
- package/src/apps/resolve-app.ts +0 -81
- package/src/apps/source-fingerprint.ts +0 -266
- package/src/calls/__tests__/barge-in-guard.test.ts +0 -81
- package/src/calls/__tests__/voice-leg-coordinator.test.ts +0 -229
- package/src/calls/__tests__/voice-progress-cadence.test.ts +0 -274
- package/src/calls/barge-in-guard.ts +0 -118
- package/src/calls/voice-leg-coordinator.ts +0 -189
- package/src/calls/voice-progress-cadence.ts +0 -423
- package/src/cli/commands/__tests__/apps.test.ts +0 -245
- package/src/cli/commands/__tests__/roadmap.help.test.ts +0 -19
- package/src/cli/commands/channels/__tests__/send.test.ts +0 -218
- package/src/cli/commands/channels/send.ts +0 -128
- package/src/config/__tests__/platform-identity.test.ts +0 -117
- package/src/config/acp-agent-write.ts +0 -43
- package/src/config/acp-schema.test.ts +0 -81
- package/src/config/platform-identity.ts +0 -144
- package/src/config/schemas/__tests__/voice.test.ts +0 -148
- package/src/config/schemas/voice.ts +0 -150
- package/src/daemon/__tests__/skill-memory-refresh-mtime.test.ts +0 -133
- package/src/daemon/app-change-notify.ts +0 -45
- package/src/desktop/__tests__/fake-desktop.ts +0 -119
- package/src/desktop/desktop-chrome-policy.test.ts +0 -71
- package/src/desktop/desktop-chrome-policy.ts +0 -42
- package/src/desktop/desktop-dependencies.test.ts +0 -102
- package/src/desktop/desktop-dependencies.ts +0 -306
- package/src/desktop/desktop-feature.test.ts +0 -18
- package/src/desktop/desktop-feature.ts +0 -19
- package/src/desktop/desktop-panel-config.test.ts +0 -135
- package/src/desktop/desktop-panel-config.ts +0 -149
- package/src/desktop/desktop-session-manager.test.ts +0 -627
- package/src/desktop/desktop-session-manager.ts +0 -814
- package/src/desktop/desktop-stream-bridge.test.ts +0 -395
- package/src/desktop/desktop-stream-bridge.ts +0 -214
- package/src/desktop/desktop-wallpaper.test.ts +0 -191
- package/src/desktop/desktop-wallpaper.ts +0 -113
- package/src/desktop/desktop-window-theme.ts +0 -170
- package/src/i18n/AGENTS.md +0 -22
- package/src/i18n/__tests__/i18n.test.ts +0 -108
- package/src/i18n/index.ts +0 -16
- package/src/i18n/locales.ts +0 -93
- package/src/i18n/messages.ts +0 -61
- package/src/i18n/title.ts +0 -25
- package/src/mcp/__tests__/workspace-mcp-config.test.ts +0 -135
- package/src/mcp/spec-schema.ts +0 -111
- package/src/mcp/workspace-mcp-config.ts +0 -188
- package/src/messaging/providers/__tests__/proactive-address.test.ts +0 -95
- package/src/persistence/conversation-title-placeholders.ts +0 -23
- package/src/persistence/message-cursor.ts +0 -78
- package/src/persistence/migrations/__tests__/157-invite-contact-id.test.ts +0 -149
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-cursor-backfill.test.ts +0 -118
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-cursor-preserve.test.ts +0 -83
- package/src/plugins/defaults/memory/hooks/message-deleted.ts +0 -21
- package/src/plugins/defaults/memory/memory-retrospective-cursor-backfill.ts +0 -126
- package/src/plugins/defaults/memory/memory-retrospective-cursor-preserve.ts +0 -79
- package/src/plugins/defaults/memory/memory-retrospective-cursor.ts +0 -28
- package/src/plugins/defaults/memory/skill-md-mtime-poll.ts +0 -9
- package/src/providers/gemini-thought-signature.test.ts +0 -63
- package/src/providers/gemini-thought-signature.ts +0 -44
- package/src/providers/openai/__tests__/chat-completions-provider-thought-signature.test.ts +0 -613
- package/src/providers/openai/__tests__/google-thought-signature.test.ts +0 -235
- package/src/providers/openai/google-thought-signature.ts +0 -320
- package/src/runtime/__tests__/channel-send.test.ts +0 -443
- package/src/runtime/__tests__/desktop-stream-upgrade.test.ts +0 -89
- package/src/runtime/__tests__/live-voice-upgrade.test.ts +0 -58
- package/src/runtime/__tests__/runtime-ws-test-utils.ts +0 -72
- package/src/runtime/__tests__/watch-stream-upgrade.test.ts +0 -59
- package/src/runtime/channel-send.ts +0 -316
- package/src/runtime/routes/__tests__/apps-refresh-route.test.ts +0 -205
- package/src/runtime/routes/__tests__/channel-send-routes.test.ts +0 -127
- package/src/runtime/routes/__tests__/dictation-cleanup-guard.test.ts +0 -107
- package/src/runtime/routes/channel-send-routes.ts +0 -85
- package/src/runtime/routes/desktop-setup-routes.test.ts +0 -74
- package/src/runtime/routes/desktop-setup-routes.ts +0 -35
- package/src/security/__tests__/ces-http-record-backend.test.ts +0 -137
- package/src/security/ces-http-record-backend.ts +0 -120
- package/src/skills/__tests__/workspace-skill-md-signature.test.ts +0 -60
- package/src/skills/workspace-skill-md-signature.ts +0 -50
- package/src/tools/acp/status.test.ts +0 -94
- package/src/util/ca-bundle.ts +0 -13
- package/src/workspace/git-porcelain.ts +0 -66
- package/src/workspace/migrations/154-repair-retired-codex-gpt-5-4-model-ids.ts +0 -258
- package/src/workspace/migrations/155-move-front-model-config-to-voice.ts +0 -78
- package/src/workspace/migrations/156-extract-workspace-mcp-json.ts +0 -214
- package/src/workspace/migrations/__tests__/155-move-front-model-config-to-voice.test.ts +0 -102
- package/src/workspace/migrations/__tests__/156-extract-workspace-mcp-json.test.ts +0 -199
- /package/src/{calls → live-voice}/progress-phrases.ts +0 -0
|
@@ -22,7 +22,6 @@ import {
|
|
|
22
22
|
getConfiguredProvider,
|
|
23
23
|
userMessage,
|
|
24
24
|
} from "../../providers/provider-send-message.js";
|
|
25
|
-
import { isMaxTokensStopReason } from "../../providers/stop-reasons.js";
|
|
26
25
|
import { getLogger } from "../../util/logger.js";
|
|
27
26
|
import { ACTOR_PRINCIPALS } from "../auth/route-policy.js";
|
|
28
27
|
import { BadRequestError } from "./errors.js";
|
|
@@ -177,44 +176,9 @@ function buildCommandPrompt(body: DictationBody, stylePrompt?: string): string {
|
|
|
177
176
|
return sections.join("\n");
|
|
178
177
|
}
|
|
179
178
|
|
|
180
|
-
|
|
179
|
+
function computeMaxTokens(inputLength: number): number {
|
|
181
180
|
const estimatedInputTokens = Math.ceil(inputLength / 3);
|
|
182
|
-
|
|
183
|
-
// argument, plus a `reasoning` string and the JSON scaffolding around both,
|
|
184
|
-
// so the budget has to cover well more than the input alone. `max_tokens` is
|
|
185
|
-
// a ceiling rather than a target: a call that stops short of it costs no
|
|
186
|
-
// extra latency.
|
|
187
|
-
return Math.max(512, estimatedInputTokens * 2 + 256);
|
|
188
|
-
}
|
|
189
|
-
|
|
190
|
-
export type CleanupRejection = "truncated";
|
|
191
|
-
|
|
192
|
-
/**
|
|
193
|
-
* Decide whether the cleanup model's rewrite is safe to use as the payload.
|
|
194
|
-
*
|
|
195
|
-
* The rewrite replaces what the user actually said. A token-cap stop means the
|
|
196
|
-
* tool JSON was cut mid-argument, so however complete the `text` argument
|
|
197
|
-
* happens to look, it is a fragment; the raw transcript is the safer payload
|
|
198
|
-
* then. Unpolished beats wrong.
|
|
199
|
-
*
|
|
200
|
-
* Whether a shorter rewrite still preserved the meaning is the model's call
|
|
201
|
-
* (the prompt asks it to drop fillers and tighten phrasing), so there is no
|
|
202
|
-
* length check here: a deterministic ratio cannot tell a concise cleanup from
|
|
203
|
-
* a summary.
|
|
204
|
-
*/
|
|
205
|
-
export function resolveCleanedDictation(
|
|
206
|
-
raw: string,
|
|
207
|
-
cleaned: string,
|
|
208
|
-
stopReason: string | null | undefined,
|
|
209
|
-
): { text: string; rejected: CleanupRejection | null } {
|
|
210
|
-
const trimmed = cleaned.trim();
|
|
211
|
-
if (!trimmed) {
|
|
212
|
-
return { text: raw, rejected: null };
|
|
213
|
-
}
|
|
214
|
-
if (isMaxTokensStopReason(stopReason)) {
|
|
215
|
-
return { text: raw, rejected: "truncated" };
|
|
216
|
-
}
|
|
217
|
-
return { text: trimmed, rejected: null };
|
|
181
|
+
return Math.max(256, estimatedInputTokens + 128);
|
|
218
182
|
}
|
|
219
183
|
|
|
220
184
|
interface DictationResult {
|
|
@@ -365,23 +329,7 @@ async function handleDictation(body: DictationBody): Promise<DictationResult> {
|
|
|
365
329
|
...profileMeta,
|
|
366
330
|
};
|
|
367
331
|
}
|
|
368
|
-
const
|
|
369
|
-
transcription,
|
|
370
|
-
input.text ?? "",
|
|
371
|
-
response.stopReason,
|
|
372
|
-
);
|
|
373
|
-
if (rejected) {
|
|
374
|
-
// Lengths only -- transcript content must never be logged.
|
|
375
|
-
log.warn(
|
|
376
|
-
{
|
|
377
|
-
rejected,
|
|
378
|
-
stopReason: response.stopReason,
|
|
379
|
-
rawChars: transcription.length,
|
|
380
|
-
cleanedChars: input.text?.trim().length ?? 0,
|
|
381
|
-
},
|
|
382
|
-
"Dictation cleanup rejected, using raw transcription",
|
|
383
|
-
);
|
|
384
|
-
}
|
|
332
|
+
const cleanedText = input.text?.trim() || transcription;
|
|
385
333
|
const normalizedText = applyDictionary(cleanedText, profile.dictionary);
|
|
386
334
|
return {
|
|
387
335
|
text: normalizedText,
|
|
@@ -39,7 +39,6 @@ import { ROUTES as CALL_ROUTES } from "./call-routes.js";
|
|
|
39
39
|
import { ROUTES as CHANNEL_AVAILABILITY_ROUTES } from "./channel-availability-routes.js";
|
|
40
40
|
import { ROUTES as CHANNEL_READINESS_ROUTES } from "./channel-readiness-routes.js";
|
|
41
41
|
import { CHANNEL_ROUTES } from "./channel-route-definitions.js";
|
|
42
|
-
import { ROUTES as CHANNEL_SEND_ROUTES } from "./channel-send-routes.js";
|
|
43
42
|
import { ROUTES as CHANNEL_VERIFICATION_ROUTES } from "./channel-verification-routes.js";
|
|
44
43
|
import { ROUTES as CHATGPT_SUBSCRIPTION_AUTH_ROUTES } from "./chatgpt-subscription-auth-routes.js";
|
|
45
44
|
import { ROUTES as CLIENT_ROUTES } from "./client-routes.js";
|
|
@@ -63,7 +62,6 @@ import { ROUTES as DEBUG_BASH_ROUTES } from "./debug-bash-routes.js";
|
|
|
63
62
|
import { ROUTES as DEBUG_ROUTES } from "./debug-routes.js";
|
|
64
63
|
import { ROUTES as DEFAULT_PROVIDER_ROUTES } from "./default-provider-routes.js";
|
|
65
64
|
import { ROUTES as DEFER_ROUTES } from "./defer-routes.js";
|
|
66
|
-
import { ROUTES as DESKTOP_SETUP_ROUTES } from "./desktop-setup-routes.js";
|
|
67
65
|
import { ROUTES as DIAGNOSTICS_ROUTES } from "./diagnostics-routes.js";
|
|
68
66
|
import { ROUTES as DISK_PRESSURE_ROUTES } from "./disk-pressure-routes.js";
|
|
69
67
|
import { ROUTES as DOCUMENT_COMMENT_ROUTES } from "./document-comments-routes.js";
|
|
@@ -193,7 +191,6 @@ export const ROUTES: RouteDefinition[] = [
|
|
|
193
191
|
...CHANNEL_VERIFICATION_ROUTES,
|
|
194
192
|
...CHANNEL_AVAILABILITY_ROUTES,
|
|
195
193
|
...CHANNEL_READINESS_ROUTES,
|
|
196
|
-
...CHANNEL_SEND_ROUTES,
|
|
197
194
|
...BROWSER_ROUTES,
|
|
198
195
|
...BROWSER_TABS_ROUTES,
|
|
199
196
|
...BTW_ROUTES,
|
|
@@ -221,7 +218,6 @@ export const ROUTES: RouteDefinition[] = [
|
|
|
221
218
|
...DEBUG_BASH_ROUTES,
|
|
222
219
|
...DEBUG_ROUTES,
|
|
223
220
|
...DEFAULT_PROVIDER_ROUTES,
|
|
224
|
-
...DESKTOP_SETUP_ROUTES,
|
|
225
221
|
...DIAGNOSTICS_ROUTES,
|
|
226
222
|
...DISK_PRESSURE_ROUTES,
|
|
227
223
|
...RESOURCE_PRESSURE_ROUTES,
|
|
@@ -22,7 +22,6 @@ import { join } from "node:path";
|
|
|
22
22
|
import { and, desc, eq, gte, lte } from "drizzle-orm";
|
|
23
23
|
import { z } from "zod";
|
|
24
24
|
|
|
25
|
-
import { overlayWorkspaceMcpForConfigRead } from "../../mcp/workspace-mcp-config.js";
|
|
26
25
|
import { getDb, getLogsDb } from "../../persistence/db-connection.js";
|
|
27
26
|
import {
|
|
28
27
|
llmRequestLogs,
|
|
@@ -569,7 +568,6 @@ function readSanitizedConfig(): Record<string, unknown> | undefined {
|
|
|
569
568
|
}
|
|
570
569
|
}
|
|
571
570
|
|
|
572
|
-
overlayWorkspaceMcpForConfigRead(config);
|
|
573
571
|
const mcpServers = asRecord(asRecord(config.mcp)?.servers);
|
|
574
572
|
for (const server of Object.values(mcpServers ?? {})) {
|
|
575
573
|
const transport = asRecord(asRecord(server)?.transport);
|
|
@@ -14,7 +14,8 @@
|
|
|
14
14
|
|
|
15
15
|
import { z } from "zod";
|
|
16
16
|
|
|
17
|
-
import
|
|
17
|
+
import { loadRawConfig, saveRawConfig } from "../../config/loader.js";
|
|
18
|
+
import type { McpConfig, McpServerConfig } from "../../config/schemas/mcp.js";
|
|
18
19
|
import { estimateToolDefinitionTokens } from "../../context/token-estimator.js";
|
|
19
20
|
import { reloadMcpServers } from "../../daemon/mcp-reload-service.js";
|
|
20
21
|
import { McpClient } from "../../mcp/client.js";
|
|
@@ -30,10 +31,6 @@ import {
|
|
|
30
31
|
deleteMcpOAuthCredentials,
|
|
31
32
|
hasMcpOAuthTokens,
|
|
32
33
|
} from "../../mcp/mcp-oauth-provider.js";
|
|
33
|
-
import {
|
|
34
|
-
loadWorkspaceMcpConfig,
|
|
35
|
-
saveWorkspaceMcpConfig,
|
|
36
|
-
} from "../../mcp/workspace-mcp-config.js";
|
|
37
34
|
import { readPluginMcpServers } from "../../plugins/mcp-servers.js";
|
|
38
35
|
import { getMcpToolsByServer } from "../../tools/registry.js";
|
|
39
36
|
import { getLogger } from "../../util/logger.js";
|
|
@@ -68,18 +65,6 @@ const McpAddParams = z.object({
|
|
|
68
65
|
|
|
69
66
|
const McpRemoveParams = z.object({ name: z.string() });
|
|
70
67
|
|
|
71
|
-
function persistWorkspaceMcpConfig(config: {
|
|
72
|
-
servers: Record<string, McpServerConfig>;
|
|
73
|
-
}): void {
|
|
74
|
-
try {
|
|
75
|
-
saveWorkspaceMcpConfig(config);
|
|
76
|
-
} catch (err) {
|
|
77
|
-
throw new InternalError(
|
|
78
|
-
err instanceof Error ? err.message : String(err),
|
|
79
|
-
);
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
|
|
83
68
|
async function handleMcpAuthStart({
|
|
84
69
|
body,
|
|
85
70
|
}: {
|
|
@@ -91,7 +76,8 @@ async function handleMcpAuthStart({
|
|
|
91
76
|
}> {
|
|
92
77
|
const { serverId } = parseBody(McpServerIdParams, body);
|
|
93
78
|
|
|
94
|
-
const
|
|
79
|
+
const raw = loadRawConfig();
|
|
80
|
+
const servers = (raw.mcp as Partial<McpConfig> | undefined)?.servers ?? {};
|
|
95
81
|
const serverConfig = servers[serverId];
|
|
96
82
|
|
|
97
83
|
if (!serverConfig) {
|
|
@@ -267,7 +253,9 @@ function detectAuthType(headers: Record<string, string>): "bearer" | "api-key" {
|
|
|
267
253
|
async function handleMcpList(_args: {
|
|
268
254
|
body?: Record<string, unknown>;
|
|
269
255
|
}): Promise<{ servers: McpServerEntry[] }> {
|
|
270
|
-
const
|
|
256
|
+
const raw = loadRawConfig();
|
|
257
|
+
const mcpConfig = raw.mcp as Partial<McpConfig> | undefined;
|
|
258
|
+
const servers = mcpConfig?.servers ?? {};
|
|
271
259
|
const configEntries = (
|
|
272
260
|
Object.entries(servers) as [string, McpServerConfig][]
|
|
273
261
|
).filter(([, config]) => config && typeof config === "object");
|
|
@@ -446,13 +434,18 @@ async function handleMcpUpdate({
|
|
|
446
434
|
}): Promise<{ updated: true }> {
|
|
447
435
|
const { name, headers } = parseBody(McpUpdateParams, body);
|
|
448
436
|
|
|
449
|
-
const
|
|
450
|
-
const
|
|
437
|
+
const raw = loadRawConfig();
|
|
438
|
+
const mcpConfig = raw.mcp as Record<string, unknown> | undefined;
|
|
439
|
+
const serverMap = mcpConfig?.servers as
|
|
440
|
+
| Record<string, Record<string, unknown>>
|
|
441
|
+
| undefined;
|
|
451
442
|
|
|
452
|
-
if (!
|
|
443
|
+
if (!serverMap || !serverMap[name]) {
|
|
453
444
|
throw new NotFoundError(`MCP server "${name}" not found.`);
|
|
454
445
|
}
|
|
455
446
|
|
|
447
|
+
const server = serverMap[name];
|
|
448
|
+
|
|
456
449
|
if (headers !== undefined) {
|
|
457
450
|
const transport = server.transport as Record<string, unknown> | undefined;
|
|
458
451
|
if (
|
|
@@ -481,7 +474,7 @@ async function handleMcpUpdate({
|
|
|
481
474
|
}
|
|
482
475
|
}
|
|
483
476
|
|
|
484
|
-
|
|
477
|
+
saveRawConfig(raw);
|
|
485
478
|
triggerReload("internal_mcp_update");
|
|
486
479
|
|
|
487
480
|
return { updated: true };
|
|
@@ -501,7 +494,7 @@ async function handleMcpAdd({
|
|
|
501
494
|
body,
|
|
502
495
|
);
|
|
503
496
|
|
|
504
|
-
let transport:
|
|
497
|
+
let transport: Record<string, unknown>;
|
|
505
498
|
switch (transportType) {
|
|
506
499
|
case "stdio":
|
|
507
500
|
if (!command) {
|
|
@@ -524,16 +517,27 @@ async function handleMcpAdd({
|
|
|
524
517
|
);
|
|
525
518
|
}
|
|
526
519
|
|
|
527
|
-
const
|
|
520
|
+
const raw = loadRawConfig();
|
|
521
|
+
if (!raw.mcp) {
|
|
522
|
+
raw.mcp = { servers: {} };
|
|
523
|
+
}
|
|
524
|
+
const mcpConfig = raw.mcp as Record<string, unknown>;
|
|
525
|
+
if (!mcpConfig.servers) {
|
|
526
|
+
mcpConfig.servers = {};
|
|
527
|
+
}
|
|
528
|
+
const serverMap = mcpConfig.servers as Record<string, unknown>;
|
|
528
529
|
|
|
529
|
-
if (
|
|
530
|
+
if (serverMap[name]) {
|
|
530
531
|
throw new BadRequestError(
|
|
531
532
|
`MCP server "${name}" already exists. Remove it first with: assistant mcp remove ${name}`,
|
|
532
533
|
);
|
|
533
534
|
}
|
|
534
535
|
|
|
535
|
-
|
|
536
|
+
serverMap[name] = {
|
|
537
|
+
transport,
|
|
538
|
+
};
|
|
536
539
|
|
|
540
|
+
// Store auth headers in credential store, not config
|
|
537
541
|
if (headers && Object.keys(headers).length > 0) {
|
|
538
542
|
const ok = await setMcpHeaders(name, headers);
|
|
539
543
|
if (!ok) {
|
|
@@ -543,7 +547,7 @@ async function handleMcpAdd({
|
|
|
543
547
|
}
|
|
544
548
|
}
|
|
545
549
|
|
|
546
|
-
|
|
550
|
+
saveRawConfig(raw);
|
|
547
551
|
triggerReload("internal_mcp_add");
|
|
548
552
|
|
|
549
553
|
return { added: true };
|
|
@@ -560,7 +564,8 @@ async function handleMcpAuthRevoke({
|
|
|
560
564
|
}): Promise<{ revoked: true }> {
|
|
561
565
|
const { serverId } = parseBody(McpServerIdParams, body);
|
|
562
566
|
|
|
563
|
-
const
|
|
567
|
+
const raw = loadRawConfig();
|
|
568
|
+
const servers = (raw.mcp as Partial<McpConfig> | undefined)?.servers ?? {};
|
|
564
569
|
const serverConfig = servers[serverId];
|
|
565
570
|
|
|
566
571
|
if (!serverConfig) {
|
|
@@ -597,29 +602,32 @@ async function handleMcpRemove({
|
|
|
597
602
|
}): Promise<{ removed: true }> {
|
|
598
603
|
const { name } = parseBody(McpRemoveParams, body);
|
|
599
604
|
|
|
600
|
-
const
|
|
601
|
-
const
|
|
605
|
+
const raw = loadRawConfig();
|
|
606
|
+
const mcpConfig = raw.mcp as Record<string, unknown> | undefined;
|
|
607
|
+
const serverMap = mcpConfig?.servers as Record<string, unknown> | undefined;
|
|
602
608
|
|
|
603
|
-
if (!
|
|
609
|
+
if (!serverMap || !serverMap[name]) {
|
|
604
610
|
throw new NotFoundError(`MCP server "${name}" not found.`);
|
|
605
611
|
}
|
|
606
612
|
|
|
607
|
-
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
|
|
613
|
+
// Best-effort cleanup of credentials stored for this server
|
|
614
|
+
const serverConfig = serverMap[name] as Record<string, unknown>;
|
|
615
|
+
const transport = serverConfig?.transport as
|
|
616
|
+
| Record<string, unknown>
|
|
617
|
+
| undefined;
|
|
618
|
+
if (transport?.type === "sse" || transport?.type === "streamable-http") {
|
|
611
619
|
try {
|
|
612
620
|
await Promise.all([
|
|
613
621
|
deleteMcpOAuthCredentials(name),
|
|
614
622
|
deleteMcpHeaders(name),
|
|
615
623
|
]);
|
|
616
624
|
} catch {
|
|
617
|
-
//
|
|
625
|
+
// Ignore — credentials may not exist
|
|
618
626
|
}
|
|
619
627
|
}
|
|
620
628
|
|
|
621
|
-
delete
|
|
622
|
-
|
|
629
|
+
delete serverMap[name];
|
|
630
|
+
saveRawConfig(raw);
|
|
623
631
|
triggerReload("internal_mcp_remove");
|
|
624
632
|
|
|
625
633
|
return { removed: true };
|
|
@@ -22,8 +22,8 @@ import { PassThrough, Readable } from "node:stream";
|
|
|
22
22
|
|
|
23
23
|
import { z } from "zod";
|
|
24
24
|
|
|
25
|
+
import { getPlatformAssistantId } from "../../config/env.js";
|
|
25
26
|
import { invalidateConfigCache } from "../../config/loader.js";
|
|
26
|
-
import { resolvePlatformAssistantId } from "../../config/platform-identity.js";
|
|
27
27
|
import { getAssistantName } from "../../daemon/identity-helpers.js";
|
|
28
28
|
import { runAsyncSqlite } from "../../persistence/db-async-query.js";
|
|
29
29
|
import {
|
|
@@ -236,15 +236,28 @@ interface ExportManifestInputs {
|
|
|
236
236
|
/**
|
|
237
237
|
* Resolve the `assistant.id` for an export.
|
|
238
238
|
*
|
|
239
|
-
*
|
|
240
|
-
*
|
|
241
|
-
* non-empty, so we fall back to
|
|
242
|
-
* the empty string.
|
|
239
|
+
* Mirrors `platform/client.ts`'s precedence: in-memory override (set at
|
|
240
|
+
* daemon startup or by secret-routes) → credential store → daemon-internal
|
|
241
|
+
* fallback. The schema requires `id` to be non-empty, so we fall back to
|
|
242
|
+
* `DAEMON_INTERNAL_ASSISTANT_ID` rather than the empty string.
|
|
243
243
|
*/
|
|
244
244
|
async function resolveAssistantId(): Promise<string> {
|
|
245
|
-
const
|
|
246
|
-
if (
|
|
247
|
-
return
|
|
245
|
+
const inMemory = getPlatformAssistantId();
|
|
246
|
+
if (inMemory) {
|
|
247
|
+
return inMemory;
|
|
248
|
+
}
|
|
249
|
+
try {
|
|
250
|
+
const stored = await getSecureKeyAsync(
|
|
251
|
+
credentialKey("vellum", "platform_assistant_id"),
|
|
252
|
+
);
|
|
253
|
+
if (stored) {
|
|
254
|
+
return stored;
|
|
255
|
+
}
|
|
256
|
+
} catch (err) {
|
|
257
|
+
log.warn(
|
|
258
|
+
{ err },
|
|
259
|
+
"Failed to read platform_assistant_id from credential store; falling back to daemon-internal id",
|
|
260
|
+
);
|
|
248
261
|
}
|
|
249
262
|
return DAEMON_INTERNAL_ASSISTANT_ID;
|
|
250
263
|
}
|
|
@@ -39,17 +39,7 @@ import {
|
|
|
39
39
|
} from "@vellumai/service-contracts/platform-credential";
|
|
40
40
|
import { z } from "zod";
|
|
41
41
|
|
|
42
|
-
import {
|
|
43
|
-
setPlatformAssistantId,
|
|
44
|
-
setPlatformBaseUrl,
|
|
45
|
-
setPlatformOrganizationId,
|
|
46
|
-
setPlatformUserId,
|
|
47
|
-
} from "../../config/env.js";
|
|
48
42
|
import { isPlatformRemote } from "../../config/env-registry.js";
|
|
49
|
-
import {
|
|
50
|
-
resolvePlatformOrganizationId,
|
|
51
|
-
resolvePlatformUserId,
|
|
52
|
-
} from "../../config/platform-identity.js";
|
|
53
43
|
import {
|
|
54
44
|
registerCallbackRoute,
|
|
55
45
|
resolvePlatformCallbackRegistrationContext,
|
|
@@ -299,12 +289,24 @@ async function handlePlatformStatus(
|
|
|
299
289
|
): Promise<PlatformStatusResponse> {
|
|
300
290
|
const context = await resolvePlatformCallbackRegistrationContext();
|
|
301
291
|
|
|
302
|
-
const [
|
|
303
|
-
|
|
304
|
-
|
|
292
|
+
const [orgIdRaw, userIdRaw, webhookSecretRaw] = await Promise.all([
|
|
293
|
+
getSecureKeyAsync(
|
|
294
|
+
credentialKey(
|
|
295
|
+
CREDENTIAL_KEYS.organizationId.service,
|
|
296
|
+
CREDENTIAL_KEYS.organizationId.field,
|
|
297
|
+
),
|
|
298
|
+
),
|
|
299
|
+
getSecureKeyAsync(
|
|
300
|
+
credentialKey(
|
|
301
|
+
CREDENTIAL_KEYS.userId.service,
|
|
302
|
+
CREDENTIAL_KEYS.userId.field,
|
|
303
|
+
),
|
|
304
|
+
),
|
|
305
305
|
getSecureKeyAsync(credentialKey("vellum", "webhook_secret")),
|
|
306
306
|
]);
|
|
307
307
|
|
|
308
|
+
const organizationId = orgIdRaw?.trim() ?? "";
|
|
309
|
+
const userId = userIdRaw?.trim() ?? "";
|
|
308
310
|
const hasWebhookSecret = !!webhookSecretRaw;
|
|
309
311
|
|
|
310
312
|
return {
|
|
@@ -465,11 +467,6 @@ async function handlePlatformDisconnect(
|
|
|
465
467
|
);
|
|
466
468
|
}
|
|
467
469
|
|
|
468
|
-
setPlatformBaseUrl(undefined);
|
|
469
|
-
setPlatformAssistantId(undefined);
|
|
470
|
-
setPlatformOrganizationId(undefined);
|
|
471
|
-
setPlatformUserId(undefined);
|
|
472
|
-
|
|
473
470
|
// Notify connected clients
|
|
474
471
|
broadcastMessage({ type: "platform_disconnected" });
|
|
475
472
|
|
|
@@ -159,31 +159,3 @@ describe("serializeConversationSummary · enabledPlugins", () => {
|
|
|
159
159
|
expect("enabledPlugins" in summary).toBe(false);
|
|
160
160
|
});
|
|
161
161
|
});
|
|
162
|
-
|
|
163
|
-
describe("serializeConversationSummary · title keys", () => {
|
|
164
|
-
test("resolves a stored title key for the locale", () => {
|
|
165
|
-
const summary = serializeConversationSummary({
|
|
166
|
-
conversation: makeConversationRow({
|
|
167
|
-
title: "conversation.title.generating",
|
|
168
|
-
}),
|
|
169
|
-
displayMeta: { displayOrder: null, isPinned: false, groupId: null },
|
|
170
|
-
parentCache: new Map(),
|
|
171
|
-
isProcessing: false,
|
|
172
|
-
locale: "es",
|
|
173
|
-
});
|
|
174
|
-
expect(summary.title).toBe("Generando título...");
|
|
175
|
-
expect("titleState" in summary).toBe(false);
|
|
176
|
-
});
|
|
177
|
-
|
|
178
|
-
test("passes a stored display string through", () => {
|
|
179
|
-
const summary = serialize(
|
|
180
|
-
makeConversationRow({ title: "Untitled Conversation" }),
|
|
181
|
-
);
|
|
182
|
-
expect(summary.title).toBe("Untitled Conversation");
|
|
183
|
-
});
|
|
184
|
-
|
|
185
|
-
test("passes a custom title through", () => {
|
|
186
|
-
const summary = serialize(makeConversationRow({ title: "Weekly planning" }));
|
|
187
|
-
expect(summary.title).toBe("Weekly planning");
|
|
188
|
-
});
|
|
189
|
-
});
|
|
@@ -8,10 +8,6 @@
|
|
|
8
8
|
|
|
9
9
|
import { parseChannelId } from "../../channels/types.js";
|
|
10
10
|
import { normalizeConversationType } from "../../daemon/message-types/shared.js";
|
|
11
|
-
import {
|
|
12
|
-
resolveConversationTitle,
|
|
13
|
-
type SupportedLocale,
|
|
14
|
-
} from "../../i18n/index.js";
|
|
15
11
|
import { buildChannelBindingMetadata } from "../../messaging/channel-binding-metadata.js";
|
|
16
12
|
import {
|
|
17
13
|
type AttentionState,
|
|
@@ -82,7 +78,6 @@ interface ForkLineage {
|
|
|
82
78
|
function buildForkLineage(
|
|
83
79
|
conversation: ConversationRow,
|
|
84
80
|
parentCache: Map<string, ConversationRow | null>,
|
|
85
|
-
locale?: SupportedLocale,
|
|
86
81
|
): ForkLineage {
|
|
87
82
|
const parentConversationId = conversation.forkParentConversationId;
|
|
88
83
|
const parentMessageId = conversation.forkParentMessageId;
|
|
@@ -106,7 +101,7 @@ function buildForkLineage(
|
|
|
106
101
|
forkParent: {
|
|
107
102
|
conversationId: parentConversationId,
|
|
108
103
|
messageId: parentMessageId,
|
|
109
|
-
title:
|
|
104
|
+
title: parentConversation.title ?? "Untitled",
|
|
110
105
|
},
|
|
111
106
|
};
|
|
112
107
|
}
|
|
@@ -183,11 +178,6 @@ export function serializeConversationSummary(params: {
|
|
|
183
178
|
* with no daemon-store coupling.
|
|
184
179
|
*/
|
|
185
180
|
isProcessing: boolean;
|
|
186
|
-
/**
|
|
187
|
-
* Locale used to resolve stored title keys. Omitted locale is English
|
|
188
|
-
* inside {@link resolveConversationTitle}.
|
|
189
|
-
*/
|
|
190
|
-
locale?: SupportedLocale;
|
|
191
181
|
}) {
|
|
192
182
|
const {
|
|
193
183
|
conversation,
|
|
@@ -196,15 +186,14 @@ export function serializeConversationSummary(params: {
|
|
|
196
186
|
displayMeta,
|
|
197
187
|
parentCache,
|
|
198
188
|
isProcessing,
|
|
199
|
-
locale,
|
|
200
189
|
} = params;
|
|
201
190
|
const originChannel = parseChannelId(conversation.originChannel);
|
|
202
191
|
const assistantAttention = buildAssistantAttention(attentionState);
|
|
203
|
-
const forkLineage = buildForkLineage(conversation, parentCache
|
|
192
|
+
const forkLineage = buildForkLineage(conversation, parentCache);
|
|
204
193
|
|
|
205
194
|
return {
|
|
206
195
|
id: conversation.id,
|
|
207
|
-
title:
|
|
196
|
+
title: conversation.title ?? "Untitled",
|
|
208
197
|
createdAt: conversation.createdAt,
|
|
209
198
|
updatedAt: conversation.updatedAt,
|
|
210
199
|
lastMessageAt: conversation.lastMessageAt,
|
|
@@ -264,7 +253,6 @@ export function serializeConversationSummary(params: {
|
|
|
264
253
|
*/
|
|
265
254
|
export function buildConversationDetailResponse(
|
|
266
255
|
conversationId: string,
|
|
267
|
-
locale?: SupportedLocale,
|
|
268
256
|
): { conversation: ReturnType<typeof serializeConversationSummary> } | null {
|
|
269
257
|
const conversation = getConversation(conversationId);
|
|
270
258
|
if (!conversation || conversation.conversationType === "private") {
|
|
@@ -286,7 +274,6 @@ export function buildConversationDetailResponse(
|
|
|
286
274
|
// Checks in-memory flag first (hot path), falls back to the
|
|
287
275
|
// persisted `processing_started_at` column for cold conversations.
|
|
288
276
|
isProcessing: isConversationProcessing(conversation.id),
|
|
289
|
-
locale,
|
|
290
277
|
}),
|
|
291
278
|
};
|
|
292
279
|
}
|
|
@@ -4,7 +4,6 @@ import {
|
|
|
4
4
|
conversationMetadataSyncTag,
|
|
5
5
|
SYNC_TAGS,
|
|
6
6
|
} from "../../daemon/message-types/sync.js";
|
|
7
|
-
import { resolveConversationTitle } from "../../i18n/index.js";
|
|
8
7
|
import { syncAvatarToPlatform } from "../../platform/sync-avatar.js";
|
|
9
8
|
import { getAvatarImagePath } from "../../util/platform.js";
|
|
10
9
|
import { broadcastMessage } from "../assistant-event-hub.js";
|
|
@@ -258,7 +257,7 @@ export function publishConversationTitleChanged(
|
|
|
258
257
|
{
|
|
259
258
|
type: "conversation_title_updated",
|
|
260
259
|
conversationId,
|
|
261
|
-
title
|
|
260
|
+
title,
|
|
262
261
|
},
|
|
263
262
|
conversationId,
|
|
264
263
|
);
|
package/src/schedule/worker.ts
CHANGED
|
@@ -195,7 +195,7 @@ async function main(): Promise<void> {
|
|
|
195
195
|
//
|
|
196
196
|
// Bounded by MCP_STARTUP_GRACE_MS: unreachable servers must not hold the
|
|
197
197
|
// schedules that do not use them. The connect runs on past the deadline.
|
|
198
|
-
const mcpStartup = startConfiguredMcpServers();
|
|
198
|
+
const mcpStartup = startConfiguredMcpServers(getConfig().mcp);
|
|
199
199
|
await Promise.race([
|
|
200
200
|
mcpStartup,
|
|
201
201
|
// Unref'd so a connect that beats the deadline leaves nothing pending.
|
|
@@ -11,11 +11,6 @@ import { getLogger } from "../util/logger.js";
|
|
|
11
11
|
const log = getLogger("ces-rpc-record-backend");
|
|
12
12
|
|
|
13
13
|
export interface CredentialRecordBackend {
|
|
14
|
-
/**
|
|
15
|
-
* Transport id. `"ces-rpc"` is the attached CES socket backend; live
|
|
16
|
-
* catalog listing fails over to CES HTTP when that transport is down.
|
|
17
|
-
*/
|
|
18
|
-
readonly name?: string;
|
|
19
14
|
isAvailable(): boolean;
|
|
20
15
|
get(account: string): Promise<CredentialRecord | undefined>;
|
|
21
16
|
set(account: string, record: CredentialRecord): Promise<boolean>;
|
|
@@ -34,8 +29,6 @@ export interface CredentialRecordBackend {
|
|
|
34
29
|
}
|
|
35
30
|
|
|
36
31
|
export class CesRpcRecordBackend implements CredentialRecordBackend {
|
|
37
|
-
readonly name = "ces-rpc";
|
|
38
|
-
|
|
39
32
|
constructor(private readonly client: CesClient) {}
|
|
40
33
|
|
|
41
34
|
isAvailable(): boolean {
|
|
@@ -33,6 +33,7 @@
|
|
|
33
33
|
import { readdir } from "node:fs/promises";
|
|
34
34
|
import { join } from "node:path";
|
|
35
35
|
|
|
36
|
+
import type { SkillSummary } from "../config/skills.js";
|
|
36
37
|
import type { TrustContext } from "../daemon/trust-context-types.js";
|
|
37
38
|
import type { TrustClass } from "../runtime/actor-trust-resolver.js";
|
|
38
39
|
import { truncate as truncateText } from "../util/truncate.js";
|
|
@@ -55,6 +56,15 @@ export interface AdvisorContextSources {
|
|
|
55
56
|
* from the catalog section, mirroring the `skill_load` gate.
|
|
56
57
|
*/
|
|
57
58
|
enabledPluginSet?: ReadonlySet<string> | null;
|
|
59
|
+
/**
|
|
60
|
+
* Pre-resolved skill catalog, typically the parent conversation's warm
|
|
61
|
+
* `skillProjectionCache.catalog`. Passing it keeps the synchronous on-disk
|
|
62
|
+
* catalog scan out of the consult path (and matches the catalog view the
|
|
63
|
+
* parent turn's tool projection used). When absent, the section falls back
|
|
64
|
+
* to a fresh `loadSkillCatalog()` scan, the same call every agent turn's
|
|
65
|
+
* projection already makes.
|
|
66
|
+
*/
|
|
67
|
+
skillCatalog?: readonly SkillSummary[];
|
|
58
68
|
}
|
|
59
69
|
|
|
60
70
|
/** Cap a block so the assembled context never balloons the consult prompt. */
|
|
@@ -104,6 +114,7 @@ async function buildToolsSection(
|
|
|
104
114
|
*/
|
|
105
115
|
async function buildSkillsSection(
|
|
106
116
|
enabledPluginSet: ReadonlySet<string> | null | undefined,
|
|
117
|
+
preResolvedCatalog: readonly SkillSummary[] | undefined,
|
|
107
118
|
): Promise<string | null> {
|
|
108
119
|
try {
|
|
109
120
|
const [
|
|
@@ -119,17 +130,19 @@ async function buildSkillsSection(
|
|
|
119
130
|
]);
|
|
120
131
|
const config = getConfig();
|
|
121
132
|
const pluginScope = enabledPluginSet ?? null;
|
|
122
|
-
const catalog = loadSkillCatalog().filter(
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
+
const catalog = (preResolvedCatalog ?? loadSkillCatalog()).filter(
|
|
134
|
+
(skill) => {
|
|
135
|
+
if (
|
|
136
|
+
pluginScope !== null &&
|
|
137
|
+
skill.owner?.kind === "plugin" &&
|
|
138
|
+
!pluginScope.has(skill.owner.id)
|
|
139
|
+
) {
|
|
140
|
+
return false;
|
|
141
|
+
}
|
|
142
|
+
const flagKey = skillFlagKey(skill);
|
|
143
|
+
return !flagKey || isAssistantFeatureFlagEnabled(flagKey, config);
|
|
144
|
+
},
|
|
145
|
+
);
|
|
133
146
|
if (catalog.length === 0) {
|
|
134
147
|
return null;
|
|
135
148
|
}
|
|
@@ -371,7 +384,7 @@ export async function buildAdvisorContext(
|
|
|
371
384
|
const sections = await Promise.all(
|
|
372
385
|
[
|
|
373
386
|
buildToolsSection(sources.allowedToolNames),
|
|
374
|
-
buildSkillsSection(sources.enabledPluginSet),
|
|
387
|
+
buildSkillsSection(sources.enabledPluginSet, sources.skillCatalog),
|
|
375
388
|
buildWorkspaceSection(sources),
|
|
376
389
|
].map((section) => withSectionTimeout(section, sectionTimeoutMs)),
|
|
377
390
|
);
|
|
@@ -90,9 +90,7 @@ describe("executeAcpListAgents", () => {
|
|
|
90
90
|
const codex = parsed.agents.find((a: { id: string }) => a.id === "codex");
|
|
91
91
|
expect(codex.available).toBe(false);
|
|
92
92
|
expect(codex.unavailableReason).toBe("'codex-acp' is not on PATH");
|
|
93
|
-
expect(codex.setupHint).toBe(
|
|
94
|
-
"bun add -g @agentclientprotocol/codex-acp@1.10.0",
|
|
95
|
-
);
|
|
93
|
+
expect(codex.setupHint).toBe("bun add -g @agentclientprotocol/codex-acp");
|
|
96
94
|
|
|
97
95
|
const claude = parsed.agents.find((a: { id: string }) => a.id === "claude");
|
|
98
96
|
expect(claude.available).toBe(true);
|