mixdog 1.3.1 → 1.3.3
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/README.md +8 -4
- package/package.json +8 -8
- package/scripts/native-release-status.mjs +238 -0
- package/scripts/verify-runtime-dependency-versions.mjs +158 -0
- package/src/agents/reviewer/AGENT.md +5 -7
- package/src/agents/reviewer/agent.json +1 -1
- package/src/defaults/shipped-history.json +9 -1
- package/src/defaults/skills/browser-use/SKILL.md +6 -3
- package/src/defaults/skills/local-provider/SKILL.md +33 -6
- package/src/defaults/skills/pptx/scripts/qc-pages.mjs +3 -2
- package/src/defaults/skills/setup/SKILL.md +23 -1
- package/src/defaults/skills/setup/references/actions.md +50 -3
- package/src/defaults/skills/setup/references/surfaces.md +23 -3
- package/src/defaults/skills/setup-guide/SKILL.md +7 -3
- package/src/defaults/skills/visualize/SKILL.md +9 -6
- package/src/defaults/skills/visualize/references/craft.md +8 -1
- package/src/help.mjs +1 -1
- package/src/lib/keychain-cjs.cjs +4 -1
- package/src/lib/rules-builder.cjs +14 -7
- package/src/rules/agent-mode/AGENT_MODE.md +8 -5
- package/src/rules/agent-mode/MIXY.md +6 -8
- package/src/rules/lead/LEAD.md +7 -10
- package/src/rules/shared/10-tool-workflow.md +4 -0
- package/src/rules/shared/20-research.md +2 -0
- package/src/rules/shared/45-destructive.md +5 -1
- package/src/rules/shared/60-verification.md +6 -4
- package/src/runtime/agent/orchestrator/agent-runtime/agent-dispatch/preset.mjs +5 -0
- package/src/runtime/agent/orchestrator/agent-runtime/agent-dispatch/session-prep.mjs +8 -0
- package/src/runtime/agent/orchestrator/agent-runtime/agent-progress-watchdog.mjs +6 -1
- package/src/runtime/agent/orchestrator/agent-runtime/cache-strategy.mjs +114 -26
- package/src/runtime/agent/orchestrator/agent-runtime/maintenance-route.mjs +8 -0
- package/src/runtime/agent/orchestrator/agent-runtime/room-supervisor-completion.mjs +5 -4
- package/src/runtime/agent/orchestrator/agent-trace.mjs +3 -0
- package/src/runtime/agent/orchestrator/cache-break-trace.mjs +4 -0
- package/src/runtime/agent/orchestrator/config-presets.mjs +2 -0
- package/src/runtime/agent/orchestrator/config-storage.mjs +10 -3
- package/src/runtime/agent/orchestrator/config.mjs +11 -0
- package/src/runtime/agent/orchestrator/context/role-instructions.mjs +9 -2
- package/src/runtime/agent/orchestrator/mcp/agent-connectors.mjs +97 -5
- package/src/runtime/agent/orchestrator/mcp/child-tree.mjs +6 -10
- package/src/runtime/agent/orchestrator/mcp/client.mjs +7 -4
- package/src/runtime/agent/orchestrator/providers/anthropic-api-request.mjs +84 -32
- package/src/runtime/agent/orchestrator/providers/anthropic-max-tokens.mjs +38 -11
- package/src/runtime/agent/orchestrator/providers/anthropic-messages.mjs +15 -3
- package/src/runtime/agent/orchestrator/providers/anthropic-model-resolve.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/anthropic-oauth-client-version.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/anthropic-oauth.mjs +84 -42
- package/src/runtime/agent/orchestrator/providers/anthropic-turn-result.mjs +2 -0
- package/src/runtime/agent/orchestrator/providers/anthropic.mjs +14 -1
- package/src/runtime/agent/orchestrator/providers/antigravity-request.mjs +6 -2
- package/src/runtime/agent/orchestrator/providers/auto-effort.mjs +27 -8
- package/src/runtime/agent/orchestrator/providers/cursor-client-version.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/cursor-wire.mjs +31 -4
- package/src/runtime/agent/orchestrator/providers/cursor.mjs +4 -1
- package/src/runtime/agent/orchestrator/providers/custom-provider-config.mjs +14 -1
- package/src/runtime/agent/orchestrator/providers/custom-provider.mjs +11 -8
- package/src/runtime/agent/orchestrator/providers/grok-client-version.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/lib/anthropic-prefix-trace.mjs +76 -0
- package/src/runtime/agent/orchestrator/providers/lib/anthropic-request-utils.mjs +16 -0
- package/src/runtime/agent/orchestrator/providers/lib/tail-reminder-split.mjs +13 -0
- package/src/runtime/agent/orchestrator/providers/media-normalization.mjs +16 -1
- package/src/runtime/agent/orchestrator/providers/mixdog-local.mjs +3 -1
- package/src/runtime/agent/orchestrator/providers/model-proxy-provider.mjs +1 -0
- package/src/runtime/agent/orchestrator/providers/openai-codex-metadata.mjs +5 -5
- package/src/runtime/agent/orchestrator/providers/openai-compat-models.mjs +9 -5
- package/src/runtime/agent/orchestrator/providers/openai-compat-responses.mjs +9 -1
- package/src/runtime/agent/orchestrator/providers/openai-compat-wire.mjs +2 -1
- package/src/runtime/agent/orchestrator/providers/openai-direct-request.mjs +30 -3
- package/src/runtime/agent/orchestrator/providers/openai-model-capabilities.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/openai-ws.mjs +3 -1
- package/src/runtime/agent/orchestrator/providers/opencode-go-oauth.mjs +61 -8
- package/src/runtime/agent/orchestrator/providers/registry.mjs +19 -0
- package/src/runtime/agent/orchestrator/providers/wire-gateway.mjs +13 -1
- package/src/runtime/agent/orchestrator/runtime-core/config-helpers.mjs +90 -24
- package/src/runtime/agent/orchestrator/runtime-core/fs-utils.mjs +8 -1
- package/src/runtime/agent/orchestrator/runtime-core/goal-mutations.mjs +1 -1
- package/src/runtime/agent/orchestrator/runtime-core/goal-runtime.mjs +5 -0
- package/src/runtime/agent/orchestrator/runtime-core/goal-storage.mjs +68 -22
- package/src/runtime/agent/orchestrator/runtime-core/goal-tool-exec.mjs +1 -1
- package/src/runtime/agent/orchestrator/runtime-core/goal-turns.mjs +10 -1
- package/src/runtime/agent/orchestrator/runtime-core/orchestration.mjs +4 -6
- package/src/runtime/agent/orchestrator/runtime-core/route-context-state.mjs +81 -0
- package/src/runtime/agent/orchestrator/runtime-core/session-text.mjs +2 -1
- package/src/runtime/agent/orchestrator/runtime-core/tool-catalog.mjs +52 -6
- package/src/runtime/agent/orchestrator/runtime-core/tool-defs.mjs +35 -13
- package/src/runtime/agent/orchestrator/runtime-core/workflow/agents.mjs +7 -6
- package/src/runtime/agent/orchestrator/runtime-core/workflow/context.mjs +1 -1
- package/src/runtime/agent/orchestrator/runtime-core/workflow/packs.mjs +8 -4
- package/src/runtime/agent/orchestrator/runtime-core/workflow.mjs +8 -3
- package/src/runtime/agent/orchestrator/session/agent-loop.mjs +1 -1
- package/src/runtime/agent/orchestrator/session/agent-mode.mjs +0 -6
- package/src/runtime/agent/orchestrator/session/agent-room-supervisor.d.mts +1 -1
- package/src/runtime/agent/orchestrator/session/agent-room-supervisor.mjs +22 -4
- package/src/runtime/agent/orchestrator/session/agent-room.d.mts +30 -2
- package/src/runtime/agent/orchestrator/session/agent-room.mjs +196 -45
- package/src/runtime/agent/orchestrator/session/attachment-preflight.mjs +80 -0
- package/src/runtime/agent/orchestrator/session/catalog-db/schema.mjs +4 -1
- package/src/runtime/agent/orchestrator/session/compact/continuation.mjs +15 -6
- package/src/runtime/agent/orchestrator/session/compact/execution-tail.mjs +45 -19
- package/src/runtime/agent/orchestrator/session/compact/forked-summary.mjs +3 -0
- package/src/runtime/agent/orchestrator/session/compact/messages.mjs +44 -0
- package/src/runtime/agent/orchestrator/session/compact/runner.mjs +185 -37
- package/src/runtime/agent/orchestrator/session/compact/summary-mode.mjs +16 -0
- package/src/runtime/agent/orchestrator/session/compact/summary-route.mjs +87 -0
- package/src/runtime/agent/orchestrator/session/compact/summary.mjs +2 -0
- package/src/runtime/agent/orchestrator/session/compact/text-utils.mjs +6 -2
- package/src/runtime/agent/orchestrator/session/compact/user-message-kind.mjs +4 -1
- package/src/runtime/agent/orchestrator/session/compaction-archive-capture.mjs +1 -1
- package/src/runtime/agent/orchestrator/session/context-utils.mjs +41 -10
- package/src/runtime/agent/orchestrator/session/human-gate/delegation.mjs +240 -0
- package/src/runtime/agent/orchestrator/session/human-gate/gate.mjs +102 -35
- package/src/runtime/agent/orchestrator/session/human-gate/outbound-policy.mjs +20 -0
- package/src/runtime/agent/orchestrator/session/human-gate/requests.mjs +19 -9
- package/src/runtime/agent/orchestrator/session/human-gate/run-policy.mjs +73 -0
- package/src/runtime/agent/orchestrator/session/human-gate/store.mjs +55 -27
- package/src/runtime/agent/orchestrator/session/human-gate/unattended-port.mjs +15 -0
- package/src/runtime/agent/orchestrator/session/loop/compact-policy.mjs +4 -1
- package/src/runtime/agent/orchestrator/session/loop/fresh-context.mjs +199 -109
- package/src/runtime/agent/orchestrator/session/loop/loop-state.mjs +5 -0
- package/src/runtime/agent/orchestrator/session/loop/no-tool-turn/continuation.mjs +2 -0
- package/src/runtime/agent/orchestrator/session/loop/no-tool-turn/empty-nudge.mjs +1 -1
- package/src/runtime/agent/orchestrator/session/loop/no-tool-turn/output-limit.mjs +62 -13
- package/src/runtime/agent/orchestrator/session/loop/no-tool-turn.mjs +22 -6
- package/src/runtime/agent/orchestrator/session/loop/pre-dispatch-deny.mjs +6 -2
- package/src/runtime/agent/orchestrator/session/loop/route-fallback.mjs +5 -5
- package/src/runtime/agent/orchestrator/session/loop/send-phase.mjs +10 -0
- package/src/runtime/agent/orchestrator/session/loop/steering.mjs +3 -0
- package/src/runtime/agent/orchestrator/session/loop/tool-exec/before-hook.mjs +33 -8
- package/src/runtime/agent/orchestrator/session/loop/tool-exec/call-prep.mjs +5 -0
- package/src/runtime/agent/orchestrator/session/loop/tool-exec/dispatch.mjs +27 -0
- package/src/runtime/agent/orchestrator/session/loop/tool-exec.mjs +2 -1
- package/src/runtime/agent/orchestrator/session/loop/tool-exposure-migration.mjs +12 -0
- package/src/runtime/agent/orchestrator/session/loop/tool-helpers.mjs +11 -5
- package/src/runtime/agent/orchestrator/session/manager/agent-listing-notice.mjs +102 -0
- package/src/runtime/agent/orchestrator/session/manager/ask-queue.mjs +2 -0
- package/src/runtime/agent/orchestrator/session/manager/ask-session.mjs +13 -1
- package/src/runtime/agent/orchestrator/session/manager/ask-turn-auto-effort.mjs +13 -2
- package/src/runtime/agent/orchestrator/session/manager/ask-turn-execute.mjs +27 -14
- package/src/runtime/agent/orchestrator/session/manager/ask-turn-prepare.mjs +14 -0
- package/src/runtime/agent/orchestrator/session/manager/ask-turn-settle.mjs +4 -0
- package/src/runtime/agent/orchestrator/session/manager/ask-turn-steering-drain.mjs +1 -0
- package/src/runtime/agent/orchestrator/session/manager/compaction-runner.mjs +44 -18
- package/src/runtime/agent/orchestrator/session/manager/idle-cleanup.mjs +32 -1
- package/src/runtime/agent/orchestrator/session/manager/orchestration-mode-switch-notice.mjs +115 -0
- package/src/runtime/agent/orchestrator/session/manager/owner-route-fallbacks.mjs +42 -0
- package/src/runtime/agent/orchestrator/session/manager/pending-message-entry.mjs +6 -0
- package/src/runtime/agent/orchestrator/session/manager/pending-messages.mjs +3 -9
- package/src/runtime/agent/orchestrator/session/manager/pending-spool-file.mjs +1 -1
- package/src/runtime/agent/orchestrator/session/manager/pending-spool-shard.mjs +5 -3
- package/src/runtime/agent/orchestrator/session/manager/prompt-utils.mjs +36 -0
- package/src/runtime/agent/orchestrator/session/manager/rules-cache.mjs +40 -1
- package/src/runtime/agent/orchestrator/session/manager/runtime-liveness.mjs +12 -0
- package/src/runtime/agent/orchestrator/session/manager/runtime-state.mjs +20 -0
- package/src/runtime/agent/orchestrator/session/manager/session-crud.mjs +28 -9
- package/src/runtime/agent/orchestrator/session/manager/session-lifecycle.mjs +55 -27
- package/src/runtime/agent/orchestrator/session/manager/session-prompt-composition.mjs +4 -9
- package/src/runtime/agent/orchestrator/session/manager/session-record.mjs +14 -1
- package/src/runtime/agent/orchestrator/session/manager/session-tool-surface.mjs +7 -3
- package/src/runtime/agent/orchestrator/session/manager/turn-checkpoint-journal.mjs +6 -15
- package/src/runtime/agent/orchestrator/session/manager/turn-interruption.mjs +24 -8
- package/src/runtime/agent/orchestrator/session/manager/workflow-switch-notice.mjs +94 -13
- package/src/runtime/agent/orchestrator/session/pre-send-compact.mjs +52 -11
- package/src/runtime/agent/orchestrator/session/provider-prefix-guard.mjs +21 -3
- package/src/runtime/agent/orchestrator/session/routine-result.d.mts +18 -3
- package/src/runtime/agent/orchestrator/session/routine-result.mjs +126 -12
- package/src/runtime/agent/orchestrator/session/runtime-user-context.mjs +3 -1
- package/src/runtime/agent/orchestrator/session/send-with-recovery.mjs +16 -3
- package/src/runtime/agent/orchestrator/session/side-question-store.mjs +3 -1
- package/src/runtime/agent/orchestrator/session/store/canonical-reader.mjs +41 -7
- package/src/runtime/agent/orchestrator/session/store/lifecycle-barriers.mjs +10 -2
- package/src/runtime/agent/orchestrator/session/store/load-cache.mjs +14 -2
- package/src/runtime/agent/orchestrator/session/store/session-delete.mjs +15 -1
- package/src/runtime/agent/orchestrator/session/store/sweep/stale-sweep.mjs +5 -4
- package/src/runtime/agent/orchestrator/session/store/sweep/sub-agent-retention.mjs +140 -0
- package/src/runtime/agent/orchestrator/session/store/sweep/sweep-plan.mjs +5 -0
- package/src/runtime/agent/orchestrator/session/store/sweep/sweep-record.mjs +15 -5
- package/src/runtime/agent/orchestrator/session/store/sweep/sweep-row.mjs +49 -1
- package/src/runtime/agent/orchestrator/session/store-summary-catalog.mjs +80 -1
- package/src/runtime/agent/orchestrator/session/store-summary-index.mjs +40 -5
- package/src/runtime/agent/orchestrator/session/store-summary-last-message.mjs +47 -2
- package/src/runtime/agent/orchestrator/session/store-summary-reader.mjs +33 -1
- package/src/runtime/agent/orchestrator/session/store-summary-visibility.d.mts +5 -0
- package/src/runtime/agent/orchestrator/session/store-summary-visibility.mjs +37 -0
- package/src/runtime/agent/orchestrator/session/store.mjs +1 -0
- package/src/runtime/agent/orchestrator/session/tail-reminder-rules.mjs +125 -0
- package/src/runtime/agent/orchestrator/session/tool-batch/finalize.mjs +4 -0
- package/src/runtime/agent/orchestrator/session/tool-result-offload.mjs +78 -43
- package/src/runtime/agent/orchestrator/session/transcript-restore/restore.mjs +35 -5
- package/src/runtime/agent/orchestrator/session/transcript-restore/user-text.mjs +42 -2
- package/src/runtime/agent/orchestrator/tools/builtin/advisory-lock.mjs +47 -14
- package/src/runtime/agent/orchestrator/tools/builtin/atomic-write.mjs +25 -5
- package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/backgrounded-result.mjs +6 -3
- package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/completed-result.mjs +13 -14
- package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/transport-artifacts.mjs +9 -0
- package/src/runtime/agent/orchestrator/tools/builtin/bash-tool.mjs +19 -14
- package/src/runtime/agent/orchestrator/tools/builtin/builtin-tools.mjs +7 -1
- package/src/runtime/agent/orchestrator/tools/builtin/git-command-tool.mjs +127 -20
- package/src/runtime/agent/orchestrator/tools/builtin/git-worktree-tool.mjs +557 -0
- package/src/runtime/agent/orchestrator/tools/builtin/lib/shell-job-records.mjs +10 -12
- package/src/runtime/agent/orchestrator/tools/builtin/pdf-test-fixtures.mjs +5 -3
- package/src/runtime/agent/orchestrator/tools/builtin/read-image.mjs +4 -2
- package/src/runtime/agent/orchestrator/tools/builtin/read-single-media.mjs +47 -2
- package/src/runtime/agent/orchestrator/tools/builtin/read-special-files.mjs +264 -87
- package/src/runtime/agent/orchestrator/tools/builtin/shell-analysis.mjs +10 -4
- package/src/runtime/agent/orchestrator/tools/builtin/shell-jobs.mjs +42 -23
- package/src/runtime/agent/orchestrator/tools/code-graph/constants.mjs +8 -4
- package/src/runtime/agent/orchestrator/tools/lib/shell-descendants.mjs +9 -30
- package/src/runtime/agent/orchestrator/tools/lib/shell-run-settle.mjs +24 -12
- package/src/runtime/agent/orchestrator/tools/lib/shell-run-spawn.mjs +3 -2
- package/src/runtime/agent/orchestrator/tools/lib/shell-run-state.mjs +6 -2
- package/src/runtime/agent/orchestrator/tools/patch/delete-quarantine.mjs +2 -1
- package/src/runtime/agent/orchestrator/tools/patch/replay-capture.mjs +4 -2
- package/src/runtime/agent/orchestrator/tools/patch/rollback-state.mjs +33 -2
- package/src/runtime/agent/orchestrator/tools/patch-manifest.json +13 -13
- package/src/runtime/agent/orchestrator/tools/shell-command.mjs +5 -3
- package/src/runtime/agent/orchestrator/tools/shell-exec-output.mjs +3 -1
- package/src/runtime/attachments/attachment-reference.mjs +155 -0
- package/src/runtime/attachments/legacy-office.mjs +110 -0
- package/src/runtime/attachments/limits.mjs +5 -1
- package/src/runtime/attachments/office-extract.mjs +3 -6
- package/src/runtime/attachments/pdf-extract.mjs +84 -10
- package/src/runtime/attachments/prompt-restore.mjs +70 -0
- package/src/runtime/attachments/store.mjs +109 -33
- package/src/runtime/browser-bridge/client.mjs +73 -20
- package/src/runtime/channels/lib/runtime-paths.mjs +1 -1
- package/src/runtime/channels/lib/scheduler.mjs +14 -7
- package/src/runtime/channels/lib/state-file.mjs +15 -15
- package/src/runtime/channels/lib/voice-runtime-fetcher.mjs +14 -13
- package/src/runtime/channels/lib/webhook/relay-tunnel.mjs +22 -18
- package/src/runtime/channels/lib/webhook/session-dispatch.mjs +14 -36
- package/src/runtime/channels/lib/worker-main.mjs +3 -2
- package/src/runtime/effort-judge/compact-tokenizer.mjs +8 -2
- package/src/runtime/effort-judge/judge-client.mjs +66 -16
- package/src/runtime/effort-judge/model-install.mjs +47 -7
- package/src/runtime/local-provider/asset-installer.mjs +10 -4
- package/src/runtime/local-provider/catalog.mjs +5 -2
- package/src/runtime/local-provider/registered-models.mjs +64 -27
- package/src/runtime/local-provider/server.mjs +2 -3
- package/src/runtime/media/adapters/image-api.mjs +89 -0
- package/src/runtime/media/auth.mjs +64 -1
- package/src/runtime/media/catalog.mjs +66 -4
- package/src/runtime/media/jobs.mjs +4 -0
- package/src/runtime/media/lanes.mjs +46 -5
- package/src/runtime/media/media-usage.mjs +17 -0
- package/src/runtime/media/renditions.mjs +15 -15
- package/src/runtime/media/store.mjs +36 -35
- package/src/runtime/media/tool.mjs +8 -1
- package/src/runtime/memory/lib/cycle-scheduler/health-ledger.mjs +8 -2
- package/src/runtime/memory/lib/embedding-model-files.mjs +30 -7
- package/src/runtime/memory/lib/ingest/transcript-tail.mjs +16 -7
- package/src/runtime/memory/lib/memory-chunk-quality.mjs +14 -2
- package/src/runtime/memory/lib/pg/process.mjs +8 -4
- package/src/runtime/memory/lib/project-id-resolver.mjs +5 -1
- package/src/runtime/memory/lib/runtime-fetcher.mjs +6 -1
- package/src/runtime/office/core/journal.mjs +7 -14
- package/src/runtime/office/design/library/design-library-core.mjs +4 -16
- package/src/runtime/office/pdf/ocr-engine-worker.mjs +37 -0
- package/src/runtime/office/pdf/ocr-engine.mjs +146 -0
- package/src/runtime/office/pdf/pdf-ocr.mjs +51 -21
- package/src/runtime/office/pdf/pdf-render.mjs +30 -18
- package/src/runtime/office/portable/ooxml-validator.mjs +2 -2
- package/src/runtime/office/portable/portable-soffice.mjs +135 -29
- package/src/runtime/shared/agent-avatar-sprites.mjs +23 -8
- package/src/runtime/shared/agent-avatar.mjs +3 -2
- package/src/runtime/shared/agent-kind-migration.mjs +200 -0
- package/src/runtime/shared/agent-message-envelope.d.mts +6 -0
- package/src/runtime/shared/agent-message-envelope.mjs +44 -0
- package/src/runtime/shared/agent-reap-state.d.mts +4 -0
- package/src/runtime/shared/agent-room-host.d.mts +31 -0
- package/src/runtime/shared/agent-room-host.mjs +58 -0
- package/src/runtime/shared/agent-store.mjs +24 -7
- package/src/runtime/shared/agent-task-starts.mjs +27 -0
- package/src/runtime/shared/atomic-file.d.mts +50 -0
- package/src/runtime/shared/atomic-file.mjs +394 -132
- package/src/runtime/shared/background-tasks.mjs +7 -4
- package/src/runtime/shared/bot-hops.mjs +35 -0
- package/src/runtime/shared/bot-split-migration.mjs +1 -1
- package/src/runtime/shared/bounded-download.mjs +4 -2
- package/src/runtime/shared/config.mjs +39 -9
- package/src/runtime/shared/defaults-separation.mjs +6 -2
- package/src/runtime/shared/delegated-approval-host.mjs +74 -0
- package/src/runtime/shared/err-text.mjs +4 -0
- package/src/runtime/shared/error-presentation.mjs +22 -4
- package/src/runtime/shared/file-has-data.mjs +28 -0
- package/src/runtime/shared/llm/usage-ledger-import.mjs +37 -18
- package/src/runtime/shared/pending-agent-work.mjs +54 -0
- package/src/runtime/shared/process-lifecycle.mjs +8 -12
- package/src/runtime/shared/projects.mjs +50 -41
- package/src/runtime/shared/provider-accounts.mjs +17 -12
- package/src/runtime/shared/redact-directories.mjs +18 -0
- package/src/runtime/shared/remove-directory.mjs +28 -0
- package/src/runtime/shared/routine-trigger.d.mts +6 -1
- package/src/runtime/shared/routine-trigger.mjs +14 -6
- package/src/runtime/shared/run-child.d.mts +3 -0
- package/src/runtime/shared/run-child.mjs +24 -3
- package/src/runtime/shared/session-baseline-store.mjs +8 -2
- package/src/runtime/shared/session-sidebar-host.d.mts +11 -2
- package/src/runtime/shared/session-sidebar-host.mjs +16 -3
- package/src/runtime/shared/singleton-owner.mjs +7 -6
- package/src/runtime/shared/skill-tool-dependencies.mjs +4 -10
- package/src/runtime/shared/staged-update.mjs +4 -2
- package/src/runtime/shared/statusline/statusline-segments.mjs +4 -15
- package/src/runtime/shared/tool-execution-contract.mjs +10 -0
- package/src/runtime/shared/tool-work-units.mjs +12 -9
- package/src/runtime/shared/transcript-metadata.mjs +28 -3
- package/src/runtime/shared/transcript-writer/session-record.mjs +7 -6
- package/src/runtime/shared/turn-snapshot-store.mjs +5 -4
- package/src/runtime/shared/turn-snapshot.mjs +277 -124
- package/src/runtime/shared/user-cwd.mjs +9 -4
- package/src/runtime/shared/user-data-guard.mjs +92 -61
- package/src/runtime/shared/utf8-cut.mjs +10 -0
- package/src/runtime/shared/worktrees/activity-gate.mjs +251 -61
- package/src/runtime/shared/worktrees/contract.mjs +11 -3
- package/src/runtime/shared/worktrees/maintenance.mjs +11 -2
- package/src/runtime/shared/worktrees/manager.mjs +419 -52
- package/src/runtime/shared/worktrees/registry.mjs +29 -27
- package/src/runtime/shared/worktrees/tool-host.mjs +39 -0
- package/src/runtime/tidy/core-install.mjs +26 -4
- package/src/runtime/tidy/install.mjs +91 -23
- package/src/runtime/tidy/process.mjs +41 -8
- package/src/runtime/tidy/resolve.mjs +10 -7
- package/src/runtime/web-search/lib/config.mjs +4 -16
- package/src/session-runtime/agent-home-delivery.mjs +542 -204
- package/src/session-runtime/agent-profile-changes.mjs +16 -0
- package/src/session-runtime/agent-room-delivery.mjs +81 -35
- package/src/session-runtime/agent-task-sessions.mjs +811 -179
- package/src/session-runtime/agent-tool-routing.mjs +1 -0
- package/src/session-runtime/boot/apis.mjs +48 -24
- package/src/session-runtime/boot/config.mjs +1 -0
- package/src/session-runtime/boot/facade.mjs +16 -7
- package/src/session-runtime/boot/infrastructure.mjs +14 -2
- package/src/session-runtime/boot/providers.mjs +2 -2
- package/src/session-runtime/boot/shared.mjs +12 -6
- package/src/session-runtime/boot/tools.mjs +23 -3
- package/src/session-runtime/bot-status.mjs +432 -0
- package/src/session-runtime/config-lifecycle/lead-route-sync.mjs +29 -0
- package/src/session-runtime/config-lifecycle.mjs +60 -55
- package/src/session-runtime/cwd-plugins/core-memory-context.mjs +2 -4
- package/src/session-runtime/held-requests.mjs +31 -33
- package/src/session-runtime/internal-tool-executor/bridge-tools.mjs +10 -1
- package/src/session-runtime/internal-tool-executor/feature-tools.mjs +2 -2
- package/src/session-runtime/internal-tool-executor/workspace-tools.mjs +24 -26
- package/src/session-runtime/lifecycle/session-catalog.mjs +12 -2
- package/src/session-runtime/lifecycle/teardown.mjs +11 -3
- package/src/session-runtime/mcp-glue/connect.mjs +100 -186
- package/src/session-runtime/mcp-glue/initial-connect-gate.mjs +57 -0
- package/src/session-runtime/mcp-glue/server-connection.mjs +71 -0
- package/src/session-runtime/media-api.mjs +5 -2
- package/src/session-runtime/model-recency.mjs +1 -0
- package/src/session-runtime/model-route/route-tuning.mjs +4 -1
- package/src/session-runtime/model-route/set-route.mjs +61 -1
- package/src/session-runtime/owned-automation-run.mjs +8 -1
- package/src/session-runtime/provider-models/row-hydration.mjs +8 -1
- package/src/session-runtime/quick-model-rows/model-meta.mjs +2 -0
- package/src/session-runtime/quick-model-rows/provider-rows.mjs +7 -1
- package/src/session-runtime/route-resolution.mjs +16 -8
- package/src/session-runtime/route-state.mjs +1 -59
- package/src/session-runtime/routine-home-turn.mjs +5 -3
- package/src/session-runtime/runtime-bootstrap.mjs +5 -3
- package/src/session-runtime/runtime-paths.mjs +11 -5
- package/src/session-runtime/runtime-review-api.mjs +4 -1
- package/src/session-runtime/runtime-tunables.mjs +6 -0
- package/src/session-runtime/services/agent-tool/close-flow/close-all.mjs +11 -2
- package/src/session-runtime/services/agent-tool/close-flow.mjs +4 -2
- package/src/session-runtime/services/agent-tool/execute-send.mjs +1 -0
- package/src/session-runtime/services/agent-tool/execute-spawn.mjs +1 -0
- package/src/session-runtime/services/agent-tool/job-views/agent-list.mjs +34 -19
- package/src/session-runtime/services/agent-tool/restart-notify.mjs +10 -0
- package/src/session-runtime/services/agent-tool/send-flow.mjs +25 -21
- package/src/session-runtime/services/agent-tool/spawn-flow/job-start.mjs +7 -0
- package/src/session-runtime/services/agent-tool/spawn-flow/spawn-prep.mjs +6 -3
- package/src/session-runtime/services/agent-tool/spawn-flow/spawn-run.mjs +8 -5
- package/src/session-runtime/services/agent-tool/worker-index/row-liveness.mjs +22 -2
- package/src/session-runtime/services/agent-tool/worker-index.mjs +4 -6
- package/src/session-runtime/services/agent-tool.mjs +6 -0
- package/src/session-runtime/services/daemon-crash-capture/daemon-exit-record.mjs +1 -1
- package/src/session-runtime/services/daemon-crash-capture/retention.mjs +4 -3
- package/src/session-runtime/services/hook-bus/config-loader.mjs +14 -5
- package/src/session-runtime/services/hook-bus/rule-file.mjs +49 -11
- package/src/session-runtime/services/plugin-admin.mjs +26 -26
- package/src/session-runtime/services/provider-admin.mjs +26 -6
- package/src/session-runtime/services/schedule-access.mjs +33 -4
- package/src/session-runtime/services/seeds.mjs +4 -3
- package/src/session-runtime/services/usage-dashboard.mjs +1 -1
- package/src/session-runtime/services/usage-stats-model.mjs +2 -1
- package/src/session-runtime/services/worktree-access.mjs +27 -0
- package/src/session-runtime/session-create/materialize.mjs +2 -3
- package/src/session-runtime/session-create/session-options.mjs +15 -2
- package/src/session-runtime/session-hooks.mjs +9 -17
- package/src/session-runtime/settings-builtin-tools-api.mjs +65 -1
- package/src/session-runtime/settings-compaction-api.mjs +86 -39
- package/src/session-runtime/setup-tool/executor.mjs +12 -2
- package/src/session-runtime/setup-tool/settings-contract.mjs +34 -1
- package/src/session-runtime/setup-tool/tool-defs.mjs +20 -3
- package/src/session-runtime/skills-api.mjs +12 -5
- package/src/session-runtime/tool-policy/agent-profile-fold.mjs +349 -0
- package/src/session-runtime/tool-policy/mode-switch.mjs +54 -0
- package/src/session-runtime/tool-policy/pending-switches.mjs +59 -0
- package/src/session-runtime/tool-policy/policy-stage.mjs +183 -0
- package/src/session-runtime/tool-policy/session-switches.mjs +169 -0
- package/src/session-runtime/tool-policy/surface-helpers.mjs +114 -0
- package/src/session-runtime/tool-policy/workflow-overlay.mjs +145 -0
- package/src/session-runtime/tool-policy-refresh.mjs +48 -369
- package/src/session-runtime/tool-surface.mjs +10 -4
- package/src/session-runtime/turn/session-ops.mjs +8 -0
- package/src/session-runtime/turn/turn-run/turn-prepare.mjs +95 -88
- package/src/session-runtime/turn/turn-run/turn-timing.mjs +4 -3
- package/src/session-runtime/turn/turn-run.mjs +7 -2
- package/src/session-runtime/workflow-agents-api/agent-connectors.mjs +54 -7
- package/src/session-runtime/workflow-agents-api/agent-editor.mjs +527 -333
- package/src/session-runtime/workflow-agents-api/agent-route.mjs +85 -63
- package/src/session-runtime/workflow-agents-api/shared.mjs +5 -1
- package/src/session-runtime/workflow-agents-api/style-and-mode.mjs +14 -1
- package/src/session-runtime/workflow-agents-api/workflow-packs.mjs +6 -3
- package/src/session-runtime/workspace/transition-steps.mjs +1 -18
- package/src/session-runtime/workspace/transitions.mjs +279 -67
- package/src/session-runtime/workspace/workspace-state.mjs +7 -6
- package/src/session-runtime/workspace/worktree-tool.mjs +194 -0
- package/src/standalone/daemon-agent-control.mjs +4 -1
- package/src/standalone/daemon-lag-profiler.mjs +3 -1
- package/src/standalone/daemon-session-control.mjs +173 -15
- package/src/standalone/daemon-telemetry.mjs +9 -0
- package/src/standalone/daemon.mjs +33 -10
- package/src/standalone/local-session-runtime.mjs +33 -16
- package/src/standalone/session-client.mjs +7 -2
- package/src/standalone/session-protocol.mjs +8 -0
- package/src/standalone/session-runtime-inline-host/boot-loaders.mjs +2 -0
- package/src/standalone/session-service/agent-route-follow.mjs +69 -0
- package/src/standalone/session-service/session-calls/session-turns.mjs +33 -4
- package/src/standalone/session-service.mjs +21 -0
- package/src/standalone/session-state-projection.mjs +19 -9
- package/src/standalone/session-tool-output.mjs +36 -9
- package/src/standalone/staged-import.mjs +47 -0
- package/src/tui/App.jsx +2 -0
- package/src/tui/app/maintenance-pickers/auto-clear-picker.mjs +19 -13
- package/src/tui/app/message-selector.mjs +15 -2
- package/src/tui/app/model-options.mjs +16 -2
- package/src/tui/app/model-picker.mjs +2 -1
- package/src/tui/app/route-pickers.mjs +3 -1
- package/src/tui/app/settings-picker/settings-rows.mjs +2 -2
- package/src/tui/app/slash-commands.mjs +1 -1
- package/src/tui/app/usage-context-panels/context-model.mjs +8 -2
- package/src/tui/dist/index.mjs +617 -369
- package/src/tui/paste-attachments.mjs +0 -1
- package/src/tui/paste-text-policy.mjs +4 -5
- package/src/tui/prompt-history-store.mjs +16 -21
- package/src/tui/session/agent-job-feed/execution-delivery.mjs +4 -1
- package/src/tui/session/context-state.mjs +4 -0
- package/src/tui/session/notice-surface.mjs +3 -0
- package/src/tui/session/session-api/intake/abort.mjs +52 -18
- package/src/tui/session/session-api/intake/rewind.mjs +39 -4
- package/src/tui/session/session-api/media.mjs +2 -1
- package/src/tui/session/session-api/routes-agent-definitions.mjs +76 -0
- package/src/tui/session/session-api/routes-write.mjs +203 -0
- package/src/tui/session/session-api/routes.mjs +23 -247
- package/src/tui/session/session-api/settings.mjs +14 -1
- package/src/tui/session/session-flow/drain.mjs +28 -3
- package/src/tui/session/session-flow/failed-turn-rewind.mjs +4 -2
- package/src/tui/session/session-flow/queue/take-entries.mjs +8 -0
- package/src/tui/session/session-flow/steering.mjs +8 -3
- package/src/tui/session/tool-approval.mjs +142 -14
- package/src/tui/session/transcript-intake.mjs +2 -0
- package/src/tui/session/turn.mjs +23 -14
- package/src/tui/transcript-tool-failures.mjs +8 -2
- package/src/vendor/statusline/src/gateway/route-meta.mjs +7 -8
- package/src/vendor/statusline/src/gateway/session-routes.mjs +6 -7
- package/src/rules/agent-mode/ROUTINE.md +0 -6
- package/src/session-runtime/room-member-gate.mjs +0 -48
|
@@ -22,7 +22,10 @@ function customProviderModels(provider, providerConfig, discovered = providerCac
|
|
|
22
22
|
} catch {
|
|
23
23
|
return [];
|
|
24
24
|
}
|
|
25
|
-
|
|
25
|
+
const providerName = clean(config.name);
|
|
26
|
+
return effectiveCustomModelRows(config, discovered, { providerId: provider }).map((row) =>
|
|
27
|
+
providerName ? { ...row, providerName } : row
|
|
28
|
+
);
|
|
26
29
|
}
|
|
27
30
|
|
|
28
31
|
export function createQuickProviderRows({
|
|
@@ -53,6 +56,8 @@ export function createQuickProviderRows({
|
|
|
53
56
|
display: model.display || model.name || modelId,
|
|
54
57
|
contextWindow: model.contextWindow || meta.contextWindow || null,
|
|
55
58
|
outputTokens: model.outputTokens || meta.outputTokens || null,
|
|
59
|
+
// An explicit value (an override's false included) wins; the catalog fills the rest.
|
|
60
|
+
supportsVision: model.supportsVision ?? meta.supportsVision,
|
|
56
61
|
supportsReasoning: model.supportsReasoning === true || meta.supportsReasoning === true,
|
|
57
62
|
supportsFunctionCalling: model.supportsFunctionCalling === true || meta.supportsFunctionCalling === true,
|
|
58
63
|
supportsPromptCaching: model.supportsPromptCaching === true || meta.supportsPromptCaching === true,
|
|
@@ -78,6 +83,7 @@ export function createQuickProviderRows({
|
|
|
78
83
|
contextWindow: meta.contextWindow || null,
|
|
79
84
|
outputTokens: meta.outputTokens || null,
|
|
80
85
|
latest: routeLike.latest === true,
|
|
86
|
+
supportsVision: meta.supportsVision,
|
|
81
87
|
supportsReasoning: !!routeLike.effort || meta.supportsReasoning === true,
|
|
82
88
|
supportsFunctionCalling: meta.supportsFunctionCalling === true,
|
|
83
89
|
supportsPromptCaching: meta.supportsPromptCaching === true,
|
|
@@ -22,6 +22,10 @@ export function createRouteResolution({ rt, collectProviderModels, ensureProvide
|
|
|
22
22
|
if (routeHasModel()) return rt.route;
|
|
23
23
|
const models = await runAbortable(signal, () => collectProviderModels());
|
|
24
24
|
throwIfAborted(signal);
|
|
25
|
+
// A model chosen during the catalog read stands: a new task's reservation
|
|
26
|
+
// prewarm starts on the empty route, its draft model lands meanwhile, and
|
|
27
|
+
// the first prompt joins this very prewarm.
|
|
28
|
+
if (routeHasModel()) return rt.route;
|
|
25
29
|
if (!models?.length) {
|
|
26
30
|
throw new Error('No provider models available. Open /providers to sign in, then /model to choose a model.');
|
|
27
31
|
}
|
|
@@ -47,15 +51,19 @@ export function createRouteResolution({ rt, collectProviderModels, ensureProvide
|
|
|
47
51
|
.find((option) => option?.id === 'context')
|
|
48
52
|
?.options?.find((option) => clean(option?.value) === contextValue);
|
|
49
53
|
const modelDisplay = routeModelDisplay(rt.config, targetRoute, modelMeta);
|
|
50
|
-
|
|
54
|
+
// Without a known window the selection (share, exact tokens, resolved
|
|
55
|
+
// window) is kept as requested — the session sizes it from the provider's
|
|
56
|
+
// window; dropping it silently put the route back on the model's default.
|
|
57
|
+
// With one it is the clamped value, absent when it is the default window.
|
|
58
|
+
const windowKnown = contextState.contextDefaultPercent !== undefined;
|
|
59
|
+
const selectedContextWindow = [
|
|
60
|
+
contextState.selectedContextWindow,
|
|
61
|
+
contextOption?.contextWindow,
|
|
62
|
+
windowKnown ? undefined : targetRoute.selectedContextWindow,
|
|
63
|
+
]
|
|
51
64
|
.map(Number)
|
|
52
65
|
.find((value) => value > 0);
|
|
53
|
-
|
|
54
|
-
// one it is the clamped value, absent when it is the default window.
|
|
55
|
-
const contextTokens =
|
|
56
|
-
contextState.contextDefaultPercent === undefined
|
|
57
|
-
? normalizeContextTokens(targetRoute.contextTokens)
|
|
58
|
-
: contextState.contextTokens;
|
|
66
|
+
const contextTokens = windowKnown ? contextState.contextTokens : normalizeContextTokens(targetRoute.contextTokens);
|
|
59
67
|
const { contextTokens: _requestedTokens, ...routeFields } = targetRoute;
|
|
60
68
|
rt.route = {
|
|
61
69
|
...routeFields,
|
|
@@ -63,7 +71,7 @@ export function createRouteResolution({ rt, collectProviderModels, ensureProvide
|
|
|
63
71
|
fastCapable,
|
|
64
72
|
effectiveEffort,
|
|
65
73
|
effortOptions: effortItemsFor(rt.route.provider, modelMeta, effectiveEffort),
|
|
66
|
-
contextPercent: contextState.contextPercent,
|
|
74
|
+
contextPercent: windowKnown ? contextState.contextPercent : targetRoute.contextPercent,
|
|
67
75
|
contextDefaultPercent: contextState.contextDefaultPercent,
|
|
68
76
|
...(contextTokens ? { contextTokens } : {}),
|
|
69
77
|
...(selectedContextWindow ? { selectedContextWindow } : {}),
|
|
@@ -7,8 +7,6 @@ import {
|
|
|
7
7
|
import { clean, hasOwn } from '../runtime/agent/orchestrator/runtime-core/session-text.mjs';
|
|
8
8
|
import { coerceEffortFor } from '../runtime/agent/orchestrator/runtime-core/effort.mjs';
|
|
9
9
|
import { fastCapableFor } from '../runtime/agent/orchestrator/runtime-core/model-capabilities.mjs';
|
|
10
|
-
import { providerCachedModelMetadataSync } from '../runtime/agent/orchestrator/providers/provider-catalog-cache.mjs';
|
|
11
|
-
import { contextWindowRange, normalizeContextTokens } from '../runtime/shared/llm/default-context-window.mjs';
|
|
12
10
|
|
|
13
11
|
export function resolveRouteEffortState(targetRoute = {}, modelMeta = null) {
|
|
14
12
|
const requested = hasOwn(targetRoute, 'effort') ? targetRoute.effort : targetRoute.preset?.effort || null;
|
|
@@ -36,63 +34,7 @@ export function selectionFastCapable(provider, modelMeta, effort, modelParameter
|
|
|
36
34
|
return !modelMetaLooksResolved(modelMeta) || fastCapableFor(provider, modelMeta, effort, modelParameters);
|
|
37
35
|
}
|
|
38
36
|
|
|
39
|
-
|
|
40
|
-
// slider against, so they carry both windows (openai-oauth: 272k default /
|
|
41
|
-
// 1M max). Reading them keeps a percentage saved against the picker's scale
|
|
42
|
-
// meaningful; anything that only knows a single window would silently rescale
|
|
43
|
-
// it (30% of 272k instead of 30% of 1M).
|
|
44
|
-
function cachedRouteWindows(provider, model) {
|
|
45
|
-
const row = providerCachedModelMetadataSync(provider, model)?.rawProviderModel || null;
|
|
46
|
-
if (!row) return null;
|
|
47
|
-
const contextWindow = Number(row.contextWindow ?? row.context_window ?? row.max_input_tokens) || 0;
|
|
48
|
-
const maxContextWindow = Number(row.maxContextWindow ?? row.max_context_window) || 0;
|
|
49
|
-
return contextWindow > 0 || maxContextWindow > 0 ? { contextWindow, maxContextWindow } : null;
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
export function resolveRouteContextState(targetRoute = {}, modelMeta = null, windowLookup = cachedRouteWindows) {
|
|
53
|
-
// Only providers that implement getCachedModelInfo (openai-oauth, cursor,
|
|
54
|
-
// openai-compat, opencode-go) hand lookupModelMeta a window; every other one
|
|
55
|
-
// (anthropic-oauth, grok-oauth, gemini, …) gets the bare `{ id, provider }`
|
|
56
|
-
// placeholder. Reading the window from that alone yields 0, which dropped the
|
|
57
|
-
// saved context percentage for the entire session — while resolveSessionContextMeta
|
|
58
|
-
// went on to size that session from the provider/catalog window (Claude Opus 5:
|
|
59
|
-
// a full 1M rather than the selected 500k). Read the cached provider row here so
|
|
60
|
-
// the percentage and the session boundary cannot disagree.
|
|
61
|
-
const windowMeta =
|
|
62
|
-
Number(modelMeta?.contextWindow) > 0 || Number(modelMeta?.maxContextWindow) > 0
|
|
63
|
-
? modelMeta
|
|
64
|
-
: windowLookup?.(clean(targetRoute?.provider), clean(targetRoute?.model)) || modelMeta;
|
|
65
|
-
const { defaultWindow, maxWindow } = contextWindowRange({
|
|
66
|
-
provider: clean(targetRoute?.provider),
|
|
67
|
-
contextWindow: windowMeta?.contextWindow,
|
|
68
|
-
maxContextWindow: windowMeta?.maxContextWindow,
|
|
69
|
-
});
|
|
70
|
-
if (!maxWindow) {
|
|
71
|
-
return { contextPercent: undefined, contextDefaultPercent: undefined, selectedContextWindow: undefined };
|
|
72
|
-
}
|
|
73
|
-
const contextDefaultPercent = Math.max(10, Math.min(100, Math.round((defaultWindow / maxWindow) * 10) * 10));
|
|
74
|
-
// An exact token selection overrides the 10% stops. It is clamped to the
|
|
75
|
-
// selectable range; one that lands on the default window is the default.
|
|
76
|
-
const requestedTokens = normalizeContextTokens(targetRoute?.contextTokens);
|
|
77
|
-
if (requestedTokens) {
|
|
78
|
-
const contextTokens = Math.max(Math.ceil(maxWindow * 0.1), Math.min(maxWindow, requestedTokens));
|
|
79
|
-
if (contextTokens === defaultWindow) {
|
|
80
|
-
return { contextPercent: contextDefaultPercent, contextDefaultPercent, selectedContextWindow: defaultWindow };
|
|
81
|
-
}
|
|
82
|
-
const contextPercent = Math.max(10, Math.min(100, Math.round((contextTokens / maxWindow) * 10) * 10));
|
|
83
|
-
return { contextPercent, contextDefaultPercent, selectedContextWindow: contextTokens, contextTokens };
|
|
84
|
-
}
|
|
85
|
-
const requested = Number(targetRoute?.contextPercent);
|
|
86
|
-
const contextPercent =
|
|
87
|
-
Number.isFinite(requested) && requested > 0
|
|
88
|
-
? Math.max(10, Math.min(100, Math.round(requested / 10) * 10))
|
|
89
|
-
: contextDefaultPercent;
|
|
90
|
-
const selectedContextWindow =
|
|
91
|
-
contextPercent === contextDefaultPercent
|
|
92
|
-
? defaultWindow
|
|
93
|
-
: Math.max(1, Math.floor((maxWindow * contextPercent) / 100));
|
|
94
|
-
return { contextPercent, contextDefaultPercent, selectedContextWindow };
|
|
95
|
-
}
|
|
37
|
+
export { resolveRouteContextState } from '../runtime/agent/orchestrator/runtime-core/route-context-state.mjs';
|
|
96
38
|
|
|
97
39
|
/**
|
|
98
40
|
* Human label for the statusline. A display-only user alias
|
|
@@ -9,8 +9,10 @@
|
|
|
9
9
|
* it rides the thread's queue as its own `routine` entry (one per turn, never
|
|
10
10
|
* merged or steered into another), shows as a routine marker row, and selects
|
|
11
11
|
* skills only from the routine's instructions (`skillSelection`), never from a
|
|
12
|
-
* webhook payload. While it runs the thread counts as unattended
|
|
13
|
-
*
|
|
12
|
+
* webhook payload. While it runs the thread counts as an unattended run
|
|
13
|
+
* (held-requests.mjs): the saved routine is the user's grant, so it never asks
|
|
14
|
+
* (outbound actions are allowed within the bot's permissions; payments and
|
|
15
|
+
* permanent deletes are refused, human-gate/run-policy.mjs). Resolves with the
|
|
14
16
|
* reply once the turn ends; rejects when the turn fails, is cancelled, or the
|
|
15
17
|
* caller's `signal` aborts (which also aborts the turn once it runs).
|
|
16
18
|
*/
|
|
@@ -126,7 +128,7 @@ export async function runRoutineTurn(
|
|
|
126
128
|
onCommitted: () => {
|
|
127
129
|
if (started) return;
|
|
128
130
|
started = true;
|
|
129
|
-
// Nobody watches this turn:
|
|
131
|
+
// Nobody watches this turn: it never asks (run-policy.mjs).
|
|
130
132
|
unmark = markUnattendedRun(homeId, { kind, agentId, name });
|
|
131
133
|
if (aborted) void abortTurn();
|
|
132
134
|
},
|
|
@@ -13,22 +13,24 @@ import {
|
|
|
13
13
|
CODE_GRAPH_TOOL_DEFS,
|
|
14
14
|
STATUSLINE_SESSION_ROUTES,
|
|
15
15
|
STANDALONE_ROOT,
|
|
16
|
-
|
|
16
|
+
standaloneDataDir,
|
|
17
17
|
} from './runtime-paths.mjs';
|
|
18
18
|
|
|
19
19
|
export function prepareStandaloneEnvironment() {
|
|
20
20
|
process.env.MIXDOG_QUIET_SESSION_LOG ??= '1';
|
|
21
21
|
const startedAt = performance.now();
|
|
22
|
+
// Resolved per runtime start: this start's data folder, not the first one's.
|
|
23
|
+
const dataDir = standaloneDataDir();
|
|
22
24
|
ensureStandaloneEnvironment({
|
|
23
25
|
rootDir: STANDALONE_ROOT,
|
|
24
|
-
dataDir
|
|
26
|
+
dataDir,
|
|
25
27
|
});
|
|
26
28
|
// Office journals exist only for cross-process crash recovery, so startup just
|
|
27
29
|
// prunes expired ones in the background. Surfacing them as session context made
|
|
28
30
|
// every new session (agents included) re-announce unrelated leftovers for the
|
|
29
31
|
// full 30-day retention window; recovery stays reachable on demand through
|
|
30
32
|
// office action=transactions / action=recover.
|
|
31
|
-
listOfficeJournals(
|
|
33
|
+
listOfficeJournals(dataDir).catch(() => {});
|
|
32
34
|
bootProfile('standalone-env:ready', { ms: (performance.now() - startedAt).toFixed(1) });
|
|
33
35
|
}
|
|
34
36
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { dirname, join } from 'node:path';
|
|
1
|
+
import { dirname } from 'node:path';
|
|
3
2
|
import { fileURLToPath } from 'node:url';
|
|
3
|
+
import { resolvePluginData } from '../runtime/shared/plugin-paths.mjs';
|
|
4
4
|
|
|
5
5
|
export const RUNTIME = '../runtime/agent/orchestrator';
|
|
6
6
|
export const WEB_SEARCH_RUNTIME = '../runtime/web-search/index.mjs';
|
|
@@ -12,10 +12,16 @@ export const STATUSLINE_SESSION_ROUTES = '../vendor/statusline/src/gateway/sessi
|
|
|
12
12
|
|
|
13
13
|
const SESSION_RUNTIME_DIR = dirname(fileURLToPath(import.meta.url));
|
|
14
14
|
export const STANDALONE_ROOT = dirname(SESSION_RUNTIME_DIR);
|
|
15
|
-
|
|
16
|
-
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* The standalone data directory, resolved from the environment on every call.
|
|
18
|
+
* A runtime start (a pristine boundary, a second page session) retargets
|
|
19
|
+
* MIXDOG_DATA_DIR, so a load-time constant would point every later start back
|
|
20
|
+
* at the first run's folder.
|
|
21
|
+
*/
|
|
22
|
+
export const standaloneDataDir = resolvePluginData;
|
|
17
23
|
|
|
18
24
|
/** The data directory a runtime writes to: its config module's plugin data dir, else the standalone default. */
|
|
19
25
|
export function pluginDataDir(cfgMod) {
|
|
20
|
-
return cfgMod.getPluginData?.() ||
|
|
26
|
+
return cfgMod.getPluginData?.() || standaloneDataDir();
|
|
21
27
|
}
|
|
@@ -2,6 +2,7 @@ import { registerCacheInvalidationListener } from '../runtime/agent/orchestrator
|
|
|
2
2
|
import { turnReviewReply } from '../runtime/shared/turn-review-reply.mjs';
|
|
3
3
|
import {
|
|
4
4
|
clearSessionChangeHistory,
|
|
5
|
+
forgetTurnSnapshotSession,
|
|
5
6
|
getSessionReviewDiff,
|
|
6
7
|
getSessionReviewFilePatch,
|
|
7
8
|
getTurnChanges,
|
|
@@ -19,8 +20,10 @@ import { registerSessionPurgeHook } from '../runtime/agent/orchestrator/session/
|
|
|
19
20
|
|
|
20
21
|
// A deleted history stays deleted for as long as its session exists; the
|
|
21
22
|
// session's own deletion takes the marker — and its stored first-seen file
|
|
22
|
-
// contents — with it
|
|
23
|
+
// contents — with it, and its in-memory turn, parked worker reviews and
|
|
24
|
+
// bound worker trackers.
|
|
23
25
|
registerSessionPurgeHook((sessionId) => {
|
|
26
|
+
forgetTurnSnapshotSession(sessionId);
|
|
24
27
|
void forgetSessionChangeHistoryMarker(sessionId);
|
|
25
28
|
void forgetSessionBaselines(sessionId);
|
|
26
29
|
});
|
|
@@ -36,6 +36,12 @@ export function readRuntimeTunables() {
|
|
|
36
36
|
// connected tools fold synchronously; in-flight servers join through the
|
|
37
37
|
// late-tool announcement path. Operators may opt back into a grace window.
|
|
38
38
|
mcpTurnGraceMs: envDelayMs('MIXDOG_MCP_TURN_GRACE_MS', 0, { min: 0, max: 2_000 }),
|
|
39
|
+
// A spawned agent's first turn may be its only one, so it waits for the
|
|
40
|
+
// initial connect — but only this long: a slow-but-alive server (a
|
|
41
|
+
// 20 s handshake is seen in the wild) must not hold the first model
|
|
42
|
+
// request for its whole startup budget. Later servers join through the
|
|
43
|
+
// late-tool announcement path on the agent's next turn.
|
|
44
|
+
mcpAgentGraceMs: envDelayMs('MIXDOG_MCP_AGENT_GRACE_MS', 3_000, { min: 0, max: 30_000 }),
|
|
39
45
|
// Boot-time remote start is deferred past the first frame; see the caller.
|
|
40
46
|
remoteAutoStartDelayMs: envDelayMs('MIXDOG_REMOTE_AUTOSTART_DELAY_MS', 1_500, { min: 0, max: 60_000 }),
|
|
41
47
|
providerWarmupEnabled:
|
|
@@ -5,6 +5,7 @@ import { cancelBackgroundTask, listBackgroundTasks } from '../../../../runtime/s
|
|
|
5
5
|
import { presentErrorText } from '../../../../runtime/shared/err-text.mjs';
|
|
6
6
|
import { clean } from '../helpers.mjs';
|
|
7
7
|
import { isLeadPoolAgent } from '../worker-rows.mjs';
|
|
8
|
+
import { isUnnotifiedRestartFailure } from '../worker-index/row-liveness.mjs';
|
|
8
9
|
|
|
9
10
|
export function createCloseAll({ registry, close }) {
|
|
10
11
|
const { tags, tagAgents, tagCwds } = registry;
|
|
@@ -17,11 +18,13 @@ export function createCloseAll({ registry, close }) {
|
|
|
17
18
|
|
|
18
19
|
// Drop the closed workers' rows: every non-Lead row for an unscoped
|
|
19
20
|
// teardown, only this owner's (plus the rows just closed) for a scoped one.
|
|
21
|
+
// A row whose owner is still owed its restart failure stays (a process exit
|
|
22
|
+
// closes every worker; the next process tells the owner).
|
|
20
23
|
function purgeWorkerRows(ownerSessionId, closedSessionIds) {
|
|
21
24
|
registry.flushWorkerIndexMutations();
|
|
22
25
|
registry.writeWorkerRows((byKey, tombstonesByKey) => {
|
|
23
26
|
for (const [key, row] of [...byKey.entries()]) {
|
|
24
|
-
if (isLeadPoolAgent(row.agent)) continue;
|
|
27
|
+
if (isLeadPoolAgent(row.agent) || isUnnotifiedRestartFailure(row)) continue;
|
|
25
28
|
if (
|
|
26
29
|
ownerSessionId &&
|
|
27
30
|
clean(row.ownerSessionId) !== ownerSessionId &&
|
|
@@ -38,15 +41,20 @@ export function createCloseAll({ registry, close }) {
|
|
|
38
41
|
// Lead's workers: the worker index and task registry are shared by every
|
|
39
42
|
// Lead in the process, and an unscoped sweep wiped sibling Leads' idle
|
|
40
43
|
// workers mid-window.
|
|
44
|
+
// A process exit (`scope.processExit`) closes the workers but keeps their
|
|
45
|
+
// rows: the next process lists the finished ones for their pane window and
|
|
46
|
+
// settles the ones the exit cut off (restart-notify), exactly as after a
|
|
47
|
+
// crash. Dropping them emptied every sub-agent list after a daemon restart.
|
|
41
48
|
return async function closeAll(reason = 'cli-agent-close-all', scope = {}) {
|
|
42
49
|
const ownerSessionId = clean(scope.callerSessionId);
|
|
50
|
+
const keepRows = scope.processExit === true;
|
|
43
51
|
const context = ownerSessionId ? { callerSessionId: ownerSessionId } : {};
|
|
44
52
|
registry.refreshTagsFromSessions({ scanSessions: false, context });
|
|
45
53
|
const closed = [];
|
|
46
54
|
const failed = [];
|
|
47
55
|
for (const { tag, session } of registry.agentSessionEntries({ scanSessions: false, context })) {
|
|
48
56
|
try {
|
|
49
|
-
closed.push(await close({ sessionId: session.id }, context));
|
|
57
|
+
closed.push(await close({ sessionId: session.id }, context, { keepRow: keepRows }));
|
|
50
58
|
} catch (err) {
|
|
51
59
|
failed.push({ tag, error: presentErrorText(err, { surface: 'agent' }) });
|
|
52
60
|
}
|
|
@@ -57,6 +65,7 @@ export function createCloseAll({ registry, close }) {
|
|
|
57
65
|
closed.push({ closed: true, tag: task.tag || null, sessionId: task.sessionId || null, task_id: task.task_id });
|
|
58
66
|
}
|
|
59
67
|
if (!ownerSessionId) resetLocalTagState();
|
|
68
|
+
if (keepRows) return { closed, failed };
|
|
60
69
|
const closedSessionIds = new Set(closed.map((row) => clean(row.sessionId)).filter(Boolean));
|
|
61
70
|
purgeWorkerRows(ownerSessionId, closedSessionIds);
|
|
62
71
|
return { closed, failed };
|
|
@@ -37,7 +37,9 @@ export function createCloseFlow({ mgr, registry, views }) {
|
|
|
37
37
|
}
|
|
38
38
|
}
|
|
39
39
|
|
|
40
|
-
|
|
40
|
+
/** `keepRow`: a process exit closes the worker but leaves its row (and its
|
|
41
|
+
* descendants') for the next process (close-all.mjs). */
|
|
42
|
+
async function close(args, context = {}, { keepRow = false } = {}) {
|
|
41
43
|
const scopedContext = agentScope(args, context);
|
|
42
44
|
registry.refreshTagsFromSessions({ scanSessions: registry.wantsSessionScan(args), context: scopedContext });
|
|
43
45
|
const taskId = taskIdFromArgs(args);
|
|
@@ -73,7 +75,7 @@ export function createCloseFlow({ mgr, registry, views }) {
|
|
|
73
75
|
if (task?.taskId) cancelBackgroundTask(task.taskId, CLOSE_REASON);
|
|
74
76
|
// Drop the row only once the cancellation is DURABLY recorded: a failed
|
|
75
77
|
// close that still forgot the row would leave no cancelled state behind.
|
|
76
|
-
if (ok) {
|
|
78
|
+
if (ok && !keepRow) {
|
|
77
79
|
registry.forgetTerminalSession(tag, sessionId);
|
|
78
80
|
for (const descendantSessionId of descendantSessionIds) {
|
|
79
81
|
registry.removeWorkerRow({ sessionId: descendantSessionId });
|
|
@@ -70,6 +70,7 @@ export function createSendDispatch({ registry, defaultCwd, sendFlow, spawnFlow,
|
|
|
70
70
|
async function send(args, { scopedContext, callerCwd, context, notifyContext }) {
|
|
71
71
|
try {
|
|
72
72
|
const prepared = await sendFlow.prepareSend(args, scopedContext);
|
|
73
|
+
await sendFlow.adoptCaller(prepared, notifyContext);
|
|
73
74
|
return sendFlow.dispatchToExistingSession(prepared, notifyContext);
|
|
74
75
|
} catch (err) {
|
|
75
76
|
return await respawnDeadTagSend(err, args, { callerCwd, context, notifyContext });
|
|
@@ -51,6 +51,7 @@ export function createSpawnDispatch({
|
|
|
51
51
|
}
|
|
52
52
|
if (liveSessionId && registry.getLiveSession(liveSessionId)) {
|
|
53
53
|
const prepared = await sendFlow.prepareSend({ ...args, tag: explicitTag }, scopedContext);
|
|
54
|
+
await sendFlow.adoptCaller(prepared, notifyContext);
|
|
54
55
|
const route = requestedRoute(args);
|
|
55
56
|
return {
|
|
56
57
|
reused: sendFlow.dispatchToExistingSession(route ? { ...prepared, route } : prepared, notifyContext, {
|
|
@@ -25,11 +25,16 @@ export function isActiveWorkerRow(row = {}) {
|
|
|
25
25
|
return !isTerminalWorkerStatus(effective);
|
|
26
26
|
}
|
|
27
27
|
|
|
28
|
-
function
|
|
28
|
+
function rowState(session, runtime) {
|
|
29
29
|
const status = session.closed === true ? 'closed' : session.status || 'idle';
|
|
30
30
|
const stage =
|
|
31
31
|
session.stage ||
|
|
32
32
|
(status === 'idle' || status === 'error' || status === 'closed' ? status : runtime?.stage || status);
|
|
33
|
+
return { status, stage };
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
function agentRow({ tag, session, runtime, progress, now, indexRow = null }) {
|
|
37
|
+
const { status, stage } = rowState(session, runtime);
|
|
33
38
|
// Additive: the current turn's start (worker index, stamped at dispatch) so
|
|
34
39
|
// surfaces time a continued worker from its turn, not from createdAt.
|
|
35
40
|
const turnStartedAt = indexRow?.turnStartedAt || session.turnStartedAt || null;
|
|
@@ -76,24 +81,34 @@ export function createAgentList({ mgr, refreshTagsFromSessions, agentSessionEntr
|
|
|
76
81
|
return function list({ scanSessions = false, context = {}, includeTerminal = false } = {}) {
|
|
77
82
|
refreshTagsFromSessions({ scanSessions, context });
|
|
78
83
|
const now = Date.now();
|
|
79
|
-
const rows =
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
84
|
+
const rows = [];
|
|
85
|
+
for (const { tag, session, indexRow, loaded } of agentSessionEntries({ scanSessions, context })) {
|
|
86
|
+
const runtime = mgr.getSessionRuntime?.(session.id);
|
|
87
|
+
// Whether a row is listed depends on its status and stage alone, so a
|
|
88
|
+
// finished worker is dropped before its progress is read: that read
|
|
89
|
+
// loads the worker's stored session, and a Lead's status pulse (every
|
|
90
|
+
// 2 s) would otherwise read every worker it ever ran, whole transcripts
|
|
91
|
+
// on first sight, synchronously on the daemon loop.
|
|
92
|
+
if (!includeTerminal && !isActiveWorkerRow(rowState(session, runtime))) continue;
|
|
93
|
+
rows.push(
|
|
94
|
+
agentRow({
|
|
95
|
+
tag,
|
|
96
|
+
session,
|
|
97
|
+
indexRow,
|
|
98
|
+
runtime,
|
|
99
|
+
// A tag-bound entry is the getSession answer itself; an index row or
|
|
100
|
+
// a scanned summary is only a projection and still reads the session.
|
|
101
|
+
progress: progress.sessionProgressExtras(
|
|
102
|
+
session.id,
|
|
103
|
+
session.agent || null,
|
|
104
|
+
now,
|
|
105
|
+
null,
|
|
106
|
+
loaded ? { loaded: session } : {}
|
|
107
|
+
),
|
|
90
108
|
now,
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
})
|
|
96
|
-
);
|
|
97
|
-
return includeTerminal ? rows : rows.filter((row) => isActiveWorkerRow(row));
|
|
109
|
+
})
|
|
110
|
+
);
|
|
111
|
+
}
|
|
112
|
+
return rows;
|
|
98
113
|
};
|
|
99
114
|
}
|
|
@@ -28,6 +28,16 @@ export function restartNotificationId(row) {
|
|
|
28
28
|
return `restart:${clean(row.task_id) || `${clean(row.sessionId)}:${clean(row.finishedAt)}`}`;
|
|
29
29
|
}
|
|
30
30
|
|
|
31
|
+
/** The agent task id an execution id names: a task's own id, or the task a
|
|
32
|
+
* restart notification (restartNotificationId) reports; null for one keyed
|
|
33
|
+
* by session because its row recorded no task id. */
|
|
34
|
+
export function agentTaskIdOfExecution(executionId) {
|
|
35
|
+
const id = clean(executionId);
|
|
36
|
+
if (!id.startsWith('restart:')) return id || null;
|
|
37
|
+
const rest = id.slice('restart:'.length);
|
|
38
|
+
return rest && !rest.includes(':') ? rest : null;
|
|
39
|
+
}
|
|
40
|
+
|
|
31
41
|
/** `pendingRestartFailures()` lists rows whose owner is not yet told;
|
|
32
42
|
* `markRestartNotified(rows)` stamps them. `mgr` supplies the persisted
|
|
33
43
|
* pending queue (enqueuePendingMessage / markCompletionEntry /
|
|
@@ -17,7 +17,13 @@ import {
|
|
|
17
17
|
} from './job-task-reconcile.mjs';
|
|
18
18
|
import { createTurnReviewCollector } from './turn-review.mjs';
|
|
19
19
|
import { handoffContent } from '../../handoff-attachments.mjs';
|
|
20
|
+
import { rebindDelegation } from '../../../runtime/agent/orchestrator/session/human-gate/delegation.mjs';
|
|
20
21
|
import { settledWorkerStatus } from './worker-index/row-liveness.mjs';
|
|
22
|
+
import { whileTurnDispatched } from '../../../runtime/agent/orchestrator/session/manager/runtime-state.mjs';
|
|
23
|
+
|
|
24
|
+
function workerResultIdentity({ session, tag, sessionId }) {
|
|
25
|
+
return { tag, sessionId, agent: session.agent || null, provider: session.provider, model: session.model };
|
|
26
|
+
}
|
|
21
27
|
|
|
22
28
|
// `send` to an existing worker: resolve the live session, run one follow-up
|
|
23
29
|
// turn under the progress watchdog, and reconcile the job/worker row. Busy
|
|
@@ -42,11 +48,7 @@ export function createSendFlow({ mgr, defaultCwd, sessionSurface, canUseSessionS
|
|
|
42
48
|
return (result) => {
|
|
43
49
|
const abnormalError = abnormalEmptyFinishError(result, session.agent || sendAgent);
|
|
44
50
|
return {
|
|
45
|
-
tag,
|
|
46
|
-
sessionId,
|
|
47
|
-
agent: session.agent || null,
|
|
48
|
-
provider: session.provider,
|
|
49
|
-
model: session.model,
|
|
51
|
+
...workerResultIdentity({ session, tag, sessionId }),
|
|
50
52
|
content: result?.content || '',
|
|
51
53
|
...(sessionSurface?.canonical === true ? { handoffOnly: true } : {}),
|
|
52
54
|
...(abnormalError ? { error: abnormalError } : {}),
|
|
@@ -74,10 +76,12 @@ export function createSendFlow({ mgr, defaultCwd, sessionSurface, canUseSessionS
|
|
|
74
76
|
const cwd = session.cwd || defaultCwd;
|
|
75
77
|
// The caller's forwarded files ride along as attachment parts.
|
|
76
78
|
const prompt = handoffContent(text, args.attachmentParts);
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
79
|
+
return whileTurnDispatched(sessionId, () => {
|
|
80
|
+
if (canUseSessionSurface(session)) {
|
|
81
|
+
return sessionSurface.runTurn({ session, prompt, context: args.context || null, cwd, ...turnHooks });
|
|
82
|
+
}
|
|
83
|
+
return mgr.askSession(sessionId, prompt, args.context || null, null, cwd, null, turnHooks);
|
|
84
|
+
});
|
|
81
85
|
}
|
|
82
86
|
|
|
83
87
|
async function runSend(prepared, notifyContext = null, job = null) {
|
|
@@ -110,11 +114,7 @@ export function createSendFlow({ mgr, defaultCwd, sessionSurface, canUseSessionS
|
|
|
110
114
|
const settleCancelled = (error, result = null) => {
|
|
111
115
|
finalStatus = 'cancelled';
|
|
112
116
|
reconcileJobCancelled(job, {
|
|
113
|
-
tag,
|
|
114
|
-
sessionId,
|
|
115
|
-
agent: session.agent || null,
|
|
116
|
-
provider: session.provider,
|
|
117
|
-
model: session.model,
|
|
117
|
+
...workerResultIdentity({ session, tag, sessionId }),
|
|
118
118
|
content: turnPartialHandoff(error, mgr.getSession(sessionId), handoffMsgStart) || result?.content || '',
|
|
119
119
|
});
|
|
120
120
|
};
|
|
@@ -145,11 +145,7 @@ export function createSendFlow({ mgr, defaultCwd, sessionSurface, canUseSessionS
|
|
|
145
145
|
if (partial) {
|
|
146
146
|
finalStatus = 'idle';
|
|
147
147
|
const value = {
|
|
148
|
-
tag,
|
|
149
|
-
sessionId,
|
|
150
|
-
agent: session.agent || null,
|
|
151
|
-
provider: session.provider,
|
|
152
|
-
model: session.model,
|
|
148
|
+
...workerResultIdentity({ session, tag, sessionId }),
|
|
153
149
|
content: watchdogStoppedHandoff(error, partial),
|
|
154
150
|
stallAbort: true,
|
|
155
151
|
};
|
|
@@ -164,7 +160,7 @@ export function createSendFlow({ mgr, defaultCwd, sessionSurface, canUseSessionS
|
|
|
164
160
|
turnReview.complete();
|
|
165
161
|
watchdog?.stop?.();
|
|
166
162
|
registry.upsertWorkerSessionDeferred(session, tag, {
|
|
167
|
-
...settledWorkerStatus(finalStatus, stalled),
|
|
163
|
+
...settledWorkerStatus(finalStatus, stalled, job),
|
|
168
164
|
finishedAt: new Date().toISOString(),
|
|
169
165
|
});
|
|
170
166
|
reconcileJobFinally(job, finalStatus);
|
|
@@ -188,6 +184,14 @@ export function createSendFlow({ mgr, defaultCwd, sessionSurface, canUseSessionS
|
|
|
188
184
|
return { ...prepared, session: mgr.getSession(sessionId) || session };
|
|
189
185
|
}
|
|
190
186
|
|
|
187
|
+
// The calling session hands this worker new work (a `send`, or a spawn of its
|
|
188
|
+
// tag): from now on the worker acts as that caller does, so a run's worker
|
|
189
|
+
// asks when the attended chat reuses it and the other way round. Not for a
|
|
190
|
+
// completion wake, which is the worker's own continuation.
|
|
191
|
+
function adoptCaller({ sessionId }, notifyContext) {
|
|
192
|
+
return rebindDelegation(sessionId, notifyContext?.callerSessionId);
|
|
193
|
+
}
|
|
194
|
+
|
|
191
195
|
// Shared send dispatch for an already-resolved live session. Used by the
|
|
192
196
|
// `send` branch AND by the `spawn` branch when an explicit tag maps to a
|
|
193
197
|
// live session (reuse path). Busy sessions queue the prompt; idle ones run a
|
|
@@ -255,5 +259,5 @@ export function createSendFlow({ mgr, defaultCwd, sessionSurface, canUseSessionS
|
|
|
255
259
|
return true;
|
|
256
260
|
}
|
|
257
261
|
|
|
258
|
-
return { prepareSend, dispatchToExistingSession, wakeIdleWorker };
|
|
262
|
+
return { prepareSend, adoptCaller, dispatchToExistingSession, wakeIdleWorker };
|
|
259
263
|
}
|
|
@@ -4,10 +4,12 @@
|
|
|
4
4
|
* agent work, and status publication at start and after terminal settlement.
|
|
5
5
|
*/
|
|
6
6
|
import { sanitizeTaskMeta, startBackgroundTask } from '../../../../runtime/shared/background-tasks.mjs';
|
|
7
|
+
import { recordAgentTaskStart } from '../../../../runtime/shared/agent-task-starts.mjs';
|
|
7
8
|
import { resourceAdmission } from '../../../../runtime/shared/resource-admission.mjs';
|
|
8
9
|
import { clean, terminalPidForContext } from '../helpers.mjs';
|
|
9
10
|
import { renderResult } from '../render.mjs';
|
|
10
11
|
import { closeManagedSession } from '../../../lifecycle/shared.mjs';
|
|
12
|
+
import { hopOf } from '../../../../runtime/shared/bot-hops.mjs';
|
|
11
13
|
|
|
12
14
|
/** The completion callback that hands a worker's result back to its caller session; null without a handoff. */
|
|
13
15
|
function handoffNotifier(handoffSessionId, notifySessionCompletion) {
|
|
@@ -29,6 +31,8 @@ export function createJobStarter({ mgr, notifyStatusChange, notifySessionComplet
|
|
|
29
31
|
ownerSessionId: ownerSessionId || null,
|
|
30
32
|
clientHostPid: clientHostPid || null,
|
|
31
33
|
notifyFn: handoffNotifier(handoffSessionId, notifySessionCompletion),
|
|
34
|
+
// The turn that started the job: its completion returns at that bot-chain hop (bot-hops.mjs).
|
|
35
|
+
...(hopOf(notifyContext?.hop) ? { hop: notifyContext.hop } : {}),
|
|
32
36
|
};
|
|
33
37
|
const jobMeta = sanitizeTaskMeta({
|
|
34
38
|
...(meta || {}),
|
|
@@ -82,6 +86,9 @@ export function createJobStarter({ mgr, notifyStatusChange, notifySessionComplet
|
|
|
82
86
|
}
|
|
83
87
|
},
|
|
84
88
|
});
|
|
89
|
+
// The model's tool call that started this job owns it (its result message
|
|
90
|
+
// carries the id: agent-task-starts.mjs).
|
|
91
|
+
recordAgentTaskStart(notifyContext?.toolCallId, task.taskId);
|
|
85
92
|
notifyStatusChange();
|
|
86
93
|
return task;
|
|
87
94
|
};
|
|
@@ -9,6 +9,7 @@ import { resolveAgentWatchdogPolicy } from '../../../../runtime/agent/orchestrat
|
|
|
9
9
|
import { prepareAgentSession } from '../../../../runtime/agent/orchestrator/agent-runtime/session-builder.mjs';
|
|
10
10
|
import { getProvider } from '../../../../runtime/agent/orchestrator/providers/registry.mjs';
|
|
11
11
|
import { resolveRouteContextState } from '../../../route-state.mjs';
|
|
12
|
+
import { contextSelectionFromState } from '../../../../runtime/agent/orchestrator/runtime-core/route-context-state.mjs';
|
|
12
13
|
import { createSpawnPlanner } from './spawn-plan.mjs';
|
|
13
14
|
import { enterWorkerSpawn } from '../../../workspace/admission-gate.mjs';
|
|
14
15
|
|
|
@@ -97,11 +98,13 @@ export function createSpawnPreparer({
|
|
|
97
98
|
|
|
98
99
|
async function createSpawnedSession(plan, spec, prepState) {
|
|
99
100
|
// A sub-100 context share needs the window it selects; a percent alone
|
|
100
|
-
// keeps the full served window.
|
|
101
|
+
// keeps the full served window. A model whose window is not known yet
|
|
102
|
+
// resolves to nothing: the agent's own choice then travels as stored (the
|
|
103
|
+
// session sizes it from the provider's window) instead of being dropped
|
|
104
|
+
// for the model's default.
|
|
101
105
|
const sessionSpec = { ...spec };
|
|
102
106
|
if (plan.preset.contextPercent || plan.preset.contextTokens) {
|
|
103
|
-
|
|
104
|
-
Object.assign(sessionSpec, { contextPercent, selectedContextWindow }, contextTokens ? { contextTokens } : {});
|
|
107
|
+
Object.assign(sessionSpec, contextSelectionFromState(resolveRouteContextState(plan.preset, null), plan.preset));
|
|
105
108
|
}
|
|
106
109
|
if (sessionSurface?.canonical === true && typeof sessionSurface.createChild === 'function') {
|
|
107
110
|
return sessionSurface.createChild({ spec: sessionSpec, prompt: plan.prompt, tag: plan.tag });
|
|
@@ -26,6 +26,7 @@ import { saveSessionAsync } from '../../../../runtime/agent/orchestrator/session
|
|
|
26
26
|
import { presetDescriptor } from './spawn-prep.mjs';
|
|
27
27
|
import { workerStageForStatus } from '../worker-rows.mjs';
|
|
28
28
|
import { handoffContent } from '../../../handoff-attachments.mjs';
|
|
29
|
+
import { whileTurnDispatched } from '../../../../runtime/agent/orchestrator/session/manager/runtime-state.mjs';
|
|
29
30
|
|
|
30
31
|
// Mid-turn worker persistence cadence. The watchdog sweep runs every second;
|
|
31
32
|
// a transcript save is far more expensive than a bookkeeping stamp, so the
|
|
@@ -121,10 +122,12 @@ export function createSpawnRunner({
|
|
|
121
122
|
const { args, session, workerCwd } = prepared;
|
|
122
123
|
// The caller's forwarded files ride along as attachment parts.
|
|
123
124
|
const prompt = handoffContent(prepared.prompt, args.attachmentParts);
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
125
|
+
return whileTurnDispatched(session.id, () => {
|
|
126
|
+
if (typeof sessionSurface?.runTurn === 'function' && sessionSurface.canRun?.(session) !== false) {
|
|
127
|
+
return sessionSurface.runTurn({ session, prompt, context: args.context || null, cwd: workerCwd, ...turnHooks });
|
|
128
|
+
}
|
|
129
|
+
return mgr.askSession(session.id, prompt, args.context || null, null, workerCwd, null, turnHooks);
|
|
130
|
+
});
|
|
128
131
|
}
|
|
129
132
|
|
|
130
133
|
async function runSpawn(prepared, notifyContext = null, job = null) {
|
|
@@ -221,7 +224,7 @@ export function createSpawnRunner({
|
|
|
221
224
|
watchdog?.stop?.();
|
|
222
225
|
upsertWorkerSessionDeferred(session, tag, {
|
|
223
226
|
...presetDescriptor(agent, preset, presetName),
|
|
224
|
-
...settledWorkerStatus(finalStatus, stalled),
|
|
227
|
+
...settledWorkerStatus(finalStatus, stalled, job),
|
|
225
228
|
finishedAt: new Date().toISOString(),
|
|
226
229
|
});
|
|
227
230
|
setImmediate(notifyStatusChange);
|