@opengsd/gsd-pi 1.2.0-dev.9ad8ae33 → 1.2.0-dev.a6376d75
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/dist/cli-model-override.d.ts +15 -0
- package/dist/cli-model-override.js +21 -0
- package/dist/cli.js +1 -18
- package/dist/loader.js +6 -4
- package/dist/register-agent-bundles.d.ts +11 -2
- package/dist/register-agent-bundles.js +18 -4
- package/dist/resources/.managed-resources-content-hash +1 -1
- package/dist/resources/extensions/ask-user-questions.js +3 -2
- package/dist/resources/extensions/claude-code-cli/stream-adapter.js +447 -215
- package/dist/resources/extensions/claude-code-cli/turn-assembler.js +33 -1
- package/dist/resources/extensions/gsd/auto/closeout.js +215 -0
- package/dist/resources/extensions/gsd/auto/dispatch-history.js +21 -6
- package/dist/resources/extensions/gsd/auto/dispatch.js +365 -0
- package/dist/resources/extensions/gsd/auto/finalize.js +347 -0
- package/dist/resources/extensions/gsd/auto/loop.js +4 -1
- package/dist/resources/extensions/gsd/auto/milestone-lease-reclaim.js +56 -0
- package/dist/resources/extensions/gsd/auto/orchestrator.js +85 -15
- package/dist/resources/extensions/gsd/auto/phase-helpers.js +146 -0
- package/dist/resources/extensions/gsd/auto/phases.js +17 -2372
- package/dist/resources/extensions/gsd/auto/pre-dispatch.js +534 -0
- package/dist/resources/extensions/gsd/auto/unit-phase.js +694 -0
- package/dist/resources/extensions/gsd/auto/workflow-unit-dispatch.js +1 -1
- package/dist/resources/extensions/gsd/auto/worktree-safety-phase.js +125 -0
- package/dist/resources/extensions/gsd/auto-worktree.js +1 -1
- package/dist/resources/extensions/gsd/auto.js +15 -1
- package/dist/resources/extensions/gsd/bootstrap/dynamic-tools.js +37 -7
- package/dist/resources/extensions/gsd/commands-mcp-status.js +2 -2
- package/dist/resources/extensions/gsd/commands-workflow-templates.js +9 -2
- package/dist/resources/extensions/gsd/db/queries.js +30 -0
- package/dist/resources/extensions/gsd/doctor-environment.js +256 -125
- package/dist/resources/extensions/gsd/guided-flow.js +88 -2
- package/dist/resources/extensions/gsd/health-widget.js +87 -28
- package/dist/resources/extensions/gsd/mcp-bridge.js +10 -0
- package/dist/resources/extensions/gsd/milestone-settlement.js +2 -2
- package/dist/resources/extensions/gsd/notifications.js +12 -7
- package/dist/resources/extensions/gsd/prompts/complete-slice.md +1 -1
- package/dist/resources/extensions/gsd/prompts/execute-task.md +2 -1
- package/dist/resources/extensions/gsd/prompts/run-uat.md +2 -0
- package/dist/resources/extensions/gsd/prompts/workflow-start.md +2 -1
- package/dist/resources/extensions/gsd/skill-activation.js +3 -6
- package/dist/resources/extensions/gsd/state.js +6 -2
- package/dist/resources/extensions/gsd/tool-surface-readiness.js +83 -31
- package/dist/resources/extensions/gsd/tools/complete-task.js +62 -0
- package/dist/resources/extensions/gsd/unit-context-composer.js +1 -1
- package/dist/resources/extensions/gsd/unit-registry.js +34 -4
- package/dist/resources/extensions/gsd/workflow-mcp-auto-prep.js +2 -0
- package/dist/resources/extensions/gsd/workflow-mcp-readiness-cache.js +105 -0
- package/dist/resources/extensions/gsd/worktree-safety.js +28 -26
- package/dist/resources/extensions/mcp-client/manager.js +6 -1
- package/dist/runtime-checks.d.ts +10 -0
- package/dist/runtime-checks.js +27 -0
- 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 +8 -8
- 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/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 +8 -8
- package/dist/web/standalone/.next/server/middleware-build-manifest.js +1 -1
- 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 -2
- package/packages/cloud-mcp-gateway/package.json +2 -2
- package/packages/contracts/package.json +1 -1
- package/packages/daemon/package.json +4 -4
- package/packages/gsd-agent-core/dist/sdk.d.ts.map +1 -1
- package/packages/gsd-agent-core/dist/sdk.js +6 -4
- package/packages/gsd-agent-core/dist/sdk.js.map +1 -1
- package/packages/gsd-agent-core/package.json +5 -5
- package/packages/gsd-agent-modes/dist/modes/interactive/components/settings-selector.d.ts +2 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/settings-selector.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/settings-selector.js +10 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/settings-selector.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/tool-execution.d.ts +8 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/tool-execution.js +50 -6
- package/packages/gsd-agent-modes/dist/modes/interactive/components/tool-execution.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/transcript-design.d.ts +2 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/transcript-design.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/transcript-design.js +34 -5
- package/packages/gsd-agent-modes/dist/modes/interactive/components/transcript-design.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-mode.d.ts +1 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-mode.js +12 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-mode.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-settings.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-settings.js +4 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-settings.js.map +1 -1
- package/packages/gsd-agent-modes/package.json +7 -7
- package/packages/mcp-server/README.md +12 -3
- package/packages/mcp-server/dist/cli-runner.d.ts +40 -0
- package/packages/mcp-server/dist/cli-runner.d.ts.map +1 -0
- package/packages/mcp-server/dist/cli-runner.js +137 -0
- package/packages/mcp-server/dist/cli-runner.js.map +1 -0
- package/packages/mcp-server/dist/cli.js +2 -58
- package/packages/mcp-server/dist/cli.js.map +1 -1
- package/packages/mcp-server/dist/pid-registry.d.ts +46 -0
- package/packages/mcp-server/dist/pid-registry.d.ts.map +1 -0
- package/packages/mcp-server/dist/pid-registry.js +452 -0
- package/packages/mcp-server/dist/pid-registry.js.map +1 -0
- package/packages/mcp-server/dist/probe-mode.d.ts +4 -0
- package/packages/mcp-server/dist/probe-mode.d.ts.map +1 -0
- package/packages/mcp-server/dist/probe-mode.js +10 -0
- package/packages/mcp-server/dist/probe-mode.js.map +1 -0
- package/packages/mcp-server/dist/stdio-watchdog.d.ts +8 -0
- package/packages/mcp-server/dist/stdio-watchdog.d.ts.map +1 -0
- package/packages/mcp-server/dist/stdio-watchdog.js +40 -0
- package/packages/mcp-server/dist/stdio-watchdog.js.map +1 -0
- package/packages/mcp-server/dist/workflow-tools.d.ts.map +1 -1
- package/packages/mcp-server/dist/workflow-tools.js +62 -43
- package/packages/mcp-server/dist/workflow-tools.js.map +1 -1
- package/packages/mcp-server/package.json +5 -5
- package/packages/native/package.json +1 -1
- package/packages/pi-agent-core/dist/agent-loop.js +43 -2
- package/packages/pi-agent-core/dist/agent-loop.js.map +1 -1
- package/packages/pi-agent-core/package.json +1 -1
- package/packages/pi-ai/package.json +1 -1
- package/packages/pi-coding-agent/dist/core/settings-manager.d.ts +3 -0
- package/packages/pi-coding-agent/dist/core/settings-manager.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/core/settings-manager.js +11 -0
- package/packages/pi-coding-agent/dist/core/settings-manager.js.map +1 -1
- package/packages/pi-coding-agent/dist/theme/theme.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/theme/theme.js +45 -17
- package/packages/pi-coding-agent/dist/theme/theme.js.map +1 -1
- package/packages/pi-coding-agent/package.json +7 -7
- package/packages/pi-tui/dist/index.d.ts +1 -1
- package/packages/pi-tui/dist/index.d.ts.map +1 -1
- package/packages/pi-tui/dist/index.js +1 -1
- package/packages/pi-tui/dist/index.js.map +1 -1
- package/packages/pi-tui/dist/terminal-image.d.ts +33 -0
- package/packages/pi-tui/dist/terminal-image.d.ts.map +1 -1
- package/packages/pi-tui/dist/terminal-image.js +54 -2
- package/packages/pi-tui/dist/terminal-image.js.map +1 -1
- package/packages/pi-tui/dist/tui.d.ts +8 -0
- package/packages/pi-tui/dist/tui.d.ts.map +1 -1
- package/packages/pi-tui/dist/tui.js +63 -18
- package/packages/pi-tui/dist/tui.js.map +1 -1
- package/packages/pi-tui/dist/utils.d.ts.map +1 -1
- package/packages/pi-tui/dist/utils.js +110 -36
- package/packages/pi-tui/dist/utils.js.map +1 -1
- package/packages/pi-tui/package.json +2 -2
- package/packages/rpc-client/package.json +2 -2
- package/pkg/dist/theme/theme.d.ts.map +1 -1
- package/pkg/dist/theme/theme.js +45 -17
- package/pkg/dist/theme/theme.js.map +1 -1
- package/pkg/package.json +1 -1
- package/src/resources/extensions/ask-user-questions.ts +7 -2
- package/src/resources/extensions/claude-code-cli/stream-adapter.ts +531 -226
- package/src/resources/extensions/claude-code-cli/tests/stream-adapter.test.ts +672 -7
- package/src/resources/extensions/claude-code-cli/turn-assembler.ts +38 -1
- package/src/resources/extensions/gsd/auto/closeout.ts +309 -0
- package/src/resources/extensions/gsd/auto/dispatch-history.ts +22 -6
- package/src/resources/extensions/gsd/auto/dispatch.ts +449 -0
- package/src/resources/extensions/gsd/auto/finalize.ts +445 -0
- package/src/resources/extensions/gsd/auto/loop.ts +4 -1
- package/src/resources/extensions/gsd/auto/milestone-lease-reclaim.ts +74 -0
- package/src/resources/extensions/gsd/auto/orchestrator.ts +95 -15
- package/src/resources/extensions/gsd/auto/phase-helpers.ts +199 -0
- package/src/resources/extensions/gsd/auto/phases.ts +58 -3061
- package/src/resources/extensions/gsd/auto/pre-dispatch.ts +704 -0
- package/src/resources/extensions/gsd/auto/unit-phase.ts +910 -0
- package/src/resources/extensions/gsd/auto/workflow-unit-dispatch.ts +1 -1
- package/src/resources/extensions/gsd/auto/worktree-safety-phase.ts +149 -0
- package/src/resources/extensions/gsd/auto-worktree.ts +1 -1
- package/src/resources/extensions/gsd/auto.ts +20 -1
- package/src/resources/extensions/gsd/bootstrap/dynamic-tools.ts +56 -6
- package/src/resources/extensions/gsd/commands-mcp-status.ts +2 -2
- package/src/resources/extensions/gsd/commands-workflow-templates.ts +11 -4
- package/src/resources/extensions/gsd/db/queries.ts +29 -0
- package/src/resources/extensions/gsd/doctor-environment.ts +267 -142
- package/src/resources/extensions/gsd/guided-flow.ts +128 -2
- package/src/resources/extensions/gsd/health-widget.ts +91 -27
- package/src/resources/extensions/gsd/mcp-bridge.ts +39 -0
- package/src/resources/extensions/gsd/milestone-settlement.ts +2 -2
- package/src/resources/extensions/gsd/notifications.ts +13 -6
- package/src/resources/extensions/gsd/prompts/complete-slice.md +1 -1
- package/src/resources/extensions/gsd/prompts/execute-task.md +2 -1
- package/src/resources/extensions/gsd/prompts/run-uat.md +2 -0
- package/src/resources/extensions/gsd/prompts/workflow-start.md +2 -1
- package/src/resources/extensions/gsd/skill-activation.ts +3 -6
- package/src/resources/extensions/gsd/state.ts +7 -1
- package/src/resources/extensions/gsd/tests/auto-abort-pause-regression.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/auto-blocked-remediation-message.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/auto-loop.test.ts +206 -22
- package/src/resources/extensions/gsd/tests/auto-orchestrator.test.ts +76 -12
- package/src/resources/extensions/gsd/tests/auto-pause-double-entry-guard.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/auto-paused-ui-cleanup.test.ts +77 -1
- package/src/resources/extensions/gsd/tests/auto-phases-lifecycle.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/auto-unit-closeout.test.ts +169 -1
- package/src/resources/extensions/gsd/tests/complete-task.test.ts +141 -5
- package/src/resources/extensions/gsd/tests/deep-project-auto-loop.test.ts +2 -1
- package/src/resources/extensions/gsd/tests/derive-state-helpers.test.ts +36 -0
- package/src/resources/extensions/gsd/tests/dispatch-history.test.ts +55 -0
- package/src/resources/extensions/gsd/tests/dist-redirect.mjs +8 -0
- package/src/resources/extensions/gsd/tests/engine-interfaces-contract.test.ts +117 -91
- package/src/resources/extensions/gsd/tests/ensure-db-open.test.ts +113 -0
- package/src/resources/extensions/gsd/tests/guided-dispatch-root.test.ts +16 -0
- package/src/resources/extensions/gsd/tests/integration/auto-worktree.test.ts +15 -0
- package/src/resources/extensions/gsd/tests/integration/doctor-environment-async.test.ts +104 -0
- package/src/resources/extensions/gsd/tests/integration/run-uat.test.ts +18 -0
- package/src/resources/extensions/gsd/tests/journal-integration.test.ts +47 -16
- package/src/resources/extensions/gsd/tests/mcp-readiness-preflight.test.ts +205 -0
- package/src/resources/extensions/gsd/tests/mcp-status.test.ts +6 -5
- package/src/resources/extensions/gsd/tests/milestone-merge-stash-restore.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/milestone-report-path.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/milestone-settlement.test.ts +92 -0
- package/src/resources/extensions/gsd/tests/milestone-transition-state-rebuild.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/notifications.test.ts +64 -9
- package/src/resources/extensions/gsd/tests/parallel-skill-prompt-integration.test.ts +2 -2
- package/src/resources/extensions/gsd/tests/parsers-legacy-importers.test.ts +5 -0
- package/src/resources/extensions/gsd/tests/phases-merge-error-stops-auto.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/phases-terminal-complete-idempotent.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/plan-gate-failed-doctor-heal-hint.test.ts +3 -3
- package/src/resources/extensions/gsd/tests/prompt-contracts.test.ts +10 -2
- package/src/resources/extensions/gsd/tests/provider-errors.test.ts +2 -4
- package/src/resources/extensions/gsd/tests/remote-notification-from-desktop.test.ts +31 -81
- package/src/resources/extensions/gsd/tests/runtime-invariant-modules.test.ts +7 -1
- package/src/resources/extensions/gsd/tests/skill-activation.test.ts +20 -17
- package/src/resources/extensions/gsd/tests/start-auto-detached.test.ts +7 -3
- package/src/resources/extensions/gsd/tests/stop-auto-race-null-unit.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/token-tool-gating.test.ts +4 -2
- package/src/resources/extensions/gsd/tests/tool-surface-readiness.test.ts +184 -10
- package/src/resources/extensions/gsd/tests/uok-plan-v2-wiring.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/workflow-mcp-readiness-cache.test.ts +119 -0
- package/src/resources/extensions/gsd/tests/workflow-mcp.test.ts +65 -2
- package/src/resources/extensions/gsd/tests/workflow-phase-contract-matrix.test.ts +332 -0
- package/src/resources/extensions/gsd/tests/workflow-templates.test.ts +92 -0
- package/src/resources/extensions/gsd/tests/worktree-health-dispatch.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/worktree-project-root-degrade.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/worktree-safety-phase.test.ts +100 -0
- package/src/resources/extensions/gsd/tests/worktree-safety.test.ts +72 -0
- package/src/resources/extensions/gsd/tool-surface-readiness.ts +126 -19
- package/src/resources/extensions/gsd/tools/complete-task.ts +87 -0
- package/src/resources/extensions/gsd/unit-context-composer.ts +1 -1
- package/src/resources/extensions/gsd/unit-registry.ts +34 -4
- package/src/resources/extensions/gsd/workflow-mcp-auto-prep.ts +2 -0
- package/src/resources/extensions/gsd/workflow-mcp-readiness-cache.ts +150 -0
- package/src/resources/extensions/gsd/worktree-safety.ts +41 -39
- package/src/resources/extensions/mcp-client/manager.ts +7 -1
- /package/dist/web/standalone/.next/static/{FBNo5cT_chy7YNoAQsU3o → xyMkEaICFHJoa98VgJyzY}/_buildManifest.js +0 -0
- /package/dist/web/standalone/.next/static/{FBNo5cT_chy7YNoAQsU3o → xyMkEaICFHJoa98VgJyzY}/_ssgManifest.js +0 -0
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
import type { ExtensionContext } from "@gsd/pi-coding-agent";
|
|
5
5
|
import type { GSDState } from "./types.js";
|
|
6
6
|
import { runProviderChecks, summariseProviderIssues } from "./doctor-providers.js";
|
|
7
|
-
import { runEnvironmentChecks } from "./doctor-environment.js";
|
|
7
|
+
import { runEnvironmentChecks, runEnvironmentChecksAsync } from "./doctor-environment.js";
|
|
8
8
|
import { loadEffectiveGSDPreferences } from "./preferences.js";
|
|
9
9
|
import { nativeIsRepo, nativeLastCommitEpoch, nativeGetCurrentBranch, nativeCommitSubject } from "./native-git-bridge.js";
|
|
10
10
|
import { loadLedgerFromDisk, getProjectTotals } from "./metrics.js";
|
|
@@ -22,7 +22,31 @@ export const HEALTH_WIDGET_ACTIVE_HINTS =
|
|
|
22
22
|
|
|
23
23
|
// ── Data loader ────────────────────────────────────────────────────────────────
|
|
24
24
|
|
|
25
|
-
|
|
25
|
+
// Last-commit lookup is subprocess-backed (native-git-bridge → git spawns),
|
|
26
|
+
// so it is treated like the other expensive checks: skipped on first paint,
|
|
27
|
+
// run only by the background refresh.
|
|
28
|
+
function loadLastCommitInfo(basePath: string): { epoch: number | null; message: string | null } {
|
|
29
|
+
try {
|
|
30
|
+
if (nativeIsRepo(basePath)) {
|
|
31
|
+
const branch = nativeGetCurrentBranch(basePath);
|
|
32
|
+
const epoch = nativeLastCommitEpoch(basePath, branch || "HEAD");
|
|
33
|
+
if (epoch > 0) {
|
|
34
|
+
return { epoch, message: nativeCommitSubject(basePath, branch || "HEAD") || null };
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
} catch { /* non-fatal */ }
|
|
38
|
+
return { epoch: null, message: null };
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
function loadHealthWidgetData(
|
|
42
|
+
basePath: string,
|
|
43
|
+
options?: { includeChecks?: boolean },
|
|
44
|
+
): HealthWidgetData {
|
|
45
|
+
// `includeChecks` gates the expensive subprocess-backed checks (provider +
|
|
46
|
+
// environment doctor: `lsof`, `docker`, `node --version`, ...). The initial
|
|
47
|
+
// synchronous render passes `false` so first paint is never blocked on them;
|
|
48
|
+
// the async refresh (off the first-paint path) runs the full suite.
|
|
49
|
+
const includeChecks = options?.includeChecks ?? true;
|
|
26
50
|
let budgetCeiling: number | undefined;
|
|
27
51
|
let budgetSpent = 0;
|
|
28
52
|
let providerIssue: string | null = null;
|
|
@@ -44,40 +68,73 @@ function loadHealthWidgetData(basePath: string): HealthWidgetData {
|
|
|
44
68
|
}
|
|
45
69
|
} catch { /* non-fatal */ }
|
|
46
70
|
|
|
71
|
+
if (includeChecks) {
|
|
72
|
+
try {
|
|
73
|
+
const providerResults = runProviderChecks();
|
|
74
|
+
providerIssue = summariseProviderIssues(providerResults);
|
|
75
|
+
} catch { /* non-fatal */ }
|
|
76
|
+
|
|
77
|
+
try {
|
|
78
|
+
const envResults = runEnvironmentChecks(basePath);
|
|
79
|
+
for (const r of envResults) {
|
|
80
|
+
if (r.status === "error") environmentErrorCount++;
|
|
81
|
+
else if (r.status === "warning") environmentWarningCount++;
|
|
82
|
+
}
|
|
83
|
+
} catch { /* non-fatal */ }
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
// ── Last commit info ── (git spawns — gated like the other expensive checks)
|
|
87
|
+
if (includeChecks) {
|
|
88
|
+
const commit = loadLastCommitInfo(basePath);
|
|
89
|
+
lastCommitEpoch = commit.epoch;
|
|
90
|
+
lastCommitMessage = commit.message;
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
return {
|
|
94
|
+
projectState,
|
|
95
|
+
budgetCeiling,
|
|
96
|
+
budgetSpent,
|
|
97
|
+
providerIssue,
|
|
98
|
+
environmentErrorCount,
|
|
99
|
+
environmentWarningCount,
|
|
100
|
+
lastCommitEpoch,
|
|
101
|
+
lastCommitMessage,
|
|
102
|
+
lastRefreshed: Date.now(),
|
|
103
|
+
};
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
// Non-blocking variant used by the widget's background refresh: the cheap fields
|
|
107
|
+
// come from the synchronous snapshot, then provider + environment checks are
|
|
108
|
+
// layered in off the event-loop critical path (env checks run concurrently via
|
|
109
|
+
// runEnvironmentChecksAsync). Keeps the always-on widget from stalling the UI on
|
|
110
|
+
// its initial enrichment or its 60s refresh.
|
|
111
|
+
async function loadHealthWidgetDataAsync(basePath: string): Promise<HealthWidgetData> {
|
|
112
|
+
const data = loadHealthWidgetData(basePath, { includeChecks: false });
|
|
113
|
+
let providerIssue = data.providerIssue;
|
|
114
|
+
let environmentErrorCount = 0;
|
|
115
|
+
let environmentWarningCount = 0;
|
|
116
|
+
|
|
47
117
|
try {
|
|
48
|
-
|
|
49
|
-
providerIssue = summariseProviderIssues(providerResults);
|
|
118
|
+
providerIssue = summariseProviderIssues(runProviderChecks());
|
|
50
119
|
} catch { /* non-fatal */ }
|
|
51
120
|
|
|
52
121
|
try {
|
|
53
|
-
const envResults =
|
|
122
|
+
const envResults = await runEnvironmentChecksAsync(basePath);
|
|
54
123
|
for (const r of envResults) {
|
|
55
124
|
if (r.status === "error") environmentErrorCount++;
|
|
56
125
|
else if (r.status === "warning") environmentWarningCount++;
|
|
57
126
|
}
|
|
58
127
|
} catch { /* non-fatal */ }
|
|
59
128
|
|
|
60
|
-
|
|
61
|
-
try {
|
|
62
|
-
if (nativeIsRepo(basePath)) {
|
|
63
|
-
const branch = nativeGetCurrentBranch(basePath);
|
|
64
|
-
const epoch = nativeLastCommitEpoch(basePath, branch || "HEAD");
|
|
65
|
-
if (epoch > 0) {
|
|
66
|
-
lastCommitEpoch = epoch;
|
|
67
|
-
lastCommitMessage = nativeCommitSubject(basePath, branch || "HEAD") || null;
|
|
68
|
-
}
|
|
69
|
-
}
|
|
70
|
-
} catch { /* non-fatal */ }
|
|
129
|
+
const commit = loadLastCommitInfo(basePath);
|
|
71
130
|
|
|
72
131
|
return {
|
|
73
|
-
|
|
74
|
-
budgetCeiling,
|
|
75
|
-
budgetSpent,
|
|
132
|
+
...data,
|
|
76
133
|
providerIssue,
|
|
77
134
|
environmentErrorCount,
|
|
78
135
|
environmentWarningCount,
|
|
79
|
-
lastCommitEpoch,
|
|
80
|
-
lastCommitMessage,
|
|
136
|
+
lastCommitEpoch: commit.epoch,
|
|
137
|
+
lastCommitMessage: commit.message,
|
|
81
138
|
lastRefreshed: Date.now(),
|
|
82
139
|
};
|
|
83
140
|
}
|
|
@@ -95,8 +152,13 @@ export function initHealthWidget(ctx: ExtensionContext): void {
|
|
|
95
152
|
|
|
96
153
|
const basePath = projectRoot();
|
|
97
154
|
|
|
98
|
-
// String-array fallback — used in RPC mode (factory is a no-op there)
|
|
99
|
-
|
|
155
|
+
// String-array fallback — used in RPC mode (factory is a no-op there).
|
|
156
|
+
// Skip the expensive provider/environment doctor checks here: this runs
|
|
157
|
+
// synchronously on the interactive-startup path, where running them would
|
|
158
|
+
// block first paint by ~0.9s (lsof/docker probes, otherwise run again
|
|
159
|
+
// immediately by the factory below). The factory's async refresh fills in
|
|
160
|
+
// real health once the screen is up.
|
|
161
|
+
const initialData = loadHealthWidgetData(basePath, { includeChecks: false });
|
|
100
162
|
ctx.ui.setWidget("gsd-health", buildHealthLines(initialData), { placement: "belowEditor" });
|
|
101
163
|
|
|
102
164
|
// Factory-based widget for TUI mode — replaces the string-array above
|
|
@@ -110,7 +172,7 @@ export function initHealthWidget(ctx: ExtensionContext): void {
|
|
|
110
172
|
if (refreshInFlight) return;
|
|
111
173
|
refreshInFlight = true;
|
|
112
174
|
try {
|
|
113
|
-
data =
|
|
175
|
+
data = await loadHealthWidgetDataAsync(basePath);
|
|
114
176
|
cachedLines = undefined;
|
|
115
177
|
if (!isDisposed) _tui.requestRender();
|
|
116
178
|
} catch { /* non-fatal */ } finally {
|
|
@@ -118,9 +180,11 @@ export function initHealthWidget(ctx: ExtensionContext): void {
|
|
|
118
180
|
}
|
|
119
181
|
};
|
|
120
182
|
|
|
121
|
-
// Fire first enrichment
|
|
122
|
-
//
|
|
123
|
-
|
|
183
|
+
// Fire the first full enrichment off the first-paint path. setTimeout(0)
|
|
184
|
+
// yields to the initial render + input loop, so the expensive doctor checks
|
|
185
|
+
// (provider + environment) never delay the moment the user sees the UI.
|
|
186
|
+
// requestRender() inside refresh repaints the widget once data is ready.
|
|
187
|
+
setTimeout(() => { void refresh(); }, 0);
|
|
124
188
|
|
|
125
189
|
const refreshTimer = setInterval(() => {
|
|
126
190
|
void refresh();
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
// mcp-bridge.ts — stable runtime seam for MCP server consumption (phase 1).
|
|
2
|
+
export {
|
|
3
|
+
loadWriteGateSnapshot,
|
|
4
|
+
shouldBlockPendingGateInSnapshot,
|
|
5
|
+
shouldBlockQueueExecutionInSnapshot,
|
|
6
|
+
} from "./bootstrap/write-gate.js";
|
|
7
|
+
export { ensureDbOpen } from "./bootstrap/dynamic-tools.js";
|
|
8
|
+
export {
|
|
9
|
+
_getAdapter,
|
|
10
|
+
checkpointDatabase,
|
|
11
|
+
closeDatabase,
|
|
12
|
+
getAllMilestones,
|
|
13
|
+
getDb,
|
|
14
|
+
getGateResults,
|
|
15
|
+
getMilestoneSlices,
|
|
16
|
+
getPendingGates,
|
|
17
|
+
getSliceTasks,
|
|
18
|
+
insertDecision,
|
|
19
|
+
insertMilestone,
|
|
20
|
+
insertSlice,
|
|
21
|
+
openDatabase,
|
|
22
|
+
upsertMilestonePlanning,
|
|
23
|
+
} from "./gsd-db.js";
|
|
24
|
+
export { invalidateStateCache, isReusableGhostMilestone } from "./state.js";
|
|
25
|
+
export { loadEffectiveGSDPreferences } from "./preferences.js";
|
|
26
|
+
export {
|
|
27
|
+
saveDecisionToDb,
|
|
28
|
+
saveRequirementToDb,
|
|
29
|
+
updateRequirementInDb,
|
|
30
|
+
} from "./db-writer.js";
|
|
31
|
+
export { rebuildState } from "./doctor.js";
|
|
32
|
+
export { queryJournal } from "./journal.js";
|
|
33
|
+
export {
|
|
34
|
+
claimReservedId,
|
|
35
|
+
findMilestoneIds,
|
|
36
|
+
getReservedMilestoneIds,
|
|
37
|
+
milestoneIdSort,
|
|
38
|
+
nextMilestoneId,
|
|
39
|
+
} from "./milestone-ids.js";
|
|
@@ -74,8 +74,8 @@ export function evaluateAllCompleteSettlement(
|
|
|
74
74
|
action: "pause",
|
|
75
75
|
message:
|
|
76
76
|
`Milestone ${milestoneId} is complete, but its worktree branch has not been merged to main. ` +
|
|
77
|
-
`Retry with \`/gsd dispatch complete-milestone ${milestoneId}\`
|
|
78
|
-
nextAction: `Retry \`/gsd dispatch complete-milestone ${milestoneId}
|
|
77
|
+
`Retry with \`/gsd dispatch complete-milestone ${milestoneId}\` to finish the system-owned merge.`,
|
|
78
|
+
nextAction: `Retry \`/gsd dispatch complete-milestone ${milestoneId}\`.`,
|
|
79
79
|
milestoneId,
|
|
80
80
|
};
|
|
81
81
|
}
|
|
@@ -4,7 +4,12 @@
|
|
|
4
4
|
import { execFileSync } from "node:child_process";
|
|
5
5
|
import type { NotificationPreferences } from "./types.js";
|
|
6
6
|
import { loadEffectiveGSDPreferences } from "./preferences.js";
|
|
7
|
-
import { sendRemoteNotification } from "../remote-questions/notify.js";
|
|
7
|
+
import { sendRemoteNotification as _sendRemoteNotification } from "../remote-questions/notify.js";
|
|
8
|
+
|
|
9
|
+
/** Swappable dispatcher for remote notifications — exported so tests can mock it. */
|
|
10
|
+
export const remoteNotificationDispatcher = {
|
|
11
|
+
send: _sendRemoteNotification,
|
|
12
|
+
};
|
|
8
13
|
|
|
9
14
|
export type NotifyLevel = "info" | "success" | "warning" | "error";
|
|
10
15
|
export type NotificationKind = "complete" | "error" | "budget" | "milestone" | "attention";
|
|
@@ -30,28 +35,30 @@ export function sendDesktopNotification(
|
|
|
30
35
|
level: NotifyLevel = "info",
|
|
31
36
|
kind: NotificationKind = "complete",
|
|
32
37
|
projectName?: string,
|
|
38
|
+
deps: { notifications?: NotificationPreferences } = {},
|
|
33
39
|
): void {
|
|
34
40
|
// When a projectName is provided and the title is the default "GSD",
|
|
35
41
|
// replace it with a project-qualified title for multi-project clarity.
|
|
36
42
|
if (projectName && title === "GSD") {
|
|
37
43
|
title = formatNotificationTitle(projectName);
|
|
38
44
|
}
|
|
39
|
-
const
|
|
45
|
+
const loadedPreferences = loadEffectiveGSDPreferences()?.preferences;
|
|
46
|
+
const notifications = deps.notifications ?? loadedPreferences?.notifications;
|
|
40
47
|
|
|
41
48
|
// Remote notifications fire independently of desktop preferences.
|
|
42
49
|
// sendRemoteNotification handles "not configured" gracefully (early return).
|
|
43
|
-
void
|
|
50
|
+
void remoteNotificationDispatcher.send(title, message).catch(() => {});
|
|
44
51
|
|
|
45
|
-
if (!shouldSendDesktopNotification(kind,
|
|
52
|
+
if (!shouldSendDesktopNotification(kind, notifications)) return;
|
|
46
53
|
|
|
47
54
|
// cmux delivery and desktop delivery are independent — if cmux import or
|
|
48
55
|
// delivery fails, we must still attempt the native desktop notification.
|
|
49
56
|
const runCmux = async () => {
|
|
50
57
|
try {
|
|
51
58
|
const { CmuxClient, emitOsc777Notification, resolveCmuxConfig } = await import("../cmux/index.js");
|
|
52
|
-
const cmux = resolveCmuxConfig(
|
|
59
|
+
const cmux = resolveCmuxConfig(loadedPreferences);
|
|
53
60
|
if (cmux.notifications) {
|
|
54
|
-
const delivered = CmuxClient.fromPreferences(
|
|
61
|
+
const delivered = CmuxClient.fromPreferences(loadedPreferences).notify(title, message);
|
|
55
62
|
if (delivered) return true;
|
|
56
63
|
emitOsc777Notification(title, message);
|
|
57
64
|
}
|
|
@@ -38,7 +38,7 @@ Use `subagent` only when useful: reviewer, security, or tester. Apply findings b
|
|
|
38
38
|
10. Prepare `gsd_slice_complete` content with camelCase fields `milestoneId`, `sliceId`, `sliceTitle`, `oneLiner`, `narrative`, `verification`, and `uatContent`.
|
|
39
39
|
11. Draft concrete UAT with preconditions, steps, expected outcomes, edge cases, and UAT Type. Declare the type as a bullet under a `## UAT Type` heading, exactly like `- UAT mode: browser-executable`.
|
|
40
40
|
**Web apps:** when inlined Web App UAT guidance is present, declare `browser-executable` or `runtime-executable` (not `artifact-driven`) for localhost/browser/screenshot steps; include dev-server preconditions and name Playwright specs when they exist.
|
|
41
|
-
12. Review the inlined task-summary excerpts for DECISIONS.md/KNOWLEDGE.md-worthy decisions and gotchas. Read full `*-SUMMARY.md` only if needed. Capture with `capture_thought`; do not append knowledge files.
|
|
41
|
+
12. Review the inlined task-summary excerpts for DECISIONS.md/KNOWLEDGE.md-worthy decisions and gotchas. Read full `*-SUMMARY.md` only if needed. Capture with `gsd_capture_thought` (MCP-scoped `mcp__...__gsd_capture_thought`), not bare `capture_thought`; do not append knowledge files.
|
|
42
42
|
13. When verification passes, call `gsd_slice_complete`. The DB-backed tool is the canonical write path. Do **not** manually write `{{sliceSummaryPath}}`. Do **not** manually write `{{sliceUatPath}}`. Do not edit roadmap checkboxes.
|
|
43
43
|
14. Do not run git commands.
|
|
44
44
|
15. If the current project state needs refresh, call `gsd_summary_save` with `artifact_type: "PROJECT"` and the full updated project markdown as `content`; omit `milestone_id`. Do not write or edit `.gsd/PROJECT.md` directly.
|
|
@@ -52,6 +52,7 @@ You execute. The inlined task plan is authoritative. Verify referenced files and
|
|
|
52
52
|
|
|
53
53
|
- If task sections exist for Failure Modes (Q5), Load Profile (Q6), Negative Tests (Q7), or Observability Impact, implement and verify them.
|
|
54
54
|
- Verify must-haves with concrete commands or observable behavior.
|
|
55
|
+
- Run verification commands through `gsd_exec` / Context Mode evidence when workflow MCP tools are presented. Use `gsd_exec_search` before rerunning noisy checks, and `gsd_resume` after compaction or resume. Do not call direct `bash` for final verification evidence in this unit.
|
|
55
56
|
- Run slice-level verification from the slice plan. Final tasks need all checks passing; intermediate tasks should record partial passes.
|
|
56
57
|
- Populate `## Verification Evidence` with `formatEvidenceTable` rows: command, exit code, verdict, duration. If no checks were found, say so.
|
|
57
58
|
- For UI/browser/DOM/user-visible web changes, exercise the real flow and record explicit checks.
|
|
@@ -64,7 +65,7 @@ Keep about **{{verificationBudget}}** for verification and summary. If context i
|
|
|
64
65
|
|
|
65
66
|
- If the plan is fundamentally invalid, set `blocker_discovered: true` in the summary and explain.
|
|
66
67
|
- For downstream-impacting ambiguity that cannot be resolved from code, plans, or decisions, include an `escalation` object with question, options, recommendation, rationale, and `continueWithDefault`.
|
|
67
|
-
- Capture meaningful architecture/pattern/observability decisions with `
|
|
68
|
+
- Capture meaningful architecture/pattern/observability decisions with `gsd_capture_thought` (or MCP-scoped `mcp__...__gsd_capture_thought`) when workflow MCP tools are presented; capture non-obvious gotchas or conventions only when they save future investigation.
|
|
68
69
|
- Use the inlined Task Summary template below. Read `{{taskSummaryTemplatePath}}` only if the inlined template is absent or visibly truncated.
|
|
69
70
|
- Call `gsd_task_complete` with camelCase fields `milestoneId`, `sliceId`, `taskId`, `oneLiner`, `narrative`, `verification`, and `verificationEvidence`. Include `blockerDiscovered: true` when a stale-path safety failure or other plan-invalidating blocker prevents execution.
|
|
70
71
|
- The DB-backed tool is the canonical write path. Do **not** manually write `{{taskSummaryPath}}` or edit PLAN.md checkboxes; the tool renders the summary and updates state.
|
|
@@ -10,6 +10,8 @@ If any inlined plan, summary, verification command, or prior artifact names an a
|
|
|
10
10
|
|
|
11
11
|
All relevant context has been preloaded below. Start working immediately without re-reading these files.
|
|
12
12
|
|
|
13
|
+
If a `.gsd/**` or `.gsd/**/*` glob returns no matches, treat that as a possible symlink-backed traversal limitation; do not infer that the GSD harness is missing. Use the preloaded UAT context and direct `.gsd/...` file paths named in this prompt instead.
|
|
14
|
+
|
|
13
15
|
{{inlinedContext}}
|
|
14
16
|
|
|
15
17
|
{{skillActivation}}
|
|
@@ -25,4 +25,5 @@ Follow the workflow defined below. Execute each phase in order, completing one b
|
|
|
25
25
|
3. **Atomic commits.** Commit working code after each meaningful change. Use conventional commit format: `<type>(<scope>): <description>`.
|
|
26
26
|
4. **Verify before shipping.** Run the project's test suite and build before marking the workflow complete.
|
|
27
27
|
5. **Decision gates, not ceremony.** After each phase, summarize what changed. For low/medium complexity, ask for confirmation only when the next phase depends on a real user choice or external approval. For high complexity, confirm before proceeding to each new phase.
|
|
28
|
-
6. **
|
|
28
|
+
6. **Persist workflow state.** If the artifact directory contains `STATE.json`, update it after each phase: mark the finished phase `completed`, mark the next phase `active`, set `currentPhase` to the active phase index, and refresh `updatedAt`. When every phase is completed, set `completedAt` to the completion timestamp.
|
|
29
|
+
7. **Stay focused.** This is a {{complexity}}-complexity workflow. Match your ceremony level to the task — don't over-engineer or under-deliver.
|
|
@@ -134,11 +134,8 @@ const SAFE_SKILL_NAME = /^[a-z0-9][a-z0-9-]*$/;
|
|
|
134
134
|
function formatSkillActivationBlock(skillNames: string[]): string {
|
|
135
135
|
const safe = skillNames.filter(name => SAFE_SKILL_NAME.test(name));
|
|
136
136
|
if (safe.length === 0) return "";
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
// parameter name, causing tool validation failures — see #2224.
|
|
140
|
-
const calls = safe.map(name => `Call Skill({ skill: '${name}' })`).join('. ');
|
|
141
|
-
return `<skill_activation>${calls}.</skill_activation>`;
|
|
137
|
+
const reads = safe.map(name => `Read the installed '${name}' skill file from <available_skills>`).join(". ");
|
|
138
|
+
return `<skill_activation>${reads}.</skill_activation>`;
|
|
142
139
|
}
|
|
143
140
|
|
|
144
141
|
/**
|
|
@@ -157,7 +154,7 @@ function formatSkillRecommendationsBlock(unitType: string | undefined, skillName
|
|
|
157
154
|
if (!unitType) return "";
|
|
158
155
|
const safe = skillNames.filter(name => SAFE_SKILL_NAME.test(name));
|
|
159
156
|
if (safe.length === 0) return "";
|
|
160
|
-
return `<skill_recommendations unit="${unitType}">For this unit type, also consider
|
|
157
|
+
return `<skill_recommendations unit="${unitType}">For this unit type, also consider reading these installed skill files from <available_skills>: ${safe.join(", ")}. These are recommendations, not requirements.</skill_recommendations>`;
|
|
161
158
|
}
|
|
162
159
|
|
|
163
160
|
export function buildSkillActivationBlock(params: {
|
|
@@ -60,6 +60,7 @@ import {
|
|
|
60
60
|
getAllMilestones,
|
|
61
61
|
getMilestone,
|
|
62
62
|
getMilestoneSlices,
|
|
63
|
+
getSlicesByMilestoneIds,
|
|
63
64
|
getSliceTasks,
|
|
64
65
|
getReplanHistory,
|
|
65
66
|
getSlice,
|
|
@@ -477,13 +478,18 @@ async function buildRegistryAndFindActive(
|
|
|
477
478
|
let activeMilestoneHasDraft = false;
|
|
478
479
|
let firstDeferredQueuedShell: { id: string; title: string; deps: string[]; hasDraftContext: boolean } | null = null;
|
|
479
480
|
|
|
481
|
+
const activeMilestoneIds = milestones
|
|
482
|
+
.filter((m) => !parkedMilestoneIds.has(m.id))
|
|
483
|
+
.map((m) => m.id);
|
|
484
|
+
const slicesByMilestone = getSlicesByMilestoneIds(activeMilestoneIds);
|
|
485
|
+
|
|
480
486
|
for (const m of milestones) {
|
|
481
487
|
if (parkedMilestoneIds.has(m.id)) {
|
|
482
488
|
registry.push({ id: m.id, title: stripMilestonePrefix(m.title) || m.id, status: 'parked' });
|
|
483
489
|
continue;
|
|
484
490
|
}
|
|
485
491
|
|
|
486
|
-
const slices =
|
|
492
|
+
const slices = slicesByMilestone.get(m.id) ?? [];
|
|
487
493
|
|
|
488
494
|
// DB-authoritative completeness (#4179): only trust completeMilestoneIds,
|
|
489
495
|
// which is itself derived from DB status. SUMMARY-file presence alone must
|
|
@@ -2,7 +2,7 @@ import test from "node:test";
|
|
|
2
2
|
import assert from "node:assert/strict";
|
|
3
3
|
|
|
4
4
|
import { _buildAbortedPauseContext, isUserInitiatedAbortMessage } from "../bootstrap/agent-end-recovery.js";
|
|
5
|
-
import { _buildCancelledUnitStopReason, _isPauseOriginCancelledResult } from "../auto/
|
|
5
|
+
import { _buildCancelledUnitStopReason, _isPauseOriginCancelledResult } from "../auto/phase-helpers.js";
|
|
6
6
|
|
|
7
7
|
test("aborted agent_end maps errorMessage into structured aborted pause context", () => {
|
|
8
8
|
const withMessage = _buildAbortedPauseContext({ errorMessage: "provider aborted request" });
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import test from "node:test";
|
|
2
2
|
import assert from "node:assert/strict";
|
|
3
3
|
|
|
4
|
-
import { runPreDispatch } from "../auto/
|
|
4
|
+
import { runPreDispatch } from "../auto/pre-dispatch.ts";
|
|
5
5
|
|
|
6
6
|
test("blocked remediation warning uses /gsd dispatch reassess and hides internal tool name", async () => {
|
|
7
7
|
const notifications: Array<{ message: string; level?: string }> = [];
|