@vellumai/assistant 0.12.2 → 0.12.3-staging.2
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/.env.example +2 -0
- package/AGENTS.md +1 -1
- package/ARCHITECTURE.md +43 -29
- package/Dockerfile +63 -0
- package/docs/architecture/integrations.md +7 -0
- package/docs/architecture/memory.md +17 -2
- package/docs/architecture/security.md +10 -5
- package/docs/architecture/turn-actor.md +2 -0
- package/docs/credential-execution-service.md +1 -1
- package/docs/desktop-browser-cli.md +50 -5
- package/docs/live-voice-task-outcomes.md +100 -0
- package/docs/mode-sessions.md +183 -0
- package/docs/voice-input-diagnostics.md +58 -0
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/package.json +2 -1
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/src/__tests__/secret-detection.test.ts +1 -0
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/src/index.ts +1 -0
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/src/integration-categories.ts +36 -0
- package/node_modules/@vellumai/ces-client/node_modules/@vellumai/service-contracts/src/secret-detection.ts +4 -1
- package/node_modules/@vellumai/environments/src/shell.test.ts +21 -0
- package/node_modules/@vellumai/environments/src/shell.ts +24 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/package.json +2 -1
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/src/__tests__/secret-detection.test.ts +1 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/src/index.ts +1 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/src/integration-categories.ts +36 -0
- package/node_modules/@vellumai/gateway-client/node_modules/@vellumai/service-contracts/src/secret-detection.ts +4 -1
- package/node_modules/@vellumai/gateway-client/src/gateway-ipc-contracts.ts +20 -0
- package/node_modules/@vellumai/gateway-client/src/inbound-contract.ts +8 -2
- package/node_modules/@vellumai/gateway-client/src/index.ts +4 -1
- package/node_modules/@vellumai/gateway-client/src/outbound-contract.ts +38 -7
- package/node_modules/@vellumai/gateway-client/src/trust-verdict-contract.ts +5 -6
- package/node_modules/@vellumai/service-contracts/package.json +2 -1
- package/node_modules/@vellumai/service-contracts/src/__tests__/secret-detection.test.ts +1 -0
- package/node_modules/@vellumai/service-contracts/src/index.ts +1 -0
- package/node_modules/@vellumai/service-contracts/src/integration-categories.ts +36 -0
- package/node_modules/@vellumai/service-contracts/src/secret-detection.ts +4 -1
- package/node_modules/@vellumai/slack-text/src/index.ts +4 -8
- package/openapi.yaml +716 -16
- package/package.json +1 -1
- package/scripts/smoke-desktop-browser-cli.ts +11 -26
- package/scripts/smoke-desktop-window-theme.ts +2 -3
- package/scripts/sync-llm-catalog.ts +3 -0
- package/scripts/voice-ttft-spike.ts +2 -2
- package/src/__tests__/agent-loop-output-hooks.test.ts +150 -1
- package/src/__tests__/agent-loop-provider-error-recording.test.ts +87 -19
- package/src/__tests__/agent-loop.test.ts +259 -0
- package/src/__tests__/agent-wake-delegation-prompt.test.ts +64 -2
- package/src/__tests__/annotate-activity-metadata.test.ts +3 -1
- package/src/__tests__/annotate-risk-options.test.ts +2 -0
- package/src/__tests__/answered-question-persistence.test.ts +2 -0
- package/src/__tests__/anthropic-gateway-shared.test.ts +22 -0
- package/src/__tests__/anthropic-provider.test.ts +55 -0
- package/src/__tests__/approval-interception-trust-gates.test.ts +40 -0
- package/src/__tests__/approval-message-composer.test.ts +1 -118
- package/src/__tests__/approval-routes-http.test.ts +3 -0
- package/src/__tests__/assistant-event-hub-connection-history.test.ts +111 -0
- package/src/__tests__/assistant-event-hub-targeted.test.ts +50 -0
- package/src/__tests__/assistant-event-targeting.test.ts +186 -0
- package/src/__tests__/assistant-stream-state.test.ts +29 -9
- package/src/__tests__/attachments-store.test.ts +22 -3
- package/src/__tests__/browser-fill-credential.test.ts +11 -22
- package/src/__tests__/btw-routes.test.ts +4 -1
- package/src/__tests__/build-persisted-content.test.ts +1 -1
- package/src/__tests__/call-conversation-messages.test.ts +5 -0
- package/src/__tests__/call-recovery.test.ts +7 -2
- package/src/__tests__/call-routes-http.test.ts +12 -0
- package/src/__tests__/call-store.test.ts +7 -2
- package/src/__tests__/channel-approval.test.ts +9 -14
- package/src/__tests__/channel-reply-delivery.test.ts +56 -0
- package/src/__tests__/channel-retry-sweep.test.ts +9 -0
- package/src/__tests__/chat-credential-redaction.test.ts +23 -0
- package/src/__tests__/chat-reveal-guard-priming.test.ts +2 -0
- package/src/__tests__/checker.test.ts +11 -3
- package/src/__tests__/client-os-metadata-persistence.test.ts +35 -1
- package/src/__tests__/computer-use-screenshot-attachments.test.ts +411 -0
- package/src/__tests__/computer-use-screenshot-selection.test.ts +50 -0
- package/src/__tests__/computer-use-skill-manifest-regression.test.ts +0 -25
- package/src/__tests__/computer-use-tools.test.ts +1 -233
- package/src/__tests__/config-model-image-provider.test.ts +39 -0
- package/src/__tests__/config-schema.test.ts +16 -0
- package/src/__tests__/config-watcher.test.ts +24 -0
- package/src/__tests__/context-search-agent-runner.test.ts +260 -1
- package/src/__tests__/context-search-fanout.test.ts +1 -1
- package/src/__tests__/context-search-types.test.ts +7 -7
- package/src/__tests__/conversation-agent-loop-disk-pressure.test.ts +8 -2
- package/src/__tests__/conversation-agent-loop-fatal-cleanup.test.ts +2 -0
- package/src/__tests__/conversation-agent-loop-inference-profile.test.ts +2 -0
- package/src/__tests__/conversation-agent-loop-overflow.test.ts +2 -0
- package/src/__tests__/conversation-agent-loop.test.ts +797 -16
- package/src/__tests__/conversation-app-control-lifecycle.test.ts +53 -1
- package/src/__tests__/conversation-attachments.test.ts +106 -0
- package/src/__tests__/conversation-evictor.test.ts +62 -37
- package/src/__tests__/conversation-fork-crud.test.ts +191 -0
- package/src/__tests__/conversation-history-boundary-repair-failure.test.ts +174 -0
- package/src/__tests__/conversation-loop-db-lock-resilience.test.ts +2 -0
- package/src/__tests__/conversation-process-app-control-preactivation.test.ts +2 -0
- package/src/__tests__/conversation-rendered-delegation-state.test.ts +276 -0
- package/src/__tests__/conversation-retry-route.test.ts +22 -0
- package/src/__tests__/conversation-routes-disk-view.test.ts +2 -0
- package/src/__tests__/conversation-routes-enabled-plugins.test.ts +2 -0
- package/src/__tests__/conversation-routes-guardian-reply.test.ts +10 -0
- package/src/__tests__/conversation-routes-hidden-queue.test.ts +2 -0
- package/src/__tests__/conversation-routes-slash-commands.test.ts +2 -0
- package/src/__tests__/conversation-runtime-assembly.test.ts +29 -0
- package/src/__tests__/conversation-surface-snapshots.test.ts +543 -0
- package/src/__tests__/conversation-surfaces-action-delivery.test.ts +151 -0
- package/src/__tests__/conversation-surfaces-point-at-budget.test.ts +63 -1
- package/src/__tests__/conversation-tool-setup-attribution.test.ts +23 -0
- package/src/__tests__/conversation-undo.test.ts +61 -0
- package/src/__tests__/credential-execution-client.test.ts +72 -55
- package/src/__tests__/credential-prompt-route.test.ts +35 -3
- package/src/__tests__/cu-unified-flow.test.ts +82 -1
- package/src/__tests__/db-conversation-tool-surface.test.ts +221 -0
- package/src/__tests__/db-mode-sessions-migration.test.ts +175 -0
- package/src/__tests__/deterministic-verification-control-plane.test.ts +2 -0
- package/src/__tests__/dm-backfill.test.ts +91 -1
- package/src/__tests__/document-create-route.test.ts +88 -0
- package/src/__tests__/document-sync-tags.test.ts +27 -0
- package/src/__tests__/emit-signal-routing-intent.test.ts +142 -2
- package/src/__tests__/events-tail-route.test.ts +58 -0
- package/src/__tests__/evict-conversations-for-reload.test.ts +57 -8
- package/src/__tests__/guardian-action-sweep.test.ts +16 -0
- package/src/__tests__/guardian-dispatch.test.ts +13 -0
- package/src/__tests__/headless-browser-interactions.test.ts +64 -20
- package/src/__tests__/heartbeat-service.test.ts +2 -59
- package/src/__tests__/helpers/mock-conversation.ts +21 -0
- package/src/__tests__/helpers/native-web-search-harness.ts +2 -0
- package/src/__tests__/helpers/verification-sessions-ipc-sim.ts +5 -0
- package/src/__tests__/history-repair.test.ts +53 -0
- package/src/__tests__/host-cu-proxy.test.ts +46 -2
- package/src/__tests__/http-user-message-parity.test.ts +2 -0
- package/src/__tests__/image-credentials.test.ts +49 -0
- package/src/__tests__/image-service-dispatcher.test.ts +45 -0
- package/src/__tests__/inference-profile-session-handler.test.ts +26 -0
- package/src/__tests__/interrupt-on-send.test.ts +57 -43
- package/src/__tests__/interrupt-turn-note.test.ts +5 -6
- package/src/__tests__/list-messages-tool-merge.test.ts +85 -1
- package/src/__tests__/llm-catalog-parity.test.ts +27 -4
- package/src/__tests__/media-generate-image.test.ts +49 -1
- package/src/__tests__/message-provenance-contact-id.test.ts +69 -0
- package/src/__tests__/migration-export-to-gcs.test.ts +142 -0
- package/src/__tests__/mode-session-history.test.ts +245 -0
- package/src/__tests__/mode-session-recovery.test.ts +222 -0
- package/src/__tests__/mode-session-wire.test.ts +141 -0
- package/src/__tests__/notification-guardian-path.test.ts +7 -0
- package/src/__tests__/notification-telegram-adapter.test.ts +2 -2
- package/src/__tests__/notification-vellum-adapter.test.ts +34 -0
- package/src/__tests__/oauth-apps-routes.test.ts +1 -0
- package/src/__tests__/oauth-commands-routes.test.ts +114 -101
- package/src/__tests__/oauth-connect-orchestrator.test.ts +2 -0
- package/src/__tests__/oauth-provider-serializer.test.ts +13 -0
- package/src/__tests__/oauth-providers-routes.test.ts +3 -0
- package/src/__tests__/outbound-slack-persistence.test.ts +2 -0
- package/src/__tests__/persist-media-references.test.ts +50 -0
- package/src/__tests__/persistence-secret-redaction.test.ts +2 -0
- package/src/__tests__/plugin-api-provider.test.ts +5 -0
- package/src/__tests__/plugin-api-resolve-credential.test.ts +97 -0
- package/src/__tests__/plugin-import-boundary-guard.test.ts +9 -1
- package/src/__tests__/process-message-display-content.test.ts +56 -0
- package/src/__tests__/reaction-persistence.test.ts +5 -0
- package/src/__tests__/request-secret-standalone-channel-gate.test.ts +25 -9
- package/src/__tests__/run-conversation-turn-persistence.test.ts +138 -1
- package/src/__tests__/runtime-events-sse-reconnect.test.ts +1 -1
- package/src/__tests__/schedule-routes.test.ts +20 -0
- package/src/__tests__/scheduler-result-notification.test.ts +23 -4
- package/src/__tests__/script-proxy-certs.test.ts +1 -1
- package/src/__tests__/scripted-turn-metadata-persistence.test.ts +73 -0
- package/src/__tests__/secret-ingress-http.test.ts +2 -0
- package/src/__tests__/secret-routes-platform-proxy.test.ts +86 -31
- package/src/__tests__/secret-routes-scrub.test.ts +22 -27
- package/src/__tests__/secret-scanner.test.ts +20 -0
- package/src/__tests__/secure-keys-managed-failover.test.ts +8 -0
- package/src/__tests__/secure-keys.test.ts +50 -4
- package/src/__tests__/send-endpoint-busy.test.ts +163 -1
- package/src/__tests__/server-history-render.test.ts +91 -1
- package/src/__tests__/server-tool-pairing.test.ts +107 -0
- package/src/__tests__/settings-routes.test.ts +50 -1
- package/src/__tests__/skill-script-runner-sandbox.test.ts +32 -0
- package/src/__tests__/skills.test.ts +5 -4
- package/src/__tests__/subagent-fork-notifications.test.ts +1 -2
- package/src/__tests__/subagent-manager-notify.test.ts +1 -2
- package/src/__tests__/subagent-notify-parent.test.ts +146 -39
- package/src/__tests__/subagent-notify-stale-rebuild.test.ts +2 -4
- package/src/__tests__/subagent-tool-gate-mode.test.ts +226 -0
- package/src/__tests__/surface-completion-in-flight-snapshot.test.ts +2 -0
- package/src/__tests__/terminal-tools.test.ts +8 -0
- package/src/__tests__/thread-backfill.test.ts +53 -0
- package/src/__tests__/tool-preview-lifecycle.test.ts +2 -0
- package/src/__tests__/tool-result-follow-up.test.ts +99 -0
- package/src/__tests__/tool-result-metadata-plumbing.test.ts +66 -1
- package/src/__tests__/tool-start-timestamp.test.ts +2 -0
- package/src/__tests__/twilio-routes.test.ts +1 -0
- package/src/__tests__/unicode.test.ts +36 -0
- package/src/__tests__/web-search-backend-failure.test.ts +1 -1
- package/src/activation/progress-store.test.ts +12 -7
- package/src/agent/loop.ts +136 -53
- package/src/agent/tool-result-follow-up.ts +70 -0
- package/src/api/attachment-provenance.test.ts +68 -0
- package/src/api/computer-use-tool.test.ts +55 -0
- package/src/api/computer-use-tool.ts +27 -0
- package/src/api/events/assistant-outbound-attachment.ts +3 -0
- package/src/api/events/assistant-turn-start.ts +3 -0
- package/src/api/events/desktop-activity-changed.ts +10 -0
- package/src/api/events/generation-handoff.ts +2 -0
- package/src/api/events/message-complete.ts +2 -0
- package/src/api/events/notification-conversation-created.ts +14 -16
- package/src/api/events/notification-intent.ts +4 -2
- package/src/api/events/question-request.ts +1 -0
- package/src/api/events/tool-result.ts +85 -0
- package/src/api/events/tool-use-start.ts +3 -0
- package/src/api/events/user-message-echo.ts +3 -0
- package/src/api/index.ts +42 -6
- package/src/api/mode-session.test.ts +131 -0
- package/src/api/mode-session.ts +148 -0
- package/src/api/remember-tool.ts +15 -0
- package/src/api/responses/conversation-message.ts +9 -0
- package/src/approvals/AGENTS.md +4 -2
- package/src/approvals/approval-primitive.ts +5 -2
- package/src/approvals/scoped-approval-grants.ts +6 -2
- package/src/browser/__tests__/operations.test.ts +29 -0
- package/src/browser/operation-meta.ts +2 -1
- package/src/browser/operations.ts +29 -0
- package/src/browser/virtual-desktop-target.ts +2 -9
- package/src/bundler/bundle-signer.ts +1 -3
- package/src/calls/__tests__/barge-in-guard.test.ts +3 -0
- package/src/calls/__tests__/call-controller.test.ts +94 -0
- package/src/calls/__tests__/call-funnel-telemetry.test.ts +204 -0
- package/src/calls/__tests__/voice-control-protocol.test.ts +15 -0
- package/src/calls/__tests__/voice-escalation-judge.test.ts +209 -0
- package/src/calls/__tests__/voice-leg-coordinator.test.ts +168 -0
- package/src/{live-voice/__tests__/live-voice-metrics.test.ts → calls/__tests__/voice-metrics.test.ts} +32 -38
- package/src/calls/__tests__/voice-session-bridge.test.ts +576 -122
- package/src/calls/barge-in-guard.ts +5 -0
- package/src/calls/call-controller.ts +196 -1
- package/src/calls/call-domain.ts +4 -0
- package/src/calls/call-store.ts +87 -2
- package/src/calls/guardian-action-sweep.ts +22 -8
- package/src/calls/media-stream-audio-transcode.ts +1 -3
- package/src/calls/typesafe-noul.ts +156 -0
- package/src/calls/voice-control-protocol.ts +6 -0
- package/src/calls/voice-escalation-judge.ts +145 -0
- package/src/calls/voice-escalation-target.ts +10 -0
- package/src/calls/voice-leg-coordinator.ts +121 -3
- package/src/{live-voice/live-voice-metrics.ts → calls/voice-metrics.ts} +94 -87
- package/src/calls/voice-session-bridge.ts +256 -112
- package/src/calls/voice-triage-escalate.ts +7 -0
- package/src/cli/__tests__/roadmap-cli.test.ts +4 -41
- package/src/cli/commands/__tests__/cli-test-harness.ts +21 -3
- package/src/cli/commands/__tests__/notifications.test.ts +35 -10
- package/src/cli/commands/__tests__/plugins.test.ts +20 -1
- package/src/cli/commands/__tests__/schedules.test.ts +14 -0
- package/src/cli/commands/bash.help.ts +4 -3
- package/src/cli/commands/browser.help.ts +9 -6
- package/src/cli/commands/browser.ts +0 -1
- package/src/cli/commands/clients.help.ts +46 -0
- package/src/cli/commands/clients.ts +116 -0
- package/src/cli/commands/credentials.help.ts +9 -4
- package/src/cli/commands/notifications.help.ts +16 -2
- package/src/cli/commands/notifications.ts +30 -8
- package/src/cli/commands/oauth/index.help.ts +10 -0
- package/src/cli/commands/oauth/providers.ts +12 -0
- package/src/cli/commands/oauth/request.test.ts +179 -2
- package/src/cli/commands/oauth/request.ts +41 -10
- package/src/cli/commands/plugins.ts +12 -5
- package/src/cli/commands/roadmap.help.ts +18 -21
- package/src/cli/commands/roadmap.ts +4 -21
- package/src/cli/commands/schedules.ts +2 -0
- package/src/cli/lib/__tests__/inspect-plugin.test.ts +54 -0
- package/src/cli/lib/__tests__/install-from-github.test.ts +41 -0
- package/src/cli/lib/__tests__/list-installed-plugins.test.ts +5 -2
- package/src/cli/lib/__tests__/local-plugin-upgrade.test.ts +133 -51
- package/src/cli/lib/__tests__/plugin-catalog-cache.test.ts +8 -2
- package/src/cli/lib/bundled-marketplace.json +906 -1
- package/src/cli/lib/bundled-plugin-packages.json +783 -1
- package/src/cli/lib/inspect-plugin.ts +11 -4
- package/src/cli/lib/plugin-marketplace.ts +8 -0
- package/src/cli/lib/publish-plugin.ts +1 -2
- package/src/cli/lib/upgrade-plugin.ts +19 -11
- package/src/cli/output.ts +18 -4
- package/src/config/__tests__/default-provider.test.ts +6 -0
- package/src/config/__tests__/memory-retrospective-schema.test.ts +14 -1
- package/src/config/bundled-skills/computer-use/SKILL.md +1 -1
- package/src/config/bundled-skills/computer-use/TOOLS.json +89 -1
- package/src/config/bundled-skills/image-studio/SKILL.md +17 -2
- package/src/config/bundled-skills/image-studio/tools/media-generate-image.ts +7 -11
- package/src/config/bundled-skills/schedule/SKILL.md +6 -6
- package/src/config/bundled-skills/sequences/TOOLS.json +1 -5
- package/src/config/call-site-defaults.ts +9 -0
- package/src/config/feature-flag-registry.json +16 -0
- package/src/config/loader.ts +9 -17
- package/src/config/platform-identity.ts +8 -8
- package/src/config/profile-text-generation.test.ts +51 -0
- package/src/config/profile-text-generation.ts +51 -0
- package/src/config/schemas/__tests__/memory-v3.test.ts +12 -0
- package/src/config/schemas/__tests__/tools.test.ts +31 -0
- package/src/config/schemas/call-site-catalog.ts +14 -0
- package/src/config/schemas/channels.ts +0 -18
- package/src/config/schemas/llm.ts +9 -2
- package/src/config/schemas/mcp.ts +6 -1
- package/src/config/schemas/memory-retrospective.ts +11 -2
- package/src/config/schemas/memory-v3.ts +12 -0
- package/src/config/schemas/services.ts +15 -6
- package/src/config/schemas/tools.ts +10 -0
- package/src/config/session-groups-gate.ts +21 -0
- package/src/config/skills.ts +2 -6
- package/src/conversations/__tests__/message-consolidation.test.ts +149 -0
- package/src/conversations/message-consolidation.ts +102 -5
- package/src/credential-execution/ces-connect.test.ts +69 -0
- package/src/credential-execution/ces-connect.ts +115 -0
- package/src/credential-execution/ces-runtime.ts +55 -93
- package/src/credential-execution/executable-discovery.ts +34 -142
- package/src/credential-execution/process-manager.test.ts +20 -24
- package/src/credential-execution/process-manager.ts +24 -19
- package/src/daemon/__tests__/conversation-surfaces-launch.test.ts +10 -1
- package/src/daemon/__tests__/conversation-tool-setup.test.ts +43 -0
- package/src/daemon/__tests__/inference-profile-notification.test.ts +2 -0
- package/src/daemon/__tests__/turn-tail-deleted-conversation.test.ts +36 -0
- package/src/daemon/assistant-attachments.ts +20 -12
- package/src/daemon/browser-mode-session.test.ts +402 -0
- package/src/daemon/browser-mode-session.ts +186 -0
- package/src/daemon/chat-credential-redaction.ts +16 -1
- package/src/daemon/computer-use-mode-session.test.ts +210 -0
- package/src/daemon/computer-use-mode-session.ts +105 -0
- package/src/daemon/config-watcher.ts +10 -0
- package/src/daemon/conversation-agent-loop-handlers.ts +132 -13
- package/src/daemon/conversation-agent-loop.ts +231 -25
- package/src/daemon/conversation-attachments.ts +93 -12
- package/src/daemon/conversation-evictor.ts +5 -24
- package/src/daemon/conversation-history.ts +10 -0
- package/src/daemon/conversation-interrupt-repair.ts +4 -43
- package/src/daemon/conversation-interrupt.ts +7 -11
- package/src/daemon/conversation-messaging.ts +58 -5
- package/src/daemon/conversation-mode-session.test.ts +1667 -0
- package/src/daemon/conversation-mode-session.ts +1008 -0
- package/src/daemon/conversation-process.ts +5 -0
- package/src/daemon/conversation-runtime-assembly.ts +10 -20
- package/src/daemon/conversation-skill-tools.ts +1 -0
- package/src/daemon/conversation-store.ts +4 -4
- package/src/daemon/conversation-surface-snapshots.ts +135 -0
- package/src/daemon/conversation-surfaces.ts +113 -5
- package/src/daemon/conversation-tool-setup.ts +79 -6
- package/src/daemon/conversation-turn-finalize.ts +26 -13
- package/src/daemon/conversation.ts +215 -58
- package/src/daemon/daemon-control.ts +3 -7
- package/src/daemon/handlers/config-model.ts +7 -5
- package/src/daemon/handlers/shared.ts +55 -16
- package/src/daemon/host-cu-proxy.ts +51 -22
- package/src/daemon/lifecycle.ts +30 -13
- package/src/daemon/mcp-reload-service.ts +1 -1
- package/src/daemon/message-protocol.ts +0 -1
- package/src/daemon/message-provenance.ts +28 -4
- package/src/daemon/message-types/shared.ts +1 -0
- package/src/daemon/mode-session-startup-recovery.ts +23 -0
- package/src/daemon/mode-session-tracking.ts +54 -0
- package/src/daemon/orphan-reaper.ts +4 -3
- package/src/daemon/persist-media-references.ts +20 -3
- package/src/daemon/process-message.ts +13 -4
- package/src/daemon/tool-setup-types.ts +6 -0
- package/src/daemon/virtual-desktop-context.ts +21 -0
- package/src/daemon/wake-conversation-ops.ts +50 -15
- package/src/desktop/__tests__/fake-desktop.ts +1 -0
- package/src/desktop/desktop-accessibility-script.ts +88 -0
- package/src/desktop/desktop-accessibility.test.ts +160 -0
- package/src/desktop/desktop-accessibility.ts +169 -0
- package/src/desktop/desktop-automation-lease.test.ts +302 -64
- package/src/desktop/desktop-automation-lease.ts +129 -54
- package/src/desktop/desktop-browser-endpoint.ts +4 -0
- package/src/desktop/desktop-computer-use-routing.test.ts +330 -0
- package/src/desktop/desktop-computer-use.test.ts +449 -0
- package/src/desktop/desktop-computer-use.ts +502 -0
- package/src/desktop/desktop-dependencies.ts +47 -293
- package/src/desktop/desktop-display.ts +2 -2
- package/src/desktop/desktop-help.ts +15 -0
- package/src/desktop/desktop-panel-config.test.ts +13 -3
- package/src/desktop/desktop-panel-config.ts +109 -15
- package/src/desktop/desktop-session-manager.test.ts +69 -21
- package/src/desktop/desktop-session-manager.ts +76 -22
- package/src/desktop/desktop-stream-bridge.test.ts +76 -132
- package/src/desktop/desktop-stream-bridge.ts +9 -11
- package/src/desktop/desktop-wallpaper-renderer.ts +132 -0
- package/src/desktop/desktop-wallpaper-worker.ts +17 -0
- package/src/desktop/desktop-wallpaper.test.ts +48 -7
- package/src/desktop/desktop-wallpaper.ts +34 -102
- package/src/desktop/desktop-window-theme.ts +5 -25
- package/src/desktop/virtual-desktop-feature.ts +53 -3
- package/src/desktop/virtual-desktop-platform.test.ts +5 -9
- package/src/documents/document-store.ts +23 -0
- package/src/heartbeat/__tests__/heartbeat-service.test.ts +22 -26
- package/src/heartbeat/heartbeat-service.ts +5 -33
- package/src/ipc/__tests__/browser-ipc.test.ts +215 -6
- package/src/ipc/assistant-server.ts +2 -0
- package/src/ipc/routes/__tests__/channel-reply-ipc-routes.test.ts +111 -0
- package/src/ipc/routes/channel-reply-ipc-routes.ts +73 -0
- package/src/live-voice/__tests__/continuation-judge.test.ts +151 -0
- package/src/live-voice/__tests__/live-activity-reporter.test.ts +154 -15
- package/src/live-voice/__tests__/live-voice-flux-turn-end.test.ts +743 -31
- package/src/live-voice/__tests__/live-voice-look-follow-up.test.ts +191 -10
- package/src/live-voice/__tests__/live-voice-session-groups-gate.test.ts +87 -0
- package/src/live-voice/__tests__/live-voice-session-manager.test.ts +5 -1
- package/src/live-voice/__tests__/live-voice-sight-frame-echo.test.ts +41 -0
- package/src/live-voice/__tests__/live-voice-sight-frame.test.ts +1017 -9
- package/src/live-voice/__tests__/live-voice-triage-escalate.test.ts +224 -1
- package/src/live-voice/__tests__/live-voice-tts-session.test.ts +101 -0
- package/src/live-voice/__tests__/live-voice-tts.test.ts +44 -0
- package/src/live-voice/__tests__/live-voice-vad.test.ts +939 -75
- package/src/live-voice/__tests__/microphone-idle-gate.test.ts +87 -0
- package/src/live-voice/__tests__/session-controls.test.ts +23 -0
- package/src/live-voice/__tests__/task-outcomes.test.ts +117 -0
- package/src/live-voice/__tests__/voice-input-diagnostics.test.ts +117 -0
- package/src/live-voice/camera-mode-session.test.ts +265 -0
- package/src/live-voice/camera-mode-session.ts +277 -0
- package/src/live-voice/continuation-judge.ts +123 -0
- package/src/live-voice/live-activity-reporter.ts +115 -6
- package/src/live-voice/live-voice-manager.ts +36 -1
- package/src/live-voice/live-voice-photo.ts +88 -7
- package/src/live-voice/live-voice-session-manager.ts +15 -0
- package/src/live-voice/live-voice-session.ts +1443 -747
- package/src/live-voice/live-voice-tts.ts +22 -4
- package/src/live-voice/microphone-idle-gate.ts +56 -0
- package/src/live-voice/protocol.ts +171 -4
- package/src/live-voice/session-controls.ts +11 -3
- package/src/live-voice/task-outcomes.ts +131 -0
- package/src/live-voice/voice-input-diagnostics.ts +117 -0
- package/src/mcp/__tests__/manager-tool-caps.test.ts +156 -0
- package/src/mcp/__tests__/startup.test.ts +30 -7
- package/src/mcp/__tests__/tool-caps.test.ts +134 -0
- package/src/mcp/manager.ts +171 -101
- package/src/mcp/startup.ts +33 -13
- package/src/mcp/tool-caps.ts +184 -0
- package/src/media/__tests__/image-models.test.ts +58 -0
- package/src/media/image-credentials.ts +5 -0
- package/src/media/image-models.ts +52 -0
- package/src/media/image-service.ts +8 -0
- package/src/media/openrouter-image-service.test.ts +133 -0
- package/src/media/openrouter-image-service.ts +153 -0
- package/src/media/types.ts +1 -1
- package/src/messaging/provider-message-metadata.ts +3 -3
- package/src/messaging/providers/__tests__/transport-dispatch.test.ts +65 -11
- package/src/messaging/providers/discord/send.ts +4 -17
- package/src/messaging/providers/discord/transport.ts +2 -2
- package/src/messaging/providers/outlook/client.ts +16 -22
- package/src/messaging/providers/telegram-bot/send.test.ts +236 -1
- package/src/messaging/providers/telegram-bot/send.ts +10 -7
- package/src/messaging/providers/telegram-bot/transport.ts +3 -10
- package/src/messaging/providers/whatsapp/send.test.ts +169 -4
- package/src/monitoring/__tests__/control.test.ts +17 -5
- package/src/monitoring/control.ts +15 -5
- package/src/notifications/AGENTS.md +1 -1
- package/src/notifications/README.md +83 -99
- package/src/notifications/__tests__/broadcaster.test.ts +1 -1
- package/src/notifications/__tests__/channel-allowlist.test.ts +39 -0
- package/src/notifications/__tests__/copy-composer.test.ts +71 -1
- package/src/notifications/__tests__/decision-engine.test.ts +79 -2
- package/src/notifications/__tests__/deterministic-checks.test.ts +10 -10
- package/src/notifications/__tests__/home-feed-side-effect.test.ts +93 -4
- package/src/notifications/__tests__/notification-utils.test.ts +18 -0
- package/src/notifications/adapters/macos.ts +37 -46
- package/src/notifications/broadcaster.ts +5 -6
- package/src/notifications/channel-allowlist.ts +44 -0
- package/src/notifications/copy-composer.ts +11 -26
- package/src/notifications/decision-engine.ts +24 -14
- package/src/notifications/deterministic-checks.ts +1 -1
- package/src/notifications/emit-signal.ts +123 -37
- package/src/notifications/home-feed-side-effect.ts +9 -7
- package/src/notifications/notification-utils.ts +19 -0
- package/src/notifications/schedule-result-producer.ts +4 -6
- package/src/notifications/signal.ts +4 -19
- package/src/notifications/types.ts +15 -0
- package/src/oauth/AGENTS.md +2 -0
- package/src/oauth/__tests__/identity-verifier.test.ts +36 -1
- package/src/oauth/connection-resolver.ts +1 -2
- package/src/oauth/identity-verifier.ts +24 -0
- package/src/oauth/oauth-store.ts +12 -4
- package/src/oauth/provider-serializer.ts +8 -0
- package/src/oauth/seed-providers.ts +42 -0
- package/src/onboarding/onboarding-events-store.ts +99 -12
- package/src/permissions/confirmation-guardian-request.test.ts +16 -0
- package/src/permissions/confirmation-guardian-request.ts +2 -3
- package/src/permissions/question-prompter.test.ts +31 -0
- package/src/permissions/question-prompter.ts +2 -0
- package/src/persistence/__tests__/client-connection-events-store.test.ts +322 -0
- package/src/persistence/attachments-store.ts +84 -44
- package/src/persistence/client-connection-events-store.ts +377 -0
- package/src/persistence/conversation-crud.ts +166 -26
- package/src/persistence/conversation-mode-sessions.test.ts +424 -0
- package/src/persistence/conversation-mode-sessions.ts +460 -0
- package/src/persistence/conversation-plugin-facade.ts +30 -0
- package/src/persistence/conversation-queries.ts +6 -19
- package/src/persistence/conversation-tool-surface.ts +135 -0
- package/src/persistence/conversation-types.test.ts +32 -0
- package/src/persistence/conversation-types.ts +26 -4
- package/src/persistence/llm-usage-store.ts +3 -9
- package/src/persistence/message-metadata.ts +25 -0
- package/src/persistence/migrations/378-create-conversation-tool-surfaces.test.ts +78 -0
- package/src/persistence/migrations/378-create-conversation-tool-surfaces.ts +29 -0
- package/src/persistence/migrations/379-oauth-providers-response-ok-field.test.ts +92 -0
- package/src/persistence/migrations/379-oauth-providers-response-ok-field.ts +32 -0
- package/src/persistence/migrations/380-conversation-tool-surfaces-delegate-independent-tasks.test.ts +90 -0
- package/src/persistence/migrations/380-conversation-tool-surfaces-delegate-independent-tasks.ts +34 -0
- package/src/persistence/migrations/381-create-conversation-mode-sessions.ts +41 -0
- package/src/persistence/migrations/382-create-client-connection-events.ts +40 -0
- package/src/persistence/migrations/__tests__/382-create-client-connection-events.test.ts +56 -0
- package/src/persistence/schema/conversation-tool-surfaces.ts +32 -0
- package/src/persistence/schema/conversations.ts +67 -0
- package/src/persistence/schema/index.ts +1 -0
- package/src/persistence/schema/infrastructure.ts +29 -0
- package/src/persistence/schema/oauth.ts +1 -0
- package/src/persistence/steps.ts +41 -3
- package/src/plugin-api/__tests__/plugin-name-env.test.ts +249 -0
- package/src/plugin-api/conversation-turn.ts +31 -7
- package/src/plugin-api/effective-context-window.ts +33 -0
- package/src/plugin-api/index.ts +35 -6
- package/src/plugin-api/plugin-channel-turn-trust.test.ts +133 -0
- package/src/plugin-api/plugin-channel-turn-trust.ts +71 -0
- package/src/plugin-api/plugin-name-env.ts +125 -0
- package/src/plugin-api/resolve-credential.ts +79 -20
- package/src/plugin-api/vision-support.test.ts +22 -0
- package/src/plugin-api/vision-support.ts +17 -5
- package/src/plugins/__tests__/active-plugin-env.test.ts +136 -0
- package/src/plugins/active-plugin-env.ts +51 -0
- package/src/plugins/defaults/index.ts +24 -0
- package/src/plugins/defaults/memory/AGENTS.md +39 -5
- package/src/plugins/defaults/memory/__tests__/archive-removal-framing.test.ts +64 -0
- package/src/plugins/defaults/memory/__tests__/buffer-file.test.ts +365 -0
- package/src/plugins/defaults/memory/__tests__/buffer-format.test.ts +43 -0
- package/src/plugins/defaults/memory/__tests__/conversation-memory-purge.test.ts +1 -0
- package/src/plugins/defaults/memory/__tests__/db-memory-attach.test.ts +2 -0
- package/src/plugins/defaults/memory/__tests__/fixtures/buffer-appender.ts +17 -0
- package/src/plugins/defaults/memory/__tests__/memory-retrospective-job.test.ts +74 -0
- package/src/plugins/defaults/memory/__tests__/memory-run-evidence.test.ts +161 -0
- package/src/plugins/defaults/memory/__tests__/relocated-memory-test-rows.ts +10 -0
- package/src/plugins/defaults/memory/__tests__/worker-control.test.ts +19 -6
- package/src/plugins/defaults/memory/buffer-file.ts +354 -0
- package/src/plugins/defaults/memory/buffer-format.ts +40 -0
- package/src/plugins/defaults/memory/context-search/agent-protocol.ts +9 -12
- package/src/plugins/defaults/memory/context-search/agent-runner.ts +77 -22
- package/src/plugins/defaults/memory/context-search/format.ts +53 -8
- package/src/plugins/defaults/memory/context-search/limits.ts +10 -12
- package/src/plugins/defaults/memory/context-search/recall-input.ts +38 -0
- package/src/plugins/defaults/memory/context-search/search.ts +8 -14
- package/src/plugins/defaults/memory/context-search/sources/conversations.ts +1 -0
- package/src/plugins/defaults/memory/context-search/sources/memory-v2.ts +2 -1
- package/src/plugins/defaults/memory/context-search/sources/workspace.ts +2 -1
- package/src/plugins/defaults/memory/context-search/types.ts +1 -11
- package/src/plugins/defaults/memory/conversation-memory-purge.ts +4 -0
- package/src/plugins/defaults/memory/graph/__tests__/handle-remember-v2.test.ts +11 -4
- package/src/plugins/defaults/memory/graph/capability-seed.ts +1 -2
- package/src/plugins/defaults/memory/graph/tool-handlers.ts +13 -63
- package/src/plugins/defaults/memory/graph/tools.ts +35 -64
- package/src/plugins/defaults/memory/host-utils.ts +0 -10
- package/src/plugins/defaults/memory/injectors.ts +4 -3
- package/src/plugins/defaults/memory/memory-retrospective-job.ts +72 -183
- package/src/plugins/defaults/memory/memory-run-evidence.ts +213 -0
- package/src/plugins/defaults/memory/src/memory-eval-routes.ts +2 -3
- package/src/plugins/defaults/memory/src/memory-item-routes.test.ts +6 -1
- package/src/plugins/defaults/memory/src/memory-item-routes.ts +2 -1
- package/src/plugins/defaults/memory/substrate/__tests__/consolidation-job.test.ts +407 -99
- package/src/plugins/defaults/memory/substrate/__tests__/consolidation-prompt-flag-gating-guard.test.ts +10 -0
- package/src/plugins/defaults/memory/substrate/__tests__/prompts-consolidation.test.ts +107 -7
- package/src/plugins/defaults/memory/substrate/consolidation-job.ts +307 -86
- package/src/plugins/defaults/memory/substrate/consolidation-tool-surface.ts +34 -0
- package/src/plugins/defaults/memory/substrate/page-index.ts +2 -1
- package/src/plugins/defaults/memory/substrate/prompts/consolidation.ts +91 -51
- package/src/plugins/defaults/memory/substrate/sweep-job.ts +1 -1
- package/src/plugins/defaults/memory/tools.test.ts +124 -9
- package/src/plugins/defaults/memory/tools.ts +38 -11
- package/src/plugins/defaults/memory/v1/graph/consolidation.ts +2 -2
- package/src/plugins/defaults/memory/v1/graph/extraction.ts +2 -1
- package/src/plugins/defaults/memory/v1/graph/retriever.ts +1 -1
- package/src/plugins/defaults/memory/v2/__tests__/migration.test.ts +5 -0
- package/src/plugins/defaults/memory/v2/__tests__/reranker.test.ts +5 -2
- package/src/plugins/defaults/memory/v2/reranker.ts +2 -1
- package/src/plugins/defaults/memory/v3/__tests__/injection.test.ts +81 -1
- package/src/plugins/defaults/memory/v3/__tests__/orchestrate.test.ts +87 -0
- package/src/plugins/defaults/memory/v3/__tests__/plugin-schema.test.ts +12 -0
- package/src/plugins/defaults/memory/v3/__tests__/pool-log-store.test.ts +332 -15
- package/src/plugins/defaults/memory/v3/__tests__/pool-select.test.ts +626 -27
- package/src/plugins/defaults/memory/v3/__tests__/shadow-plugin.test.ts +148 -28
- package/src/plugins/defaults/memory/v3/card.ts +2 -1
- package/src/plugins/defaults/memory/v3/injector.ts +212 -178
- package/src/plugins/defaults/memory/v3/orchestrate.ts +159 -32
- package/src/plugins/defaults/memory/v3/plugin-schema.ts +54 -4
- package/src/plugins/defaults/memory/v3/pool-log-store.ts +275 -37
- package/src/plugins/defaults/memory/v3/pool-select.test.ts +47 -5
- package/src/plugins/defaults/memory/v3/pool-select.ts +710 -59
- package/src/plugins/defaults/memory/v3/sections.ts +2 -1
- package/src/plugins/defaults/memory/v3/shadow-plugin.ts +41 -14
- package/src/plugins/defaults/memory/worker-control.ts +15 -5
- package/src/plugins/defaults/task-progress/__tests__/registration.test.ts +70 -0
- package/src/plugins/defaults/task-progress/__tests__/task-progress-context.test.ts +380 -0
- package/src/plugins/defaults/task-progress/hooks/post-compact.ts +19 -0
- package/src/plugins/defaults/task-progress/hooks/user-prompt-submit.ts +24 -0
- package/src/plugins/defaults/task-progress/package.json +14 -0
- package/src/plugins/defaults/task-progress/src/apply-task-progress-context.ts +93 -0
- package/src/plugins/defaults/task-progress/src/format-task-progress-context.ts +67 -0
- package/src/plugins/defaults/tool-error/hooks/post-tool-use.ts +4 -1
- package/src/plugins/defaults/tool-result-truncate/terminal.ts +1 -46
- package/src/prompts/__tests__/parallel-tasks-section.test.ts +25 -0
- package/src/prompts/delegation-gate.ts +57 -0
- package/src/prompts/system-prompt.ts +14 -32
- package/src/providers/__tests__/context-overflow-error.test.ts +10 -0
- package/src/providers/__tests__/search-provider-catalog.test.ts +18 -0
- package/src/providers/anthropic/client.ts +10 -1
- package/src/providers/anthropic-gateway-shared.ts +6 -0
- package/src/providers/fetch-provider-catalog.ts +11 -0
- package/src/providers/gemini/client.ts +25 -8
- package/src/providers/inference/adapter-factory.ts +6 -0
- package/src/providers/jev/client.test.ts +270 -0
- package/src/providers/jev/client.ts +534 -0
- package/src/providers/model-catalog.ts +59 -3
- package/src/providers/openai/__tests__/chat-completions-extra-body.test.ts +94 -1
- package/src/providers/openai/__tests__/chat-completions-provider-reasoning.test.ts +106 -1
- package/src/providers/openai/__tests__/chat-template-flatten.test.ts +24 -0
- package/src/providers/openai/__tests__/google-thought-signature.test.ts +1 -2
- package/src/providers/openai/chat-completions-provider.ts +100 -29
- package/src/providers/openai/google-thought-signature.ts +0 -6
- package/src/providers/openai/responses-provider.ts +23 -1
- package/src/providers/ratelimit.ts +1 -3
- package/src/providers/search-provider-catalog.ts +24 -0
- package/src/providers/server-tool-pairing.ts +16 -7
- package/src/providers/speech-to-text/__tests__/deepgram-flux-frames.test.ts +24 -0
- package/src/providers/speech-to-text/__tests__/deepgram-flux-realtime.test.ts +7 -1
- package/src/providers/speech-to-text/__tests__/vellum-managed-realtime.test.ts +50 -1
- package/src/providers/speech-to-text/deepgram-flux-frames.ts +11 -0
- package/src/providers/speech-to-text/vellum-managed-flux-realtime.ts +13 -0
- package/src/providers/types.ts +5 -0
- package/src/routes/control.ts +7 -5
- package/src/runtime/AGENTS.md +6 -4
- package/src/runtime/__tests__/agent-wake.test.ts +94 -1
- package/src/runtime/actor-trust-resolver.ts +3 -3
- package/src/runtime/agent-wake.ts +32 -5
- package/src/runtime/approval-message-composer.ts +3 -69
- package/src/runtime/assistant-event-hub.ts +73 -75
- package/src/runtime/assistant-event-publish-options.ts +7 -0
- package/src/runtime/assistant-event-targeting.ts +79 -0
- package/src/runtime/assistant-stream-state.ts +13 -100
- package/src/runtime/background-job-runner.ts +5 -5
- package/src/runtime/channel-retry-sweep.ts +1 -0
- package/src/runtime/guardian-action-message-composer.ts +8 -161
- package/src/runtime/guardian-action-service.ts +2 -17
- package/src/runtime/guardian-reply-router.ts +29 -40
- package/src/runtime/http-server.ts +2 -2
- package/src/runtime/http-types.ts +6 -0
- package/src/runtime/message-composer-types.ts +3 -61
- package/src/runtime/migrations/__tests__/vbundle-import-parity.test.ts +67 -1
- package/src/runtime/migrations/__tests__/vbundle-import-policy.test.ts +89 -0
- package/src/runtime/migrations/vbundle-builder.ts +24 -1
- package/src/runtime/migrations/vbundle-import-analyzer.ts +13 -4
- package/src/runtime/migrations/vbundle-import-policy.ts +43 -11
- package/src/runtime/migrations/vbundle-importer.ts +4 -1
- package/src/runtime/migrations/vbundle-streaming-importer.ts +4 -1
- package/src/runtime/migrations/vbundle-validator.ts +1 -0
- package/src/runtime/pending-interactions-mode-session.test.ts +62 -0
- package/src/runtime/pending-interactions.ts +29 -0
- package/src/runtime/routes/__tests__/client-history-routes.test.ts +104 -0
- package/src/runtime/routes/__tests__/image-generation-routes.test.ts +97 -0
- package/src/runtime/routes/__tests__/inference-profiles-routes.test.ts +24 -2
- package/src/runtime/routes/__tests__/roadmap-routes.test.ts +29 -6
- package/src/runtime/routes/browser-context.ts +31 -11
- package/src/runtime/routes/browser-routes.ts +43 -4
- package/src/runtime/routes/btw-routes.ts +9 -4
- package/src/runtime/routes/channel-route-shared.ts +1 -9
- package/src/runtime/routes/client-routes.ts +108 -0
- package/src/runtime/routes/conversation-management-routes.ts +4 -1
- package/src/runtime/routes/conversation-routes.ts +125 -14
- package/src/runtime/routes/credential-prompt-routes.ts +4 -3
- package/src/runtime/routes/credential-routes.ts +1 -2
- package/src/runtime/routes/desktop-setup-routes.test.ts +9 -18
- package/src/runtime/routes/desktop-setup-routes.ts +8 -7
- package/src/runtime/routes/documents-routes.ts +51 -0
- package/src/runtime/routes/email-routes.ts +3 -7
- package/src/runtime/routes/events-routes.ts +75 -54
- package/src/runtime/routes/guardian-approval-interception.ts +24 -0
- package/src/runtime/routes/identity-routes.ts +1 -5
- package/src/runtime/routes/image-generation-routes.ts +8 -14
- package/src/runtime/routes/inbound-message-handler.ts +37 -41
- package/src/runtime/routes/inbound-stages/backfill-sender-provenance.test.ts +168 -0
- package/src/runtime/routes/inbound-stages/backfill-sender-provenance.ts +96 -0
- package/src/runtime/routes/inbound-stages/background-dispatch.test.ts +39 -10
- package/src/runtime/routes/inbound-stages/background-dispatch.ts +9 -9
- package/src/runtime/routes/inbound-stages/reaction-intercept.ts +2 -0
- package/src/runtime/routes/inference-profile-session-handler.ts +11 -1
- package/src/runtime/routes/inference-profiles-routes.ts +9 -0
- package/src/runtime/routes/llm-context-normalization.ts +1 -7
- package/src/runtime/routes/migration-routes.ts +73 -2
- package/src/runtime/routes/notification-routes.ts +10 -0
- package/src/runtime/routes/oauth-commands-routes.ts +57 -54
- package/src/runtime/routes/oauth-providers.ts +11 -0
- package/src/runtime/routes/oauth-request-hints.test.ts +246 -0
- package/src/runtime/routes/oauth-request-hints.ts +149 -0
- package/src/runtime/routes/plugins-routes.ts +6 -0
- package/src/runtime/routes/roadmap-routes.ts +47 -8
- package/src/runtime/routes/schedule-routes.ts +2 -0
- package/src/runtime/routes/secret-routes.ts +99 -119
- package/src/runtime/routes/settings-routes.ts +10 -4
- package/src/runtime/routes/watcher-routes.ts +1 -3
- package/src/runtime/trust-class.test.ts +7 -6
- package/src/runtime/trust-class.ts +9 -17
- package/src/schedule/__tests__/worker-control.test.ts +36 -5
- package/src/schedule/__tests__/worker-mcp-bootstrap.test.ts +107 -0
- package/src/schedule/__tests__/worker-mcp-readiness.test.ts +173 -0
- package/src/schedule/__tests__/worker-mcp-tools.test.ts +13 -47
- package/src/schedule/run-script.ts +2 -2
- package/src/schedule/scheduler.ts +47 -11
- package/src/schedule/tool-surface-readiness.ts +65 -0
- package/src/schedule/worker-control.ts +15 -5
- package/src/schedule/worker-mcp.ts +85 -0
- package/src/schedule/worker.ts +9 -31
- package/src/security/secure-keys.ts +74 -112
- package/src/skills/clawhub.ts +3 -8
- package/src/skills/managed-store.ts +1 -5
- package/src/stt/types.ts +4 -0
- package/src/subagent/notify.ts +54 -34
- package/src/subagent/parent-notification.ts +6 -0
- package/src/telemetry/__tests__/phone-call-funnel.test.ts +72 -0
- package/src/telemetry/phone-call-funnel.ts +144 -0
- package/src/tools/__tests__/tool-schema-root-combinator-guard.test.ts +81 -0
- package/src/tools/ask-question/ask-question-tool.test.ts +167 -5
- package/src/tools/ask-question/ask-question-tool.ts +120 -22
- package/src/tools/browser/browser-execution.ts +29 -60
- package/src/tools/browser/cdp-client/__tests__/cdp-dom-helpers.test.ts +561 -39
- package/src/tools/browser/cdp-client/cdp-dom-helpers.ts +435 -39
- package/src/tools/browser/cdp-client/cdp-inspect-client.ts +1 -8
- package/src/tools/client-os.ts +15 -0
- package/src/tools/computer-use/skill-proxy-bridge.ts +1 -1
- package/src/tools/computer-use/target.ts +42 -0
- package/src/tools/document/document-tool.ts +13 -18
- package/src/tools/execution-target.ts +14 -16
- package/src/tools/host-terminal/host-shell.ts +16 -7
- package/src/tools/network/__tests__/web-fetch-tinyfish.test.ts +250 -0
- package/src/tools/network/__tests__/web-search.test.ts +203 -0
- package/src/tools/network/web-fetch.ts +274 -7
- package/src/tools/network/web-search.ts +468 -6
- package/src/tools/permission-checker.ts +3 -3
- package/src/tools/policy-context.ts +3 -1
- package/src/tools/shared/filesystem/file-ops-service.ts +1 -31
- package/src/tools/shared/shell-output.test.ts +10 -0
- package/src/tools/shared/shell-output.ts +14 -2
- package/src/tools/skills/load.ts +2 -1
- package/src/tools/skills/sandbox-runner.ts +24 -4
- package/src/tools/skills/scaffold-managed.ts +2 -1
- package/src/tools/skills/skill-script-runner.ts +7 -0
- package/src/tools/skills/skill-tool-factory.ts +15 -1
- package/src/tools/terminal/__tests__/safe-env.test.ts +44 -4
- package/src/tools/terminal/__tests__/sanitized-bash.test.ts +0 -14
- package/src/tools/terminal/safe-env.ts +39 -24
- package/src/tools/terminal/sanitized-bash.ts +15 -2
- package/src/tools/terminal/shell-launch.test.ts +162 -0
- package/src/tools/terminal/shell.test.ts +29 -0
- package/src/tools/terminal/shell.ts +15 -7
- package/src/tools/tool-approval-handler.ts +5 -1
- package/src/tools/tool-types.ts +3 -3
- package/src/tools/types.ts +8 -2
- package/src/util/__tests__/worker-process-command.test.ts +5 -4
- package/src/util/abort-reasons.ts +18 -26
- package/src/util/browser-human-verification.ts +14 -0
- package/src/util/canonicalize-identity.test.ts +21 -0
- package/src/util/canonicalize-identity.ts +16 -0
- package/src/util/errors.ts +13 -3
- package/src/util/host-process.test.ts +17 -1
- package/src/util/host-process.ts +24 -0
- package/src/util/provider-error-patterns.ts +3 -0
- package/src/util/unicode.ts +29 -0
- package/src/util/worker-process.ts +77 -35
- package/src/workspace/migrations/157-add-desktop-files-launcher.ts +94 -0
- package/src/workspace/migrations/__tests__/156-extract-workspace-mcp-json.test.ts +4 -10
- package/src/workspace/migrations/__tests__/157-add-desktop-files-launcher.test.ts +113 -0
- package/src/workspace/migrations/registry.ts +2 -0
- package/src/__tests__/computer-use-window-schema.test.ts +0 -24
- package/src/api/events/heartbeat-alert.ts +0 -20
- package/src/daemon/message-types/web-activity.ts +0 -65
- package/src/desktop/desktop-dependencies.test.ts +0 -131
- package/src/tools/computer-use/definitions.ts +0 -607
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "default-task-progress",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "First-party default plugin that injects a compact provider-only snapshot of active task_progress cards at user-prompt-submit and post-compact.",
|
|
5
|
+
"private": true,
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"type": "module",
|
|
8
|
+
"engines": {
|
|
9
|
+
"node": ">=20.12.0"
|
|
10
|
+
},
|
|
11
|
+
"peerDependencies": {
|
|
12
|
+
"@vellumai/plugin-api": "^0.12.2"
|
|
13
|
+
}
|
|
14
|
+
}
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
import {
|
|
2
|
+
type ContentBlock,
|
|
3
|
+
type Message,
|
|
4
|
+
} from "@vellumai/plugin-api";
|
|
5
|
+
|
|
6
|
+
import {
|
|
7
|
+
type ConversationSurfaceSnapshot,
|
|
8
|
+
listConversationSurfaceSnapshots,
|
|
9
|
+
} from "../../../../daemon/conversation-surface-snapshots.js";
|
|
10
|
+
import {
|
|
11
|
+
ACTIVE_TASK_PROGRESS_BLOCK,
|
|
12
|
+
formatActiveTaskProgressSnapshot,
|
|
13
|
+
} from "./format-task-progress-context.js";
|
|
14
|
+
|
|
15
|
+
function stripTaggedBlocksFromText(text: string): string {
|
|
16
|
+
return text.replace(ACTIVE_TASK_PROGRESS_BLOCK, "");
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
function stripActiveTaskProgressBlocks(messages: Message[]): Message[] {
|
|
20
|
+
let changed = false;
|
|
21
|
+
const next: Message[] = [];
|
|
22
|
+
for (const message of messages) {
|
|
23
|
+
const content: ContentBlock[] = [];
|
|
24
|
+
let contentChanged = false;
|
|
25
|
+
for (const block of message.content) {
|
|
26
|
+
if (block.type !== "text") {
|
|
27
|
+
content.push(block);
|
|
28
|
+
continue;
|
|
29
|
+
}
|
|
30
|
+
const stripped = stripTaggedBlocksFromText(block.text);
|
|
31
|
+
if (stripped === block.text) {
|
|
32
|
+
content.push(block);
|
|
33
|
+
continue;
|
|
34
|
+
}
|
|
35
|
+
contentChanged = true;
|
|
36
|
+
if (stripped.trim().length === 0) {
|
|
37
|
+
continue;
|
|
38
|
+
}
|
|
39
|
+
content.push({ ...block, text: stripped });
|
|
40
|
+
}
|
|
41
|
+
if (!contentChanged) {
|
|
42
|
+
next.push(message);
|
|
43
|
+
continue;
|
|
44
|
+
}
|
|
45
|
+
changed = true;
|
|
46
|
+
next.push({ ...message, content });
|
|
47
|
+
}
|
|
48
|
+
return changed ? next : messages;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
function attachToTrailingUserMessage(
|
|
52
|
+
messages: Message[],
|
|
53
|
+
snapshot: string,
|
|
54
|
+
): Message[] {
|
|
55
|
+
let userIndex = -1;
|
|
56
|
+
for (let i = messages.length - 1; i >= 0; i--) {
|
|
57
|
+
if (messages[i]?.role === "user") {
|
|
58
|
+
userIndex = i;
|
|
59
|
+
break;
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
if (userIndex === -1) {
|
|
63
|
+
return messages;
|
|
64
|
+
}
|
|
65
|
+
const user = messages[userIndex]!;
|
|
66
|
+
return [
|
|
67
|
+
...messages.slice(0, userIndex),
|
|
68
|
+
{
|
|
69
|
+
...user,
|
|
70
|
+
content: [...user.content, { type: "text" as const, text: snapshot }],
|
|
71
|
+
},
|
|
72
|
+
...messages.slice(userIndex + 1),
|
|
73
|
+
];
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/**
|
|
77
|
+
* Replace any prior tagged snapshot on the working history with the current
|
|
78
|
+
* active task-progress cards. Assigns a new message array when the history
|
|
79
|
+
* changes so the snapshot is not written back as ordinary transcript.
|
|
80
|
+
*/
|
|
81
|
+
export function applyTaskProgressContext(
|
|
82
|
+
conversationId: string,
|
|
83
|
+
messages: Message[],
|
|
84
|
+
): Message[] {
|
|
85
|
+
const snapshots: ConversationSurfaceSnapshot[] =
|
|
86
|
+
listConversationSurfaceSnapshots(conversationId);
|
|
87
|
+
const snapshotText = formatActiveTaskProgressSnapshot(snapshots);
|
|
88
|
+
const stripped = stripActiveTaskProgressBlocks(messages);
|
|
89
|
+
if (snapshotText.length === 0) {
|
|
90
|
+
return stripped;
|
|
91
|
+
}
|
|
92
|
+
return attachToTrailingUserMessage(stripped, snapshotText);
|
|
93
|
+
}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import type { ConversationSurfaceSnapshot } from "../../../../daemon/conversation-surface-snapshots.js";
|
|
2
|
+
import { getTaskProgressDataFromSurfaceData } from "../../../../runtime/task-progress.js";
|
|
3
|
+
|
|
4
|
+
export const ACTIVE_TASK_PROGRESS_OPEN = "<active_task_progress>";
|
|
5
|
+
export const ACTIVE_TASK_PROGRESS_CLOSE = "</active_task_progress>";
|
|
6
|
+
|
|
7
|
+
export const ACTIVE_TASK_PROGRESS_BLOCK =
|
|
8
|
+
/<active_task_progress\b[\s\S]*?<\/active_task_progress>/gi;
|
|
9
|
+
|
|
10
|
+
const STEP_INSTRUCTION =
|
|
11
|
+
"Update this card with ui_update as the steps change.";
|
|
12
|
+
|
|
13
|
+
function normalizeField(value: string): string {
|
|
14
|
+
return value
|
|
15
|
+
.replace(/[<>]/g, "")
|
|
16
|
+
.replace(/[\r\n\u2028\u2029]+/g, " ")
|
|
17
|
+
.replace(/\s+/g, " ")
|
|
18
|
+
.trim();
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
export function isActiveTaskProgressSurface(
|
|
22
|
+
snapshot: ConversationSurfaceSnapshot,
|
|
23
|
+
): boolean {
|
|
24
|
+
if (snapshot.surfaceType !== "card" || snapshot.completed) {
|
|
25
|
+
return false;
|
|
26
|
+
}
|
|
27
|
+
const plan = getTaskProgressDataFromSurfaceData(snapshot.data);
|
|
28
|
+
if (!plan) {
|
|
29
|
+
return false;
|
|
30
|
+
}
|
|
31
|
+
return plan.steps.some(
|
|
32
|
+
(step) => step.status === "pending" || step.status === "in_progress",
|
|
33
|
+
);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
export function formatActiveTaskProgressSnapshot(
|
|
37
|
+
snapshots: ConversationSurfaceSnapshot[],
|
|
38
|
+
): string {
|
|
39
|
+
const cards = snapshots.filter(isActiveTaskProgressSurface);
|
|
40
|
+
if (cards.length === 0) {
|
|
41
|
+
return "";
|
|
42
|
+
}
|
|
43
|
+
return cards
|
|
44
|
+
.map((snapshot) => {
|
|
45
|
+
const plan = getTaskProgressDataFromSurfaceData(snapshot.data);
|
|
46
|
+
if (!plan) {
|
|
47
|
+
return "";
|
|
48
|
+
}
|
|
49
|
+
const lines = [
|
|
50
|
+
ACTIVE_TASK_PROGRESS_OPEN,
|
|
51
|
+
`surface_id: ${normalizeField(snapshot.surfaceId)}`,
|
|
52
|
+
];
|
|
53
|
+
const title = plan.title ? normalizeField(plan.title) : "";
|
|
54
|
+
if (title.length > 0) {
|
|
55
|
+
lines.push(`title: ${title}`);
|
|
56
|
+
}
|
|
57
|
+
lines.push("steps:");
|
|
58
|
+
for (const step of plan.steps) {
|
|
59
|
+
lines.push(`- [${step.status}] ${normalizeField(step.label)}`);
|
|
60
|
+
}
|
|
61
|
+
lines.push(STEP_INSTRUCTION);
|
|
62
|
+
lines.push(ACTIVE_TASK_PROGRESS_CLOSE);
|
|
63
|
+
return lines.join("\n");
|
|
64
|
+
})
|
|
65
|
+
.filter((block) => block.length > 0)
|
|
66
|
+
.join("\n");
|
|
67
|
+
}
|
|
@@ -10,7 +10,10 @@
|
|
|
10
10
|
* guidance while the client-facing and persisted tool output stay the tool's
|
|
11
11
|
* actual result. This mirrors how Claude Code (`additionalContext`) and Codex
|
|
12
12
|
* (`additional_contexts`) surface PostToolUse feedback as separate context
|
|
13
|
-
* rather than rewriting the tool response.
|
|
13
|
+
* rather than rewriting the tool response. The one exception is an assistant
|
|
14
|
+
* turn that left a native web search deferred: its answering message must
|
|
15
|
+
* hold tool_result blocks alone, so the loop folds the guidance into the
|
|
16
|
+
* provider-bound copy of the errored tool_result (see `buildToolResultFollowUp`).
|
|
14
17
|
*
|
|
15
18
|
* The coaching is bounded per tool: once a single tool has failed
|
|
16
19
|
* `MAX_CONSECUTIVE_ERROR_NUDGES` times in a row the notice is dropped — the
|
|
@@ -6,52 +6,7 @@
|
|
|
6
6
|
* This module is side-effect free: importing it does not register any plugin.
|
|
7
7
|
*/
|
|
8
8
|
|
|
9
|
-
|
|
10
|
-
const HIGH_SURROGATE_END = 0xdbff;
|
|
11
|
-
const LOW_SURROGATE_START = 0xdc00;
|
|
12
|
-
const LOW_SURROGATE_END = 0xdfff;
|
|
13
|
-
|
|
14
|
-
function isHighSurrogate(code: number): boolean {
|
|
15
|
-
return code >= HIGH_SURROGATE_START && code <= HIGH_SURROGATE_END;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
function isLowSurrogate(code: number): boolean {
|
|
19
|
-
return code >= LOW_SURROGATE_START && code <= LOW_SURROGATE_END;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
/**
|
|
23
|
-
* Slice a string by code-unit indices without splitting a surrogate pair, so
|
|
24
|
-
* the result never ends or begins mid-emoji. Indices are clamped to the
|
|
25
|
-
* string bounds; a cut that would land between a high/low surrogate is nudged
|
|
26
|
-
* inward to the nearest whole code point.
|
|
27
|
-
*/
|
|
28
|
-
function safeStringSlice(
|
|
29
|
-
str: string,
|
|
30
|
-
start = 0,
|
|
31
|
-
end: number = str.length,
|
|
32
|
-
): string {
|
|
33
|
-
let safeStart = Math.max(0, Math.min(str.length, start));
|
|
34
|
-
let safeEnd = Math.max(safeStart, Math.min(str.length, end));
|
|
35
|
-
|
|
36
|
-
if (safeEnd < str.length && safeEnd > safeStart) {
|
|
37
|
-
const lastCode = str.charCodeAt(safeEnd - 1);
|
|
38
|
-
if (isHighSurrogate(lastCode)) {
|
|
39
|
-
safeEnd--;
|
|
40
|
-
}
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
if (safeStart > 0 && safeStart < str.length) {
|
|
44
|
-
const firstCode = str.charCodeAt(safeStart);
|
|
45
|
-
if (isLowSurrogate(firstCode)) {
|
|
46
|
-
safeStart++;
|
|
47
|
-
if (safeStart > safeEnd) {
|
|
48
|
-
safeEnd = safeStart;
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
return str.slice(safeStart, safeEnd);
|
|
54
|
-
}
|
|
9
|
+
import { safeStringSlice } from "@vellumai/plugin-api";
|
|
55
10
|
|
|
56
11
|
/**
|
|
57
12
|
* Minimum number of characters to preserve when truncating.
|
|
@@ -103,6 +103,31 @@ describe("parallel-tasks system prompt section", () => {
|
|
|
103
103
|
}
|
|
104
104
|
});
|
|
105
105
|
|
|
106
|
+
test("an explicit rendered state replaces the derivation", () => {
|
|
107
|
+
// A fork wake replaying its source's recorded surface renders what the
|
|
108
|
+
// source's live turn rendered, whatever its own scope could spawn.
|
|
109
|
+
expect(
|
|
110
|
+
buildSystemPrompt({
|
|
111
|
+
canSpawnSubagents: false,
|
|
112
|
+
delegateIndependentTasks: true,
|
|
113
|
+
}),
|
|
114
|
+
).toContain(HEADING);
|
|
115
|
+
expect(
|
|
116
|
+
buildSystemPrompt({
|
|
117
|
+
canSpawnSubagents: true,
|
|
118
|
+
delegateIndependentTasks: false,
|
|
119
|
+
}),
|
|
120
|
+
).not.toContain(HEADING);
|
|
121
|
+
// It is the rendered state, not a capability claim: the channel gate has
|
|
122
|
+
// already been applied by the turn that recorded it.
|
|
123
|
+
expect(
|
|
124
|
+
buildSystemPrompt({
|
|
125
|
+
channelCapabilities: channel("slack"),
|
|
126
|
+
delegateIndependentTasks: true,
|
|
127
|
+
}),
|
|
128
|
+
).toContain(HEADING);
|
|
129
|
+
});
|
|
130
|
+
|
|
106
131
|
test("delegates only independent tasks and keeps small requests inline", () => {
|
|
107
132
|
const prompt = buildSystemPrompt({ canSpawnSubagents: true });
|
|
108
133
|
expect(prompt).toContain("several independent things at once");
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import type { ChannelCapabilities } from "../daemon/conversation-runtime-assembly.js";
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Whether this turn arrived on an external messaging surface (Slack, Telegram,
|
|
5
|
+
* email, a plugin channel) rather than the app itself.
|
|
6
|
+
*
|
|
7
|
+
* `resolveChannelCapabilities` folds every first-party client (macOS, web,
|
|
8
|
+
* iOS, CLI, the HTTP API) onto the `vellum` channel, and a prompt built
|
|
9
|
+
* outside a turn carries no capabilities at all, so those two cases are the
|
|
10
|
+
* app and everything else is a channel the gateway delivers to over a reply
|
|
11
|
+
* callback.
|
|
12
|
+
*/
|
|
13
|
+
export function isExternalChannelTurn(
|
|
14
|
+
capabilities: ChannelCapabilities | undefined,
|
|
15
|
+
): boolean {
|
|
16
|
+
const channel = capabilities?.channel;
|
|
17
|
+
return channel !== undefined && channel !== "vellum";
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
/** The two inputs the delegation section's gate reads. */
|
|
21
|
+
export interface DelegationGateInputs {
|
|
22
|
+
/**
|
|
23
|
+
* Whether the turn can actually spawn subagents, read off its resolved
|
|
24
|
+
* tool surface (`canSpawnSubagentsForTurn`). Absent means no.
|
|
25
|
+
*/
|
|
26
|
+
canSpawnSubagents?: boolean;
|
|
27
|
+
channelCapabilities?: ChannelCapabilities;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* The delegation section's gate: the turn can spawn AND a subagent's answer
|
|
32
|
+
* would reach whoever asked.
|
|
33
|
+
*
|
|
34
|
+
* Off unless a caller states it can spawn, and the caller that states it
|
|
35
|
+
* derives the answer from the turn's resolved tool surface rather than
|
|
36
|
+
* assuming (`canSpawnSubagentsForTurn`). Guidance about handing work to
|
|
37
|
+
* subagents is worth nothing to a turn that cannot spawn, and worse than
|
|
38
|
+
* nothing when it makes that turn defer work it has to do inline.
|
|
39
|
+
*
|
|
40
|
+
* Off on an external channel for the second reason: a subagent's terminal
|
|
41
|
+
* summary reaches the parent through the conversation's event sink, which an
|
|
42
|
+
* app client reads and a channel does not, so a delegated answer would never
|
|
43
|
+
* be delivered to the person who asked for it.
|
|
44
|
+
*
|
|
45
|
+
* Its own module so the conversation's prompt build and the prompt builder
|
|
46
|
+
* share one derivation: the conversation resolves the state once, hands it to
|
|
47
|
+
* the builder, and keeps it for the wire-surface recorder, so the prompt the
|
|
48
|
+
* provider receives and the state a fork replays are the same value.
|
|
49
|
+
*/
|
|
50
|
+
export function resolveDelegateIndependentTasks(
|
|
51
|
+
options: DelegationGateInputs | undefined,
|
|
52
|
+
): boolean {
|
|
53
|
+
return (
|
|
54
|
+
options?.canSpawnSubagents === true &&
|
|
55
|
+
!isExternalChannelTurn(options?.channelCapabilities)
|
|
56
|
+
);
|
|
57
|
+
}
|
|
@@ -26,6 +26,7 @@ import {
|
|
|
26
26
|
import { stripCommentLines } from "../util/strip-comment-lines.js";
|
|
27
27
|
import { cleanupBootstrapFiles } from "./bootstrap-cleanup.js";
|
|
28
28
|
import { SYSTEM_PROMPT_CACHE_BOUNDARY } from "./cache-boundary.js";
|
|
29
|
+
import { resolveDelegateIndependentTasks } from "./delegation-gate.js";
|
|
29
30
|
import { resolveGuardianPersona, resolveUserSlug } from "./persona-resolver.js";
|
|
30
31
|
import { renderWorkspaceSections } from "./sections.js";
|
|
31
32
|
import { isTemplateContent } from "./template-detection.js";
|
|
@@ -440,23 +441,15 @@ export interface BuildSystemPromptOptions {
|
|
|
440
441
|
* pass), rather than from a caller's assumption.
|
|
441
442
|
*/
|
|
442
443
|
canSpawnSubagents?: boolean;
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
* app and everything else is a channel the gateway delivers to over a reply
|
|
453
|
-
* callback.
|
|
454
|
-
*/
|
|
455
|
-
function isExternalChannelTurn(
|
|
456
|
-
capabilities: ChannelCapabilities | undefined,
|
|
457
|
-
): boolean {
|
|
458
|
-
const channel = capabilities?.channel;
|
|
459
|
-
return channel !== undefined && channel !== "vellum";
|
|
444
|
+
/**
|
|
445
|
+
* The delegation section's rendered state, replacing the derivation from
|
|
446
|
+
* `canSpawnSubagents` and `channelCapabilities` when set. A fork wake
|
|
447
|
+
* replaying its source conversation's recorded surface passes the state
|
|
448
|
+
* the source's live turn rendered (`ConversationToolSurface`), so the
|
|
449
|
+
* fork's system prompt matches the source's byte for byte even though the
|
|
450
|
+
* wake's own scope cannot spawn; a spawn is still rejected at execution.
|
|
451
|
+
*/
|
|
452
|
+
delegateIndependentTasks?: boolean;
|
|
460
453
|
}
|
|
461
454
|
|
|
462
455
|
/**
|
|
@@ -525,22 +518,11 @@ export function buildSystemPrompt(options?: BuildSystemPromptOptions): string {
|
|
|
525
518
|
const ctx = {
|
|
526
519
|
...options,
|
|
527
520
|
hasNoClient,
|
|
528
|
-
// The delegation section's gate
|
|
529
|
-
//
|
|
530
|
-
//
|
|
531
|
-
// Off unless a caller states it can spawn, and the caller that states it
|
|
532
|
-
// derives the answer from the turn's resolved tool surface rather than
|
|
533
|
-
// assuming (`canSpawnSubagentsForTurn`). Guidance about handing work to
|
|
534
|
-
// subagents is worth nothing to a turn that cannot spawn, and worse than
|
|
535
|
-
// nothing when it makes that turn defer work it has to do inline.
|
|
536
|
-
//
|
|
537
|
-
// Off on an external channel for the second reason: a subagent's terminal
|
|
538
|
-
// summary reaches the parent through the conversation's event sink, which
|
|
539
|
-
// an app client reads and a channel does not, so a delegated answer would
|
|
540
|
-
// never be delivered to the person who asked for it.
|
|
521
|
+
// The delegation section's gate, or the rendered state a replaying wake
|
|
522
|
+
// carries from its source (see `resolveDelegateIndependentTasks`).
|
|
541
523
|
delegateIndependentTasks:
|
|
542
|
-
options?.
|
|
543
|
-
|
|
524
|
+
options?.delegateIndependentTasks ??
|
|
525
|
+
resolveDelegateIndependentTasks(options),
|
|
544
526
|
isContainerized: getIsContainerized(),
|
|
545
527
|
sendUserMessageTool: options?.sendUserMessageTool === true,
|
|
546
528
|
workspaceDir: getWorkspaceDir(),
|
|
@@ -47,6 +47,16 @@ describe("ContextOverflowError", () => {
|
|
|
47
47
|
expect((err as Error & { cause?: unknown }).cause).toBe(cause);
|
|
48
48
|
});
|
|
49
49
|
|
|
50
|
+
test("forwards rawRequest onto the ProviderError", () => {
|
|
51
|
+
const rawRequest = { model: "claude-opus-4.6", messages: [] };
|
|
52
|
+
const err = new ContextOverflowError("m", "anthropic", {
|
|
53
|
+
actualTokens: 10,
|
|
54
|
+
maxTokens: 5,
|
|
55
|
+
rawRequest,
|
|
56
|
+
});
|
|
57
|
+
expect(err.rawRequest).toEqual(rawRequest);
|
|
58
|
+
});
|
|
59
|
+
|
|
50
60
|
test("omits optional fields when unset", () => {
|
|
51
61
|
const err = new ContextOverflowError("m", "gemini");
|
|
52
62
|
expect(err.actualTokens).toBeUndefined();
|
|
@@ -86,4 +86,22 @@ describe("search-provider-catalog", () => {
|
|
|
86
86
|
expect(getSearchProvider("brave")?.displayName).toBe("Brave");
|
|
87
87
|
expect(getSearchProvider("unknown-xyz")).toBeUndefined();
|
|
88
88
|
});
|
|
89
|
+
|
|
90
|
+
test("SearXNG is a keyless BYOK provider that requires an instance URL", () => {
|
|
91
|
+
const searxng = getSearchProvider("searxng");
|
|
92
|
+
expect(searxng?.kind).toBe("byok");
|
|
93
|
+
expect(searxng?.keyless).toBe(true);
|
|
94
|
+
expect(searxng?.supportsApiBase).toBe(true);
|
|
95
|
+
expect(searxng?.defaultApiBase).toBeUndefined();
|
|
96
|
+
expect(searxng?.envVar).toBe("SEARXNG_API_KEY");
|
|
97
|
+
});
|
|
98
|
+
|
|
99
|
+
test("TinyFish is a keyed BYOK provider with a cloud API base", () => {
|
|
100
|
+
const tinyfish = getSearchProvider("tinyfish");
|
|
101
|
+
expect(tinyfish?.kind).toBe("byok");
|
|
102
|
+
expect(tinyfish?.keyless).toBeUndefined();
|
|
103
|
+
expect(tinyfish?.supportsApiBase).toBe(true);
|
|
104
|
+
expect(tinyfish?.defaultApiBase).toBe("https://api.search.tinyfish.ai");
|
|
105
|
+
expect(tinyfish?.envVar).toBe("TINYFISH_API_KEY");
|
|
106
|
+
});
|
|
89
107
|
});
|
|
@@ -958,6 +958,7 @@ export class AnthropicProvider implements Provider {
|
|
|
958
958
|
// (30 min default) from an external transport abort (bun fetch deadline,
|
|
959
959
|
// edge LB, NAT idle) — only the latter should be retried.
|
|
960
960
|
let innerTimeoutSignal: AbortSignal | undefined;
|
|
961
|
+
let inspectableRequest: unknown | undefined;
|
|
961
962
|
try {
|
|
962
963
|
sentMessages = await this.buildSentMessages(messages);
|
|
963
964
|
const {
|
|
@@ -1344,6 +1345,7 @@ export class AnthropicProvider implements Provider {
|
|
|
1344
1345
|
const streamOnce = async (
|
|
1345
1346
|
streamParams: Anthropic.MessageStreamParams,
|
|
1346
1347
|
): Promise<Anthropic.Message> => {
|
|
1348
|
+
inspectableRequest = streamParams;
|
|
1347
1349
|
const stream: UnifiedStream = useFastMode
|
|
1348
1350
|
? (this.client.beta.messages.stream(
|
|
1349
1351
|
{
|
|
@@ -1768,6 +1770,7 @@ export class AnthropicProvider implements Provider {
|
|
|
1768
1770
|
statusCode: error.status,
|
|
1769
1771
|
reason: "context_overflow",
|
|
1770
1772
|
cause: error,
|
|
1773
|
+
rawRequest: inspectableRequest,
|
|
1771
1774
|
},
|
|
1772
1775
|
);
|
|
1773
1776
|
}
|
|
@@ -1779,7 +1782,11 @@ export class AnthropicProvider implements Provider {
|
|
|
1779
1782
|
reason?: ProviderErrorReason;
|
|
1780
1783
|
apiErrorType?: string;
|
|
1781
1784
|
apiErrorCode?: string;
|
|
1785
|
+
rawRequest?: unknown;
|
|
1782
1786
|
} = {};
|
|
1787
|
+
if (inspectableRequest !== undefined) {
|
|
1788
|
+
errorOptions.rawRequest = inspectableRequest;
|
|
1789
|
+
}
|
|
1783
1790
|
if (retryAfterMs !== undefined) {
|
|
1784
1791
|
errorOptions.retryAfterMs = retryAfterMs;
|
|
1785
1792
|
}
|
|
@@ -1832,7 +1839,9 @@ export class AnthropicProvider implements Provider {
|
|
|
1832
1839
|
}`,
|
|
1833
1840
|
"anthropic",
|
|
1834
1841
|
undefined,
|
|
1835
|
-
abortReason
|
|
1842
|
+
abortReason
|
|
1843
|
+
? { cause: error, abortReason, rawRequest: inspectableRequest }
|
|
1844
|
+
: { cause: error, rawRequest: inspectableRequest },
|
|
1836
1845
|
);
|
|
1837
1846
|
}
|
|
1838
1847
|
}
|
|
@@ -45,6 +45,9 @@ export function retagDelegateError(
|
|
|
45
45
|
maxTokens: error.maxTokens,
|
|
46
46
|
statusCode: error.statusCode,
|
|
47
47
|
cause: error,
|
|
48
|
+
...(error.rawRequest !== undefined
|
|
49
|
+
? { rawRequest: error.rawRequest }
|
|
50
|
+
: {}),
|
|
48
51
|
});
|
|
49
52
|
}
|
|
50
53
|
if (error instanceof ProviderError && error.provider !== providerName) {
|
|
@@ -57,6 +60,9 @@ export function retagDelegateError(
|
|
|
57
60
|
apiErrorCode: error.apiErrorCode,
|
|
58
61
|
apiErrorParam: error.apiErrorParam,
|
|
59
62
|
rawBody: error.rawBody,
|
|
63
|
+
...(error.rawRequest !== undefined
|
|
64
|
+
? { rawRequest: error.rawRequest }
|
|
65
|
+
: {}),
|
|
60
66
|
});
|
|
61
67
|
}
|
|
62
68
|
throw error;
|
|
@@ -84,6 +84,17 @@ export const FETCH_PROVIDER_CATALOG: readonly FetchProviderCatalogEntry[] = [
|
|
|
84
84
|
supportsApiBase: true,
|
|
85
85
|
defaultApiBase: "https://api.fastcrw.com",
|
|
86
86
|
},
|
|
87
|
+
{
|
|
88
|
+
id: "tinyfish",
|
|
89
|
+
displayName: "TinyFish",
|
|
90
|
+
kind: "byok",
|
|
91
|
+
apiKeyPrefix: "TinyFish API key...",
|
|
92
|
+
envVar: "TINYFISH_API_KEY",
|
|
93
|
+
secretKey: "tinyfish",
|
|
94
|
+
privacyPolicyUrl: "https://www.tinyfish.ai/privacy-policy",
|
|
95
|
+
supportsApiBase: true,
|
|
96
|
+
defaultApiBase: "https://api.fetch.tinyfish.ai",
|
|
97
|
+
},
|
|
87
98
|
];
|
|
88
99
|
|
|
89
100
|
/** Provider ids accepted by the web-fetch config schema. */
|
|
@@ -439,6 +439,14 @@ export class GeminiProvider implements Provider {
|
|
|
439
439
|
)
|
|
440
440
|
: undefined;
|
|
441
441
|
|
|
442
|
+
let inspectableRequest:
|
|
443
|
+
| {
|
|
444
|
+
model: string;
|
|
445
|
+
contents: unknown;
|
|
446
|
+
config: genai.GenerateContentConfig;
|
|
447
|
+
}
|
|
448
|
+
| undefined;
|
|
449
|
+
|
|
442
450
|
try {
|
|
443
451
|
recordProviderRequestDiagnostics({ model_id: activeModel });
|
|
444
452
|
const geminiContents = await this.toGeminiContents(messages, activeModel);
|
|
@@ -476,6 +484,12 @@ export class GeminiProvider implements Provider {
|
|
|
476
484
|
geminiConfig.httpOptions = { headers: usageAttributionHeaders };
|
|
477
485
|
}
|
|
478
486
|
|
|
487
|
+
inspectableRequest = {
|
|
488
|
+
model: activeModel,
|
|
489
|
+
contents: geminiContents,
|
|
490
|
+
config: stripGeminiHttpOptions(geminiConfig),
|
|
491
|
+
};
|
|
492
|
+
|
|
479
493
|
// Accumulate from streaming chunks
|
|
480
494
|
let fullText = "";
|
|
481
495
|
const functionCalls: Array<{
|
|
@@ -583,11 +597,6 @@ export class GeminiProvider implements Provider {
|
|
|
583
597
|
content.push(block);
|
|
584
598
|
}
|
|
585
599
|
|
|
586
|
-
const rawRequest = {
|
|
587
|
-
model: activeModel,
|
|
588
|
-
contents: geminiContents,
|
|
589
|
-
config: stripGeminiHttpOptions(geminiConfig),
|
|
590
|
-
};
|
|
591
600
|
const rawResponse = {
|
|
592
601
|
model: responseModel,
|
|
593
602
|
text: fullText || null,
|
|
@@ -609,7 +618,7 @@ export class GeminiProvider implements Provider {
|
|
|
609
618
|
...(cachedTokens > 0 ? { cacheReadInputTokens: cachedTokens } : {}),
|
|
610
619
|
},
|
|
611
620
|
stopReason: finishReason,
|
|
612
|
-
rawRequest,
|
|
621
|
+
rawRequest: inspectableRequest,
|
|
613
622
|
rawResponse,
|
|
614
623
|
};
|
|
615
624
|
} catch (error) {
|
|
@@ -630,6 +639,7 @@ export class GeminiProvider implements Provider {
|
|
|
630
639
|
maxTokens: overflow.maxTokens,
|
|
631
640
|
statusCode: error.status,
|
|
632
641
|
cause: error,
|
|
642
|
+
rawRequest: inspectableRequest,
|
|
633
643
|
},
|
|
634
644
|
);
|
|
635
645
|
}
|
|
@@ -639,7 +649,12 @@ export class GeminiProvider implements Provider {
|
|
|
639
649
|
error.status,
|
|
640
650
|
// Skip reason on caller-abort: abortReason already carries the intent
|
|
641
651
|
// and short-circuits classification/retry (mirrors the Anthropic client).
|
|
642
|
-
|
|
652
|
+
abortReason
|
|
653
|
+
? { abortReason, rawRequest: inspectableRequest }
|
|
654
|
+
: {
|
|
655
|
+
reason: deriveGeminiReason(error),
|
|
656
|
+
rawRequest: inspectableRequest,
|
|
657
|
+
},
|
|
643
658
|
);
|
|
644
659
|
}
|
|
645
660
|
throw new ProviderError(
|
|
@@ -648,7 +663,9 @@ export class GeminiProvider implements Provider {
|
|
|
648
663
|
}`,
|
|
649
664
|
"gemini",
|
|
650
665
|
undefined,
|
|
651
|
-
abortReason
|
|
666
|
+
abortReason
|
|
667
|
+
? { cause: error, abortReason, rawRequest: inspectableRequest }
|
|
668
|
+
: { cause: error, rawRequest: inspectableRequest },
|
|
652
669
|
);
|
|
653
670
|
}
|
|
654
671
|
}
|
|
@@ -35,6 +35,7 @@ import { AtlasCloudProvider } from "../atlascloud/client.js";
|
|
|
35
35
|
import { BasetenProvider } from "../baseten/client.js";
|
|
36
36
|
import { FireworksProvider } from "../fireworks/client.js";
|
|
37
37
|
import { GeminiProvider } from "../gemini/client.js";
|
|
38
|
+
import { JevProvider } from "../jev/client.js";
|
|
38
39
|
import { MinimaxProvider } from "../minimax/client.js";
|
|
39
40
|
import { PROVIDER_CATALOG } from "../model-catalog.js";
|
|
40
41
|
import { OllamaProvider } from "../ollama/client.js";
|
|
@@ -205,6 +206,11 @@ const ADAPTER_FACTORIES: Record<string, AdapterFactory> = {
|
|
|
205
206
|
streamTimeoutMs,
|
|
206
207
|
...(baseURL ? { baseURL } : {}),
|
|
207
208
|
}),
|
|
209
|
+
typesafe: ({ apiKey, model, streamTimeoutMs, baseURL }) =>
|
|
210
|
+
new JevProvider(apiKey, model, {
|
|
211
|
+
streamTimeoutMs,
|
|
212
|
+
...(baseURL ? { baseURL } : {}),
|
|
213
|
+
}),
|
|
208
214
|
vellum: ({ apiKey, model, streamTimeoutMs, baseURL }) =>
|
|
209
215
|
new VellumProvider(apiKey, model, {
|
|
210
216
|
streamTimeoutMs,
|