@opengsd/gsd-pi 1.0.2-dev.867e002 → 1.0.2-dev.cce3612
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/onboarding.js +22 -3
- package/dist/resources/.managed-resources-content-hash +1 -1
- package/dist/resources/extensions/context7/index.js +12 -2
- package/dist/resources/extensions/get-secrets-from-user.js +16 -16
- package/dist/resources/extensions/google-cli/index.js +30 -0
- package/dist/resources/extensions/google-cli/models.js +55 -0
- package/dist/resources/extensions/google-cli/package.json +11 -0
- package/dist/resources/extensions/google-cli/readiness.js +12 -0
- package/dist/resources/extensions/google-cli/stream-adapter.js +191 -0
- package/dist/resources/extensions/gsd/auto/loop.js +62 -1
- package/dist/resources/extensions/gsd/auto/orchestrator.js +4 -2
- package/dist/resources/extensions/gsd/auto/phases.js +37 -0
- package/dist/resources/extensions/gsd/auto/run-unit.js +8 -0
- package/dist/resources/extensions/gsd/auto/session.js +3 -0
- package/dist/resources/extensions/gsd/auto-dispatch.js +17 -7
- package/dist/resources/extensions/gsd/auto-post-unit.js +18 -2
- package/dist/resources/extensions/gsd/auto-prompts.js +5 -236
- package/dist/resources/extensions/gsd/auto-recovery.js +10 -5
- package/dist/resources/extensions/gsd/auto-start.js +232 -49
- package/dist/resources/extensions/gsd/auto.js +6 -1
- package/dist/resources/extensions/gsd/bootstrap/db-tools.js +4 -3
- package/dist/resources/extensions/gsd/bootstrap/register-extension.js +39 -5
- package/dist/resources/extensions/gsd/bootstrap/register-hooks.js +17 -7
- package/dist/resources/extensions/gsd/bootstrap/system-context.js +3 -27
- package/dist/resources/extensions/gsd/closeout-recovery.js +7 -1
- package/dist/resources/extensions/gsd/commands/handlers/auto.js +9 -1
- package/dist/resources/extensions/gsd/commands-usage.js +105 -1
- package/dist/resources/extensions/gsd/config-overlay.js +20 -14
- package/dist/resources/extensions/gsd/context-overlay.js +22 -16
- package/dist/resources/extensions/gsd/dashboard-overlay.js +10 -23
- package/dist/resources/extensions/gsd/doctor-engine-checks.js +87 -0
- package/dist/resources/extensions/gsd/doctor-providers.js +54 -24
- package/dist/resources/extensions/gsd/doctor.js +6 -1
- package/dist/resources/extensions/gsd/git-conflict-state.js +26 -1
- package/dist/resources/extensions/gsd/guided-flow.js +5 -6
- package/dist/resources/extensions/gsd/key-manager.js +45 -13
- package/dist/resources/extensions/gsd/milestone-reopen-events.js +28 -0
- package/dist/resources/extensions/gsd/notification-overlay.js +8 -9
- package/dist/resources/extensions/gsd/parallel-monitor-overlay.js +15 -13
- package/dist/resources/extensions/gsd/preferences-skills.js +11 -4
- package/dist/resources/extensions/gsd/preferences.js +14 -2
- package/dist/resources/extensions/gsd/prompt-loader.js +2 -0
- package/dist/resources/extensions/gsd/prompts/discuss.md +4 -2
- package/dist/resources/extensions/gsd/prompts/guided-discuss-milestone.md +2 -0
- package/dist/resources/extensions/gsd/prompts/system.md +1 -3
- package/dist/resources/extensions/gsd/queue-reorder-ui.js +28 -18
- package/dist/resources/extensions/gsd/repository-registry.js +3 -1
- package/dist/resources/extensions/gsd/skill-activation.js +233 -0
- package/dist/resources/extensions/gsd/skill-catalog.data.js +820 -0
- package/dist/resources/extensions/gsd/skill-catalog.install.js +179 -0
- package/dist/resources/extensions/gsd/skill-catalog.js +5 -1028
- package/dist/resources/extensions/gsd/skill-discovery.js +121 -79
- package/dist/resources/extensions/gsd/skill-scope.js +52 -0
- package/dist/resources/extensions/gsd/skill-telemetry.js +6 -39
- package/dist/resources/extensions/gsd/skills.js +60 -0
- package/dist/resources/extensions/gsd/state-reconciliation/drift/artifact-db.js +351 -0
- package/dist/resources/extensions/gsd/state-reconciliation/index.js +41 -0
- package/dist/resources/extensions/gsd/state-reconciliation/registry.js +4 -0
- package/dist/resources/extensions/gsd/tools/complete-task.js +9 -0
- package/dist/resources/extensions/gsd/tools/workflow-tool-executors.js +63 -2
- package/dist/resources/extensions/gsd/tui/render-kit.js +51 -0
- package/dist/resources/extensions/gsd/unit-context-manifest.js +35 -26
- package/dist/resources/extensions/gsd/user-input-boundary.js +1 -1
- package/dist/resources/extensions/gsd/vision-ask.js +22 -0
- package/dist/resources/extensions/gsd/visualizer-overlay.js +8 -36
- package/dist/resources/extensions/gsd/worktree-lifecycle.js +24 -3
- package/dist/resources/extensions/search-the-web/native-search.js +57 -8
- package/dist/resources/extensions/shared/confirm-ui.js +9 -6
- package/dist/resources/extensions/shared/dialog-frame.js +42 -0
- package/dist/resources/extensions/shared/interview-ui.js +42 -30
- package/dist/resources/extensions/shared/next-action-ui.js +6 -6
- package/dist/resources/skills/create-skill/references/gsd-skill-ecosystem.md +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/chunks/1834.js +2 -2
- 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 +1 -1
- 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/session/agent-session-extensions.d.ts +1 -0
- package/packages/gsd-agent-core/dist/session/agent-session-extensions.d.ts.map +1 -1
- package/packages/gsd-agent-core/dist/session/agent-session-extensions.js +22 -8
- package/packages/gsd-agent-core/dist/session/agent-session-extensions.js.map +1 -1
- package/packages/gsd-agent-core/package.json +5 -5
- package/packages/gsd-agent-modes/dist/modes/interactive/components/dialog-container.d.ts +12 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/dialog-container.d.ts.map +1 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/dialog-container.js +45 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/dialog-container.js.map +1 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-editor.d.ts +3 -2
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-editor.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-editor.js +11 -11
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-editor.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-input.d.ts +3 -3
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-input.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-input.js +13 -11
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-input.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-selector.d.ts +3 -3
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-selector.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-selector.js +12 -10
- package/packages/gsd-agent-modes/dist/modes/interactive/components/extension-selector.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/index.d.ts +1 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/index.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/index.js +1 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/components/index.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/login-dialog.d.ts +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/login-dialog.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/login-dialog.js +2 -2
- package/packages/gsd-agent-modes/dist/modes/interactive/components/login-dialog.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/oauth-selector.d.ts +6 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/oauth-selector.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/oauth-selector.js +9 -6
- package/packages/gsd-agent-modes/dist/modes/interactive/components/oauth-selector.js.map +1 -1
- 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 +0 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/components/transcript-design.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-auth.d.ts +3 -0
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-auth.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-auth.js +144 -2
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-auth.js.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-session.d.ts.map +1 -1
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-session.js +2 -14
- package/packages/gsd-agent-modes/dist/modes/interactive/interactive-selectors-session.js.map +1 -1
- package/packages/gsd-agent-modes/package.json +7 -7
- package/packages/mcp-server/dist/workflow-tools.js +1 -1
- package/packages/mcp-server/dist/workflow-tools.js.map +1 -1
- package/packages/mcp-server/package.json +3 -3
- package/packages/native/package.json +1 -1
- package/packages/pi-agent-core/dist/harness/skills.d.ts.map +1 -1
- package/packages/pi-agent-core/dist/harness/skills.js +6 -0
- package/packages/pi-agent-core/dist/harness/skills.js.map +1 -1
- package/packages/pi-agent-core/dist/harness/system-prompt.d.ts +7 -0
- package/packages/pi-agent-core/dist/harness/system-prompt.d.ts.map +1 -1
- package/packages/pi-agent-core/dist/harness/system-prompt.js +7 -0
- package/packages/pi-agent-core/dist/harness/system-prompt.js.map +1 -1
- package/packages/pi-agent-core/package.json +1 -1
- package/packages/pi-ai/dist/models.generated.d.ts +8 -59
- package/packages/pi-ai/dist/models.generated.d.ts.map +1 -1
- package/packages/pi-ai/dist/models.generated.js +21 -72
- package/packages/pi-ai/dist/models.generated.js.map +1 -1
- package/packages/pi-ai/dist/providers/anthropic.d.ts.map +1 -1
- package/packages/pi-ai/dist/providers/anthropic.js +50 -0
- package/packages/pi-ai/dist/providers/anthropic.js.map +1 -1
- package/packages/pi-ai/dist/providers/openai-responses-shared.d.ts.map +1 -1
- package/packages/pi-ai/dist/providers/openai-responses-shared.js +28 -4
- package/packages/pi-ai/dist/providers/openai-responses-shared.js.map +1 -1
- package/packages/pi-ai/dist/types.d.ts +2 -0
- package/packages/pi-ai/dist/types.d.ts.map +1 -1
- package/packages/pi-ai/dist/types.js.map +1 -1
- package/packages/pi-ai/package.json +1 -1
- package/packages/pi-coding-agent/README.md +1 -1
- package/packages/pi-coding-agent/dist/core/extensions/extension-upstream-types.d.ts +2 -2
- package/packages/pi-coding-agent/dist/core/extensions/extension-upstream-types.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/core/extensions/extension-upstream-types.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/extensions/loader.js +1 -1
- package/packages/pi-coding-agent/dist/core/extensions/loader.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/extensions/runner.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/core/extensions/runner.js +8 -2
- package/packages/pi-coding-agent/dist/core/extensions/runner.js.map +1 -1
- package/packages/pi-coding-agent/dist/core/skills.d.ts +3 -0
- package/packages/pi-coding-agent/dist/core/skills.d.ts.map +1 -1
- package/packages/pi-coding-agent/dist/core/skills.js +3 -0
- package/packages/pi-coding-agent/dist/core/skills.js.map +1 -1
- package/packages/pi-coding-agent/package.json +7 -7
- package/packages/pi-tui/package.json +1 -1
- package/packages/rpc-client/package.json +2 -2
- package/pkg/package.json +1 -1
- package/src/resources/extensions/context7/index.ts +15 -2
- package/src/resources/extensions/get-secrets-from-user.ts +17 -16
- package/src/resources/extensions/google-cli/index.ts +34 -0
- package/src/resources/extensions/google-cli/models.ts +57 -0
- package/src/resources/extensions/google-cli/package.json +11 -0
- package/src/resources/extensions/google-cli/readiness.ts +15 -0
- package/src/resources/extensions/google-cli/stream-adapter.ts +245 -0
- package/src/resources/extensions/gsd/auto/loop.ts +74 -1
- package/src/resources/extensions/gsd/auto/orchestrator.ts +4 -2
- package/src/resources/extensions/gsd/auto/phases.ts +46 -0
- package/src/resources/extensions/gsd/auto/run-unit.ts +10 -0
- package/src/resources/extensions/gsd/auto/session.ts +3 -0
- package/src/resources/extensions/gsd/auto-dispatch.ts +31 -11
- package/src/resources/extensions/gsd/auto-post-unit.ts +37 -2
- package/src/resources/extensions/gsd/auto-prompts.ts +4 -284
- package/src/resources/extensions/gsd/auto-recovery.ts +10 -7
- package/src/resources/extensions/gsd/auto-start.ts +307 -56
- package/src/resources/extensions/gsd/auto.ts +6 -1
- package/src/resources/extensions/gsd/bootstrap/db-tools.ts +4 -3
- package/src/resources/extensions/gsd/bootstrap/register-extension.ts +42 -5
- package/src/resources/extensions/gsd/bootstrap/register-hooks.ts +18 -6
- package/src/resources/extensions/gsd/bootstrap/system-context.ts +3 -28
- package/src/resources/extensions/gsd/closeout-recovery.ts +6 -1
- package/src/resources/extensions/gsd/commands/handlers/auto.ts +9 -1
- package/src/resources/extensions/gsd/commands-usage.ts +110 -5
- package/src/resources/extensions/gsd/config-overlay.ts +19 -16
- package/src/resources/extensions/gsd/context-overlay.ts +24 -19
- package/src/resources/extensions/gsd/dashboard-overlay.ts +14 -27
- package/src/resources/extensions/gsd/doctor-engine-checks.ts +99 -0
- package/src/resources/extensions/gsd/doctor-providers.ts +55 -27
- package/src/resources/extensions/gsd/doctor-types.ts +2 -0
- package/src/resources/extensions/gsd/doctor.ts +6 -1
- package/src/resources/extensions/gsd/git-conflict-state.ts +25 -1
- package/src/resources/extensions/gsd/guided-flow.ts +5 -6
- package/src/resources/extensions/gsd/key-manager.ts +57 -14
- package/src/resources/extensions/gsd/milestone-reopen-events.ts +28 -0
- package/src/resources/extensions/gsd/notification-overlay.ts +12 -11
- package/src/resources/extensions/gsd/parallel-monitor-overlay.ts +16 -12
- package/src/resources/extensions/gsd/preferences-skills.ts +11 -4
- package/src/resources/extensions/gsd/preferences.ts +17 -2
- package/src/resources/extensions/gsd/prompt-loader.ts +2 -0
- package/src/resources/extensions/gsd/prompts/discuss.md +4 -2
- package/src/resources/extensions/gsd/prompts/guided-discuss-milestone.md +2 -0
- package/src/resources/extensions/gsd/prompts/system.md +1 -3
- package/src/resources/extensions/gsd/queue-reorder-ui.ts +29 -20
- package/src/resources/extensions/gsd/repository-registry.ts +3 -1
- package/src/resources/extensions/gsd/skill-activation.ts +292 -0
- package/src/resources/extensions/gsd/skill-catalog.data.ts +858 -0
- package/src/resources/extensions/gsd/skill-catalog.install.ts +205 -0
- package/src/resources/extensions/gsd/skill-catalog.ts +16 -1087
- package/src/resources/extensions/gsd/skill-discovery.ts +134 -78
- package/src/resources/extensions/gsd/skill-scope.ts +63 -0
- package/src/resources/extensions/gsd/skill-telemetry.ts +6 -40
- package/src/resources/extensions/gsd/skills.ts +75 -0
- package/src/resources/extensions/gsd/state-reconciliation/drift/artifact-db.ts +499 -0
- package/src/resources/extensions/gsd/state-reconciliation/index.ts +40 -0
- package/src/resources/extensions/gsd/state-reconciliation/registry.ts +8 -0
- package/src/resources/extensions/gsd/state-reconciliation/types.ts +30 -0
- package/src/resources/extensions/gsd/tests/auto-loop.test.ts +328 -2
- package/src/resources/extensions/gsd/tests/auto-orchestrator.test.ts +21 -0
- package/src/resources/extensions/gsd/tests/auto-post-unit-artifact-diagnostic.test.ts +28 -2
- package/src/resources/extensions/gsd/tests/auto-recovery.test.ts +41 -0
- package/src/resources/extensions/gsd/tests/auto-start-orphan-bootstrap.test.ts +436 -0
- package/src/resources/extensions/gsd/tests/closeout-recovery.test.ts +15 -0
- package/src/resources/extensions/gsd/tests/collect-from-manifest.test.ts +31 -0
- package/src/resources/extensions/gsd/tests/commands-context.test.ts +5 -3
- package/src/resources/extensions/gsd/tests/commands-dispatcher-workspace-git.test.ts +15 -2
- package/src/resources/extensions/gsd/tests/commands-usage.test.ts +97 -0
- package/src/resources/extensions/gsd/tests/context-chart.test.ts +9 -0
- package/src/resources/extensions/gsd/tests/dashboard-overlay.test.ts +25 -0
- package/src/resources/extensions/gsd/tests/discord-invite-links.test.ts +1 -0
- package/src/resources/extensions/gsd/tests/discuss-prompt.test.ts +4 -2
- package/src/resources/extensions/gsd/tests/discuss-tool-scoping.test.ts +1 -1
- package/src/resources/extensions/gsd/tests/doctor-providers.test.ts +105 -0
- package/src/resources/extensions/gsd/tests/doctor-scope-db-unavailable.test.ts +101 -1
- package/src/resources/extensions/gsd/tests/guided-discuss-milestone-prompt-rendering.test.ts +6 -0
- package/src/resources/extensions/gsd/tests/key-manager.test.ts +23 -4
- package/src/resources/extensions/gsd/tests/notification-overlay.test.ts +6 -1
- package/src/resources/extensions/gsd/tests/orphaned-worktree-audit.test.ts +70 -10
- package/src/resources/extensions/gsd/tests/parallel-monitor-overlay.test.ts +7 -1
- package/src/resources/extensions/gsd/tests/post-unit-retry-on-orchestrator-bridge.test.ts +93 -0
- package/src/resources/extensions/gsd/tests/queue-reorder-ui.test.ts +46 -0
- package/src/resources/extensions/gsd/tests/register-extension-guard.test.ts +116 -11
- package/src/resources/extensions/gsd/tests/repository-registry.test.ts +30 -1
- package/src/resources/extensions/gsd/tests/show-config-command.test.ts +4 -0
- package/src/resources/extensions/gsd/tests/skill-discovery.test.ts +111 -0
- package/src/resources/extensions/gsd/tests/skill-scope-auto.test.ts +67 -0
- package/src/resources/extensions/gsd/tests/skills.test.ts +55 -0
- package/src/resources/extensions/gsd/tests/start-auto-detached.test.ts +13 -2
- package/src/resources/extensions/gsd/tests/state-reconciliation-drift.test.ts +303 -0
- package/src/resources/extensions/gsd/tests/token-tool-gating.test.ts +19 -0
- package/src/resources/extensions/gsd/tests/tool-param-optionality.test.ts +24 -1
- package/src/resources/extensions/gsd/tests/tui-border-assertions.ts +28 -0
- package/src/resources/extensions/gsd/tests/tui-render-kit.test.ts +14 -0
- package/src/resources/extensions/gsd/tests/unit-context-manifest.test.ts +18 -0
- package/src/resources/extensions/gsd/tests/user-input-boundary.test.ts +26 -0
- package/src/resources/extensions/gsd/tests/vision-ask.test.ts +23 -0
- package/src/resources/extensions/gsd/tests/visualizer-overlay.test.ts +6 -1
- package/src/resources/extensions/gsd/tests/workflow-mcp-auto-prep.test.ts +74 -1
- package/src/resources/extensions/gsd/tests/workflow-tool-executors.test.ts +82 -0
- package/src/resources/extensions/gsd/tests/workspace-git-preflight.test.ts +16 -1
- package/src/resources/extensions/gsd/tests/worktree-lifecycle.test.ts +28 -0
- package/src/resources/extensions/gsd/tests/zombie-gsd-state.test.ts +45 -1
- package/src/resources/extensions/gsd/tools/complete-task.ts +9 -0
- package/src/resources/extensions/gsd/tools/workflow-tool-executors.ts +82 -5
- package/src/resources/extensions/gsd/tui/render-kit.ts +82 -0
- package/src/resources/extensions/gsd/unit-context-manifest.ts +37 -26
- package/src/resources/extensions/gsd/user-input-boundary.ts +1 -1
- package/src/resources/extensions/gsd/vision-ask.ts +28 -0
- package/src/resources/extensions/gsd/visualizer-overlay.ts +12 -40
- package/src/resources/extensions/gsd/worktree-lifecycle.ts +37 -2
- package/src/resources/extensions/search-the-web/native-search.ts +60 -8
- package/src/resources/extensions/shared/confirm-ui.ts +8 -12
- package/src/resources/extensions/shared/dialog-frame.ts +71 -0
- package/src/resources/extensions/shared/interview-ui.ts +43 -42
- package/src/resources/extensions/shared/next-action-ui.ts +6 -6
- package/src/resources/extensions/shared/tests/confirm-ui.test.ts +57 -0
- package/src/resources/extensions/shared/tests/interview-ui-border.test.ts +163 -0
- package/src/resources/extensions/shared/tests/next-action-ui-hasui.test.ts +55 -0
- package/src/resources/skills/create-skill/references/gsd-skill-ecosystem.md +1 -1
- /package/dist/web/standalone/.next/static/{praHP_OATcjBkvAVejjGK → orfEoZqDIo6Be_Z9ZFipD}/_buildManifest.js +0 -0
- /package/dist/web/standalone/.next/static/{praHP_OATcjBkvAVejjGK → orfEoZqDIo6Be_Z9ZFipD}/_ssgManifest.js +0 -0
|
@@ -33,6 +33,7 @@ import { resolveWorktreeProjectRoot } from "../worktree-root.js";
|
|
|
33
33
|
import { extractSubagentAgentClasses } from "./subagent-input.js";
|
|
34
34
|
import { approvalGateIdForUnit, isExplicitApprovalResponse, shouldPauseForUserApprovalQuestion } from "../user-input-boundary.js";
|
|
35
35
|
import { resolveSkillManifest } from "../skill-manifest.js";
|
|
36
|
+
import { applyUnitSkillVisibility, unitHasSkillManifest } from "../skill-scope.js";
|
|
36
37
|
import { getGuidedUnitContext } from "../guided-unit-context.js";
|
|
37
38
|
import { registerPlanMilestoneSchemaRecovery } from "./plan-milestone-schema-recovery.js";
|
|
38
39
|
|
|
@@ -357,8 +358,7 @@ export function scopeGsdWorkflowToolsForDispatch(
|
|
|
357
358
|
? buildMinimalAutoGsdToolSet(current, unitType, registeredToolNames)
|
|
358
359
|
: buildMinimalGsdWorkflowToolSet(current, registeredToolNames);
|
|
359
360
|
const toolsChanged = !(scoped.length === current.length && scoped.every((name, index) => name === current[index]));
|
|
360
|
-
const
|
|
361
|
-
const canScopeSkills = skillManifest !== null && pi.getVisibleSkills && pi.setVisibleSkills;
|
|
361
|
+
const canScopeSkills = unitHasSkillManifest(unitType) && pi.getVisibleSkills && pi.setVisibleSkills;
|
|
362
362
|
if (!toolsChanged && !canScopeSkills) {
|
|
363
363
|
return null;
|
|
364
364
|
}
|
|
@@ -366,8 +366,8 @@ export function scopeGsdWorkflowToolsForDispatch(
|
|
|
366
366
|
pi.setActiveTools(scoped);
|
|
367
367
|
}
|
|
368
368
|
const visibleSkills = canScopeSkills ? pi.getVisibleSkills!() : undefined;
|
|
369
|
-
if (canScopeSkills) {
|
|
370
|
-
pi.setVisibleSkills
|
|
369
|
+
if (canScopeSkills && pi.setVisibleSkills) {
|
|
370
|
+
applyUnitSkillVisibility({ setVisibleSkills: pi.setVisibleSkills }, unitType);
|
|
371
371
|
}
|
|
372
372
|
return {
|
|
373
373
|
tools: toolsChanged ? current : null,
|
|
@@ -615,9 +615,21 @@ export function registerHooks(
|
|
|
615
615
|
// project MCP config that /gsd mcp init would write.
|
|
616
616
|
await prepareWorkflowMcpForHookContext(ctx, beforeAgentBasePath);
|
|
617
617
|
|
|
618
|
+
let systemPrompt = event.systemPrompt;
|
|
619
|
+
const { appendDiscoveredSkillsFallback, hasSkillSnapshot, refreshCatalogForNewSkills } = await import("../skill-discovery.js");
|
|
620
|
+
if (hasSkillSnapshot()) {
|
|
621
|
+
const loadedSkills = await refreshCatalogForNewSkills({
|
|
622
|
+
reload: () => (ctx as ExtensionContext & { reload: () => Promise<void> }).reload(),
|
|
623
|
+
notify: (message, level) => ctx.ui.notify(message, level),
|
|
624
|
+
});
|
|
625
|
+
if (loadedSkills.length > 0) {
|
|
626
|
+
systemPrompt = appendDiscoveredSkillsFallback(ctx.getSystemPrompt(), loadedSkills);
|
|
627
|
+
}
|
|
628
|
+
}
|
|
629
|
+
|
|
618
630
|
// GSD's own context injection (existing behavior — unchanged).
|
|
619
631
|
const { buildBeforeAgentStartResult } = await import("./system-context.js");
|
|
620
|
-
const gsdResult = await buildBeforeAgentStartResult(event, ctx);
|
|
632
|
+
const gsdResult = await buildBeforeAgentStartResult({ ...event, systemPrompt }, ctx);
|
|
621
633
|
|
|
622
634
|
// Refresh the snapshot used by ecosystem getPhase()/getActiveUnit().
|
|
623
635
|
// deriveState has its own ~100ms cache so this is cheap on repeat calls.
|
|
@@ -630,7 +642,7 @@ export function registerHooks(
|
|
|
630
642
|
|
|
631
643
|
// Chain ecosystem handlers using pi's runner.ts chaining protocol:
|
|
632
644
|
// each handler sees the systemPrompt mutated by prior handlers.
|
|
633
|
-
let currentSystemPrompt = gsdResult?.systemPrompt ??
|
|
645
|
+
let currentSystemPrompt = gsdResult?.systemPrompt ?? systemPrompt;
|
|
634
646
|
// `any` because pi's BeforeAgentStartEventResult.message uses an internal
|
|
635
647
|
// CustomMessage type that's not re-exported (see ecosystem/gsd-extension-api.ts).
|
|
636
648
|
let lastMessage: any = gsdResult?.message;
|
|
@@ -11,11 +11,9 @@ import { loadPrompt, getTemplatesDir } from "../prompt-loader.js";
|
|
|
11
11
|
import { readForensicsMarker } from "../forensics.js";
|
|
12
12
|
import { resolveAllSkillReferences, renderPreferencesForSystemPrompt, loadEffectiveGSDPreferences } from "../preferences.js";
|
|
13
13
|
import { resolveModelWithFallbacksForUnit } from "../preferences-models.js";
|
|
14
|
-
import { resolveSkillReference } from "../preferences-skills.js";
|
|
15
14
|
import { resolveGsdRootFile, resolveSliceFile, resolveSlicePath, resolveTaskFile, resolveTaskFiles, resolveTasksDir, relSliceFile, relSlicePath, relTaskFile } from "../paths.js";
|
|
16
15
|
import { extractIntroAndRules } from "../knowledge-parser.js";
|
|
17
16
|
import { ensureCodebaseMapFresh, readCodebaseMap } from "../codebase-generator.js";
|
|
18
|
-
import { hasSkillSnapshot, detectNewSkills, formatSkillsXml } from "../skill-discovery.js";
|
|
19
17
|
import { getActiveAutoWorktreeContext } from "../auto-worktree.js";
|
|
20
18
|
import { getActiveWorktreeName, getWorktreeOriginalCwd } from "../worktree-session-state.js";
|
|
21
19
|
import { deriveState } from "../state.js";
|
|
@@ -72,20 +70,6 @@ export const BUNDLED_SKILL_TRIGGERS: Array<{ trigger: string; skill: string }> =
|
|
|
72
70
|
{ trigger: "Deep code optimization audit — perf anti-patterns, memory leaks, algorithmic complexity, bundle size, I/O, caching, dead code (parallel pattern-based hunt)", skill: "code-optimizer" },
|
|
73
71
|
];
|
|
74
72
|
|
|
75
|
-
function buildBundledSkillsTable(): string {
|
|
76
|
-
const cwd = process.cwd();
|
|
77
|
-
const rows: string[] = [];
|
|
78
|
-
for (const { trigger, skill } of BUNDLED_SKILL_TRIGGERS) {
|
|
79
|
-
const resolution = resolveSkillReference(skill, cwd);
|
|
80
|
-
if (resolution.method === "unresolved") continue; // skill not installed — omit from prompt
|
|
81
|
-
rows.push(`| ${trigger} | \`${resolution.resolvedPath}\` |`);
|
|
82
|
-
}
|
|
83
|
-
if (rows.length === 0) {
|
|
84
|
-
return "*No bundled skills found. Install or sync skills to `~/.gsd/agent/skills/`, `~/.agents/skills/`, or `~/.claude/skills/`.*";
|
|
85
|
-
}
|
|
86
|
-
return `| Trigger | Skill to load |\n|---|---|\n${rows.join("\n")}`;
|
|
87
|
-
}
|
|
88
|
-
|
|
89
73
|
function warnDeprecatedAgentInstructions(): void {
|
|
90
74
|
const paths = [
|
|
91
75
|
join(gsdHome(), "agent-instructions.md"),
|
|
@@ -110,7 +94,6 @@ export async function buildBeforeAgentStartResult(
|
|
|
110
94
|
|
|
111
95
|
const stopContextTimer = debugTime("context-inject");
|
|
112
96
|
const systemContent = loadPrompt("system", {
|
|
113
|
-
bundledSkillsTable: buildBundledSkillsTable(),
|
|
114
97
|
templatesDir: getTemplatesDir(),
|
|
115
98
|
shortcutDashboard: formatShortcut("Ctrl+Alt+G"),
|
|
116
99
|
shortcutShell: formatShortcut("Ctrl+Alt+B"),
|
|
@@ -141,7 +124,7 @@ export async function buildBeforeAgentStartResult(
|
|
|
141
124
|
if (loadedPreferences) {
|
|
142
125
|
const cwd = basePath;
|
|
143
126
|
const report = resolveAllSkillReferences(loadedPreferences.preferences, cwd);
|
|
144
|
-
preferenceBlock = `\n\n${renderPreferencesForSystemPrompt(loadedPreferences.preferences, report.resolutions)}`;
|
|
127
|
+
preferenceBlock = `\n\n${renderPreferencesForSystemPrompt(loadedPreferences.preferences, report.resolutions, { includeResolvedPaths: false })}`;
|
|
145
128
|
if (report.warnings.length > 0) {
|
|
146
129
|
ctx.ui.notify(
|
|
147
130
|
`GSD skill preferences: ${report.warnings.length} unresolved skill${report.warnings.length === 1 ? "" : "s"}: ${report.warnings.join(", ")}`,
|
|
@@ -201,14 +184,6 @@ export async function buildBeforeAgentStartResult(
|
|
|
201
184
|
);
|
|
202
185
|
}
|
|
203
186
|
|
|
204
|
-
let newSkillsBlock = "";
|
|
205
|
-
if (hasSkillSnapshot()) {
|
|
206
|
-
const newSkills = detectNewSkills();
|
|
207
|
-
if (newSkills.length > 0) {
|
|
208
|
-
newSkillsBlock = formatSkillsXml(newSkills);
|
|
209
|
-
}
|
|
210
|
-
}
|
|
211
|
-
|
|
212
187
|
let codebaseBlock = "";
|
|
213
188
|
try {
|
|
214
189
|
const codebaseOptions = loadedPreferences?.preferences?.codebase
|
|
@@ -264,13 +239,13 @@ export async function buildBeforeAgentStartResult(
|
|
|
264
239
|
// Keeping it out of `fullSystem` preserves provider prompt-cache stability
|
|
265
240
|
// for the static system/tool prefix. The dynamic memory block rides the
|
|
266
241
|
// volatile context message instead. (#5019)
|
|
267
|
-
const fullSystem = `${event.systemPrompt}\n\n[SYSTEM CONTEXT — GSD]\n\n${systemContent}${preferenceBlock}${knowledgeBlock}${codebaseBlock}${
|
|
242
|
+
const fullSystem = `${event.systemPrompt}\n\n[SYSTEM CONTEXT — GSD]\n\n${systemContent}${preferenceBlock}${knowledgeBlock}${codebaseBlock}${worktreeBlock}${subagentModelBlock}`;
|
|
268
243
|
|
|
269
244
|
stopContextTimer({
|
|
270
245
|
systemPromptSize: fullSystem.length,
|
|
271
246
|
injectionSize: injection?.length ?? forensicsInjection?.length ?? 0,
|
|
272
247
|
hasPreferences: preferenceBlock.length > 0,
|
|
273
|
-
hasNewSkills:
|
|
248
|
+
hasNewSkills: false,
|
|
274
249
|
});
|
|
275
250
|
|
|
276
251
|
const contextMessage = buildContextMessage({ memoryBlock, injection, forensicsInjection });
|
|
@@ -205,7 +205,12 @@ export function getCloseoutManualResolveBlocker(basePath: string): string | null
|
|
|
205
205
|
return `Unmerged paths remain in ${basePath}: ${conflictProbe.unmerged.slice(0, 5).join(", ")}`;
|
|
206
206
|
}
|
|
207
207
|
|
|
208
|
-
|
|
208
|
+
let status: string;
|
|
209
|
+
try {
|
|
210
|
+
status = runGit(basePath, ["status", "--porcelain"]);
|
|
211
|
+
} catch {
|
|
212
|
+
return `Could not inspect git status in ${basePath}.`;
|
|
213
|
+
}
|
|
209
214
|
if (status) {
|
|
210
215
|
return `Working tree still has uncommitted changes in ${basePath}. Commit, stash, or run /gsd closeout retry first.`;
|
|
211
216
|
}
|
|
@@ -208,7 +208,15 @@ export async function handleAutoCommand(trimmed: string, ctx: ExtensionCommandCo
|
|
|
208
208
|
|
|
209
209
|
if (trimmed === "") {
|
|
210
210
|
if (!(await guardRemoteSession(ctx, pi))) return true;
|
|
211
|
-
|
|
211
|
+
const basePath = projectRoot();
|
|
212
|
+
const { hasGsdBootstrapArtifacts } = await import("../../detection.js");
|
|
213
|
+
const { gsdRoot } = await import("../../paths.js");
|
|
214
|
+
if (!hasGsdBootstrapArtifacts(gsdRoot(basePath))) {
|
|
215
|
+
const { showSmartEntry } = await import("../../guided-flow.js");
|
|
216
|
+
await showSmartEntry(ctx, pi, basePath, { step: true });
|
|
217
|
+
return true;
|
|
218
|
+
}
|
|
219
|
+
if (await hasUnresolvedCloseoutBlocker(ctx, basePath)) return true;
|
|
212
220
|
const { showGsdHome } = await import("../../gsd-command-home.js");
|
|
213
221
|
await showGsdHome(ctx, pi, projectRoot());
|
|
214
222
|
return true;
|
|
@@ -4,10 +4,12 @@
|
|
|
4
4
|
* Shows current LLM context window usage and session token totals.
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
|
-
import type { ExtensionCommandContext, ContextUsage, SessionEntry } from "@gsd/pi-coding-agent";
|
|
7
|
+
import type { ExtensionCommandContext, ContextUsage, SessionEntry, Theme } from "@gsd/pi-coding-agent";
|
|
8
|
+
import { Key, matchesKey } from "@gsd/pi-tui";
|
|
8
9
|
|
|
9
10
|
import { formatCost, formatPercent, formatTokenCount } from "./metrics.js";
|
|
10
11
|
import { loadEffectiveGSDPreferences } from "./preferences.js";
|
|
12
|
+
import { renderDialogFrame, renderKeyHints } from "./tui/render-kit.js";
|
|
11
13
|
|
|
12
14
|
export interface SessionTokenTotals {
|
|
13
15
|
input: number;
|
|
@@ -160,6 +162,101 @@ export function formatUsageReport(options: {
|
|
|
160
162
|
return lines.join("\n");
|
|
161
163
|
}
|
|
162
164
|
|
|
165
|
+
async function showUsageDialog(
|
|
166
|
+
ctx: ExtensionCommandContext,
|
|
167
|
+
reportText: string,
|
|
168
|
+
): Promise<boolean | undefined> {
|
|
169
|
+
return ctx.ui.custom<boolean>((tui, theme: Theme, _kb, done) => {
|
|
170
|
+
let cachedLines: string[] | undefined;
|
|
171
|
+
let cachedWidth: number | undefined;
|
|
172
|
+
let cachedRows: number | undefined;
|
|
173
|
+
let cachedScrollOffset: number | undefined;
|
|
174
|
+
let scrollOffset = 0;
|
|
175
|
+
let lastMaxScroll = 0;
|
|
176
|
+
let lastVisibleRows = 1;
|
|
177
|
+
|
|
178
|
+
function render(width: number): string[] {
|
|
179
|
+
const terminalRows = process.stdout.rows || 0;
|
|
180
|
+
if (
|
|
181
|
+
cachedLines &&
|
|
182
|
+
cachedWidth === width &&
|
|
183
|
+
cachedRows === terminalRows &&
|
|
184
|
+
cachedScrollOffset === scrollOffset
|
|
185
|
+
) {
|
|
186
|
+
return cachedLines;
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
const contentWidth = Math.max(1, width - 4);
|
|
190
|
+
const body = reportText.split("\n");
|
|
191
|
+
if (body[0] === "Context Usage") body.shift();
|
|
192
|
+
while (body[0] === "") body.shift();
|
|
193
|
+
const maxOverlayRows = terminalRows > 0 ? Math.max(5, Math.floor(terminalRows * 0.8)) : 24;
|
|
194
|
+
const frameRows = 4;
|
|
195
|
+
const visibleRows = Math.max(1, maxOverlayRows - frameRows);
|
|
196
|
+
const maxScroll = Math.max(0, body.length - visibleRows);
|
|
197
|
+
scrollOffset = Math.min(Math.max(scrollOffset, 0), maxScroll);
|
|
198
|
+
lastMaxScroll = maxScroll;
|
|
199
|
+
lastVisibleRows = visibleRows;
|
|
200
|
+
const visible = body.slice(scrollOffset, scrollOffset + visibleRows);
|
|
201
|
+
const scrollable = body.length > visibleRows;
|
|
202
|
+
|
|
203
|
+
cachedLines = renderDialogFrame(theme, "Context Usage", visible, width, {
|
|
204
|
+
footer: renderKeyHints(theme, scrollable ? ["↑↓ scroll", "any key close"] : ["any key close"], contentWidth),
|
|
205
|
+
scroll: { offset: scrollOffset, visibleRows, totalRows: body.length },
|
|
206
|
+
});
|
|
207
|
+
cachedWidth = width;
|
|
208
|
+
cachedRows = terminalRows;
|
|
209
|
+
cachedScrollOffset = scrollOffset;
|
|
210
|
+
return cachedLines;
|
|
211
|
+
}
|
|
212
|
+
|
|
213
|
+
function scrollBy(delta: number): boolean {
|
|
214
|
+
if (lastMaxScroll <= 0) return false;
|
|
215
|
+
const nextOffset = Math.min(Math.max(scrollOffset + delta, 0), lastMaxScroll);
|
|
216
|
+
if (nextOffset !== scrollOffset) {
|
|
217
|
+
scrollOffset = nextOffset;
|
|
218
|
+
cachedLines = undefined;
|
|
219
|
+
cachedScrollOffset = undefined;
|
|
220
|
+
tui.requestRender();
|
|
221
|
+
}
|
|
222
|
+
return true;
|
|
223
|
+
}
|
|
224
|
+
|
|
225
|
+
return {
|
|
226
|
+
render,
|
|
227
|
+
invalidate: () => {
|
|
228
|
+
cachedLines = undefined;
|
|
229
|
+
cachedWidth = undefined;
|
|
230
|
+
cachedRows = undefined;
|
|
231
|
+
cachedScrollOffset = undefined;
|
|
232
|
+
},
|
|
233
|
+
handleInput: (data: string) => {
|
|
234
|
+
if (matchesKey(data, Key.down) || matchesKey(data, "j")) {
|
|
235
|
+
if (scrollBy(1)) return;
|
|
236
|
+
}
|
|
237
|
+
if (matchesKey(data, Key.up) || matchesKey(data, "k")) {
|
|
238
|
+
if (scrollBy(-1)) return;
|
|
239
|
+
}
|
|
240
|
+
if (matchesKey(data, Key.pageDown)) {
|
|
241
|
+
if (scrollBy(lastVisibleRows)) return;
|
|
242
|
+
}
|
|
243
|
+
if (matchesKey(data, Key.pageUp)) {
|
|
244
|
+
if (scrollBy(-lastVisibleRows)) return;
|
|
245
|
+
}
|
|
246
|
+
done(true);
|
|
247
|
+
},
|
|
248
|
+
};
|
|
249
|
+
}, {
|
|
250
|
+
overlay: true,
|
|
251
|
+
overlayOptions: {
|
|
252
|
+
width: "70%",
|
|
253
|
+
minWidth: 64,
|
|
254
|
+
maxHeight: "80%",
|
|
255
|
+
anchor: "center",
|
|
256
|
+
},
|
|
257
|
+
});
|
|
258
|
+
}
|
|
259
|
+
|
|
163
260
|
export async function handleUsage(args: string, ctx: ExtensionCommandContext): Promise<void> {
|
|
164
261
|
const contextUsage = ctx.getContextUsage?.();
|
|
165
262
|
const sessionTotals = scanSessionTokenTotals(ctx.sessionManager.getEntries());
|
|
@@ -187,8 +284,16 @@ export async function handleUsage(args: string, ctx: ExtensionCommandContext): P
|
|
|
187
284
|
return;
|
|
188
285
|
}
|
|
189
286
|
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
287
|
+
const reportText = formatUsageReport({ modelLabel, contextUsage, sessionTotals });
|
|
288
|
+
|
|
289
|
+
if (ctx.hasUI) {
|
|
290
|
+
try {
|
|
291
|
+
const result = await showUsageDialog(ctx, reportText);
|
|
292
|
+
if (result !== undefined) return;
|
|
293
|
+
} catch {
|
|
294
|
+
// Fall back to text notify below when custom overlays are unavailable.
|
|
295
|
+
}
|
|
296
|
+
}
|
|
297
|
+
|
|
298
|
+
ctx.ui.notify(reportText, "info");
|
|
194
299
|
}
|
|
@@ -10,6 +10,7 @@
|
|
|
10
10
|
import type { Theme } from "@gsd/pi-coding-agent";
|
|
11
11
|
import { matchesKey, Key, truncateToWidth } from "@gsd/pi-tui";
|
|
12
12
|
|
|
13
|
+
import { renderDialogFrame, renderKeyHints } from "./tui/render-kit.js";
|
|
13
14
|
import {
|
|
14
15
|
loadEffectiveGSDPreferences,
|
|
15
16
|
loadGlobalGSDPreferences,
|
|
@@ -231,6 +232,7 @@ export class GSDConfigOverlay {
|
|
|
231
232
|
private onClose: () => void;
|
|
232
233
|
private sections: ConfigSection[];
|
|
233
234
|
private cachedLines?: string[];
|
|
235
|
+
private cachedWidth?: number;
|
|
234
236
|
private scrollOffset = 0;
|
|
235
237
|
private disposed = false;
|
|
236
238
|
|
|
@@ -247,6 +249,7 @@ export class GSDConfigOverlay {
|
|
|
247
249
|
|
|
248
250
|
invalidate(): void {
|
|
249
251
|
this.cachedLines = undefined;
|
|
252
|
+
this.cachedWidth = undefined;
|
|
250
253
|
}
|
|
251
254
|
|
|
252
255
|
dispose(): void {
|
|
@@ -286,16 +289,13 @@ export class GSDConfigOverlay {
|
|
|
286
289
|
}
|
|
287
290
|
|
|
288
291
|
render(width: number): string[] {
|
|
289
|
-
if (this.cachedLines) return this.cachedLines;
|
|
292
|
+
if (this.cachedLines && this.cachedWidth === width) return this.cachedLines;
|
|
290
293
|
|
|
291
294
|
const t = this.theme;
|
|
292
|
-
const w = Math.max(
|
|
295
|
+
const w = Math.max(1, width);
|
|
296
|
+
const contentWidth = Math.max(1, w - 4);
|
|
293
297
|
const allLines: string[] = [];
|
|
294
298
|
|
|
295
|
-
// Header
|
|
296
|
-
allLines.push(t.bold(t.fg("accent", " GSD Configuration ")));
|
|
297
|
-
allLines.push(t.fg("muted", "\u2500".repeat(w)));
|
|
298
|
-
|
|
299
299
|
// Find max label width for alignment
|
|
300
300
|
let maxLabel = 0;
|
|
301
301
|
for (const section of this.sections) {
|
|
@@ -306,26 +306,29 @@ export class GSDConfigOverlay {
|
|
|
306
306
|
const labelPad = Math.min(maxLabel + 2, 24);
|
|
307
307
|
|
|
308
308
|
for (const section of this.sections) {
|
|
309
|
-
allLines.push("");
|
|
309
|
+
if (allLines.length > 0) allLines.push("");
|
|
310
310
|
allLines.push(t.bold(t.fg("accent", ` ${section.title}`)));
|
|
311
311
|
|
|
312
312
|
for (const row of section.rows) {
|
|
313
313
|
const label = t.fg("muted", ` ${row.label.padEnd(labelPad)}`);
|
|
314
314
|
const value = row.accent ? t.bold(row.value) : row.value;
|
|
315
|
-
allLines.push(truncateToWidth(`${label}${value}`,
|
|
315
|
+
allLines.push(truncateToWidth(`${label}${value}`, contentWidth));
|
|
316
316
|
}
|
|
317
317
|
}
|
|
318
318
|
|
|
319
|
-
allLines.push("");
|
|
320
|
-
allLines.push(t.fg("muted", ` ${"\u2500".repeat(w - 4)}`));
|
|
321
|
-
allLines.push(t.fg("muted", " esc/q close \u2502 \u2191\u2193/jk scroll \u2502 /gsd prefs to edit"));
|
|
322
|
-
|
|
323
319
|
// Apply scroll
|
|
324
|
-
const
|
|
320
|
+
const terminalRows = process.stdout.rows || 32;
|
|
321
|
+
const maxBodyRows = Math.max(1, Math.min(allLines.length, terminalRows - 12));
|
|
322
|
+
const maxScroll = Math.max(0, allLines.length - maxBodyRows);
|
|
325
323
|
this.scrollOffset = Math.min(this.scrollOffset, maxScroll);
|
|
326
|
-
const visible = allLines.slice(this.scrollOffset);
|
|
324
|
+
const visible = allLines.slice(this.scrollOffset, this.scrollOffset + maxBodyRows);
|
|
325
|
+
const footer = renderKeyHints(t, ["esc/q close", "\u2191\u2193/jk scroll", "/gsd prefs to edit"], contentWidth);
|
|
327
326
|
|
|
328
|
-
this.cachedLines = visible
|
|
329
|
-
|
|
327
|
+
this.cachedLines = renderDialogFrame(t, "GSD Configuration", visible, w, {
|
|
328
|
+
footer,
|
|
329
|
+
scroll: { offset: this.scrollOffset, visibleRows: maxBodyRows, totalRows: allLines.length },
|
|
330
|
+
});
|
|
331
|
+
this.cachedWidth = width;
|
|
332
|
+
return this.cachedLines;
|
|
330
333
|
}
|
|
331
334
|
}
|
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
*/
|
|
4
4
|
|
|
5
5
|
import type { Theme, ThemeColor } from "@gsd/pi-coding-agent";
|
|
6
|
-
import { matchesKey, Key, truncateToWidth
|
|
6
|
+
import { matchesKey, Key, truncateToWidth } from "@gsd/pi-tui";
|
|
7
7
|
|
|
8
8
|
import type { ContextBreakdownReport, ContextSectionBreakdown } from "./commands-context.js";
|
|
9
9
|
import { formatTokenCount } from "./metrics.js";
|
|
10
|
-
import { renderProgressBar, rightAlign } from "./tui/render-kit.js";
|
|
10
|
+
import { renderDialogFrame, renderKeyHints, renderProgressBar, rightAlign } from "./tui/render-kit.js";
|
|
11
11
|
|
|
12
12
|
const SECTION_COLORS: ThemeColor[] = ["accent", "success", "warning", "borderAccent", "text"];
|
|
13
13
|
|
|
@@ -70,6 +70,7 @@ export class GSDContextOverlay {
|
|
|
70
70
|
private onClose: () => void;
|
|
71
71
|
private report: ContextBreakdownReport;
|
|
72
72
|
private cachedLines?: string[];
|
|
73
|
+
private cachedWidth?: number;
|
|
73
74
|
private scrollOffset = 0;
|
|
74
75
|
private disposed = false;
|
|
75
76
|
|
|
@@ -87,6 +88,7 @@ export class GSDContextOverlay {
|
|
|
87
88
|
|
|
88
89
|
invalidate(): void {
|
|
89
90
|
this.cachedLines = undefined;
|
|
91
|
+
this.cachedWidth = undefined;
|
|
90
92
|
}
|
|
91
93
|
|
|
92
94
|
dispose(): void {
|
|
@@ -125,24 +127,22 @@ export class GSDContextOverlay {
|
|
|
125
127
|
}
|
|
126
128
|
|
|
127
129
|
render(width: number): string[] {
|
|
128
|
-
if (this.cachedLines) return this.cachedLines;
|
|
130
|
+
if (this.cachedLines && this.cachedWidth === width) return this.cachedLines;
|
|
129
131
|
|
|
130
132
|
const theme = this.theme;
|
|
131
|
-
const w = Math.max(
|
|
133
|
+
const w = Math.max(1, width);
|
|
134
|
+
const contentWidth = Math.max(1, w - 4);
|
|
132
135
|
const totals = getContextChartTotals(this.report);
|
|
133
136
|
const chartTotal = Math.max(totals.inContext, totals.estimated, 1);
|
|
134
137
|
const lines: string[] = [];
|
|
135
138
|
|
|
136
|
-
lines.push(theme.bold(theme.fg("accent", " Context Breakdown ")));
|
|
137
|
-
lines.push(theme.fg("muted", "─".repeat(w)));
|
|
138
|
-
|
|
139
139
|
if (this.report.modelLabel) {
|
|
140
|
-
lines.push(rightAlign(theme.fg("muted", "Model"), theme.fg("text", this.report.modelLabel),
|
|
140
|
+
lines.push(rightAlign(theme.fg("muted", "Model"), theme.fg("text", this.report.modelLabel), contentWidth));
|
|
141
141
|
}
|
|
142
142
|
|
|
143
143
|
lines.push("");
|
|
144
144
|
if (totals.window != null) {
|
|
145
|
-
const usageBarWidth = Math.max(
|
|
145
|
+
const usageBarWidth = Math.max(8, contentWidth - 28);
|
|
146
146
|
const usageBar = renderProgressBar(theme, totals.inContext, totals.window, usageBarWidth, {
|
|
147
147
|
filledColor: totals.inContext / totals.window > 0.85 ? "warning" : "accent",
|
|
148
148
|
});
|
|
@@ -151,7 +151,7 @@ export class GSDContextOverlay {
|
|
|
151
151
|
lines.push(` ${theme.fg("muted", "Estimated")} ${theme.fg("text", formatTokenCount(chartTotal))}`);
|
|
152
152
|
}
|
|
153
153
|
|
|
154
|
-
const splitWidth = Math.max(
|
|
154
|
+
const splitWidth = Math.max(8, Math.floor((contentWidth - 8) / 2));
|
|
155
155
|
const systemBar = renderProgressBar(theme, totals.systemTokens, chartTotal, splitWidth, { filledColor: "accent" });
|
|
156
156
|
const convBar = renderProgressBar(theme, totals.conversationTokens, chartTotal, splitWidth, { filledColor: "success" });
|
|
157
157
|
lines.push("");
|
|
@@ -160,11 +160,11 @@ export class GSDContextOverlay {
|
|
|
160
160
|
|
|
161
161
|
lines.push("");
|
|
162
162
|
lines.push(theme.bold(theme.fg("accent", " System prompt")));
|
|
163
|
-
lines.push(...renderSectionBars(theme, this.report.systemSections, chartTotal,
|
|
163
|
+
lines.push(...renderSectionBars(theme, this.report.systemSections, chartTotal, contentWidth, 22));
|
|
164
164
|
|
|
165
165
|
lines.push("");
|
|
166
166
|
lines.push(theme.bold(theme.fg("accent", " Conversation")));
|
|
167
|
-
lines.push(...renderSectionBars(theme, this.report.conversationSections, chartTotal,
|
|
167
|
+
lines.push(...renderSectionBars(theme, this.report.conversationSections, chartTotal, contentWidth, 22));
|
|
168
168
|
|
|
169
169
|
lines.push("");
|
|
170
170
|
lines.push(theme.bold(theme.fg("accent", " Skills")));
|
|
@@ -172,7 +172,7 @@ export class GSDContextOverlay {
|
|
|
172
172
|
if (skills.available.length > 0) {
|
|
173
173
|
lines.push(` ${theme.fg("muted", "Available")} ${theme.fg("text", `${skills.available.length}`)}`);
|
|
174
174
|
const preview = skills.available.slice(0, 8).join(", ");
|
|
175
|
-
lines.push(truncateToWidth(` ${preview}${skills.available.length > 8 ? "…" : ""}`,
|
|
175
|
+
lines.push(truncateToWidth(` ${preview}${skills.available.length > 8 ? "…" : ""}`, contentWidth));
|
|
176
176
|
} else {
|
|
177
177
|
lines.push(theme.fg("dim", " none in prompt"));
|
|
178
178
|
}
|
|
@@ -187,13 +187,18 @@ export class GSDContextOverlay {
|
|
|
187
187
|
lines.push(theme.bold(theme.fg("accent", " Agents")));
|
|
188
188
|
lines.push(` ${theme.fg("muted", "Subagent spawns")} ${theme.fg("text", String(this.report.subagentSpawns))}`);
|
|
189
189
|
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
const maxScroll = Math.max(0, lines.length - 24);
|
|
190
|
+
const terminalRows = process.stdout.rows || 32;
|
|
191
|
+
const maxBodyRows = Math.max(1, Math.min(lines.length, terminalRows - 12));
|
|
192
|
+
const maxScroll = Math.max(0, lines.length - maxBodyRows);
|
|
195
193
|
this.scrollOffset = Math.min(this.scrollOffset, maxScroll);
|
|
196
|
-
|
|
194
|
+
const visible = lines.slice(this.scrollOffset, this.scrollOffset + maxBodyRows);
|
|
195
|
+
const footer = renderKeyHints(theme, ["esc/q close", "↑↓ scroll", "/gsd context --open"], contentWidth);
|
|
196
|
+
|
|
197
|
+
this.cachedLines = renderDialogFrame(theme, "Context Breakdown", visible, w, {
|
|
198
|
+
footer,
|
|
199
|
+
scroll: { offset: this.scrollOffset, visibleRows: maxBodyRows, totalRows: lines.length },
|
|
200
|
+
});
|
|
201
|
+
this.cachedWidth = width;
|
|
197
202
|
return this.cachedLines;
|
|
198
203
|
}
|
|
199
204
|
}
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
*/
|
|
9
9
|
|
|
10
10
|
import type { Theme } from "@gsd/pi-coding-agent";
|
|
11
|
-
import { truncateToWidth,
|
|
11
|
+
import { truncateToWidth, matchesKey, Key } from "@gsd/pi-tui";
|
|
12
12
|
import { deriveState } from "./state.js";
|
|
13
13
|
import { loadFile } from "./files.js";
|
|
14
14
|
import { isDbAvailable, getMilestoneSlices, getSliceTasks } from "./gsd-db.js";
|
|
@@ -29,6 +29,7 @@ import { estimateTimeRemaining } from "./auto-dashboard.js";
|
|
|
29
29
|
import { computeProgressScore, formatProgressLine } from "./progress-score.js";
|
|
30
30
|
import { runEnvironmentChecks, type EnvironmentCheckResult } from "./doctor-environment.js";
|
|
31
31
|
import { formattedShortcutPair } from "./shortcut-defs.js";
|
|
32
|
+
import { renderDialogFrame, renderKeyHints } from "./tui/render-kit.js";
|
|
32
33
|
|
|
33
34
|
export function unitLabel(type: string): string {
|
|
34
35
|
switch (type) {
|
|
@@ -258,35 +259,26 @@ export class GSDDashboardOverlay {
|
|
|
258
259
|
|
|
259
260
|
const content = this.buildContentLines(width);
|
|
260
261
|
const viewportHeight = Math.max(5, process.stdout.rows ? process.stdout.rows - 8 : 24);
|
|
261
|
-
const
|
|
262
|
-
const visibleContentRows = Math.max(1, viewportHeight - chromeHeight);
|
|
262
|
+
const visibleContentRows = Math.max(1, viewportHeight - 4);
|
|
263
263
|
const maxScroll = Math.max(0, content.length - visibleContentRows);
|
|
264
264
|
this.scrollOffset = Math.min(this.scrollOffset, maxScroll);
|
|
265
265
|
const visibleContent = content.slice(this.scrollOffset, this.scrollOffset + visibleContentRows);
|
|
266
|
-
|
|
267
|
-
const
|
|
266
|
+
const contentWidth = Math.max(1, width - 4);
|
|
267
|
+
const footer = renderKeyHints(
|
|
268
|
+
this.theme,
|
|
269
|
+
["↑↓ scroll", "g/G top/end", `Esc/${formattedShortcutPair("dashboard")} close`],
|
|
270
|
+
contentWidth,
|
|
271
|
+
);
|
|
272
|
+
const lines = renderDialogFrame(this.theme, "GSD Dashboard", visibleContent, width, {
|
|
273
|
+
footer,
|
|
274
|
+
scroll: { offset: this.scrollOffset, visibleRows: visibleContentRows, totalRows: content.length },
|
|
275
|
+
});
|
|
268
276
|
|
|
269
277
|
this.cachedWidth = width;
|
|
270
278
|
this.cachedLines = lines;
|
|
271
279
|
return lines;
|
|
272
280
|
}
|
|
273
281
|
|
|
274
|
-
private wrapInBox(inner: string[], width: number): string[] {
|
|
275
|
-
const th = this.theme;
|
|
276
|
-
const border = (s: string) => th.fg("borderAccent", s);
|
|
277
|
-
const innerWidth = width - 4;
|
|
278
|
-
const lines: string[] = [];
|
|
279
|
-
|
|
280
|
-
lines.push(border("╭" + "─".repeat(width - 2) + "╮"));
|
|
281
|
-
for (const line of inner) {
|
|
282
|
-
const truncated = truncateToWidth(line, innerWidth);
|
|
283
|
-
const padWidth = Math.max(0, innerWidth - visibleWidth(truncated));
|
|
284
|
-
lines.push(border("│") + " " + truncated + " ".repeat(padWidth) + " " + border("│"));
|
|
285
|
-
}
|
|
286
|
-
lines.push(border("╰" + "─".repeat(width - 2) + "╯"));
|
|
287
|
-
return lines;
|
|
288
|
-
}
|
|
289
|
-
|
|
290
282
|
private buildContentLines(width: number): string[] {
|
|
291
283
|
const th = this.theme;
|
|
292
284
|
const shellWidth = width - 4;
|
|
@@ -303,7 +295,6 @@ export class GSDDashboardOverlay {
|
|
|
303
295
|
const hr = () => row(th.fg("dim", "─".repeat(contentWidth)));
|
|
304
296
|
const centered = (content: string) => row(centerLine(content, contentWidth));
|
|
305
297
|
|
|
306
|
-
const title = th.fg("accent", th.bold("GSD Dashboard"));
|
|
307
298
|
const isRemote = !!this.dashData.remoteSession;
|
|
308
299
|
const status = this.dashData.active
|
|
309
300
|
? `${Date.now() % 2000 < 1000 ? th.fg("success", "●") : th.fg("dim", "○")} ${th.fg("success", "AUTO")}`
|
|
@@ -328,7 +319,7 @@ export class GSDDashboardOverlay {
|
|
|
328
319
|
} else if (isRemote) {
|
|
329
320
|
elapsedParts = th.fg("dim", `since ${this.dashData.remoteSession!.startedAt.replace("T", " ").slice(0, 19)}`);
|
|
330
321
|
}
|
|
331
|
-
lines.push(row(joinColumns(`${
|
|
322
|
+
lines.push(row(joinColumns(`${status}${worktreeTag}`, elapsedParts, contentWidth)));
|
|
332
323
|
|
|
333
324
|
// Progress score — traffic light indicator (#1221)
|
|
334
325
|
if (this.dashData.active || this.dashData.paused) {
|
|
@@ -610,10 +601,6 @@ export class GSDDashboardOverlay {
|
|
|
610
601
|
}
|
|
611
602
|
}
|
|
612
603
|
|
|
613
|
-
lines.push(blank());
|
|
614
|
-
lines.push(hr());
|
|
615
|
-
lines.push(centered(th.fg("dim", `↑↓ scroll · g/G top/end · Esc/${formattedShortcutPair("dashboard")} close`)));
|
|
616
|
-
|
|
617
604
|
return lines;
|
|
618
605
|
}
|
|
619
606
|
|