gsd-pi 2.77.0-dev.eaa4973bc → 2.78.0-dev.aeeb2ca00
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 +53 -17
- package/dist/claude-cli-check.js +46 -10
- package/dist/headless.js +49 -4
- package/dist/resource-loader.d.ts +40 -0
- package/dist/resource-loader.js +32 -13
- package/dist/resources/extensions/browser-tools/capture.js +9 -0
- package/dist/resources/extensions/browser-tools/tests/browser-tools-integration.test.mjs +8 -59
- package/dist/resources/extensions/browser-tools/tests/browser-tools-unit.test.cjs +36 -24
- package/dist/resources/extensions/browser-tools/tests/capture-sharp-optional.test.cjs +69 -71
- package/dist/resources/extensions/browser-tools/tools/forms.js +5 -1
- package/dist/resources/extensions/browser-tools/tools/intent.js +5 -1
- package/dist/resources/extensions/claude-code-cli/readiness.js +72 -16
- package/dist/resources/extensions/claude-code-cli/stream-adapter.js +481 -17
- package/dist/resources/extensions/github-sync/templates.js +103 -0
- package/dist/resources/extensions/google-search/index.js +3 -2
- package/dist/resources/extensions/gsd/auto/loop.js +124 -2
- package/dist/resources/extensions/gsd/auto/phases.js +57 -39
- package/dist/resources/extensions/gsd/auto/session.js +6 -2
- package/dist/resources/extensions/gsd/auto-dispatch.js +142 -29
- package/dist/resources/extensions/gsd/auto-model-selection.js +124 -4
- package/dist/resources/extensions/gsd/auto-post-unit.js +150 -64
- package/dist/resources/extensions/gsd/auto-prompts.js +372 -104
- package/dist/resources/extensions/gsd/auto-recovery.js +197 -48
- package/dist/resources/extensions/gsd/auto-start.js +107 -29
- package/dist/resources/extensions/gsd/auto-tool-tracking.js +47 -7
- package/dist/resources/extensions/gsd/auto-worktree.js +122 -26
- package/dist/resources/extensions/gsd/auto.js +76 -21
- package/dist/resources/extensions/gsd/bootstrap/agent-end-recovery.js +19 -1
- package/dist/resources/extensions/gsd/bootstrap/db-tools.js +209 -0
- package/dist/resources/extensions/gsd/bootstrap/provider-error-resume.js +3 -6
- package/dist/resources/extensions/gsd/bootstrap/register-hooks.js +7 -3
- package/dist/resources/extensions/gsd/bootstrap/write-gate.js +127 -9
- package/dist/resources/extensions/gsd/component-loader.js +447 -0
- package/dist/resources/extensions/gsd/component-types.js +69 -0
- package/dist/resources/extensions/gsd/context-store.js +23 -7
- package/dist/resources/extensions/gsd/detection.js +49 -1
- package/dist/resources/extensions/gsd/dispatch-guard.js +2 -17
- package/dist/resources/extensions/gsd/docs/preferences-reference.md +1 -1
- package/dist/resources/extensions/gsd/forensics.js +106 -0
- package/dist/resources/extensions/gsd/gate-registry.js +2 -2
- package/dist/resources/extensions/gsd/git-constants.js +28 -1
- package/dist/resources/extensions/gsd/git-self-heal.js +27 -0
- package/dist/resources/extensions/gsd/git-service.js +126 -2
- package/dist/resources/extensions/gsd/gsd-db.js +6 -3
- package/dist/resources/extensions/gsd/guided-flow.js +39 -13
- package/dist/resources/extensions/gsd/memory-extractor.js +7 -1
- package/dist/resources/extensions/gsd/milestone-scope-classifier.js +299 -0
- package/dist/resources/extensions/gsd/milestone-summary-classifier.js +37 -0
- package/dist/resources/extensions/gsd/model-cost-table.js +3 -0
- package/dist/resources/extensions/gsd/model-router.js +6 -0
- package/dist/resources/extensions/gsd/native-git-bridge.js +34 -4
- package/dist/resources/extensions/gsd/preferences-validation.js +23 -0
- package/dist/resources/extensions/gsd/prompt-cache-optimizer.js +4 -0
- package/dist/resources/extensions/gsd/prompts/complete-milestone.md +6 -2
- package/dist/resources/extensions/gsd/prompts/discuss-headless.md +23 -4
- package/dist/resources/extensions/gsd/prompts/doctor-heal.md +5 -4
- package/dist/resources/extensions/gsd/prompts/plan-slice.md +15 -2
- package/dist/resources/extensions/gsd/safety/git-checkpoint.js +11 -0
- package/dist/resources/extensions/gsd/service-tier.js +5 -2
- package/dist/resources/extensions/gsd/session-lock.js +19 -10
- package/dist/resources/extensions/gsd/skill-manifest.js +168 -0
- package/dist/resources/extensions/gsd/slice-cadence.js +238 -0
- package/dist/resources/extensions/gsd/slice-parallel-orchestrator.js +278 -8
- package/dist/resources/extensions/gsd/state-transition-matrix.js +118 -0
- package/dist/resources/extensions/gsd/state.js +69 -58
- package/dist/resources/extensions/gsd/sync-lock.js +98 -42
- package/dist/resources/extensions/gsd/tools/validate-milestone.js +7 -2
- package/dist/resources/extensions/gsd/unit-context-composer.js +147 -0
- package/dist/resources/extensions/gsd/unit-context-manifest.js +370 -0
- package/dist/resources/extensions/gsd/uok/dispatch-envelope.js +33 -0
- package/dist/resources/extensions/gsd/uok/execution-graph.js +10 -0
- package/dist/resources/extensions/gsd/uok/gate-runner.js +53 -5
- package/dist/resources/extensions/gsd/uok/gitops.js +2 -1
- package/dist/resources/extensions/gsd/uok/loop-adapter.js +37 -10
- package/dist/resources/extensions/gsd/uok/parity-report.js +58 -0
- package/dist/resources/extensions/gsd/uok/plan-v2.js +10 -4
- package/dist/resources/extensions/gsd/uok/writer.js +82 -0
- package/dist/resources/extensions/gsd/workflow-mcp.js +6 -0
- package/dist/resources/extensions/gsd/worktree-manager.js +85 -8
- package/dist/resources/extensions/gsd/worktree-resolver.js +86 -7
- package/dist/resources/extensions/gsd/worktree-telemetry.js +198 -0
- package/dist/resources/extensions/mcp-client/index.js +3 -1
- package/dist/resources/extensions/ollama/index.js +5 -1
- package/dist/resources/extensions/remote-questions/manager.js +11 -5
- package/dist/tsconfig.extensions.tsbuildinfo +1 -1
- package/dist/web/standalone/.next/BUILD_ID +1 -1
- package/dist/web/standalone/.next/app-path-routes-manifest.json +11 -11
- package/dist/web/standalone/.next/build-manifest.json +2 -2
- package/dist/web/standalone/.next/prerender-manifest.json +3 -3
- package/dist/web/standalone/.next/server/app/_global-error.html +1 -1
- package/dist/web/standalone/.next/server/app/_global-error.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_global-error.segments/_global-error/__PAGE__.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_global-error.segments/_global-error.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_not-found.html +1 -1
- package/dist/web/standalone/.next/server/app/_not-found.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_not-found.segments/_full.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_not-found.segments/_head.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_not-found.segments/_index.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_not-found.segments/_not-found.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/_not-found.segments/_tree.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/api/git/route.js +1 -1
- package/dist/web/standalone/.next/server/app/index.html +1 -1
- package/dist/web/standalone/.next/server/app/index.rsc +1 -1
- package/dist/web/standalone/.next/server/app/index.segments/__PAGE__.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/index.segments/_full.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/index.segments/_head.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/index.segments/_index.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app/index.segments/_tree.segment.rsc +1 -1
- package/dist/web/standalone/.next/server/app-paths-manifest.json +11 -11
- package/dist/web/standalone/.next/server/chunks/1926.js +1 -1
- package/dist/web/standalone/.next/server/chunks/6897.js +1 -1
- package/dist/web/standalone/.next/server/middleware-build-manifest.js +1 -1
- package/dist/web/standalone/.next/server/middleware-manifest.json +5 -5
- package/dist/web/standalone/.next/server/pages/404.html +1 -1
- package/dist/web/standalone/.next/server/pages/500.html +1 -1
- package/dist/web/standalone/.next/server/server-reference-manifest.json +1 -1
- package/package.json +2 -3
- package/packages/daemon/package.json +2 -2
- package/packages/daemon/src/logger.ts +4 -3
- package/packages/mcp-server/dist/server.d.ts +24 -0
- package/packages/mcp-server/dist/server.d.ts.map +1 -1
- package/packages/mcp-server/dist/server.js +88 -87
- package/packages/mcp-server/dist/server.js.map +1 -1
- package/packages/mcp-server/dist/workflow-tools.d.ts.map +1 -1
- package/packages/mcp-server/dist/workflow-tools.js +15 -6
- package/packages/mcp-server/dist/workflow-tools.js.map +1 -1
- package/packages/mcp-server/package.json +2 -2
- package/packages/mcp-server/src/mcp-server.test.ts +25 -3
- package/packages/mcp-server/src/readers/graph.test.ts +87 -15
- package/packages/mcp-server/src/secure-env-collect.test.ts +232 -237
- package/packages/mcp-server/src/server.ts +131 -105
- package/packages/mcp-server/src/workflow-tools.test.ts +85 -0
- package/packages/mcp-server/src/workflow-tools.ts +19 -6
- package/packages/mcp-server/tsconfig.tsbuildinfo +1 -1
- package/packages/native/package.json +2 -2
- package/packages/native/src/__tests__/_test-coverage-guard.test.mjs +98 -0
- package/packages/native/src/__tests__/module-compat.test.mjs +59 -27
- package/packages/native/src/__tests__/ps.test.mjs +14 -8
- package/packages/native/src/__tests__/stream-process.test.mjs +23 -2
- package/packages/native/src/__tests__/truncate.test.mjs +17 -2
- package/packages/pi-agent-core/package.json +1 -1
- package/packages/pi-agent-core/src/agent-loop.test.ts +5 -15
- package/packages/pi-agent-core/src/agent.test.ts +96 -102
- package/packages/pi-agent-core/tsconfig.tsbuildinfo +1 -1
- package/packages/pi-ai/dist/models/capability-patches.d.ts.map +1 -1
- package/packages/pi-ai/dist/models/capability-patches.js +9 -2
- package/packages/pi-ai/dist/models/capability-patches.js.map +1 -1
- package/packages/pi-ai/dist/models/generated/index.d.ts +34 -0
- package/packages/pi-ai/dist/models/generated/index.d.ts.map +1 -1
- package/packages/pi-ai/dist/models/generated/openai-codex.d.ts +17 -0
- package/packages/pi-ai/dist/models/generated/openai-codex.d.ts.map +1 -1
- package/packages/pi-ai/dist/models/generated/openai-codex.js +17 -0
- package/packages/pi-ai/dist/models/generated/openai-codex.js.map +1 -1
- package/packages/pi-ai/dist/models/generated/openai.d.ts +17 -0
- package/packages/pi-ai/dist/models/generated/openai.d.ts.map +1 -1
- package/packages/pi-ai/dist/models/generated/openai.js +17 -0
- package/packages/pi-ai/dist/models/generated/openai.js.map +1 -1
- package/packages/pi-ai/dist/models.generated.test.js +43 -70
- package/packages/pi-ai/dist/models.generated.test.js.map +1 -1
- package/packages/pi-ai/dist/models.test.js +36 -11
- package/packages/pi-ai/dist/models.test.js.map +1 -1
- package/packages/pi-ai/package.json +1 -1
- package/packages/pi-ai/scripts/generate-models.ts +44 -0
- package/packages/pi-ai/src/models/capability-patches.ts +10 -2
- package/packages/pi-ai/src/models/generated/openai-codex.ts +17 -0
- package/packages/pi-ai/src/models/generated/openai.ts +17 -0
- package/packages/pi-ai/src/models.generated.test.ts +46 -73
- package/packages/pi-ai/src/models.test.ts +48 -11
- package/packages/pi-ai/tsconfig.tsbuildinfo +1 -1
- package/packages/pi-coding-agent/dist/core/agent-session-abort-order.test.js +96 -32
- package/packages/pi-coding-agent/dist/core/agent-session-abort-order.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/agent-session-model-switch.test.js +75 -12
- package/packages/pi-coding-agent/dist/core/agent-session-model-switch.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/agent-session-tool-refresh.test.js +99 -31
- package/packages/pi-coding-agent/dist/core/agent-session-tool-refresh.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/extensions/loader.d.ts +5 -0
- package/packages/pi-coding-agent/dist/core/extensions/loader.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/core/extensions/loader.js +61 -0
- package/packages/pi-coding-agent/dist/core/extensions/loader.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/lsp/lsp-integration.test.js +30 -4
- package/packages/pi-coding-agent/dist/core/lsp/lsp-integration.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/model-registry-auth-mode.test.js +17 -0
- package/packages/pi-coding-agent/dist/core/model-registry-auth-mode.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/resource-loader-cache-reset.test.js +76 -18
- package/packages/pi-coding-agent/dist/core/resource-loader-cache-reset.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/retry-handler.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/core/retry-handler.js +2 -6
- package/packages/pi-coding-agent/dist/core/retry-handler.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/retry-handler.test.js +5 -1
- package/packages/pi-coding-agent/dist/core/retry-handler.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/retryable-error-regex.d.ts +18 -0
- package/packages/pi-coding-agent/dist/core/retryable-error-regex.d.ts.map +1 -0
- package/packages/pi-coding-agent/dist/core/retryable-error-regex.js +18 -0
- package/packages/pi-coding-agent/dist/core/retryable-error-regex.js.map +1 -0
- package/packages/pi-coding-agent/dist/core/system-prompt.d.ts +20 -0
- package/packages/pi-coding-agent/dist/core/system-prompt.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/core/system-prompt.js +16 -2
- package/packages/pi-coding-agent/dist/core/system-prompt.js.map +1 -1
- package/packages/pi-coding-agent/dist/index.d.ts +1 -0
- package/packages/pi-coding-agent/dist/index.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/index.js +1 -0
- package/packages/pi-coding-agent/dist/index.js.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/components/__tests__/tool-execution.test.js +36 -5
- package/packages/pi-coding-agent/dist/modes/interactive/components/__tests__/tool-execution.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/components/dynamic-border.test.js +20 -13
- package/packages/pi-coding-agent/dist/modes/interactive/components/dynamic-border.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/components/tool-execution.js +30 -12
- package/packages/pi-coding-agent/dist/modes/interactive/components/tool-execution.js.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.js +18 -3
- package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.js.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.test.js +125 -0
- package/packages/pi-coding-agent/dist/modes/interactive/controllers/input-controller.test.js.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/interactive-mode-state.d.ts +2 -0
- package/packages/pi-coding-agent/dist/modes/interactive/interactive-mode-state.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/interactive-mode-state.js.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/interactive-mode.d.ts +4 -0
- package/packages/pi-coding-agent/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/modes/interactive/interactive-mode.js +105 -13
- package/packages/pi-coding-agent/dist/modes/interactive/interactive-mode.js.map +1 -1
- package/packages/pi-coding-agent/dist/tests/system-prompt-skill-filter.test.d.ts +2 -0
- package/packages/pi-coding-agent/dist/tests/system-prompt-skill-filter.test.d.ts.map +1 -0
- package/packages/pi-coding-agent/dist/tests/system-prompt-skill-filter.test.js +130 -0
- package/packages/pi-coding-agent/dist/tests/system-prompt-skill-filter.test.js.map +1 -0
- package/packages/pi-coding-agent/package.json +1 -1
- package/packages/pi-coding-agent/src/core/agent-session-abort-order.test.ts +113 -37
- package/packages/pi-coding-agent/src/core/agent-session-model-switch.test.ts +89 -17
- package/packages/pi-coding-agent/src/core/agent-session-tool-refresh.test.ts +112 -43
- package/packages/pi-coding-agent/src/core/extensions/loader.ts +58 -0
- package/packages/pi-coding-agent/src/core/lsp/lsp-integration.test.ts +35 -4
- package/packages/pi-coding-agent/src/core/model-registry-auth-mode.test.ts +20 -0
- package/packages/pi-coding-agent/src/core/resource-loader-cache-reset.test.ts +93 -28
- package/packages/pi-coding-agent/src/core/retry-handler.test.ts +5 -1
- package/packages/pi-coding-agent/src/core/retry-handler.ts +2 -8
- package/packages/pi-coding-agent/src/core/retryable-error-regex.ts +18 -0
- package/packages/pi-coding-agent/src/core/system-prompt.ts +35 -1
- package/packages/pi-coding-agent/src/index.ts +1 -0
- package/packages/pi-coding-agent/src/modes/interactive/components/__tests__/tool-execution.test.ts +49 -3
- package/packages/pi-coding-agent/src/modes/interactive/components/dynamic-border.test.ts +26 -20
- package/packages/pi-coding-agent/src/modes/interactive/components/tool-execution.ts +48 -9
- package/packages/pi-coding-agent/src/modes/interactive/controllers/input-controller.test.ts +146 -1
- package/packages/pi-coding-agent/src/modes/interactive/controllers/input-controller.ts +20 -3
- package/packages/pi-coding-agent/src/modes/interactive/interactive-mode-state.ts +2 -0
- package/packages/pi-coding-agent/src/modes/interactive/interactive-mode.ts +119 -13
- package/packages/pi-coding-agent/src/tests/system-prompt-skill-filter.test.ts +157 -0
- package/packages/pi-coding-agent/tsconfig.tsbuildinfo +1 -1
- package/packages/pi-tui/dist/__tests__/autocomplete.test.js +18 -8
- package/packages/pi-tui/dist/__tests__/autocomplete.test.js.map +1 -1
- package/packages/pi-tui/dist/__tests__/overlay-layout.test.js +128 -17
- package/packages/pi-tui/dist/__tests__/overlay-layout.test.js.map +1 -1
- package/packages/pi-tui/dist/__tests__/stdin-buffer.test.js +37 -11
- package/packages/pi-tui/dist/__tests__/stdin-buffer.test.js.map +1 -1
- package/packages/pi-tui/dist/__tests__/tui.test.js +18 -30
- package/packages/pi-tui/dist/__tests__/tui.test.js.map +1 -1
- package/packages/pi-tui/dist/components/__tests__/input.test.js +10 -3
- package/packages/pi-tui/dist/components/__tests__/input.test.js.map +1 -1
- package/packages/pi-tui/dist/components/__tests__/loader.test.js +53 -9
- package/packages/pi-tui/dist/components/__tests__/loader.test.js.map +1 -1
- package/packages/pi-tui/dist/components/__tests__/markdown-maxlines.test.js +6 -2
- package/packages/pi-tui/dist/components/__tests__/markdown-maxlines.test.js.map +1 -1
- package/packages/pi-tui/dist/components/editor.d.ts +14 -0
- package/packages/pi-tui/dist/components/editor.d.ts.map +1 -1
- package/packages/pi-tui/dist/components/editor.js +19 -0
- package/packages/pi-tui/dist/components/editor.js.map +1 -1
- package/packages/pi-tui/dist/components/image.test.js +6 -5
- package/packages/pi-tui/dist/components/image.test.js.map +1 -1
- package/packages/pi-tui/dist/editor-component.d.ts +2 -0
- package/packages/pi-tui/dist/editor-component.d.ts.map +1 -1
- package/packages/pi-tui/dist/editor-component.js.map +1 -1
- package/packages/pi-tui/package.json +1 -1
- package/packages/pi-tui/src/__tests__/autocomplete.test.ts +24 -8
- package/packages/pi-tui/src/__tests__/overlay-layout.test.ts +140 -17
- package/packages/pi-tui/src/__tests__/stdin-buffer.test.ts +42 -11
- package/packages/pi-tui/src/__tests__/tui.test.ts +18 -37
- package/packages/pi-tui/src/components/__tests__/input.test.ts +19 -3
- package/packages/pi-tui/src/components/__tests__/loader.test.ts +112 -35
- package/packages/pi-tui/src/components/__tests__/markdown-maxlines.test.ts +9 -2
- package/packages/pi-tui/src/components/editor.ts +22 -0
- package/packages/pi-tui/src/components/image.test.ts +10 -5
- package/packages/pi-tui/src/editor-component.ts +3 -0
- package/packages/pi-tui/tsconfig.tsbuildinfo +1 -1
- package/packages/rpc-client/dist/rpc-client.test.js +101 -51
- package/packages/rpc-client/dist/rpc-client.test.js.map +1 -1
- package/packages/rpc-client/package.json +1 -1
- package/packages/rpc-client/src/rpc-client.test.ts +109 -52
- package/packages/rpc-client/tsconfig.tsbuildinfo +1 -1
- package/pkg/package.json +1 -1
- package/scripts/install.js +15 -1
- package/src/resources/extensions/browser-tools/capture.ts +12 -0
- package/src/resources/extensions/browser-tools/tests/browser-tools-integration.test.mjs +8 -59
- package/src/resources/extensions/browser-tools/tests/browser-tools-unit.test.cjs +36 -24
- package/src/resources/extensions/browser-tools/tests/capture-sharp-optional.test.cjs +69 -71
- package/src/resources/extensions/browser-tools/tools/forms.ts +5 -1
- package/src/resources/extensions/browser-tools/tools/intent.ts +5 -1
- package/src/resources/extensions/claude-code-cli/readiness.ts +75 -16
- package/src/resources/extensions/claude-code-cli/stream-adapter.ts +518 -19
- package/src/resources/extensions/claude-code-cli/tests/stream-adapter.test.ts +919 -75
- package/src/resources/extensions/github-sync/templates.ts +151 -0
- package/src/resources/extensions/github-sync/tests/cli.test.ts +76 -7
- package/src/resources/extensions/github-sync/tests/templates.test.ts +92 -1
- package/src/resources/extensions/google-search/index.ts +3 -2
- package/src/resources/extensions/gsd/auto/loop.ts +142 -2
- package/src/resources/extensions/gsd/auto/phases.ts +62 -38
- package/src/resources/extensions/gsd/auto/session.ts +7 -2
- package/src/resources/extensions/gsd/auto-dispatch.ts +156 -29
- package/src/resources/extensions/gsd/auto-model-selection.ts +131 -4
- package/src/resources/extensions/gsd/auto-post-unit.ts +163 -73
- package/src/resources/extensions/gsd/auto-prompts.ts +385 -93
- package/src/resources/extensions/gsd/auto-recovery.ts +230 -51
- package/src/resources/extensions/gsd/auto-start.ts +127 -9
- package/src/resources/extensions/gsd/auto-tool-tracking.ts +51 -7
- package/src/resources/extensions/gsd/auto-worktree.ts +130 -26
- package/src/resources/extensions/gsd/auto.ts +90 -23
- package/src/resources/extensions/gsd/bootstrap/agent-end-recovery.ts +20 -1
- package/src/resources/extensions/gsd/bootstrap/db-tools.ts +221 -0
- package/src/resources/extensions/gsd/bootstrap/provider-error-resume.ts +3 -7
- package/src/resources/extensions/gsd/bootstrap/register-hooks.ts +7 -3
- package/src/resources/extensions/gsd/bootstrap/write-gate.ts +158 -9
- package/src/resources/extensions/gsd/component-loader.ts +598 -0
- package/src/resources/extensions/gsd/component-types.ts +362 -0
- package/src/resources/extensions/gsd/context-store.ts +25 -8
- package/src/resources/extensions/gsd/detection.ts +58 -1
- package/src/resources/extensions/gsd/dispatch-guard.ts +2 -20
- package/src/resources/extensions/gsd/docs/preferences-reference.md +1 -1
- package/src/resources/extensions/gsd/forensics.ts +118 -1
- package/src/resources/extensions/gsd/gate-registry.ts +2 -2
- package/src/resources/extensions/gsd/git-constants.ts +30 -1
- package/src/resources/extensions/gsd/git-self-heal.ts +31 -0
- package/src/resources/extensions/gsd/git-service.ts +149 -2
- package/src/resources/extensions/gsd/gsd-db.ts +6 -3
- package/src/resources/extensions/gsd/guided-flow.ts +57 -14
- package/src/resources/extensions/gsd/journal.ts +11 -1
- package/src/resources/extensions/gsd/memory-extractor.ts +11 -3
- package/src/resources/extensions/gsd/milestone-scope-classifier.ts +366 -0
- package/src/resources/extensions/gsd/milestone-summary-classifier.ts +42 -0
- package/src/resources/extensions/gsd/model-cost-table.ts +3 -0
- package/src/resources/extensions/gsd/model-router.ts +6 -0
- package/src/resources/extensions/gsd/native-git-bridge.ts +34 -4
- package/src/resources/extensions/gsd/preferences-validation.ts +21 -0
- package/src/resources/extensions/gsd/prompt-cache-optimizer.ts +4 -0
- package/src/resources/extensions/gsd/prompts/complete-milestone.md +6 -2
- package/src/resources/extensions/gsd/prompts/discuss-headless.md +23 -4
- package/src/resources/extensions/gsd/prompts/doctor-heal.md +5 -4
- package/src/resources/extensions/gsd/prompts/plan-slice.md +15 -2
- package/src/resources/extensions/gsd/safety/git-checkpoint.ts +15 -0
- package/src/resources/extensions/gsd/service-tier.ts +5 -2
- package/src/resources/extensions/gsd/session-lock.ts +20 -10
- package/src/resources/extensions/gsd/skill-manifest.ts +175 -0
- package/src/resources/extensions/gsd/slice-cadence.ts +299 -0
- package/src/resources/extensions/gsd/slice-parallel-orchestrator.ts +309 -8
- package/src/resources/extensions/gsd/state-transition-matrix.ts +152 -0
- package/src/resources/extensions/gsd/state.ts +76 -66
- package/src/resources/extensions/gsd/sync-lock.ts +97 -39
- package/src/resources/extensions/gsd/tests/artifact-retry-cap.test.ts +270 -0
- package/src/resources/extensions/gsd/tests/artifacts-table-preserved-on-cache-invalidate.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/auto-deterministic-error-classification-4973.test.ts +341 -0
- package/src/resources/extensions/gsd/tests/auto-discuss-milestone-deadlock-4973.test.ts +264 -0
- package/src/resources/extensions/gsd/tests/auto-loop.test.ts +133 -292
- package/src/resources/extensions/gsd/tests/auto-model-selection-tool-poisoning.test.ts +742 -0
- package/src/resources/extensions/gsd/tests/auto-model-selection.test.ts +78 -0
- package/src/resources/extensions/gsd/tests/auto-phases-lifecycle.test.ts +61 -0
- package/src/resources/extensions/gsd/tests/auto-recovery.test.ts +93 -0
- package/src/resources/extensions/gsd/tests/auto-remediate-slice-status.test.ts +4 -1
- package/src/resources/extensions/gsd/tests/auto-retry-mcp-churn-fixes.test.ts +8 -194
- package/src/resources/extensions/gsd/tests/auto-start-clean-runtime-db-gated.test.ts +3 -2
- package/src/resources/extensions/gsd/tests/auto-start-cold-db-bootstrap.test.ts +2 -2
- package/src/resources/extensions/gsd/tests/auto-start-needs-discussion.test.ts +15 -58
- package/src/resources/extensions/gsd/tests/auto-start-worktree-db-path.test.ts +2 -2
- package/src/resources/extensions/gsd/tests/auto-thinking-restore.test.ts +3 -2
- package/src/resources/extensions/gsd/tests/auto-warning-noise-regression.test.ts +3 -2
- package/src/resources/extensions/gsd/tests/bootstrap-derive-state-db-open.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/cache-staleness-regression.test.ts +17 -21
- package/src/resources/extensions/gsd/tests/canonical-milestone-root.test.ts +108 -0
- package/src/resources/extensions/gsd/tests/complete-milestone-excerpt.test.ts +263 -0
- package/src/resources/extensions/gsd/tests/complete-milestone.test.ts +25 -0
- package/src/resources/extensions/gsd/tests/complete-slice-composer.test.ts +192 -0
- package/src/resources/extensions/gsd/tests/complete-slice-verification-gate.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/complete-task.test.ts +16 -8
- package/src/resources/extensions/gsd/tests/component-loader.test.ts +589 -0
- package/src/resources/extensions/gsd/tests/component-types.test.ts +127 -0
- package/src/resources/extensions/gsd/tests/context-store.test.ts +79 -0
- package/src/resources/extensions/gsd/tests/copy-planning-artifacts-samepath.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/crash-recovery.test.ts +50 -1
- package/src/resources/extensions/gsd/tests/custom-engine-loop-integration.test.ts +159 -0
- package/src/resources/extensions/gsd/tests/db-access-guardrails.test.ts +1 -0
- package/src/resources/extensions/gsd/tests/derive-state-crossval.test.ts +3 -3
- package/src/resources/extensions/gsd/tests/derive-state-db-disk-reconcile.test.ts +40 -0
- package/src/resources/extensions/gsd/tests/derive-state-db.test.ts +91 -3
- package/src/resources/extensions/gsd/tests/derive-state.test.ts +4 -4
- package/src/resources/extensions/gsd/tests/discuss-slice-structured-questions.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/discuss-tool-scope-leak.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/dispatch-complete-milestone-guard.test.ts +5 -0
- package/src/resources/extensions/gsd/tests/dispatch-guard.test.ts +25 -0
- package/src/resources/extensions/gsd/tests/dispatch-missing-task-plans.test.ts +14 -0
- package/src/resources/extensions/gsd/tests/dispatcher-stuck-planning.test.ts +3 -2
- package/src/resources/extensions/gsd/tests/double-merge-guard.test.ts +4 -3
- package/src/resources/extensions/gsd/tests/empty-content-abort-loop.test.ts +4 -3
- package/src/resources/extensions/gsd/tests/execution-entry-missing-context-4671.test.ts +173 -0
- package/src/resources/extensions/gsd/tests/extension-bootstrap-isolation.test.ts +139 -129
- package/src/resources/extensions/gsd/tests/finalize-timeout-guard.test.ts +8 -104
- package/src/resources/extensions/gsd/tests/gate-state-canonicalization.test.ts +102 -0
- package/src/resources/extensions/gsd/tests/gate-storage.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/google-search-stub.test.ts +14 -4
- package/src/resources/extensions/gsd/tests/headless-milestone-parity.test.ts +117 -0
- package/src/resources/extensions/gsd/tests/hook-key-parsing.test.ts +4 -55
- package/src/resources/extensions/gsd/tests/integration/all-milestones-complete-merge.test.ts +7 -56
- package/src/resources/extensions/gsd/tests/integration/auto-recovery.test.ts +20 -0
- package/src/resources/extensions/gsd/tests/integration/doctor-proactive.test.ts +18 -2
- package/src/resources/extensions/gsd/tests/integration/queue-completed-milestone-perf.test.ts +10 -4
- package/src/resources/extensions/gsd/tests/integration/state-machine-edge-cases.test.ts +144 -7
- package/src/resources/extensions/gsd/tests/integration/state-machine-live-validation.test.ts +4 -0
- package/src/resources/extensions/gsd/tests/integration/state-machine-runtime-failures.test.ts +2 -16
- package/src/resources/extensions/gsd/tests/interactive-routing-bypass.test.ts +9 -3
- package/src/resources/extensions/gsd/tests/interrupted-session-ui.test.ts +6 -9
- package/src/resources/extensions/gsd/tests/journal-integration.test.ts +64 -0
- package/src/resources/extensions/gsd/tests/knowledge.test.ts +93 -1
- package/src/resources/extensions/gsd/tests/mcp-client-security.test.ts +8 -37
- package/src/resources/extensions/gsd/tests/memory-extractor.test.ts +5 -15
- package/src/resources/extensions/gsd/tests/merge-conflict-stops-loop.test.ts +227 -55
- package/src/resources/extensions/gsd/tests/milestone-scope-classifier.test.ts +187 -0
- package/src/resources/extensions/gsd/tests/milestone-summary-classifier.test.ts +30 -0
- package/src/resources/extensions/gsd/tests/model-cost-table.test.ts +9 -1
- package/src/resources/extensions/gsd/tests/model-router.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/native-git-bridge-exec-fallback.test.ts +6 -48
- package/src/resources/extensions/gsd/tests/notification-widget.test.ts +6 -3
- package/src/resources/extensions/gsd/tests/orphaned-worktree-audit.test.ts +59 -2
- package/src/resources/extensions/gsd/tests/parallel-research-dispatch.test.ts +273 -130
- package/src/resources/extensions/gsd/tests/pipeline-variant-dispatch.test.ts +301 -0
- package/src/resources/extensions/gsd/tests/pre-execution-pause-wiring.test.ts +32 -1
- package/src/resources/extensions/gsd/tests/preferences-worktree-sync.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/prompt-cache-optimizer.test.ts +12 -0
- package/src/resources/extensions/gsd/tests/prompt-step-ordering.test.ts +15 -4
- package/src/resources/extensions/gsd/tests/provider-errors.test.ts +23 -24
- package/src/resources/extensions/gsd/tests/queue-auto-guard.test.ts +32 -0
- package/src/resources/extensions/gsd/tests/queue-draft-detection.test.ts +3 -2
- package/src/resources/extensions/gsd/tests/queued-discuss-fast-path.test.ts +4 -5
- package/src/resources/extensions/gsd/tests/ready-phrase-no-files-4573.test.ts +75 -2
- package/src/resources/extensions/gsd/tests/reassess-default-optin.test.ts +132 -0
- package/src/resources/extensions/gsd/tests/recovery-attempts-reset.test.ts +8 -40
- package/src/resources/extensions/gsd/tests/regex-hardening.test.ts +136 -256
- package/src/resources/extensions/gsd/tests/research-milestone-composer.test.ts +114 -0
- package/src/resources/extensions/gsd/tests/restore-tools-after-discuss.test.ts +6 -3
- package/src/resources/extensions/gsd/tests/run-uat-composer.test.ts +148 -0
- package/src/resources/extensions/gsd/tests/service-tier.test.ts +4 -0
- package/src/resources/extensions/gsd/tests/session-lock-regression.test.ts +29 -0
- package/src/resources/extensions/gsd/tests/sidecar-queue.test.ts +3 -2
- package/src/resources/extensions/gsd/tests/silent-catch-diagnostics.test.ts +55 -95
- package/src/resources/extensions/gsd/tests/single-writer-v3-tool-surface.test.ts +158 -0
- package/src/resources/extensions/gsd/tests/skill-activation.test.ts +120 -1
- package/src/resources/extensions/gsd/tests/skill-manifest.test.ts +112 -0
- package/src/resources/extensions/gsd/tests/slice-cadence.test.ts +242 -0
- package/src/resources/extensions/gsd/tests/slice-context-injection.test.ts +3 -2
- package/src/resources/extensions/gsd/tests/slice-parallel-orchestrator.test.ts +164 -1
- package/src/resources/extensions/gsd/tests/smart-entry-draft.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/stale-dirlistcache-4648.test.ts +112 -0
- package/src/resources/extensions/gsd/tests/state-machine-full-walkthrough.test.ts +29 -5
- package/src/resources/extensions/gsd/tests/state-transition-matrix.test.ts +44 -0
- package/src/resources/extensions/gsd/tests/stop-auto-race-null-unit.test.ts +3 -3
- package/src/resources/extensions/gsd/tests/structured-data-formatter.test.ts +11 -92
- package/src/resources/extensions/gsd/tests/subagent-model-dispatch.test.ts +7 -6
- package/src/resources/extensions/gsd/tests/survivor-branch-complete.test.ts +102 -101
- package/src/resources/extensions/gsd/tests/sync-lock.test.ts +31 -0
- package/src/resources/extensions/gsd/tests/sync-worktree-skip-current.test.ts +4 -3
- package/src/resources/extensions/gsd/tests/test-helpers.test.ts +98 -0
- package/src/resources/extensions/gsd/tests/test-helpers.ts +153 -0
- package/src/resources/extensions/gsd/tests/token-profile.test.ts +8 -1
- package/src/resources/extensions/gsd/tests/tool-invocation-error-loop-break.test.ts +61 -1
- package/src/resources/extensions/gsd/tests/tool-naming.test.ts +8 -1
- package/src/resources/extensions/gsd/tests/unit-context-composer.test.ts +355 -0
- package/src/resources/extensions/gsd/tests/unit-context-manifest.test.ts +258 -0
- package/src/resources/extensions/gsd/tests/uok-contracts.test.ts +51 -0
- package/src/resources/extensions/gsd/tests/uok-execution-graph.test.ts +16 -0
- package/src/resources/extensions/gsd/tests/uok-gate-runner.test.ts +75 -0
- package/src/resources/extensions/gsd/tests/uok-gitops-wiring.test.ts +49 -26
- package/src/resources/extensions/gsd/tests/uok-loop-adapter-writer.test.ts +65 -0
- package/src/resources/extensions/gsd/tests/uok-parity-report.test.ts +42 -0
- package/src/resources/extensions/gsd/tests/uok-plan-v2-wiring.test.ts +19 -2
- package/src/resources/extensions/gsd/tests/uok-writer.test.ts +75 -0
- package/src/resources/extensions/gsd/tests/validate-milestone.test.ts +12 -0
- package/src/resources/extensions/gsd/tests/verify-artifact-tightened.test.ts +144 -80
- package/src/resources/extensions/gsd/tests/visualizer-critical-path.test.ts +20 -54
- package/src/resources/extensions/gsd/tests/visualizer-overlay.test.ts +342 -277
- package/src/resources/extensions/gsd/tests/worker-model-override.test.ts +37 -29
- package/src/resources/extensions/gsd/tests/worktree-db.test.ts +226 -266
- package/src/resources/extensions/gsd/tests/worktree-health-monorepo.test.ts +103 -67
- package/src/resources/extensions/gsd/tests/worktree-nested-git-safety.test.ts +92 -90
- package/src/resources/extensions/gsd/tests/worktree-submodule-safety.test.ts +238 -59
- package/src/resources/extensions/gsd/tests/worktree-sync-overwrite-loop.test.ts +113 -161
- package/src/resources/extensions/gsd/tests/worktree-telemetry.test.ts +210 -0
- package/src/resources/extensions/gsd/tests/write-gate-planning-unit.test.ts +262 -0
- package/src/resources/extensions/gsd/tests/write-gate-predicates.test.ts +186 -0
- package/src/resources/extensions/gsd/tests/write-gate.test.ts +7 -5
- package/src/resources/extensions/gsd/tests/zombie-gsd-state.test.ts +80 -96
- package/src/resources/extensions/gsd/tools/validate-milestone.ts +8 -2
- package/src/resources/extensions/gsd/types.ts +3 -3
- package/src/resources/extensions/gsd/unit-context-composer.ts +218 -0
- package/src/resources/extensions/gsd/unit-context-manifest.ts +574 -0
- package/src/resources/extensions/gsd/uok/contracts.ts +65 -0
- package/src/resources/extensions/gsd/uok/dispatch-envelope.ts +56 -0
- package/src/resources/extensions/gsd/uok/execution-graph.ts +22 -0
- package/src/resources/extensions/gsd/uok/gate-runner.ts +65 -5
- package/src/resources/extensions/gsd/uok/gitops.ts +6 -1
- package/src/resources/extensions/gsd/uok/loop-adapter.ts +45 -10
- package/src/resources/extensions/gsd/uok/parity-report.ts +84 -0
- package/src/resources/extensions/gsd/uok/plan-v2.ts +13 -5
- package/src/resources/extensions/gsd/uok/writer.ts +113 -0
- package/src/resources/extensions/gsd/workflow-mcp.ts +6 -0
- package/src/resources/extensions/gsd/worktree-manager.ts +108 -7
- package/src/resources/extensions/gsd/worktree-resolver.ts +96 -9
- package/src/resources/extensions/gsd/worktree-telemetry.ts +322 -0
- package/src/resources/extensions/mcp-client/index.ts +3 -1
- package/src/resources/extensions/mcp-client/tests/server-name-spaces.test.ts +70 -36
- package/src/resources/extensions/ollama/index.ts +5 -1
- package/src/resources/extensions/ollama/ollama-auth-mode.test.ts +123 -15
- package/src/resources/extensions/ollama/ollama-status-indicator.test.ts +206 -19
- package/src/resources/extensions/remote-questions/manager.ts +36 -4
- package/src/resources/extensions/remote-questions/tests/command-polling.test.ts +200 -190
- package/src/resources/extensions/shared/tests/interview-preview.test.ts +11 -3
- package/src/resources/extensions/voice/tests/linux-ready.test.ts +129 -113
- package/packages/pi-ai/dist/utils/oauth/oauth-providers.test.d.ts +0 -2
- package/packages/pi-ai/dist/utils/oauth/oauth-providers.test.d.ts.map +0 -1
- package/packages/pi-ai/dist/utils/oauth/oauth-providers.test.js +0 -289
- package/packages/pi-ai/dist/utils/oauth/oauth-providers.test.js.map +0 -1
- package/packages/pi-ai/src/utils/oauth/oauth-providers.test.ts +0 -363
- package/src/resources/extensions/gsd/tests/auto-start-model-capture.test.ts +0 -143
- package/src/resources/extensions/gsd/tests/complete-milestone-false-merge.test.ts +0 -157
- package/src/resources/extensions/gsd/tests/dashboard-model-label-ordering.test.ts +0 -107
- package/src/resources/extensions/gsd/tests/find-missing-summaries-closed.test.ts +0 -48
- package/src/resources/extensions/gsd/tests/forensics-context-persist.test.ts +0 -159
- package/src/resources/extensions/gsd/tests/forensics-db-completion.test.ts +0 -96
- package/src/resources/extensions/gsd/tests/forensics-dedup.test.ts +0 -79
- package/src/resources/extensions/gsd/tests/forensics-hook-key-parse.test.ts +0 -74
- package/src/resources/extensions/gsd/tests/forensics-journal.test.ts +0 -162
- package/src/resources/extensions/gsd/tests/gitignore-bg-shell.test.ts +0 -38
- package/src/resources/extensions/gsd/tests/gsd-no-project-error.test.ts +0 -73
- package/src/resources/extensions/gsd/tests/idle-watchdog-stall-override.test.ts +0 -125
- package/src/resources/extensions/gsd/tests/import-done-milestones.test.ts +0 -42
- /package/dist/web/standalone/.next/static/{5wbu35_C2_MQ3Jj1lEVDx → cAJH99yNS1UPbeSEiNRrV}/_buildManifest.js +0 -0
- /package/dist/web/standalone/.next/static/{5wbu35_C2_MQ3Jj1lEVDx → cAJH99yNS1UPbeSEiNRrV}/_ssgManifest.js +0 -0
|
@@ -653,15 +653,72 @@ export function containsTypeScriptSyntax(source: string): boolean {
|
|
|
653
653
|
* are compiled once and reused across all extensions.
|
|
654
654
|
*/
|
|
655
655
|
let _extensionLoaderJiti: ReturnType<typeof createJiti> | null = null;
|
|
656
|
+
// Tracks every extension-module path that jiti has compiled through the shared
|
|
657
|
+
// singleton so resetExtensionLoaderCache() can also evict Node's global
|
|
658
|
+
// require.cache entries for those modules. jiti stores compiled modules under
|
|
659
|
+
// `nativeRequire.cache[filename]` when `moduleCache: true`, so a new singleton
|
|
660
|
+
// still returns the stale cached module on re-import without this eviction.
|
|
661
|
+
const _loadedExtensionPaths = new Set<string>();
|
|
662
|
+
const _extensionRequire = createRequire(import.meta.url);
|
|
656
663
|
|
|
657
664
|
/**
|
|
658
665
|
* Reset the shared jiti singleton so the next call to getExtensionLoaderJiti()
|
|
659
666
|
* creates a fresh instance. This prevents memory leaks in long-running daemon
|
|
660
667
|
* processes (every loaded module stays cached forever) and ensures stale modules
|
|
661
668
|
* are not returned when extension source changes on disk.
|
|
669
|
+
*
|
|
670
|
+
* #3616: resetting the singleton alone is insufficient — jiti stores compiled
|
|
671
|
+
* modules in Node's global require.cache when `moduleCache: true`, which is
|
|
672
|
+
* shared across singletons. We also evict cached entries for every extension
|
|
673
|
+
* path we've previously loaded so the next import recompiles from disk.
|
|
662
674
|
*/
|
|
663
675
|
export function resetExtensionLoaderCache(): void {
|
|
664
676
|
_extensionLoaderJiti = null;
|
|
677
|
+
// Build a set of exact cache keys we expect (raw path, resolved path,
|
|
678
|
+
// realpath) AND a set of (basename, containing-directory) pairs so we
|
|
679
|
+
// can also catch entries that jiti/Node wrote under a canonicalized
|
|
680
|
+
// form (Windows drive-letter case, separator swap, UNC prefix, symlink
|
|
681
|
+
// resolution). require.cache is shared across all createRequire
|
|
682
|
+
// instances for CJS, so iterating any instance's cache covers jiti's
|
|
683
|
+
// internal `nativeRequire.cache` writes.
|
|
684
|
+
const exact = new Set<string>();
|
|
685
|
+
const signatures = new Set<string>();
|
|
686
|
+
const makeSignature = (p: string): string => {
|
|
687
|
+
const normalized = p.replace(/\\/g, "/").toLowerCase();
|
|
688
|
+
const slash = normalized.lastIndexOf("/");
|
|
689
|
+
const base = slash >= 0 ? normalized.slice(slash + 1) : normalized;
|
|
690
|
+
// Use the trailing two path segments as the signature — unique
|
|
691
|
+
// enough to avoid collisions in typical filesystems while tolerating
|
|
692
|
+
// drive-letter / separator variations that differ in the prefix.
|
|
693
|
+
const parent = slash >= 0 ? normalized.slice(0, slash) : "";
|
|
694
|
+
const parentSlash = parent.lastIndexOf("/");
|
|
695
|
+
const parentSeg = parentSlash >= 0 ? parent.slice(parentSlash + 1) : parent;
|
|
696
|
+
return `${parentSeg}/${base}`;
|
|
697
|
+
};
|
|
698
|
+
for (const raw of _loadedExtensionPaths) {
|
|
699
|
+
exact.add(raw);
|
|
700
|
+
try {
|
|
701
|
+
exact.add(_extensionRequire.resolve(raw));
|
|
702
|
+
} catch {
|
|
703
|
+
// unresolvable — fall through; signature scan may still hit it
|
|
704
|
+
}
|
|
705
|
+
try {
|
|
706
|
+
exact.add(fs.realpathSync(raw));
|
|
707
|
+
} catch {
|
|
708
|
+
// file may have been deleted already; ignore
|
|
709
|
+
}
|
|
710
|
+
signatures.add(makeSignature(raw));
|
|
711
|
+
}
|
|
712
|
+
for (const key of Object.keys(_extensionRequire.cache)) {
|
|
713
|
+
if (exact.has(key) || signatures.has(makeSignature(key))) {
|
|
714
|
+
try {
|
|
715
|
+
delete _extensionRequire.cache[key];
|
|
716
|
+
} catch {
|
|
717
|
+
// require.cache is best-effort; ignore failures (e.g. frozen cache).
|
|
718
|
+
}
|
|
719
|
+
}
|
|
720
|
+
}
|
|
721
|
+
_loadedExtensionPaths.clear();
|
|
665
722
|
}
|
|
666
723
|
|
|
667
724
|
function getExtensionLoaderJiti() {
|
|
@@ -696,6 +753,7 @@ async function loadExtensionModule(extensionPath: string) {
|
|
|
696
753
|
const jiti = getExtensionLoaderJiti();
|
|
697
754
|
|
|
698
755
|
const module = await jiti.import(extensionPath, { default: true });
|
|
756
|
+
_loadedExtensionPaths.add(extensionPath);
|
|
699
757
|
const factory = module as ExtensionFactory;
|
|
700
758
|
return typeof factory !== "function" ? undefined : factory;
|
|
701
759
|
}
|
|
@@ -315,8 +315,19 @@ test("LSP integration: typescript-language-server", async (t) => {
|
|
|
315
315
|
textDocument: { uri: mathUri, languageId: "typescript", version: 1, text: mathContent },
|
|
316
316
|
});
|
|
317
317
|
|
|
318
|
-
//
|
|
319
|
-
|
|
318
|
+
// Poll for a published diagnostics notification on main.ts, which
|
|
319
|
+
// is the observable signal that TypeScript has finished indexing
|
|
320
|
+
// the opened file. Previous magic-sleep (3000ms) was too short on
|
|
321
|
+
// slow CI machines and wasteful on fast ones (#4798).
|
|
322
|
+
const INDEX_DEADLINE_MS = 15_000;
|
|
323
|
+
const indexDeadline = Date.now() + INDEX_DEADLINE_MS;
|
|
324
|
+
while (Date.now() < indexDeadline) {
|
|
325
|
+
const diags = lsp
|
|
326
|
+
.getNotifications("textDocument/publishDiagnostics")
|
|
327
|
+
.filter((n) => (n.params as { uri: string }).uri === mainUri);
|
|
328
|
+
if (diags.length > 0) break;
|
|
329
|
+
await new Promise((r) => setTimeout(r, 50));
|
|
330
|
+
}
|
|
320
331
|
|
|
321
332
|
// ---- Hover ----
|
|
322
333
|
await t.test("hover on 'add' call", async () => {
|
|
@@ -381,8 +392,28 @@ test("LSP integration: typescript-language-server", async (t) => {
|
|
|
381
392
|
|
|
382
393
|
// ---- Diagnostics (published via notification) ----
|
|
383
394
|
await t.test("diagnostics for type error", async () => {
|
|
384
|
-
//
|
|
385
|
-
|
|
395
|
+
// Poll for the specific type-error diagnostic on main.ts
|
|
396
|
+
// instead of sleeping a fixed 2s. tsserver pushes diagnostics
|
|
397
|
+
// incrementally — we need to wait until at least one diag
|
|
398
|
+
// contains a type-error signal, not just any diag.
|
|
399
|
+
const DIAG_DEADLINE_MS = 10_000;
|
|
400
|
+
const diagDeadline = Date.now() + DIAG_DEADLINE_MS;
|
|
401
|
+
while (Date.now() < diagDeadline) {
|
|
402
|
+
const candidates = lsp
|
|
403
|
+
.getNotifications("textDocument/publishDiagnostics")
|
|
404
|
+
.filter((n) => (n.params as { uri: string }).uri === mainUri)
|
|
405
|
+
.flatMap(
|
|
406
|
+
(n) => (n.params as { diagnostics: Array<{ message: string }> }).diagnostics,
|
|
407
|
+
);
|
|
408
|
+
if (
|
|
409
|
+
candidates.some(
|
|
410
|
+
(d) => d.message.includes("not assignable") || d.message.includes("Type"),
|
|
411
|
+
)
|
|
412
|
+
) {
|
|
413
|
+
break;
|
|
414
|
+
}
|
|
415
|
+
await new Promise((r) => setTimeout(r, 50));
|
|
416
|
+
}
|
|
386
417
|
|
|
387
418
|
const diagNotifications = lsp.getNotifications("textDocument/publishDiagnostics");
|
|
388
419
|
const mainDiags = diagNotifications.filter(
|
|
@@ -39,6 +39,10 @@ function findModel(registry: ModelRegistry, provider: string, id: string): Model
|
|
|
39
39
|
return registry.getAvailable().find((m) => m.provider === provider && m.id === id);
|
|
40
40
|
}
|
|
41
41
|
|
|
42
|
+
function availableModelIds(registry: ModelRegistry): Set<string> {
|
|
43
|
+
return new Set(registry.getAvailable().map((model) => `${model.provider}/${model.id}`));
|
|
44
|
+
}
|
|
45
|
+
|
|
42
46
|
function makeModel(provider: string, id: string, api: string): Model<Api> {
|
|
43
47
|
return {
|
|
44
48
|
id,
|
|
@@ -93,6 +97,22 @@ function createStreamSpy(): {
|
|
|
93
97
|
// ─── Registration ─────────────────────────────────────────────────────────────
|
|
94
98
|
|
|
95
99
|
describe("ModelRegistry authMode — registration", () => {
|
|
100
|
+
it("includes GPT-5.5 in the authenticated all-models menu backing list", () => {
|
|
101
|
+
const registry = createInMemoryRegistry({
|
|
102
|
+
openai: { type: "api_key", key: "sk-test" },
|
|
103
|
+
"openai-codex": {
|
|
104
|
+
type: "oauth",
|
|
105
|
+
access: "codex-access",
|
|
106
|
+
refresh: "codex-refresh",
|
|
107
|
+
expires: Date.now() + 60_000,
|
|
108
|
+
},
|
|
109
|
+
});
|
|
110
|
+
|
|
111
|
+
const ids = availableModelIds(registry);
|
|
112
|
+
assert.ok(ids.has("openai/gpt-5.5"), "all-models menu backing list should include openai/gpt-5.5");
|
|
113
|
+
assert.ok(ids.has("openai-codex/gpt-5.5"), "all-models menu backing list should include openai-codex/gpt-5.5");
|
|
114
|
+
});
|
|
115
|
+
|
|
96
116
|
it("registers externalCli provider with streamSimple and without apiKey/oauth", () => {
|
|
97
117
|
const registry = createRegistry();
|
|
98
118
|
const spy = createStreamSpy();
|
|
@@ -1,42 +1,107 @@
|
|
|
1
|
-
//
|
|
2
|
-
//
|
|
1
|
+
// Regression test for #3616: DefaultResourceLoader.reload() must invalidate
|
|
2
|
+
// the jiti module cache before loading extensions, so that edits to
|
|
3
|
+
// extension source on disk are picked up on the next reload (not served
|
|
4
|
+
// stale from memory).
|
|
5
|
+
//
|
|
6
|
+
// Verified end-to-end behaviourally: we write a .ts extension that
|
|
7
|
+
// registers a tool whose NAME is a module-scope constant, load it,
|
|
8
|
+
// rewrite the source with a new constant value, reload(), and assert
|
|
9
|
+
// the observable tool name reflects the NEW source. Without jiti cache
|
|
10
|
+
// invalidation, the second reload would re-register the stale name.
|
|
3
11
|
|
|
4
|
-
import test, { describe } from "node:test";
|
|
5
12
|
import assert from "node:assert/strict";
|
|
6
|
-
import {
|
|
13
|
+
import { mkdtempSync, rmSync, utimesSync, writeFileSync } from "node:fs";
|
|
14
|
+
import { tmpdir } from "node:os";
|
|
7
15
|
import { join } from "node:path";
|
|
16
|
+
import { afterEach, beforeEach, describe, it } from "node:test";
|
|
8
17
|
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
);
|
|
18
|
+
import { DefaultResourceLoader } from "./resource-loader.js";
|
|
19
|
+
import { SettingsManager } from "./settings-manager.js";
|
|
20
|
+
import { resetExtensionLoaderCache } from "./extensions/loader.js";
|
|
13
21
|
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
22
|
+
let testDir: string;
|
|
23
|
+
|
|
24
|
+
function writeExtensionWithToolName(extPath: string, toolName: string): void {
|
|
25
|
+
// Extension factory signature expected by the loader. Uses `any` so the
|
|
26
|
+
// test stays decoupled from the ExtensionAPI type shape.
|
|
27
|
+
writeFileSync(
|
|
28
|
+
extPath,
|
|
29
|
+
[
|
|
30
|
+
`const TOOL_NAME = "${toolName}";`,
|
|
31
|
+
`export default function activate(api: any) {`,
|
|
32
|
+
` api.registerTool({`,
|
|
33
|
+
` name: TOOL_NAME,`,
|
|
34
|
+
` label: TOOL_NAME,`,
|
|
35
|
+
` description: "test tool — source-generated name",`,
|
|
36
|
+
` parameters: { type: "object", properties: {}, additionalProperties: false },`,
|
|
37
|
+
` execute: async () => ({ content: [], details: undefined }),`,
|
|
38
|
+
` });`,
|
|
39
|
+
`}`,
|
|
40
|
+
"",
|
|
41
|
+
].join("\n"),
|
|
42
|
+
);
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
describe("#3616 — DefaultResourceLoader.reload() invalidates extension module cache", () => {
|
|
46
|
+
beforeEach(() => {
|
|
47
|
+
testDir = mkdtempSync(join(tmpdir(), "resource-loader-cache-reset-"));
|
|
48
|
+
// Ensure a clean jiti singleton — prior tests in this process may
|
|
49
|
+
// have populated it with unrelated entries.
|
|
50
|
+
resetExtensionLoaderCache();
|
|
51
|
+
});
|
|
52
|
+
|
|
53
|
+
afterEach(() => {
|
|
54
|
+
resetExtensionLoaderCache();
|
|
55
|
+
rmSync(testDir, { recursive: true, force: true });
|
|
24
56
|
});
|
|
25
57
|
|
|
26
|
-
|
|
27
|
-
const
|
|
28
|
-
|
|
29
|
-
const reloadBody = source.slice(reloadStart, reloadStart + 4000);
|
|
58
|
+
it("reload() picks up source edits after the extension has been loaded once", async () => {
|
|
59
|
+
const agentDir = join(testDir, "agent-home");
|
|
60
|
+
const extPath = join(testDir, "reload-probe.ts");
|
|
30
61
|
|
|
31
|
-
|
|
32
|
-
|
|
62
|
+
// v1 — initial content
|
|
63
|
+
writeExtensionWithToolName(extPath, "probe_v1");
|
|
33
64
|
|
|
34
|
-
const
|
|
35
|
-
|
|
65
|
+
const loader = new DefaultResourceLoader({
|
|
66
|
+
cwd: testDir,
|
|
67
|
+
agentDir,
|
|
68
|
+
settingsManager: SettingsManager.inMemory(),
|
|
69
|
+
noExtensions: true,
|
|
70
|
+
noPromptTemplates: true,
|
|
71
|
+
noThemes: true,
|
|
72
|
+
additionalExtensionPaths: [extPath],
|
|
73
|
+
});
|
|
36
74
|
|
|
75
|
+
await loader.reload();
|
|
76
|
+
|
|
77
|
+
const toolsV1 = [...loader.getExtensions().extensions.flatMap((e) => [...e.tools.keys()])];
|
|
78
|
+
assert.ok(
|
|
79
|
+
toolsV1.includes("probe_v1"),
|
|
80
|
+
`first reload should register probe_v1; got=${JSON.stringify(toolsV1)}`,
|
|
81
|
+
);
|
|
82
|
+
|
|
83
|
+
// v2 — overwrite the source on disk with a different tool name.
|
|
84
|
+
writeExtensionWithToolName(extPath, "probe_v2");
|
|
85
|
+
// Bump mtime explicitly so file-stat–based cache strategies (jiti's
|
|
86
|
+
// moduleCache consults Node's require.cache, which some runtimes
|
|
87
|
+
// tiebreak on mtime) always see "newer than last seen". On Windows
|
|
88
|
+
// NTFS + node the default fs mtime resolution can silently collapse
|
|
89
|
+
// two writes in the same tick to an identical mtime — that fooled
|
|
90
|
+
// the Windows CI run on #3616.
|
|
91
|
+
const futureTime = new Date(Date.now() + 5000);
|
|
92
|
+
utimesSync(extPath, futureTime, futureTime);
|
|
93
|
+
|
|
94
|
+
await loader.reload();
|
|
95
|
+
|
|
96
|
+
const toolsV2 = [...loader.getExtensions().extensions.flatMap((e) => [...e.tools.keys()])];
|
|
97
|
+
assert.ok(
|
|
98
|
+
toolsV2.includes("probe_v2"),
|
|
99
|
+
`second reload must observe the edited source (probe_v2) — if reload() ` +
|
|
100
|
+
`fails to reset the jiti cache, the stale module returns probe_v1. got=${JSON.stringify(toolsV2)}`,
|
|
101
|
+
);
|
|
37
102
|
assert.ok(
|
|
38
|
-
|
|
39
|
-
|
|
103
|
+
!toolsV2.includes("probe_v1"),
|
|
104
|
+
`second reload must NOT still expose the stale probe_v1 name; got=${JSON.stringify(toolsV2)}`,
|
|
40
105
|
);
|
|
41
106
|
});
|
|
42
107
|
});
|
|
@@ -281,7 +281,11 @@ describe("RetryHandler — long-context entitlement 429 (#2803)", () => {
|
|
|
281
281
|
assert.equal(result, true, "retry should be initiated");
|
|
282
282
|
|
|
283
283
|
handler.abortRetry();
|
|
284
|
-
|
|
284
|
+
// Yield the microtask queue so any synchronous continuation
|
|
285
|
+
// scheduled by abortRetry() settles before we assert. This is
|
|
286
|
+
// deterministic — no magic-sleep dependency (#4798 / #4784).
|
|
287
|
+
await Promise.resolve();
|
|
288
|
+
await Promise.resolve();
|
|
285
289
|
|
|
286
290
|
assert.equal(continueFn.mock.calls.length, 0, "cancelled retry must not continue after explicit abort");
|
|
287
291
|
const endEvents = emittedEvents.filter((e) => e.type === "auto_retry_end");
|
|
@@ -18,6 +18,7 @@ import type { ModelRegistry } from "./model-registry.js";
|
|
|
18
18
|
import type { SettingsManager } from "./settings-manager.js";
|
|
19
19
|
import { sleep } from "../utils/sleep.js";
|
|
20
20
|
import type { AgentSessionEvent } from "./agent-session.js";
|
|
21
|
+
import { RETRYABLE_ERROR_RE } from "./retryable-error-regex.js";
|
|
21
22
|
|
|
22
23
|
/** Dependencies injected from AgentSession into RetryHandler */
|
|
23
24
|
export interface RetryHandlerDeps {
|
|
@@ -111,14 +112,7 @@ export class RetryHandler {
|
|
|
111
112
|
const contextWindow = this._deps.getModel()?.contextWindow ?? 0;
|
|
112
113
|
if (isContextOverflow(message, contextWindow)) return false;
|
|
113
114
|
|
|
114
|
-
|
|
115
|
-
// "temporarily backed off" is intentionally excluded: it is an internally-
|
|
116
|
-
// generated error from getApiKey() when credentials are in a backoff window.
|
|
117
|
-
// Re-entering the retry handler for that message creates a cascade of empty
|
|
118
|
-
// error entries in the session file, breaking resume (#3429).
|
|
119
|
-
return /overloaded|rate.?limit|too many requests|402|429|500|502|503|504|service.?unavailable|server.?error|internal.?error|connection.?error|connection.?refused|other side closed|fetch failed|upstream.?connect|reset before headers|terminated|retry delay|network.?(?:is\s+)?unavailable|credentials.*expired|requires more credits|can only afford|insufficient credits|not enough credits|extra usage is required|(?:out of|no) extra usage|third.party.*draw from extra|third.party.*not.*available/i.test(
|
|
120
|
-
err,
|
|
121
|
-
);
|
|
115
|
+
return RETRYABLE_ERROR_RE.test(message.errorMessage);
|
|
122
116
|
}
|
|
123
117
|
|
|
124
118
|
/**
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Regex matching retryable provider errors — overloaded, rate limits, transient
|
|
3
|
+
* server/connection failures, credential-backoff, quota/credit issues.
|
|
4
|
+
*
|
|
5
|
+
* Kept in its own zero-import module so tests can consume the live pattern
|
|
6
|
+
* without pulling in the full RetryHandler dependency graph (Agent /
|
|
7
|
+
* FallbackResolver / ModelRegistry / @gsd/pi-ai …). The test in
|
|
8
|
+
* `src/resources/extensions/gsd/tests/provider-errors.test.ts` previously
|
|
9
|
+
* redefined this regex inline, which meant runtime and test could drift
|
|
10
|
+
* silently on every edit (see #4837).
|
|
11
|
+
*
|
|
12
|
+
* "temporarily backed off" is intentionally excluded: it is an internally-
|
|
13
|
+
* generated error from getApiKey() when credentials are in a backoff window.
|
|
14
|
+
* Re-entering the retry handler for that message creates a cascade of empty
|
|
15
|
+
* error entries in the session file, breaking resume (#3429).
|
|
16
|
+
*/
|
|
17
|
+
export const RETRYABLE_ERROR_RE =
|
|
18
|
+
/overloaded|rate.?limit|too many requests|402|429|500|502|503|504|service.?unavailable|server.?error|internal.?error|connection.?error|connection.?refused|other side closed|fetch failed|upstream.?connect|reset before headers|terminated|retry delay|network.?(?:is\s+)?unavailable|credentials.*expired|requires more credits|can only afford|insufficient credits|not enough credits|extra usage is required|(?:out of|no) extra usage|third.party.*draw from extra|third.party.*not.*available/i;
|
|
@@ -35,6 +35,26 @@ export interface BuildSystemPromptOptions {
|
|
|
35
35
|
contextFiles?: Array<{ path: string; content: string }>;
|
|
36
36
|
/** Pre-loaded skills. */
|
|
37
37
|
skills?: Skill[];
|
|
38
|
+
/**
|
|
39
|
+
* Optional predicate applied to the `skills` list before rendering the
|
|
40
|
+
* <available_skills> catalog. Returning `false` omits a skill from the
|
|
41
|
+
* prompt (the skill remains loaded and invocable by name — only the
|
|
42
|
+
* catalog listing is suppressed).
|
|
43
|
+
*
|
|
44
|
+
* Intended for consumers that can narrow the relevant skill surface
|
|
45
|
+
* (e.g. per-unit-type manifests) to reduce cached system-prompt bloat.
|
|
46
|
+
* When omitted, all non-`disableModelInvocation` skills render — i.e.
|
|
47
|
+
* behavior is unchanged from before this option existed.
|
|
48
|
+
*
|
|
49
|
+
* Contract: the predicate must be **pure and synchronous**. It may be
|
|
50
|
+
* invoked on every system-prompt rebuild (tool-set changes and
|
|
51
|
+
* runtime resource-loader extensions both trigger one), so any state
|
|
52
|
+
* the closure captures should be stable across the rebuild window.
|
|
53
|
+
* If the predicate throws, `buildSystemPrompt` logs a warning and
|
|
54
|
+
* falls back to the unfiltered skill list — callers never see the
|
|
55
|
+
* exception and the session stays consistent.
|
|
56
|
+
*/
|
|
57
|
+
skillFilter?: (skill: Skill) => boolean;
|
|
38
58
|
}
|
|
39
59
|
|
|
40
60
|
/** Build the system prompt with tools, guidelines, and context */
|
|
@@ -48,6 +68,7 @@ export function buildSystemPrompt(options: BuildSystemPromptOptions = {}): strin
|
|
|
48
68
|
cwd,
|
|
49
69
|
contextFiles: providedContextFiles,
|
|
50
70
|
skills: providedSkills,
|
|
71
|
+
skillFilter,
|
|
51
72
|
} = options;
|
|
52
73
|
const resolvedCwd = toPosixPath(cwd ?? process.cwd());
|
|
53
74
|
|
|
@@ -66,7 +87,20 @@ export function buildSystemPrompt(options: BuildSystemPromptOptions = {}): strin
|
|
|
66
87
|
const appendSection = appendSystemPrompt ? `\n\n${appendSystemPrompt}` : "";
|
|
67
88
|
|
|
68
89
|
const contextFiles = providedContextFiles ?? [];
|
|
69
|
-
const
|
|
90
|
+
const skillsBase = providedSkills ?? [];
|
|
91
|
+
let skills = skillsBase;
|
|
92
|
+
if (skillFilter) {
|
|
93
|
+
try {
|
|
94
|
+
skills = skillsBase.filter(skillFilter);
|
|
95
|
+
} catch (error) {
|
|
96
|
+
// A consumer's predicate threw. Fall back to the unfiltered list so
|
|
97
|
+
// the session stays consistent — callers (e.g. AgentSession.setTools)
|
|
98
|
+
// must not be left with updated tools but a stale system prompt.
|
|
99
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
100
|
+
console.warn(`buildSystemPrompt: skillFilter threw; falling back to unfiltered skills. Error: ${message}`);
|
|
101
|
+
skills = skillsBase;
|
|
102
|
+
}
|
|
103
|
+
}
|
|
70
104
|
|
|
71
105
|
if (customPrompt) {
|
|
72
106
|
let prompt = customPrompt;
|
|
@@ -188,6 +188,7 @@ export type { PackageCommand, PackageCommandOptions, PackageCommandRunnerOptions
|
|
|
188
188
|
export { getPackageCommandUsage, parsePackageCommand, runPackageCommand } from "./core/package-commands.js";
|
|
189
189
|
export type { ResourceCollision, ResourceDiagnostic, ResourceLoader } from "./core/resource-loader.js";
|
|
190
190
|
export { DefaultResourceLoader } from "./core/resource-loader.js";
|
|
191
|
+
export { RETRYABLE_ERROR_RE } from "./core/retryable-error-regex.js";
|
|
191
192
|
// SDK for programmatic usage
|
|
192
193
|
export {
|
|
193
194
|
type CreateAgentSessionOptions,
|
package/packages/pi-coding-agent/src/modes/interactive/components/__tests__/tool-execution.test.ts
CHANGED
|
@@ -14,12 +14,13 @@ function renderTool(
|
|
|
14
14
|
isError: boolean;
|
|
15
15
|
details?: Record<string, unknown>;
|
|
16
16
|
},
|
|
17
|
+
toolDefinition?: { label?: string },
|
|
17
18
|
): string {
|
|
18
19
|
const component = new ToolExecutionComponent(
|
|
19
20
|
toolName,
|
|
20
21
|
args,
|
|
21
22
|
{},
|
|
22
|
-
|
|
23
|
+
toolDefinition as any,
|
|
23
24
|
{ requestRender() {} } as any,
|
|
24
25
|
);
|
|
25
26
|
component.setExpanded(true);
|
|
@@ -35,12 +36,13 @@ function renderToolCollapsed(
|
|
|
35
36
|
isError: boolean;
|
|
36
37
|
details?: Record<string, unknown>;
|
|
37
38
|
},
|
|
39
|
+
toolDefinition?: { label?: string },
|
|
38
40
|
): string {
|
|
39
41
|
const component = new ToolExecutionComponent(
|
|
40
42
|
toolName,
|
|
41
43
|
args,
|
|
42
44
|
{},
|
|
43
|
-
|
|
45
|
+
toolDefinition as any,
|
|
44
46
|
{ requestRender() {} } as any,
|
|
45
47
|
);
|
|
46
48
|
if (result) component.updateResult(result);
|
|
@@ -110,13 +112,57 @@ describe("ToolExecutionComponent", () => {
|
|
|
110
112
|
{ count: 3, enabled: true, label: "hello" },
|
|
111
113
|
);
|
|
112
114
|
|
|
113
|
-
assert.match(rendered, /
|
|
115
|
+
assert.match(rendered, /Some Unknown Tool/);
|
|
114
116
|
assert.match(rendered, /count=3/);
|
|
115
117
|
assert.match(rendered, /enabled=true/);
|
|
116
118
|
assert.match(rendered, /label="hello"/);
|
|
117
119
|
assert.doesNotMatch(rendered, /^\{$/m);
|
|
118
120
|
});
|
|
119
121
|
|
|
122
|
+
test("frame header prefers toolDefinition.label over raw tool name", () => {
|
|
123
|
+
const rendered = renderToolCollapsed(
|
|
124
|
+
"gsd_slice_complete",
|
|
125
|
+
{ sliceId: "S03" },
|
|
126
|
+
undefined,
|
|
127
|
+
{ label: "Complete Slice" },
|
|
128
|
+
);
|
|
129
|
+
|
|
130
|
+
assert.match(rendered, /Tool Complete Slice/);
|
|
131
|
+
assert.doesNotMatch(rendered, /gsd_slice_complete/);
|
|
132
|
+
});
|
|
133
|
+
|
|
134
|
+
test("frame header strips gsd_ prefix and title-cases when no label is registered", () => {
|
|
135
|
+
const rendered = renderToolCollapsed("gsd_requirement_update", { id: "R005" });
|
|
136
|
+
|
|
137
|
+
assert.match(rendered, /Tool Requirement Update/);
|
|
138
|
+
assert.doesNotMatch(rendered, /gsd_requirement_update/);
|
|
139
|
+
});
|
|
140
|
+
|
|
141
|
+
test("formatCompactArgs truncates long string values inline instead of dumping JSON", () => {
|
|
142
|
+
const longPath = "/Users/alice/.gsd/projects/4dce7b775013/worktrees/slice-S03-some-long-path-that-exceeds-limit";
|
|
143
|
+
const rendered = renderToolCollapsed("gsd_slice_complete", {
|
|
144
|
+
sliceId: "S03",
|
|
145
|
+
milestoneId: "M001",
|
|
146
|
+
worktree: longPath,
|
|
147
|
+
});
|
|
148
|
+
|
|
149
|
+
assert.match(rendered, /sliceId="S03"/);
|
|
150
|
+
assert.match(rendered, /milestoneId="M001"/);
|
|
151
|
+
assert.match(rendered, /worktree=".*…"/);
|
|
152
|
+
assert.doesNotMatch(rendered, /"sliceId":\s*"S03"/);
|
|
153
|
+
});
|
|
154
|
+
|
|
155
|
+
test("formatCompactArgs shows full string values when expanded", () => {
|
|
156
|
+
const longPath = "/Users/alice/.gsd/projects/4dce7b775013/worktrees/slice-S03-some-long-path-that-exceeds-limit";
|
|
157
|
+
const rendered = renderTool("gsd_slice_complete", {
|
|
158
|
+
sliceId: "S03",
|
|
159
|
+
worktree: longPath,
|
|
160
|
+
});
|
|
161
|
+
|
|
162
|
+
assert.match(rendered, new RegExp(longPath.replace(/\//g, "\\/")));
|
|
163
|
+
assert.doesNotMatch(rendered, /…/);
|
|
164
|
+
});
|
|
165
|
+
|
|
120
166
|
test("generic fallback truncates long output when collapsed", () => {
|
|
121
167
|
const longOutput = Array.from({ length: 25 }, (_, i) => `line ${i + 1}`).join("\n");
|
|
122
168
|
const rendered = renderToolCollapsed(
|
|
@@ -37,26 +37,32 @@ describe("DynamicBorder spinner", () => {
|
|
|
37
37
|
border.stopSpinner();
|
|
38
38
|
});
|
|
39
39
|
|
|
40
|
-
it("triggers standalone render when no external render occurred recently",
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
40
|
+
it("triggers standalone render when no external render occurred recently", () => {
|
|
41
|
+
mock.timers.enable({ apis: ["setInterval"], now: 0 });
|
|
42
|
+
try {
|
|
43
|
+
const border = new DynamicBorder((s) => s);
|
|
44
|
+
const tui = makeTUI();
|
|
45
|
+
|
|
46
|
+
// Set lastExternalRender to a time well in the past
|
|
47
|
+
const anyBorder = border as any;
|
|
48
|
+
anyBorder.lastExternalRender = 0;
|
|
49
|
+
|
|
50
|
+
border.startSpinner(tui as any, (s) => s);
|
|
51
|
+
const initialCount = tui.renderCount;
|
|
52
|
+
|
|
53
|
+
// Advance exactly one spinner interval (200ms). With mocked timers
|
|
54
|
+
// this is deterministic — no flake under CI load.
|
|
55
|
+
mock.timers.tick(200);
|
|
56
|
+
|
|
57
|
+
assert.ok(
|
|
58
|
+
tui.renderCount > initialCount,
|
|
59
|
+
"spinner should trigger requestRender after one 200ms interval when no recent external render",
|
|
60
|
+
);
|
|
61
|
+
|
|
62
|
+
border.stopSpinner();
|
|
63
|
+
} finally {
|
|
64
|
+
mock.timers.reset();
|
|
65
|
+
}
|
|
60
66
|
});
|
|
61
67
|
|
|
62
68
|
it("updates lastExternalRender on each render() call", () => {
|