mixdog 1.4.0 → 1.4.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/package.json +3 -2
- package/scripts/build-shipped-history.mjs +115 -33
- package/scripts/check-voice-runtime-inputs.mjs +25 -0
- package/scripts/gate-local.mjs +183 -63
- package/scripts/latest-guard.mjs +21 -9
- package/scripts/lib/gate-scheduler.mjs +138 -32
- package/scripts/lib/gate-timing-reporter.mjs +16 -0
- package/scripts/lib/isolated-test-env.mjs +10 -5
- package/scripts/lib/run-node-tests.mjs +91 -66
- package/scripts/lib/scoped-temp.d.mts +16 -0
- package/scripts/lib/scoped-temp.mjs +124 -0
- package/scripts/lib/stale-temp.mjs +44 -0
- package/scripts/lib/test-failure-records.mjs +14 -1
- package/scripts/lib/test-failure-summary.mjs +16 -4
- package/scripts/lib/test-spawn-ledger.mjs +12 -3
- package/scripts/post-release-check.mjs +1 -6
- package/scripts/pptx-kit-index.mjs +17 -5
- package/scripts/suite-health.mjs +115 -24
- package/scripts/test-data-dir.mjs +10 -7
- package/scripts/test.mjs +9 -14
- package/src/agents/advisor/AGENT.md +4 -4
- package/src/agents/advisor/agent.json +1 -1
- package/src/agents/explore/AGENT.md +22 -0
- package/src/agents/explore/agent.json +6 -0
- package/src/app.mjs +4 -0
- package/src/cli.mjs +7 -0
- package/src/defaults/agents.json +7 -0
- package/src/defaults/shipped-history.json +23 -2
- package/src/defaults/skills/browser-use/SKILL.md +10 -5
- package/src/defaults/skills/code-tidy/SKILL.md +71 -102
- package/src/defaults/skills/code-tidy/references/agent-cleanup.md +66 -114
- package/src/defaults/skills/code-tidy/references/cleanup-report.md +19 -35
- package/src/defaults/skills/code-tidy/references/dead-code.md +3 -9
- package/src/defaults/skills/code-tidy/references/test-suite-slop.md +16 -27
- package/src/defaults/skills/computer-use/SKILL.md +16 -4
- package/src/defaults/skills/goal-management/SKILL.md +1 -1
- package/src/defaults/skills/setup/references/actions.md +12 -6
- package/src/defaults/skills/setup/references/surfaces.md +2 -2
- package/src/defaults/skills/setup-guide/SKILL.md +5 -2
- package/src/defaults/skills/setup-guide/model-recommendations.json +13 -0
- package/src/defaults/skills/skill-creator/SKILL.md +85 -190
- package/src/defaults/skills/skill-creator/references/design.md +70 -162
- package/src/defaults/skills/skill-creator/references/evaluation.md +33 -92
- package/src/defaults/skills/test-suite/SKILL.md +194 -0
- package/src/defaults/skills/test-suite/references/case-management.md +51 -0
- package/src/defaults/skills/test-suite/references/flaky-policy.md +39 -0
- package/src/defaults/skills/test-suite/references/reliability.md +49 -0
- package/src/defaults/skills/test-suite/references/suite-design.md +78 -0
- package/src/defaults/skills/test-suite/scripts/inventory.mjs +335 -0
- package/src/defaults/skills/visualize/SKILL.md +6 -2
- package/src/lib/rules-builder.cjs +35 -42
- package/src/output-styles/common.md +2 -2
- package/src/output-styles/simple.md +1 -1
- package/src/rules/agent/AGENT.md +5 -4
- package/src/rules/lead/LEAD.md +12 -7
- package/src/rules/shared/10-tool-workflow.md +3 -1
- package/src/rules/shared/20-research.md +3 -6
- package/src/rules/shared/40-editing.md +1 -0
- package/src/rules/shared/45-destructive.md +0 -2
- package/src/rules/shared/50-execution.md +2 -0
- package/src/rules/shared/60-verification.md +10 -9
- package/src/rules/shared/70-delivery.md +8 -9
- package/src/runtime/agent/orchestrator/agent-runtime/agent-dispatch/abort-link.mjs +5 -1
- package/src/runtime/agent/orchestrator/agent-runtime/agent-dispatch.mjs +10 -1
- package/src/runtime/agent/orchestrator/agent-runtime/agent-progress-watchdog.mjs +156 -24
- package/src/runtime/agent/orchestrator/agent-runtime/cache-strategy.mjs +13 -0
- package/src/runtime/agent/orchestrator/agent-runtime/maintenance-route.mjs +4 -1
- package/src/runtime/agent/orchestrator/cache-break-trace.mjs +2 -0
- package/src/runtime/agent/orchestrator/config.mjs +12 -7
- package/src/runtime/agent/orchestrator/context/deferred-tools.mjs +8 -8
- package/src/runtime/agent/orchestrator/context/role-instructions.mjs +5 -26
- package/src/runtime/agent/orchestrator/context/skill-catalog.mjs +3 -1
- package/src/runtime/agent/orchestrator/internal-agents.mjs +3 -14
- package/src/runtime/agent/orchestrator/mcp/agent-connectors.mjs +122 -12
- package/src/runtime/agent/orchestrator/mcp/child-tree.mjs +5 -3
- package/src/runtime/agent/orchestrator/mcp/client-config.mjs +13 -2
- package/src/runtime/agent/orchestrator/mcp/client-transport.mjs +152 -58
- package/src/runtime/agent/orchestrator/mcp/client.mjs +51 -18
- package/src/runtime/agent/orchestrator/mcp/oauth-login.mjs +88 -54
- package/src/runtime/agent/orchestrator/mcp/oauth.mjs +42 -26
- package/src/runtime/agent/orchestrator/providers/account-pool.mjs +54 -8
- package/src/runtime/agent/orchestrator/providers/anthropic-api-recovery.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/anthropic-api-request.mjs +37 -31
- package/src/runtime/agent/orchestrator/providers/anthropic-api-transport.mjs +8 -2
- package/src/runtime/agent/orchestrator/providers/anthropic-max-tokens-recovery.mjs +6 -2
- package/src/runtime/agent/orchestrator/providers/anthropic-messages.mjs +2 -2
- package/src/runtime/agent/orchestrator/providers/anthropic-oauth-client-version.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/anthropic-oauth-credentials.mjs +31 -21
- package/src/runtime/agent/orchestrator/providers/anthropic-oauth-request/initial-status.mjs +3 -1
- package/src/runtime/agent/orchestrator/providers/anthropic-oauth.mjs +14 -3
- package/src/runtime/agent/orchestrator/providers/anthropic-sse.mjs +6 -0
- package/src/runtime/agent/orchestrator/providers/anthropic-turn-result.mjs +2 -2
- package/src/runtime/agent/orchestrator/providers/antigravity-oauth-login.mjs +3 -1
- package/src/runtime/agent/orchestrator/providers/antigravity-oauth-tokens.mjs +2 -2
- package/src/runtime/agent/orchestrator/providers/codex-client-meta.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/command-code-oauth-login.mjs +1 -10
- package/src/runtime/agent/orchestrator/providers/command-code-oauth.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/cursor.mjs +3 -0
- package/src/runtime/agent/orchestrator/providers/custom-provider-config.mjs +40 -0
- package/src/runtime/agent/orchestrator/providers/custom-provider-keys.mjs +34 -0
- package/src/runtime/agent/orchestrator/providers/custom-provider.mjs +3 -0
- package/src/runtime/agent/orchestrator/providers/devin-auth.mjs +14 -7
- package/src/runtime/agent/orchestrator/providers/devin-wire-transport.mjs +3 -2
- package/src/runtime/agent/orchestrator/providers/devin.mjs +3 -0
- package/src/runtime/agent/orchestrator/providers/gemini-response.mjs +2 -2
- package/src/runtime/agent/orchestrator/providers/gemini-stream.mjs +4 -1
- package/src/runtime/agent/orchestrator/providers/grok-oauth-login.mjs +248 -41
- package/src/runtime/agent/orchestrator/providers/lib/anthropic-prefix-trace.mjs +76 -11
- package/src/runtime/agent/orchestrator/providers/lib/anthropic-request-utils.mjs +45 -6
- package/src/runtime/agent/orchestrator/providers/lib/first-output-window.mjs +58 -0
- package/src/runtime/agent/orchestrator/providers/lib/listen-on.mjs +14 -0
- package/src/runtime/agent/orchestrator/providers/lib/oauth-page.mjs +0 -18
- package/src/runtime/agent/orchestrator/providers/lib/oauth-token-utils.mjs +138 -6
- package/src/runtime/agent/orchestrator/providers/mimo-oauth-login.mjs +1 -10
- package/src/runtime/agent/orchestrator/providers/mimo-oauth.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/model-cache.mjs +100 -33
- package/src/runtime/agent/orchestrator/providers/muse-code-oauth.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/oauth-secret-fields.fixtures.mjs +45 -0
- package/src/runtime/agent/orchestrator/providers/openai-compat-chat-send.mjs +1 -0
- package/src/runtime/agent/orchestrator/providers/openai-compat-chat-stream/chunk-events.mjs +9 -2
- package/src/runtime/agent/orchestrator/providers/openai-compat-chat-stream/stream-state.mjs +7 -0
- package/src/runtime/agent/orchestrator/providers/openai-compat-chat-stream.mjs +14 -3
- package/src/runtime/agent/orchestrator/providers/openai-compat-responses-events.mjs +4 -2
- package/src/runtime/agent/orchestrator/providers/openai-compat-responses.mjs +1 -0
- package/src/runtime/agent/orchestrator/providers/openai-compat-stream-common.mjs +5 -3
- package/src/runtime/agent/orchestrator/providers/openai-compat-stream.mjs +16 -3
- package/src/runtime/agent/orchestrator/providers/openai-compat-xai-send.mjs +1 -0
- package/src/runtime/agent/orchestrator/providers/openai-http-sse-response-state/response-events/output-items.mjs +5 -2
- package/src/runtime/agent/orchestrator/providers/openai-http-sse-response-state/response-events.mjs +13 -3
- package/src/runtime/agent/orchestrator/providers/openai-http-sse-response-state.mjs +13 -2
- package/src/runtime/agent/orchestrator/providers/openai-http-sse-watchdogs.mjs +81 -42
- package/src/runtime/agent/orchestrator/providers/openai-oauth-http-sse.mjs +8 -0
- package/src/runtime/agent/orchestrator/providers/openai-oauth-login.mjs +160 -31
- package/src/runtime/agent/orchestrator/providers/openai-ws-stream/event-switch.mjs +22 -12
- package/src/runtime/agent/orchestrator/providers/openai-ws-stream.mjs +7 -1
- package/src/runtime/agent/orchestrator/providers/openai-ws-watchdogs.mjs +49 -22
- package/src/runtime/agent/orchestrator/providers/opencode-go-oauth.mjs +1 -1
- package/src/runtime/agent/orchestrator/providers/opencode-go.mjs +3 -1
- package/src/runtime/agent/orchestrator/providers/registry.mjs +45 -2
- package/src/runtime/agent/orchestrator/providers/vertex-ai-auth.mjs +622 -0
- package/src/runtime/agent/orchestrator/providers/vertex-ai-maas.mjs +185 -0
- package/src/runtime/agent/orchestrator/providers/vertex-ai-models.mjs +445 -0
- package/src/runtime/agent/orchestrator/providers/vertex-ai.mjs +567 -0
- package/src/runtime/agent/orchestrator/runtime-core/ask-user-tool-defs.mjs +41 -13
- package/src/runtime/agent/orchestrator/runtime-core/builtin-features.mjs +2 -0
- package/src/runtime/agent/orchestrator/runtime-core/orchestration.mjs +8 -6
- package/src/runtime/agent/orchestrator/runtime-core/session-text.mjs +7 -3
- package/src/runtime/agent/orchestrator/runtime-core/tool-catalog-data.mjs +3 -0
- package/src/runtime/agent/orchestrator/runtime-core/tool-defs.mjs +6 -1
- package/src/runtime/agent/orchestrator/runtime-core/workflow/context.mjs +14 -5
- package/src/runtime/agent/orchestrator/runtime-core/workflow-ids.mjs +1 -0
- package/src/runtime/agent/orchestrator/runtime-core/workflow.mjs +5 -2
- package/src/runtime/agent/orchestrator/session/agent-room.d.mts +30 -5
- package/src/runtime/agent/orchestrator/session/agent-room.mjs +171 -37
- package/src/runtime/agent/orchestrator/session/cache/scoped-cache.mjs +1 -3
- package/src/runtime/agent/orchestrator/session/cache-warm.mjs +102 -12
- package/src/runtime/agent/orchestrator/session/catalog-db/schema.mjs +4 -1
- package/src/runtime/agent/orchestrator/session/compact/execution-tail.mjs +1 -8
- package/src/runtime/agent/orchestrator/session/compact/messages.mjs +23 -0
- package/src/runtime/agent/orchestrator/session/compact/observation-supersession.mjs +103 -23
- package/src/runtime/agent/orchestrator/session/compact/runner.mjs +160 -36
- package/src/runtime/agent/orchestrator/session/context-utils.mjs +13 -1
- package/src/runtime/agent/orchestrator/session/conversation-import/claude.mjs +164 -23
- package/src/runtime/agent/orchestrator/session/conversation-import/codex.mjs +139 -19
- package/src/runtime/agent/orchestrator/session/conversation-import/convert.mjs +38 -7
- package/src/runtime/agent/orchestrator/session/conversation-import/imported-session.mjs +3 -0
- package/src/runtime/agent/orchestrator/session/conversation-import/turns.mjs +100 -22
- package/src/runtime/agent/orchestrator/session/eager-dispatch.mjs +4 -3
- package/src/runtime/agent/orchestrator/session/human-gate/requests.mjs +36 -6
- package/src/runtime/agent/orchestrator/session/loop/compact-policy.mjs +33 -3
- package/src/runtime/agent/orchestrator/session/loop/fresh-context.mjs +9 -2
- package/src/runtime/agent/orchestrator/session/loop/pre-dispatch-deny.mjs +1 -1
- package/src/runtime/agent/orchestrator/session/loop/provider-tool-exclusions.mjs +13 -5
- package/src/runtime/agent/orchestrator/session/loop/route-fallback.mjs +14 -0
- package/src/runtime/agent/orchestrator/session/loop/send-phase.mjs +13 -1
- package/src/runtime/agent/orchestrator/session/loop/tool-exec/before-hook.mjs +23 -4
- package/src/runtime/agent/orchestrator/session/loop/tool-exec/dispatch.mjs +2 -0
- package/src/runtime/agent/orchestrator/session/loop/tool-exec.mjs +23 -1
- package/src/runtime/agent/orchestrator/session/loop/tool-exposure-migration.mjs +39 -21
- package/src/runtime/agent/orchestrator/session/loop/turn-limits.mjs +13 -8
- package/src/runtime/agent/orchestrator/session/manager/ask-session.mjs +50 -28
- package/src/runtime/agent/orchestrator/session/manager/ask-turn-loop-options.mjs +3 -3
- package/src/runtime/agent/orchestrator/session/manager/ask-turn-settle.mjs +3 -1
- package/src/runtime/agent/orchestrator/session/manager/owner-route-fallbacks.mjs +2 -2
- package/src/runtime/agent/orchestrator/session/manager/prompt-utils.mjs +1 -0
- package/src/runtime/agent/orchestrator/session/manager/route-fallback-chain.mjs +2 -1
- package/src/runtime/agent/orchestrator/session/manager/rules-cache.mjs +30 -13
- package/src/runtime/agent/orchestrator/session/manager/runtime-liveness.mjs +63 -6
- package/src/runtime/agent/orchestrator/session/manager/session-close.mjs +7 -0
- package/src/runtime/agent/orchestrator/session/manager/session-crud.mjs +15 -0
- package/src/runtime/agent/orchestrator/session/manager/session-lifecycle.mjs +35 -13
- package/src/runtime/agent/orchestrator/session/manager/session-prompt-composition.mjs +24 -14
- package/src/runtime/agent/orchestrator/session/manager/session-scratch-environment.mjs +70 -0
- package/src/runtime/agent/orchestrator/session/manager/session-tool-surface.mjs +0 -3
- package/src/runtime/agent/orchestrator/session/manager/tool-resolution.mjs +10 -6
- package/src/runtime/agent/orchestrator/session/manager/turn-checkpoint-context.mjs +4 -0
- package/src/runtime/agent/orchestrator/session/manager/turn-checkpoint.mjs +3 -0
- package/src/runtime/agent/orchestrator/session/manager/turn-interruption.mjs +56 -29
- package/src/runtime/agent/orchestrator/session/manager/turn-reap.mjs +125 -0
- package/src/runtime/agent/orchestrator/session/mixy-name.mjs +11 -5
- package/src/runtime/agent/orchestrator/session/pre-send-compact.mjs +5 -1
- package/src/runtime/agent/orchestrator/session/prompt-cache-touch-store.mjs +30 -7
- package/src/runtime/agent/orchestrator/session/restart-prefix-parity.fixture.mjs +154 -0
- package/src/runtime/agent/orchestrator/session/store/session-delete.mjs +7 -0
- package/src/runtime/agent/orchestrator/session/store-summary-catalog.mjs +4 -0
- package/src/runtime/agent/orchestrator/session/store-summary-fields.mjs +15 -0
- package/src/runtime/agent/orchestrator/session/store-summary-index.mjs +37 -8
- package/src/runtime/agent/orchestrator/session/store-summary-reader.mjs +252 -39
- package/src/runtime/agent/orchestrator/session/store-transcript-cache.mjs +163 -64
- package/src/runtime/agent/orchestrator/session/store-transcript-projection.mjs +164 -4
- package/src/runtime/agent/orchestrator/session/store-transcript-worker.mjs +142 -18
- package/src/runtime/agent/orchestrator/session/transcript-restore/restore.mjs +61 -2
- package/src/runtime/agent/orchestrator/stall-policy.mjs +23 -0
- package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/completed-result.mjs +6 -2
- package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/invocation-plan.mjs +2 -2
- package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/spawn-env.mjs +4 -2
- package/src/runtime/agent/orchestrator/tools/builtin/bash-tool.mjs +6 -1
- package/src/runtime/agent/orchestrator/tools/builtin/builtin-tools.mjs +46 -20
- package/src/runtime/agent/orchestrator/tools/builtin/cache-layers.mjs +7 -1
- package/src/runtime/agent/orchestrator/tools/builtin/git-command-tool.mjs +67 -31
- package/src/runtime/agent/orchestrator/tools/builtin/git-worktree-tool.mjs +25 -13
- package/src/runtime/agent/orchestrator/tools/builtin/lib/scoped-search-flight.mjs +9 -5
- package/src/runtime/agent/orchestrator/tools/builtin/lib/shell-job-records.mjs +58 -20
- package/src/runtime/agent/orchestrator/tools/builtin/read-single-stream.mjs +7 -1
- package/src/runtime/agent/orchestrator/tools/builtin/read-streaming.mjs +6 -3
- package/src/runtime/agent/orchestrator/tools/builtin/read-tool/batch-dispatch.mjs +1 -1
- package/src/runtime/agent/orchestrator/tools/builtin/read-tool/batch-publication.mjs +23 -12
- package/src/runtime/agent/orchestrator/tools/builtin/read-tool/batch-snapshot.mjs +6 -1
- package/src/runtime/agent/orchestrator/tools/builtin/read-tool.mjs +1 -8
- package/src/runtime/agent/orchestrator/tools/builtin/runtime-capabilities.mjs +20 -15
- package/src/runtime/agent/orchestrator/tools/builtin/shell-jobs.mjs +96 -20
- package/src/runtime/agent/orchestrator/tools/builtin/task-tool.mjs +59 -10
- package/src/runtime/agent/orchestrator/tools/code-graph/dispatch/federation.mjs +3 -1
- package/src/runtime/agent/orchestrator/tools/code-graph-tool-defs.mjs +1 -1
- package/src/runtime/agent/orchestrator/tools/graph-manifest.json +13 -13
- package/src/runtime/agent/orchestrator/tools/lib/isolated-test-env.mjs +4 -3
- package/src/runtime/agent/orchestrator/tools/lib/native-spawn-client.mjs +99 -2
- package/src/runtime/agent/orchestrator/tools/lib/owned-shell-trees.mjs +2 -0
- package/src/runtime/agent/orchestrator/tools/lib/shell-descendants.mjs +103 -13
- package/src/runtime/agent/orchestrator/tools/lib/shell-run-background/promote-job.mjs +3 -1
- package/src/runtime/agent/orchestrator/tools/lib/shell-run-settle.mjs +49 -15
- package/src/runtime/agent/orchestrator/tools/lib/shell-run-spawn.mjs +45 -27
- package/src/runtime/agent/orchestrator/tools/lib/shell-run-state.mjs +34 -10
- package/src/runtime/agent/orchestrator/tools/lib/shell-warm-standby.mjs +28 -4
- package/src/runtime/agent/orchestrator/tools/lib/wait-until-fixture.mjs +26 -0
- package/src/runtime/agent/orchestrator/tools/shell-command.mjs +7 -2
- package/src/runtime/agent/orchestrator/tools/spawn-manifest.json +13 -13
- package/src/runtime/channels/lib/webhook/signature.mjs +4 -1
- package/src/runtime/channels/lib/whisper-port.mjs +29 -11
- package/src/runtime/channels/lib/whisper-server.mjs +10 -1
- package/src/runtime/computer-bridge/action-schema.mjs +2 -2
- package/src/runtime/computer-bridge/core-actions.mjs +2 -2
- package/src/runtime/computer-bridge/error-recovery.mjs +5 -4
- package/src/runtime/computer-bridge/linux-action-capabilities.mjs +24 -5
- package/src/runtime/computer-bridge/linux-readiness.d.mts +7 -2
- package/src/runtime/connectors/connector-accounts-mcp.mjs +236 -103
- package/src/runtime/connectors/gmail-app-password.mjs +3 -3
- package/src/runtime/explore/explorer.mjs +93 -0
- package/src/runtime/explore/tool-defs.mjs +35 -0
- package/src/runtime/explore/tool.mjs +123 -0
- package/src/runtime/local-provider/server-process.mjs +2 -1
- package/src/runtime/media/adapters/gemini-video.mjs +4 -1
- package/src/runtime/media/adapters/xai-media.mjs +2 -1
- package/src/runtime/memory/index.mjs +4 -0
- package/src/runtime/memory/lib/embedding-provider.mjs +4 -1
- package/src/runtime/memory/lib/embedding-worker.mjs +10 -3
- package/src/runtime/memory/lib/memory-action-handlers/cycle-backfill-action.mjs +1 -7
- package/src/runtime/memory/lib/memory-chunk-quality.mjs +1 -6
- package/src/runtime/office/authoring/pdf-author-action.mjs +1 -6
- package/src/runtime/office/design/design-art-direction.mjs +29 -27
- package/src/runtime/office/pdf/pdf-writer.mjs +6 -1
- package/src/runtime/office/portable/portable-snapshot-docx.mjs +7 -1
- package/src/runtime/office/portable/portable-snapshot-shared.mjs +6 -1
- package/src/runtime/office/quality/assurance-rendered.mjs +9 -2
- package/src/runtime/office/quality/assurance-structure-docx.mjs +4 -2
- package/src/runtime/office/quality/design-review.mjs +1 -5
- package/src/runtime/office/quality/document-brief.mjs +1 -5
- package/src/runtime/office/quality/forced-break-pages.mjs +9 -6
- package/src/runtime/office/quality/quality-pipeline.mjs +1 -1
- package/src/runtime/shared/agent-route-config.mjs +17 -2
- package/src/runtime/shared/atomic-file.mjs +103 -2
- package/src/runtime/shared/background-tasks.mjs +15 -6
- package/src/runtime/shared/bot-owned-work.mjs +56 -0
- package/src/runtime/shared/connector-accounts.mjs +5 -5
- package/src/runtime/shared/connector-catalog.d.mts +11 -4
- package/src/runtime/shared/connector-catalog.mjs +60 -52
- package/src/runtime/shared/custom-provider-keys.mjs +20 -0
- package/src/runtime/shared/defaults-separation.mjs +1 -4
- package/src/runtime/shared/fetch-safe-listen.d.mts +16 -0
- package/src/runtime/shared/fetch-safe-listen.mjs +50 -0
- package/src/runtime/shared/file-has-data.mjs +26 -2
- package/src/runtime/shared/file-lock.mjs +13 -15
- package/src/runtime/shared/git-launch.d.mts +9 -0
- package/src/runtime/shared/git-launch.mjs +213 -0
- package/src/runtime/shared/git-runner-worker.mjs +2 -1
- package/src/runtime/shared/handoff-artifacts.d.mts +2 -1
- package/src/runtime/shared/handoff-artifacts.mjs +18 -8
- package/src/runtime/shared/idle-auto-clear-gate.mjs +29 -7
- package/src/runtime/shared/llm/cost.mjs +11 -2
- package/src/runtime/shared/llm/http-agent.mjs +313 -29
- package/src/runtime/shared/llm/model-catalog-projection.mjs +3 -2
- package/src/runtime/shared/llm/model-catalog.mjs +46 -6
- package/src/runtime/shared/llm/provider-catalog-registry.mjs +3 -0
- package/src/runtime/shared/llm/system-proxy.mjs +452 -0
- package/src/runtime/shared/loopback-listener.mjs +25 -2
- package/src/runtime/shared/model-route-chain.d.mts +7 -2
- package/src/runtime/shared/model-route-chain.mjs +22 -4
- package/src/runtime/shared/open-url.mjs +10 -0
- package/src/runtime/shared/provider-accounts.mjs +52 -2
- package/src/runtime/shared/session-activity-signal.mjs +14 -0
- package/src/runtime/shared/session-scratch.mjs +37 -0
- package/src/runtime/shared/staged-install-worker.mjs +5 -0
- package/src/runtime/shared/staged-update.mjs +47 -2
- package/src/runtime/shared/tool-card-model/agent-surface.mjs +1 -3
- package/src/runtime/shared/tool-card-model/card-status.mjs +15 -2
- package/src/runtime/shared/tool-result-summary.mjs +1 -1
- package/src/runtime/shared/tool-surface.mjs +113 -36
- package/src/runtime/shared/tool-work-units.mjs +6 -0
- package/src/runtime/shared/turn-snapshot-store.mjs +13 -6
- package/src/runtime/shared/turn-worktree-snapshot.mjs +414 -54
- package/src/runtime/shared/worktrees/activity-gate.mjs +215 -318
- package/src/runtime/shared/worktrees/activity-ledger-worker.mjs +56 -0
- package/src/runtime/shared/worktrees/activity-ledger.mjs +391 -0
- package/src/runtime/shared/worktrees/branch-management.mjs +9 -3
- package/src/runtime/shared/worktrees/contract.mjs +4 -1
- package/src/runtime/shared/worktrees/git.mjs +72 -0
- package/src/runtime/shared/worktrees/manager.mjs +285 -168
- package/src/runtime/shared/worktrees/test-support.mjs +6 -10
- package/src/runtime/tidy/install.mjs +95 -15
- package/src/runtime/tidy/languages.mjs +17 -15
- package/src/runtime/tidy/process.mjs +7 -4
- package/src/runtime/tidy/resolve.mjs +19 -16
- package/src/runtime/tidy/runners/biome.mjs +3 -3
- package/src/runtime/tidy/tool.mjs +1 -1
- package/src/runtime/tidy/worktree.mjs +10 -6
- package/src/runtime/visualize-bridge/client.mjs +6 -1
- package/src/runtime/visualize-bridge/tool-defs.mjs +7 -2
- package/src/runtime/web-search/index.mjs +1 -1
- package/src/session-runtime/agent-home-delivery.mjs +41 -0
- package/src/session-runtime/agent-task-sessions.mjs +458 -312
- package/src/session-runtime/agent-tool-routing.mjs +8 -41
- package/src/session-runtime/boot/tools.mjs +7 -1
- package/src/session-runtime/bot-status.mjs +107 -101
- package/src/session-runtime/bot-target.mjs +38 -0
- package/src/session-runtime/channel-config-api.mjs +6 -1
- package/src/session-runtime/connector-merge-migration.mjs +18 -15
- package/src/session-runtime/conversation-import/codex-titles.mjs +88 -0
- package/src/session-runtime/conversation-import/discovery.mjs +401 -36
- package/src/session-runtime/conversation-import/service.mjs +35 -8
- package/src/session-runtime/handoff-attachments.mjs +82 -31
- package/src/session-runtime/held-requests.mjs +3 -1
- package/src/session-runtime/internal-tool-executor/ask-user-tool.mjs +12 -13
- package/src/session-runtime/internal-tool-executor/bridge-tools.mjs +1 -0
- package/src/session-runtime/internal-tool-executor/feature-tools.mjs +2 -0
- package/src/session-runtime/internal-tool-executor/knowledge-tools.mjs +8 -0
- package/src/session-runtime/internal-tool-executor/reaction-tool.mjs +4 -1
- package/src/session-runtime/internal-tool-executor/workspace-tools.mjs +145 -112
- package/src/session-runtime/lifecycle/cold-heir.mjs +11 -6
- package/src/session-runtime/lifecycle/session-catalog.mjs +9 -1
- package/src/session-runtime/lifecycle/teardown/session-close.mjs +6 -1
- package/src/session-runtime/lifecycle/teardown.mjs +1 -1
- package/src/session-runtime/mcp-glue/server-catalog.mjs +16 -10
- package/src/session-runtime/mcp-glue/server-input.mjs +4 -1
- package/src/session-runtime/mixy-heartbeat.mjs +1 -1
- package/src/session-runtime/model-route/set-route.mjs +11 -2
- package/src/session-runtime/provider-auth/login.mjs +2 -2
- package/src/session-runtime/provider-catalog-cache.mjs +82 -36
- package/src/session-runtime/provider-models/catalog-load.mjs +23 -6
- package/src/session-runtime/provider-models.mjs +4 -2
- package/src/session-runtime/resource-mcp-api.mjs +98 -35
- package/src/session-runtime/resource-mcp-connector-accounts.mjs +44 -31
- package/src/session-runtime/resource-mcp-secrets.mjs +28 -11
- package/src/session-runtime/resource-mcp-servers.mjs +5 -4
- package/src/session-runtime/resource-recall-api.mjs +6 -1
- package/src/session-runtime/runtime-feature-gates.mjs +5 -1
- package/src/session-runtime/services/agent-tool/execute.mjs +14 -9
- package/src/session-runtime/services/agent-tool/job-views/agent-list.mjs +20 -4
- package/src/session-runtime/services/agent-tool/model-select.mjs +48 -7
- package/src/session-runtime/services/agent-tool/render.mjs +71 -17
- package/src/session-runtime/services/agent-tool/send-flow.mjs +10 -2
- package/src/session-runtime/services/agent-tool/spawn-flow/spawn-prep.mjs +8 -3
- package/src/session-runtime/services/agent-tool/spawn-flow/spawn-run.mjs +4 -1
- package/src/session-runtime/services/agent-tool/spawn-preset.mjs +6 -2
- package/src/session-runtime/services/agent-tool/tool-def.mjs +9 -9
- package/src/session-runtime/services/agent-watchdog-registry.mjs +32 -4
- package/src/session-runtime/services/channel-worker/daemon-spawn.mjs +2 -0
- package/src/session-runtime/services/daemon-candidate.mjs +4 -1
- package/src/session-runtime/services/memory-runtime-proxy/daemon-spawn.mjs +4 -0
- package/src/session-runtime/services/plugin-admin.mjs +10 -6
- package/src/session-runtime/services/provider-admin.mjs +283 -11
- package/src/session-runtime/session-turn-api.mjs +2 -0
- package/src/session-runtime/settings-builtin-tools-api.mjs +4 -1
- package/src/session-runtime/settings-system-api.mjs +1 -1
- package/src/session-runtime/setup-tool/agent-settings-actions.mjs +13 -3
- package/src/session-runtime/setup-tool/connector-widen-approval.mjs +96 -0
- package/src/session-runtime/setup-tool/executor.mjs +6 -2
- package/src/session-runtime/setup-tool/tool-defs.mjs +2 -1
- package/src/session-runtime/tool-policy/policy-stage.mjs +1 -0
- package/src/session-runtime/turn/agent-ops.mjs +23 -0
- package/src/session-runtime/workflow-agents-api/agent-connectors.mjs +49 -11
- package/src/session-runtime/workflow-agents-api/agent-editor.mjs +5 -1
- package/src/session-runtime/workflow-agents-api/agent-route.mjs +25 -5
- package/src/session-runtime/workflow-agents-api/onboarding.mjs +3 -3
- package/src/session-runtime/workspace/activity-guards.mjs +176 -0
- package/src/session-runtime/workspace/session-view.mjs +149 -0
- package/src/session-runtime/workspace/side-checkouts.mjs +203 -0
- package/src/session-runtime/workspace/transition-runner.mjs +188 -0
- package/src/session-runtime/workspace/transitions.mjs +108 -1041
- package/src/session-runtime/workspace/workspace-merge.mjs +132 -0
- package/src/session-runtime/workspace/worktree-intents.mjs +242 -0
- package/src/session-runtime/workspace/worktree-maintenance.mjs +80 -0
- package/src/session-runtime/workspace/worktree-setup.mjs +85 -0
- package/src/session-runtime/workspace/worktree-tool.mjs +73 -56
- package/src/standalone/daemon-desktop-runtime.mjs +2 -0
- package/src/standalone/daemon-session-control.mjs +169 -138
- package/src/standalone/daemon.mjs +7 -0
- package/src/standalone/desktop-service-registry.mjs +9 -0
- package/src/standalone/local-session-runtime.mjs +5 -1
- package/src/standalone/session-client/daemon-unavailable.mjs +3 -0
- package/src/standalone/session-client.mjs +5 -1
- package/src/standalone/session-frame-stream.mjs +83 -11
- package/src/standalone/session-protocol.mjs +4 -0
- package/src/standalone/session-service/agent-tree/agent-turns.mjs +16 -12
- package/src/standalone/session-service/agent-tree.mjs +45 -9
- package/src/standalone/session-service/projection/transcript-window.mjs +700 -64
- package/src/standalone/session-service/session-calls/session-action.mjs +10 -3
- package/src/standalone/session-service/session-calls/session-views.mjs +160 -104
- package/src/standalone/session-service/stored-reader.mjs +127 -40
- package/src/standalone/session-transport/client-registry/client-grace.mjs +12 -9
- package/src/tui/App.jsx +154 -164
- package/src/tui/app/app-view/floating-panel.jsx +10 -4
- package/src/tui/app/app-view/text-entry-labels.mjs +1 -0
- package/src/tui/app/clipboard.mjs +21 -10
- package/src/tui/app/model-picker/route-selection/fast-parameters.mjs +1 -3
- package/src/tui/app/model-picker/route-selection.mjs +5 -6
- package/src/tui/app/prompt-handlers/use-prompt-history-nav.mjs +1 -1
- package/src/tui/app/prompt-handlers/use-prompt-interrupt.mjs +3 -0
- package/src/tui/app/prompt-submit/provider-prompts.mjs +3 -1
- package/src/tui/app/provider-setup/api-key-actions.mjs +31 -1
- package/src/tui/app/provider-setup/oauth-actions.mjs +58 -21
- package/src/tui/app/provider-setup/provider-items.mjs +8 -2
- package/src/tui/app/provider-setup-picker.mjs +29 -18
- package/src/tui/app/shell-layout/row-budgets.mjs +12 -10
- package/src/tui/app/slash-commands.mjs +1 -0
- package/src/tui/app/slash-dispatch/session-commands.mjs +46 -0
- package/src/tui/app/slash-dispatch.mjs +1 -1
- package/src/tui/app/use-btw-panel.mjs +29 -0
- package/src/tui/app/use-context-panel-refresh.mjs +31 -0
- package/src/tui/app/use-model-catalog-cache.mjs +13 -10
- package/src/tui/app/use-mouse-input.mjs +11 -0
- package/src/tui/app/use-onboarding-start.mjs +8 -3
- package/src/tui/app/use-panel-transition.mjs +10 -1
- package/src/tui/app/use-pasted-buffers.mjs +28 -20
- package/src/tui/app/use-prompt-draft-flow.mjs +7 -0
- package/src/tui/app/use-prompt-layout-rows.mjs +3 -3
- package/src/tui/app/use-prompt-queue-history.mjs +3 -2
- package/src/tui/app/use-selection-focus.mjs +11 -2
- package/src/tui/app/use-selection-geometry.mjs +18 -9
- package/src/tui/app/use-selection-paint.mjs +4 -4
- package/src/tui/app/use-selection-stitch.mjs +3 -3
- package/src/tui/app/use-slash-palette.mjs +62 -0
- package/src/tui/app/use-terminal-chrome.mjs +2 -2
- package/src/tui/app/use-transcript-activity.mjs +47 -32
- package/src/tui/app/use-transcript-follow.mjs +12 -4
- package/src/tui/app/use-transcript-scroll.mjs +46 -17
- package/src/tui/app/use-transcript-swap-reset.mjs +27 -0
- package/src/tui/app/use-transcript-window/geometry.mjs +19 -5
- package/src/tui/app/use-transcript-window/instance-state.mjs +4 -0
- package/src/tui/app/use-transcript-window/selection-shift.mjs +5 -1
- package/src/tui/app/use-transcript-window.mjs +21 -11
- package/src/tui/app/use-tui-ready.mjs +18 -0
- package/src/tui/app/use-welcome-prompt-hint.mjs +5 -0
- package/src/tui/app/use-workflow-tab-cycle.mjs +5 -3
- package/src/tui/components/Picker.jsx +27 -3
- package/src/tui/components/QuestionPanel.jsx +13 -4
- package/src/tui/components/SignInUrl.jsx +68 -0
- package/src/tui/components/TextEntryPanel.jsx +76 -46
- package/src/tui/components/sign-in-url-layout.mjs +24 -0
- package/src/tui/dist/index.mjs +1963 -1361
- package/src/tui/session/goal-turn-state.mjs +6 -2
- package/src/tui/session/session-api/controls.mjs +4 -0
- package/src/tui/session/session-api/extensions.mjs +8 -0
- package/src/tui/session/session-api/intake/abort.mjs +2 -1
- package/src/tui/session/session-api/intake.mjs +2 -0
- package/src/tui/session/session-api/integrations.mjs +2 -2
- package/src/tui/session/session-api/routes-agent-definitions.mjs +1 -0
- package/src/tui/session/session-api/settings.mjs +2 -2
- package/src/tui/session/session-flow/queue/take-entries.mjs +11 -0
- package/src/tui/session/transcript-spill/spill-writer.mjs +15 -0
- package/src/tui/session/transcript-spill.mjs +92 -4
- package/src/tui/session/transcript-store.mjs +2 -0
- package/src/ui/statusline-agents.mjs +1 -3
- package/src/defaults/skills/skill-creator/references/source-review.md +0 -94
|
@@ -4,12 +4,22 @@
|
|
|
4
4
|
// Policy gating happens BEFORE any network call: 'never' refuses, 'ask' returns
|
|
5
5
|
// needsApproval unless the call carried approveDownloads:true, 'auto' proceeds.
|
|
6
6
|
// Toolchain engines (rustfmt, gofmt, zig fmt, ...) are never downloadable.
|
|
7
|
-
import {
|
|
7
|
+
import {
|
|
8
|
+
chmodSync,
|
|
9
|
+
existsSync,
|
|
10
|
+
mkdirSync,
|
|
11
|
+
readFileSync,
|
|
12
|
+
readdirSync,
|
|
13
|
+
renameSync,
|
|
14
|
+
rmSync,
|
|
15
|
+
statSync,
|
|
16
|
+
writeFileSync,
|
|
17
|
+
} from 'node:fs';
|
|
8
18
|
import { fileURLToPath } from 'node:url';
|
|
9
19
|
import { join } from 'node:path';
|
|
10
20
|
import { MAX_NATIVE_BINARY_DOWNLOAD_BYTES, streamResponseToFile } from '../shared/bounded-download.mjs';
|
|
11
|
-
import { platformEntryKey, platformKey, sha256File } from '../shared/native-asset.mjs';
|
|
12
|
-
import {
|
|
21
|
+
import { platformEntryKey, platformKey, sha256File, validSha256 } from '../shared/native-asset.mjs';
|
|
22
|
+
import { fileHasDataAsync } from '../shared/file-has-data.mjs';
|
|
13
23
|
import { readJsonSafe } from '../shared/json-file.mjs';
|
|
14
24
|
import { ENGINE_CATALOG } from './engines.mjs';
|
|
15
25
|
import { extractArchive } from './extract.mjs';
|
|
@@ -45,14 +55,73 @@ export function manifestAsset(manifest, id, pkey = platformEntryKey(manifest?.en
|
|
|
45
55
|
return { entry, asset, version: String(entry.version || '0'), pkey: entry?.assets?.[pkey] ? pkey : 'any' };
|
|
46
56
|
}
|
|
47
57
|
|
|
48
|
-
|
|
49
|
-
|
|
58
|
+
// The installer records the extracted binary's sha256 beside it; a reuse
|
|
59
|
+
// re-hashes the binary against that record. Like the other managed binaries
|
|
60
|
+
// (mixdog-spawn / patch / graph resolve their path once per process), the hash
|
|
61
|
+
// runs once per process per binary, again only when its size or mtime changes.
|
|
62
|
+
// An install from before the record existed has no digest file: its first use
|
|
63
|
+
// records the digest (trust on first use). An existing record that is invalid
|
|
64
|
+
// or does not match is never overwritten; that binary is tampered or corrupt.
|
|
65
|
+
export const ENGINE_DIGEST_FILE = '.engine.sha256';
|
|
66
|
+
const verifiedEngineBins = new Map();
|
|
67
|
+
|
|
68
|
+
function recordEngineDigest(digestFile, digest) {
|
|
69
|
+
const tmp = `${digestFile}.tmp-${process.pid}-${Date.now()}`;
|
|
70
|
+
try {
|
|
71
|
+
writeFileSync(tmp, digest);
|
|
72
|
+
renameSync(tmp, digestFile);
|
|
73
|
+
} catch {
|
|
74
|
+
/* unrecorded: this install is trusted for this process only */
|
|
75
|
+
} finally {
|
|
76
|
+
try {
|
|
77
|
+
rmSync(tmp, { force: true });
|
|
78
|
+
} catch {
|
|
79
|
+
/* a leftover temp file never matches the digest path */
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
// The recorded digest decides whether a binary is intact. Only an install from
|
|
85
|
+
// before the record existed has none; there alone the content probe keeps a
|
|
86
|
+
// crash-torn (empty or NUL-filled) binary from becoming the digest it is
|
|
87
|
+
// trusted by. A binary that cannot be statted, read or hashed cannot be
|
|
88
|
+
// verified, so it is not reused.
|
|
89
|
+
async function engineBinaryIntact(dir, full) {
|
|
90
|
+
try {
|
|
91
|
+
const stamp = statSync(full);
|
|
92
|
+
const key = `${stamp.size}:${stamp.mtimeMs}`;
|
|
93
|
+
if (verifiedEngineBins.get(full) === key) return true;
|
|
94
|
+
const digestFile = join(dir, ENGINE_DIGEST_FILE);
|
|
95
|
+
let recorded = null;
|
|
96
|
+
try {
|
|
97
|
+
recorded = readFileSync(digestFile, 'utf8').trim().toLowerCase();
|
|
98
|
+
} catch (error) {
|
|
99
|
+
if (error?.code !== 'ENOENT') return false;
|
|
100
|
+
}
|
|
101
|
+
if (recorded === null && !(await fileHasDataAsync(full))) return false;
|
|
102
|
+
const actual = await sha256File(full);
|
|
103
|
+
if (recorded === null) {
|
|
104
|
+
recordEngineDigest(digestFile, actual);
|
|
105
|
+
recorded = actual;
|
|
106
|
+
}
|
|
107
|
+
if (!validSha256(recorded) || actual !== recorded) return false;
|
|
108
|
+
verifiedEngineBins.set(full, key);
|
|
109
|
+
return true;
|
|
110
|
+
} catch {
|
|
111
|
+
return false;
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
/** An already-installed managed binary for `id`, or null. No network; the
|
|
116
|
+
* binary probe is async so a slow (scanned) open never stalls the event loop. */
|
|
117
|
+
export async function managedEngineBinary({ id, manifest, pluginData }) {
|
|
50
118
|
const found = manifestAsset(manifest, id);
|
|
51
119
|
if (!found || !pluginData) return null;
|
|
52
120
|
const binPath = String(found.asset.binPath || '');
|
|
53
121
|
if (!binPath) return null;
|
|
54
|
-
const
|
|
55
|
-
|
|
122
|
+
const dir = managedEngineDir(pluginData, id, found.version);
|
|
123
|
+
const full = join(dir, binPath);
|
|
124
|
+
return (await engineBinaryIntact(dir, full)) ? { path: full, version: found.version } : null;
|
|
56
125
|
}
|
|
57
126
|
|
|
58
127
|
/** Throws unless `filePath` hashes to `expected`. */
|
|
@@ -72,7 +141,13 @@ export async function verifyDownloadDigest(filePath, expected, label = LABEL) {
|
|
|
72
141
|
* Decide what an install call may do, without touching the network.
|
|
73
142
|
* Returns { targets, present, needsApproval, errors }.
|
|
74
143
|
*/
|
|
75
|
-
export function planInstall({
|
|
144
|
+
export async function planInstall({
|
|
145
|
+
ids = [],
|
|
146
|
+
manifest,
|
|
147
|
+
pluginData = '',
|
|
148
|
+
policy = 'auto',
|
|
149
|
+
approveDownloads = false,
|
|
150
|
+
} = {}) {
|
|
76
151
|
const targets = [];
|
|
77
152
|
const present = [];
|
|
78
153
|
const errors = [];
|
|
@@ -101,7 +176,7 @@ export function planInstall({ ids = [], manifest, pluginData = '', policy = 'aut
|
|
|
101
176
|
});
|
|
102
177
|
continue;
|
|
103
178
|
}
|
|
104
|
-
const installed = managedEngineBinary({ id, manifest, pluginData });
|
|
179
|
+
const installed = await managedEngineBinary({ id, manifest, pluginData });
|
|
105
180
|
if (installed) {
|
|
106
181
|
present.push({ id, version: installed.version, path: installed.path });
|
|
107
182
|
continue;
|
|
@@ -242,8 +317,9 @@ export async function installEngine(
|
|
|
242
317
|
const engineRoot = join(managedToolsDir(pluginData), target.id);
|
|
243
318
|
const finalDir = managedEngineDir(pluginData, target.id, target.version);
|
|
244
319
|
const binFull = join(finalDir, target.binPath);
|
|
245
|
-
// An engine binary a crash left NUL-filled
|
|
246
|
-
|
|
320
|
+
// An engine binary a crash left NUL-filled, or that no longer matches its
|
|
321
|
+
// recorded digest, is not present: it is installed again.
|
|
322
|
+
if (await engineBinaryIntact(finalDir, binFull)) {
|
|
247
323
|
return { id: target.id, version: target.version, path: binFull, bytes: 0, status: 'present' };
|
|
248
324
|
}
|
|
249
325
|
mkdirSync(engineRoot, { recursive: true });
|
|
@@ -272,12 +348,16 @@ export async function installEngine(
|
|
|
272
348
|
/* best-effort */
|
|
273
349
|
}
|
|
274
350
|
}
|
|
351
|
+
writeFileSync(join(stageDir, ENGINE_DIGEST_FILE), await sha256File(stagedBin));
|
|
275
352
|
try {
|
|
276
|
-
if (existsSync(finalDir) && !
|
|
353
|
+
if (existsSync(finalDir) && !(await engineBinaryIntact(finalDir, binFull))) {
|
|
354
|
+
verifiedEngineBins.delete(binFull);
|
|
355
|
+
rmSync(finalDir, { recursive: true, force: true });
|
|
356
|
+
}
|
|
277
357
|
renameSync(stageDir, finalDir);
|
|
278
358
|
} catch (error) {
|
|
279
|
-
// A concurrent install won the race
|
|
280
|
-
if (!
|
|
359
|
+
// A concurrent install won the race only if the surviving copy verifies.
|
|
360
|
+
if (!(await engineBinaryIntact(finalDir, binFull))) throw error;
|
|
281
361
|
}
|
|
282
362
|
return { id: target.id, version: target.version, path: binFull, bytes, status: 'installed' };
|
|
283
363
|
} finally {
|
|
@@ -305,7 +385,7 @@ export async function installEngines({
|
|
|
305
385
|
stallTimeoutMs = undefined,
|
|
306
386
|
} = {}) {
|
|
307
387
|
const loaded = manifest || readEnginesManifest();
|
|
308
|
-
const plan = planInstall({ ids, manifest: loaded, pluginData, policy, approveDownloads });
|
|
388
|
+
const plan = await planInstall({ ids, manifest: loaded, pluginData, policy, approveDownloads });
|
|
309
389
|
const installed = [...plan.present];
|
|
310
390
|
const errors = [...plan.errors];
|
|
311
391
|
if (!pluginData && plan.targets.length > 0) {
|
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
// on the id. AUX_LANGUAGE_EXTENSIONS adds the config/markup languages the graph
|
|
7
7
|
// never parses but formatters do (PowerShell, JSON, TOML, ...).
|
|
8
8
|
import { extname } from 'node:path';
|
|
9
|
+
import { startGit } from '../shared/git-launch.mjs';
|
|
9
10
|
import { runProcess } from './process.mjs';
|
|
10
11
|
|
|
11
12
|
export const CODE_LANGUAGE_EXTENSIONS = Object.freeze({
|
|
@@ -156,21 +157,22 @@ export function parseGraphLangs(stdout) {
|
|
|
156
157
|
|
|
157
158
|
/** git-tracked files under `cwd`, filtered to the requested scope paths. */
|
|
158
159
|
async function listScopedFiles({ cwd, paths = [], signal = null, timeoutMs = 20_000 } = {}) {
|
|
159
|
-
const
|
|
160
|
-
'
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
{ cwd, signal, timeoutMs }
|
|
160
|
+
const args = [
|
|
161
|
+
'-c',
|
|
162
|
+
'core.quotepath=false',
|
|
163
|
+
'--literal-pathspecs',
|
|
164
|
+
'ls-files',
|
|
165
|
+
'--cached',
|
|
166
|
+
'--others',
|
|
167
|
+
'--exclude-standard',
|
|
168
|
+
'-z',
|
|
169
|
+
'--',
|
|
170
|
+
...paths,
|
|
171
|
+
];
|
|
172
|
+
const result = await startGit(
|
|
173
|
+
process.env,
|
|
174
|
+
(command, env) => runProcess(command, args, { cwd, signal, timeoutMs, env }),
|
|
175
|
+
(outcome) => ({ code: outcome.errorCode })
|
|
174
176
|
);
|
|
175
177
|
if (result.code !== 0) {
|
|
176
178
|
return {
|
|
@@ -108,8 +108,9 @@ function captureInto(state, key, chunk, cap) {
|
|
|
108
108
|
|
|
109
109
|
/**
|
|
110
110
|
* Spawn `bin` with `args` and collect its output.
|
|
111
|
-
* Resolves `{code, signal, stdout, stderr, timedOut, error}` — a
|
|
112
|
-
*
|
|
111
|
+
* Resolves `{code, signal, stdout, stderr, timedOut, error, errorCode}` — a
|
|
112
|
+
* failed spawn is reported (`errorCode`: its code, e.g. ENOENT), never thrown,
|
|
113
|
+
* so one broken engine cannot abort the multiplexer.
|
|
113
114
|
*/
|
|
114
115
|
export function runProcess(
|
|
115
116
|
bin,
|
|
@@ -151,6 +152,7 @@ export function runProcess(
|
|
|
151
152
|
timedOut: false,
|
|
152
153
|
truncated: false,
|
|
153
154
|
error: error?.message || String(error),
|
|
155
|
+
errorCode: error?.code || '',
|
|
154
156
|
});
|
|
155
157
|
return;
|
|
156
158
|
}
|
|
@@ -209,7 +211,7 @@ export function runProcess(
|
|
|
209
211
|
|
|
210
212
|
// One exit path for both outcomes: whoever settles first reports the
|
|
211
213
|
// captured output and clears the timers.
|
|
212
|
-
const settle = (code, exitSignal, error) => {
|
|
214
|
+
const settle = (code, exitSignal, error, errorCode = '') => {
|
|
213
215
|
if (settled) return;
|
|
214
216
|
settled = true;
|
|
215
217
|
clearTimers();
|
|
@@ -221,12 +223,13 @@ export function runProcess(
|
|
|
221
223
|
timedOut,
|
|
222
224
|
truncated: Boolean(state.stdoutTruncated || state.stderrTruncated),
|
|
223
225
|
error,
|
|
226
|
+
errorCode,
|
|
224
227
|
});
|
|
225
228
|
};
|
|
226
229
|
|
|
227
230
|
child.stdout?.on('data', (chunk) => captureInto(state, 'stdout', chunk, cap));
|
|
228
231
|
child.stderr?.on('data', (chunk) => captureInto(state, 'stderr', chunk, cap));
|
|
229
|
-
child.on('error', (error) => settle(-1, null, error?.message || String(error)));
|
|
232
|
+
child.on('error', (error) => settle(-1, null, error?.message || String(error), error?.code || ''));
|
|
230
233
|
if (input != null && child.stdin) {
|
|
231
234
|
child.stdin.on('error', () => {
|
|
232
235
|
/* child may close stdin early */
|
|
@@ -135,7 +135,7 @@ function installableFlag(entry, manifest) {
|
|
|
135
135
|
return entry.managed && manifestAsset(manifest, entry.id) ? { installable: true } : {};
|
|
136
136
|
}
|
|
137
137
|
|
|
138
|
-
function resolveOne({ cwd, entry, config, env, manifest, pluginData, pathIndex }) {
|
|
138
|
+
async function resolveOne({ cwd, entry, config, env, manifest, pluginData, pathIndex }) {
|
|
139
139
|
const base = {
|
|
140
140
|
id: entry.id,
|
|
141
141
|
kind: entry.kind,
|
|
@@ -169,7 +169,8 @@ function resolveOne({ cwd, entry, config, env, manifest, pluginData, pathIndex }
|
|
|
169
169
|
installHint: entry.hostInstallHint || entry.installHint,
|
|
170
170
|
};
|
|
171
171
|
}
|
|
172
|
-
const managed =
|
|
172
|
+
const managed =
|
|
173
|
+
entry.managed && pluginData ? await managedEngineBinary({ id: entry.id, manifest, pluginData }) : null;
|
|
173
174
|
if (managed) {
|
|
174
175
|
return {
|
|
175
176
|
...base,
|
|
@@ -194,7 +195,7 @@ function resolveOne({ cwd, entry, config, env, manifest, pluginData, pathIndex }
|
|
|
194
195
|
const onPath = pathBinary(entry, env, pathIndex);
|
|
195
196
|
if (onPath) return { ...base, source: 'path', path: onPath.path, ...commandFor(entry, onPath.path) };
|
|
196
197
|
if (entry.managed && pluginData) {
|
|
197
|
-
const managed = managedEngineBinary({ id: entry.id, manifest, pluginData });
|
|
198
|
+
const managed = await managedEngineBinary({ id: entry.id, manifest, pluginData });
|
|
198
199
|
if (managed) {
|
|
199
200
|
return {
|
|
200
201
|
...base,
|
|
@@ -282,20 +283,22 @@ export async function resolveEngines({
|
|
|
282
283
|
else if (languages.length > 0) requested = enginesForLanguages(languages);
|
|
283
284
|
const unknown = engineIds.filter((id) => !ENGINE_IDS.includes(id));
|
|
284
285
|
|
|
285
|
-
// One listing per PATH dir for the whole batch
|
|
286
|
-
//
|
|
286
|
+
// One listing per PATH dir for the whole batch (the desktop's Code Tidy
|
|
287
|
+
// status read at startup runs this on the host loop).
|
|
287
288
|
const pathIndex = createPathIndex(env);
|
|
288
|
-
const resolved =
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
result.
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
289
|
+
const resolved = await Promise.all(
|
|
290
|
+
requested.map(async (id) => {
|
|
291
|
+
const entry = ENGINE_CATALOG[id];
|
|
292
|
+
const result = await resolveOne({ cwd, entry, config, env, manifest: loadedManifest, pluginData, pathIndex });
|
|
293
|
+
const configFile = projectConfigFileFor(cwd, entry);
|
|
294
|
+
if (configFile) result.configFile = configFile;
|
|
295
|
+
if (entry.requiresConfig && !configFile && result.source !== 'project-config') {
|
|
296
|
+
result.skipped = 'no project config for this engine';
|
|
297
|
+
}
|
|
298
|
+
if (entry.toolchain) result.toolchain = true;
|
|
299
|
+
return result;
|
|
300
|
+
})
|
|
301
|
+
);
|
|
299
302
|
|
|
300
303
|
// A project driving Prettier/ESLint from node_modules/.bin keeps them: Biome
|
|
301
304
|
// stands down rather than reformatting against the project's own config.
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
// Biome — JSON reporter for check, `--write` (1.x: `--apply`) for fix.
|
|
2
|
-
import { availableParallelism } from 'node:os';
|
|
3
2
|
import { mapLimit, runProcess } from '../process.mjs';
|
|
4
3
|
import {
|
|
5
4
|
FILES_PER_SPAWN,
|
|
@@ -19,8 +18,9 @@ export const BIOME_CHECK_ARGS = ['check', '--reporter=json', '--max-diagnostics=
|
|
|
19
18
|
export const BIOME_TRUNCATED_NOTE =
|
|
20
19
|
'biome JSON output was truncated; split the scope and re-run to get complete diagnostics';
|
|
21
20
|
const EXPLAIN_TIMEOUT_MS = 8_000;
|
|
22
|
-
// One short single-rule process each
|
|
23
|
-
|
|
21
|
+
// One short single-rule process each, a few at a time: the host is the
|
|
22
|
+
// user's working machine, so the fan-out does not grow with its core count.
|
|
23
|
+
const EXPLAIN_CONCURRENCY = 4;
|
|
24
24
|
|
|
25
25
|
function severityOf(value) {
|
|
26
26
|
const level = String(value || '').toLowerCase();
|
|
@@ -214,7 +214,7 @@ async function satisfyMissingEngines({ resolution, cwd, engineFilter, approveDow
|
|
|
214
214
|
if (policy === 'never') return { resolution, needsApproval: null, installed: null };
|
|
215
215
|
const { installEngines, planInstall } = await import('./install.mjs');
|
|
216
216
|
if (policy !== 'auto' && !approveDownloads) {
|
|
217
|
-
const plan = planInstall({
|
|
217
|
+
const plan = await planInstall({
|
|
218
218
|
ids: installable,
|
|
219
219
|
manifest: resolution.manifest,
|
|
220
220
|
pluginData: resolution.pluginData,
|
|
@@ -7,6 +7,7 @@
|
|
|
7
7
|
// already non-conforming in HEAD had to be reverted by hand. Scope still comes
|
|
8
8
|
// from `paths` and nothing here derives one from a diff: the split is a report
|
|
9
9
|
// the caller reads before writing, so they can pass a precise file list.
|
|
10
|
+
import { startGit } from '../shared/git-launch.mjs';
|
|
10
11
|
import { normalizeRel } from './languages.mjs';
|
|
11
12
|
import { runProcess, which } from './process.mjs';
|
|
12
13
|
|
|
@@ -44,13 +45,16 @@ export async function listWorkingTreeChanges({
|
|
|
44
45
|
env = process.env,
|
|
45
46
|
} = {}) {
|
|
46
47
|
if (!which('git', { env })) return { files: null, error: '', skipped: NO_GIT_REASON };
|
|
48
|
+
// The git the caller's own PATH names, as the lookup above found it.
|
|
49
|
+
const git = (args) =>
|
|
50
|
+
startGit(
|
|
51
|
+
env,
|
|
52
|
+
(command, childEnv) => runProcess(command, args, { cwd, signal, timeoutMs, env: childEnv }),
|
|
53
|
+
(result) => ({ code: result.errorCode })
|
|
54
|
+
);
|
|
47
55
|
const [status, prefix] = await Promise.all([
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
['-c', 'core.quotepath=false', '--literal-pathspecs', 'status', '--porcelain', '-z', '--untracked-files=all'],
|
|
51
|
-
{ cwd, signal, timeoutMs, env }
|
|
52
|
-
),
|
|
53
|
-
runProcess('git', ['rev-parse', '--show-prefix'], { cwd, signal, timeoutMs, env }),
|
|
56
|
+
git(['-c', 'core.quotepath=false', '--literal-pathspecs', 'status', '--porcelain', '-z', '--untracked-files=all']),
|
|
57
|
+
git(['rev-parse', '--show-prefix']),
|
|
54
58
|
]);
|
|
55
59
|
const failed = [status, prefix].find((result) => result.code !== 0);
|
|
56
60
|
if (failed) {
|
|
@@ -43,6 +43,9 @@ export function validateVisualizeArgs(args) {
|
|
|
43
43
|
return { ok: false, error: 'action must be open, close, annotate, capture, export, check, or inspect' };
|
|
44
44
|
const input = args.input ?? {};
|
|
45
45
|
if (typeof input !== 'object' || Array.isArray(input)) return { ok: false, error: 'input must be an object' };
|
|
46
|
+
if (args.action === 'open' && input.verify != null && typeof input.verify !== 'boolean') {
|
|
47
|
+
return { ok: false, error: 'open input.verify must be a boolean' };
|
|
48
|
+
}
|
|
46
49
|
if (args.action === 'open' && input.content != null) {
|
|
47
50
|
const content = input.content;
|
|
48
51
|
if (input.targets != null)
|
|
@@ -114,7 +117,7 @@ export function validateVisualizeArgs(args) {
|
|
|
114
117
|
if (args.action === 'export') {
|
|
115
118
|
if (input.format !== 'png' && input.format !== 'pdf')
|
|
116
119
|
return { ok: false, error: 'export requires input.format png or pdf' };
|
|
117
|
-
if (typeof input.output !== 'string' || !new RegExp(
|
|
120
|
+
if (typeof input.output !== 'string' || !new RegExp(`\\.${input.format}$`, 'i').test(input.output.trim())) {
|
|
118
121
|
return { ok: false, error: `export requires input.output ending in .${input.format}` };
|
|
119
122
|
}
|
|
120
123
|
if (input.version != null && !(Number.isInteger(input.version) && input.version >= 1)) {
|
|
@@ -163,6 +166,8 @@ export async function executeVisualizeTool(args, options = {}) {
|
|
|
163
166
|
cwd: options.cwd || process.cwd(),
|
|
164
167
|
action: validated.action,
|
|
165
168
|
input: validated.input,
|
|
169
|
+
// The call's id: the host names it in its turn-end record of opens whose tab is gone.
|
|
170
|
+
...(options.callId ? { callId: String(options.callId) } : {}),
|
|
166
171
|
};
|
|
167
172
|
let discovery = readBridgeDiscovery(DISCOVERY_FILE);
|
|
168
173
|
if (!discovery) return toolError(unavailableMessage());
|
|
@@ -10,8 +10,8 @@ export const TOOL_DEFS = [
|
|
|
10
10
|
name: 'visualize',
|
|
11
11
|
title: 'Mixdog Visualize',
|
|
12
12
|
description:
|
|
13
|
-
'Show the user
|
|
14
|
-
'open: input.targets (1-3 file paths, relative to the working directory or absolute anywhere on this machine; 2-3 = side-by-side comparison; or a single http(s) URL alone, never mixed with files or other URLs), optional label, optional version (show that kept version of a file tab read-only; each open/reload that changes the files keeps a version). close: optional tab (omit = all). ' +
|
|
13
|
+
'Show the user a finished deliverable you produced or changed (mockups, docs, decks, sheets, PDFs, images, video, local dev pages) in the desktop side panel beside the chat. A summary, plan or report of your own work is not one either: it stays in the chat. Your own check screenshots are not deliverables: look at them with read; open with verify: true only to run check/inspect/capture/export. Panel tabs auto-reload when a file changes, so re-opening after edits is unnecessary. ' +
|
|
14
|
+
'open: input.targets (1-3 file paths, relative to the working directory or absolute anywhere on this machine; 2-3 = side-by-side comparison; or a single http(s) URL alone, never mixed with files or other URLs), optional label, optional version (show that kept version of a file tab read-only; each open/reload that changes the files keeps a version), optional verify (true = you open only to check your own work with check/inspect/capture/export: the user is not shown the tab and it closes when the turn ends; leave it off for anything the user should see). close: optional tab (omit = all). ' +
|
|
15
15
|
'annotate: tab + add [{selector,label?}] | remove [selector] | clear; HTML pages only, never edits the file. capture: tab + output (.png path). ' +
|
|
16
16
|
'export: tab + format (png|pdf) + output (project-relative path ending .png/.pdf) + optional version (a kept version of the tab) + optional overwrite (true replaces an existing file, only under design/; otherwise an existing file is refused). Writes a record of the approved page inside the project and returns its project-relative path, size/dimensions and the page problems seen while rendering. A single HTML page (file, or inline html/chart) is rendered whole in a hidden window, so the tab need not be on screen (PDF: HTML pages only; PNG has a pixel cap, over it export pdf or shorten the page); any other tab exports as capture does (the displayed tab, PNG only). Same project containment as capture: links and paths outside the working directory are refused. ' +
|
|
17
17
|
'check: tab; HTML pages only; waits briefly for the page to settle and returns only its runtime problems (uncaught errors, unhandled rejections, CSP violations, console errors/warnings, missing local assets). ' +
|
|
@@ -61,6 +61,11 @@ export const TOOL_DEFS = [
|
|
|
61
61
|
description:
|
|
62
62
|
'open (file tabs): kept version number to show read-only instead of the live files. export: kept version number to render instead of the live page.',
|
|
63
63
|
},
|
|
64
|
+
verify: {
|
|
65
|
+
type: 'boolean',
|
|
66
|
+
description:
|
|
67
|
+
'open (files or content): true to check your own work only; the user is not shown the tab and it closes when the turn ends.',
|
|
68
|
+
},
|
|
64
69
|
tab: { type: 'string', description: 'Tab id from open (close: omit for all).' },
|
|
65
70
|
add: {
|
|
66
71
|
type: 'array',
|
|
@@ -102,7 +102,7 @@ function normalizeUrlArgs(rawArgs) {
|
|
|
102
102
|
function invalidArgsResponse(error) {
|
|
103
103
|
if (!(error instanceof z.ZodError)) return null;
|
|
104
104
|
return {
|
|
105
|
-
content: [{ type: 'text', text: JSON.stringify({ error: 'Invalid arguments', details: error.
|
|
105
|
+
content: [{ type: 'text', text: JSON.stringify({ error: 'Invalid arguments', details: error.issues }) }],
|
|
106
106
|
isError: true,
|
|
107
107
|
};
|
|
108
108
|
}
|
|
@@ -332,6 +332,9 @@ export function createRoutineResultQueue(
|
|
|
332
332
|
rounds: section(doc, 'rounds'),
|
|
333
333
|
// Reporting turns not yet queued, by submission id (agent-task-sessions.mjs).
|
|
334
334
|
watches: section(doc, 'watches'),
|
|
335
|
+
// The bot-sent turns that hold no watch (reports off, or a watch that could
|
|
336
|
+
// not be stored), by submission id: work a restart re-attaches.
|
|
337
|
+
owned: section(doc, 'owned'),
|
|
335
338
|
// Posted task results whose wake turn was not taken yet, per home.
|
|
336
339
|
wakes: section(doc, 'wakes'),
|
|
337
340
|
});
|
|
@@ -559,6 +562,26 @@ export function createRoutineResultQueue(
|
|
|
559
562
|
return { ...doc, watches };
|
|
560
563
|
});
|
|
561
564
|
},
|
|
565
|
+
/** Keep `work` ({ runId, agentId, taskSessionId, owner, at }): a bot-sent
|
|
566
|
+
* turn that reports nothing, until its work ends. It is no watch: it
|
|
567
|
+
* owes no report, starts no hand-off and takes no part in a watch cap. */
|
|
568
|
+
async own(work) {
|
|
569
|
+
await update((doc) => ({ ...doc, owned: { ...doc.owned, [work.runId]: work } }));
|
|
570
|
+
},
|
|
571
|
+
/** Every stored record of bot-sent work that reports nothing, oldest first. */
|
|
572
|
+
async owned() {
|
|
573
|
+
return Object.values((await read()).owned);
|
|
574
|
+
},
|
|
575
|
+
/** Drop the records of `runIds` (a run id or a list; their work ended), in one write. */
|
|
576
|
+
async disown(runIds) {
|
|
577
|
+
const ids = [runIds].flat();
|
|
578
|
+
await update((doc) => {
|
|
579
|
+
if (!ids.some((runId) => doc.owned[runId])) return undefined;
|
|
580
|
+
const owned = { ...doc.owned };
|
|
581
|
+
for (const runId of ids) delete owned[runId];
|
|
582
|
+
return { ...doc, owned };
|
|
583
|
+
});
|
|
584
|
+
},
|
|
562
585
|
/** The user spoke in `homeId`: its round trips count from zero again. */
|
|
563
586
|
async resetRounds(homeId) {
|
|
564
587
|
await update((doc) => {
|
|
@@ -1351,6 +1374,9 @@ export function createAgentHomeDelivery({
|
|
|
1351
1374
|
unwatchTask: (runId) => queue.unwatch(runId),
|
|
1352
1375
|
followTask: (runId, submissionId) => queue.followWatch(runId, submissionId),
|
|
1353
1376
|
taskWatches: () => queue.watches(),
|
|
1377
|
+
ownTask: (work) => queue.own(work),
|
|
1378
|
+
disownTask: (runId) => queue.disown(runId),
|
|
1379
|
+
ownedTasks: () => queue.owned(),
|
|
1354
1380
|
resetRounds: (homeId) => queue.resetRounds(homeId),
|
|
1355
1381
|
};
|
|
1356
1382
|
}
|
|
@@ -1446,6 +1472,21 @@ export async function followAgentTask(runId, submissionId) {
|
|
|
1446
1472
|
return (await processDelivery()).followTask(runId, submissionId);
|
|
1447
1473
|
}
|
|
1448
1474
|
|
|
1475
|
+
/** Keep the record of one bot-sent turn that reports nothing until its work ends. */
|
|
1476
|
+
export async function ownAgentTask(work) {
|
|
1477
|
+
return (await processDelivery()).ownTask(work);
|
|
1478
|
+
}
|
|
1479
|
+
|
|
1480
|
+
/** Drop the record of one bot-sent turn that reports nothing (its work ended). */
|
|
1481
|
+
export async function disownAgentTask(runId) {
|
|
1482
|
+
return (await processDelivery()).disownTask(runId);
|
|
1483
|
+
}
|
|
1484
|
+
|
|
1485
|
+
/** The bot-sent turns that report nothing and whose work was not seen to end. */
|
|
1486
|
+
export async function agentOwnedTasks() {
|
|
1487
|
+
return (await processDelivery()).ownedTasks();
|
|
1488
|
+
}
|
|
1489
|
+
|
|
1449
1490
|
/** A user's own message in `homeId`: its round trips with every target restart. */
|
|
1450
1491
|
export async function resetAgentTaskRounds(homeId) {
|
|
1451
1492
|
return (await processDelivery()).resetRounds(homeId);
|