@selesai/code 0.5.28 → 0.6.1
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/CHANGELOG.md +24 -0
- package/README.md +1 -1
- package/dist/cli/args.d.ts.map +1 -1
- package/dist/cli/args.js +9 -1
- package/dist/cli/args.js.map +1 -1
- package/dist/cli/config-selector.d.ts.map +1 -1
- package/dist/cli/config-selector.js +1 -1
- package/dist/cli/config-selector.js.map +1 -1
- package/dist/cli/credential-print.d.ts +23 -0
- package/dist/cli/credential-print.d.ts.map +1 -0
- package/dist/cli/credential-print.js +117 -0
- package/dist/cli/credential-print.js.map +1 -0
- package/dist/cli/startup-ui.d.ts.map +1 -1
- package/dist/cli/startup-ui.js +1 -1
- package/dist/cli/startup-ui.js.map +1 -1
- package/dist/core/agent-session-runtime.d.ts.map +1 -1
- package/dist/core/agent-session-runtime.js +3 -0
- package/dist/core/agent-session-runtime.js.map +1 -1
- package/dist/core/agent-session.d.ts +12 -1
- package/dist/core/agent-session.d.ts.map +1 -1
- package/dist/core/agent-session.js +20 -14
- package/dist/core/agent-session.js.map +1 -1
- package/dist/core/compaction/compaction.d.ts.map +1 -1
- package/dist/core/compaction/compaction.js +11 -3
- package/dist/core/compaction/compaction.js.map +1 -1
- package/dist/core/extensions/runner.d.ts +1 -0
- package/dist/core/extensions/runner.d.ts.map +1 -1
- package/dist/core/extensions/runner.js +11 -0
- package/dist/core/extensions/runner.js.map +1 -1
- package/dist/core/extensions/types.d.ts +14 -1
- package/dist/core/extensions/types.d.ts.map +1 -1
- package/dist/core/extensions/types.js.map +1 -1
- package/dist/core/footer-data-provider.d.ts +10 -0
- package/dist/core/footer-data-provider.d.ts.map +1 -1
- package/dist/core/footer-data-provider.js +1 -1
- package/dist/core/footer-data-provider.js.map +1 -1
- package/dist/core/llama/provider.d.ts.map +1 -1
- package/dist/core/llama/provider.js +8 -3
- package/dist/core/llama/provider.js.map +1 -1
- package/dist/core/model-config.d.ts +30 -0
- package/dist/core/model-config.d.ts.map +1 -1
- package/dist/core/model-config.js +6 -0
- package/dist/core/model-config.js.map +1 -1
- package/dist/core/model-registry.d.ts.map +1 -1
- package/dist/core/model-registry.js +2 -2
- package/dist/core/model-registry.js.map +1 -1
- package/dist/core/model-resolver.d.ts +1 -0
- package/dist/core/model-resolver.d.ts.map +1 -1
- package/dist/core/model-resolver.js +20 -3
- package/dist/core/model-resolver.js.map +1 -1
- package/dist/core/model-runtime.d.ts +2 -0
- package/dist/core/model-runtime.d.ts.map +1 -1
- package/dist/core/model-runtime.js +5 -4
- package/dist/core/model-runtime.js.map +1 -1
- package/dist/core/package-manager.d.ts.map +1 -1
- package/dist/core/package-manager.js +13 -6
- package/dist/core/package-manager.js.map +1 -1
- package/dist/core/remote-catalog-provider.d.ts +1 -1
- package/dist/core/remote-catalog-provider.d.ts.map +1 -1
- package/dist/core/remote-catalog-provider.js +24 -11
- package/dist/core/remote-catalog-provider.js.map +1 -1
- package/dist/core/resource-loader.d.ts +15 -0
- package/dist/core/resource-loader.d.ts.map +1 -1
- package/dist/core/resource-loader.js +66 -9
- package/dist/core/resource-loader.js.map +1 -1
- package/dist/core/settings-manager.d.ts +1 -1
- package/dist/core/settings-manager.d.ts.map +1 -1
- package/dist/core/settings-manager.js.map +1 -1
- package/dist/core/system-prompt.d.ts.map +1 -1
- package/dist/core/system-prompt.js +19 -1
- package/dist/core/system-prompt.js.map +1 -1
- package/dist/core/system-prompt.test.d.ts +2 -0
- package/dist/core/system-prompt.test.d.ts.map +1 -0
- package/dist/core/system-prompt.test.js +89 -0
- package/dist/core/system-prompt.test.js.map +1 -0
- package/dist/core/tools/bash.d.ts +2 -0
- package/dist/core/tools/bash.d.ts.map +1 -1
- package/dist/core/tools/bash.js +34 -5
- package/dist/core/tools/bash.js.map +1 -1
- package/dist/core/tools/tool-definition-wrapper.d.ts.map +1 -1
- package/dist/core/tools/tool-definition-wrapper.js +3 -1
- package/dist/core/tools/tool-definition-wrapper.js.map +1 -1
- package/dist/defaults/models.json +13 -45
- package/dist/defaults/settings.json +1 -2
- package/dist/extensions/copy-turn.test.ts +131 -0
- package/dist/extensions/copy-turn.ts +6 -1
- package/dist/extensions/package.json +0 -1
- package/dist/extensions/pi-intercom/CHANGELOG.md +249 -0
- package/dist/extensions/pi-intercom/README.md +102 -39
- package/dist/extensions/pi-intercom/broker/broker.ts +1233 -36
- package/dist/extensions/pi-intercom/broker/client.test.ts +83 -0
- package/dist/extensions/pi-intercom/broker/client.ts +315 -12
- package/dist/extensions/pi-intercom/broker/extension-state.ts +186 -0
- package/dist/extensions/pi-intercom/broker/extension.test.ts +387 -0
- package/dist/extensions/pi-intercom/broker/framing.test.ts +114 -0
- package/dist/extensions/pi-intercom/broker/framing.ts +82 -24
- package/dist/extensions/pi-intercom/broker/paths.test.ts +153 -0
- package/dist/extensions/pi-intercom/broker/paths.ts +117 -8
- package/dist/extensions/pi-intercom/broker/runtime-claim.test.ts +34 -0
- package/dist/extensions/pi-intercom/broker/runtime-claim.ts +21 -0
- package/dist/extensions/pi-intercom/broker/spawn.test.ts +160 -23
- package/dist/extensions/pi-intercom/broker/spawn.ts +113 -27
- package/dist/extensions/pi-intercom/config.test.ts +93 -0
- package/dist/extensions/pi-intercom/config.ts +55 -6
- package/dist/extensions/pi-intercom/cwd.test.ts +40 -0
- package/dist/extensions/pi-intercom/cwd.ts +31 -0
- package/dist/extensions/pi-intercom/extension-api.ts +44 -0
- package/dist/extensions/pi-intercom/format-context.test.ts +31 -0
- package/dist/extensions/pi-intercom/format-context.ts +32 -0
- package/dist/extensions/pi-intercom/index.ts +742 -145
- package/dist/extensions/pi-intercom/intercom.integration.test.ts +2646 -0
- package/dist/extensions/pi-intercom/package.json +15 -5
- package/dist/extensions/pi-intercom/reply-tracker.test.ts +134 -0
- package/dist/extensions/pi-intercom/reply-tracker.ts +31 -13
- package/dist/extensions/pi-intercom/skills/pi-intercom/SKILL.md +13 -11
- package/dist/extensions/pi-intercom/test/inline-message.test.ts +184 -0
- package/dist/extensions/pi-intercom/test/overlay-width.test.ts +66 -0
- package/dist/extensions/pi-intercom/types.ts +94 -4
- package/dist/extensions/pi-intercom/ui/compose.ts +8 -4
- package/dist/extensions/pi-intercom/ui/inline-message.ts +61 -25
- package/dist/extensions/pi-intercom/ui/session-list.ts +7 -3
- package/dist/extensions/pi-subagents/CHANGELOG.md +88 -0
- package/dist/extensions/pi-subagents/LICENSE +21 -0
- package/dist/extensions/pi-subagents/README.md +158 -69
- package/dist/extensions/pi-subagents/agents/architect.md +5 -4
- package/dist/extensions/pi-subagents/agents/builder.md +6 -4
- package/dist/extensions/pi-subagents/agents/commentator.md +3 -2
- package/dist/extensions/pi-subagents/agents/explorer.md +3 -2
- package/dist/extensions/pi-subagents/agents/recapper.md +3 -2
- package/dist/extensions/pi-subagents/agents/researcher.md +4 -3
- package/dist/extensions/pi-subagents/package-lock.json +2 -2
- package/dist/extensions/pi-subagents/package.json +3 -3
- package/dist/extensions/pi-subagents/prompts/review-loop.md +1 -1
- package/dist/extensions/pi-subagents/skills/pi-subagents/SKILL.md +22 -988
- package/dist/extensions/pi-subagents/skills/pi-subagents/references/constraints-and-recipes.md +257 -0
- package/dist/extensions/pi-subagents/skills/pi-subagents/references/execution-controls.md +431 -0
- package/dist/extensions/pi-subagents/skills/pi-subagents/references/management-authoring-rpc.md +144 -0
- package/dist/extensions/pi-subagents/skills/pi-subagents/references/prompting-and-roles.md +281 -0
- package/dist/extensions/pi-subagents/src/agents/agent-management.ts +125 -37
- package/dist/extensions/pi-subagents/src/agents/agent-serializer.ts +4 -0
- package/dist/extensions/pi-subagents/src/agents/agents.ts +118 -9
- package/dist/extensions/pi-subagents/src/agents/skills.ts +14 -12
- package/dist/extensions/pi-subagents/src/agents/task-aware-routing.ts +125 -0
- package/dist/extensions/pi-subagents/src/api/delegation.ts +3 -0
- package/dist/extensions/pi-subagents/src/api/preflight.ts +17 -13
- package/dist/extensions/pi-subagents/src/extension/chain-validation.ts +17 -1
- package/dist/extensions/pi-subagents/src/extension/index.ts +22 -8
- package/dist/extensions/pi-subagents/src/extension/rpc.ts +248 -6
- package/dist/extensions/pi-subagents/src/extension/schemas.ts +33 -8
- package/dist/extensions/pi-subagents/src/extension/tool-description.ts +32 -14
- package/dist/extensions/pi-subagents/src/intercom/intercom-bridge.ts +9 -4
- package/dist/extensions/pi-subagents/src/intercom/result-intercom.ts +33 -4
- package/dist/extensions/pi-subagents/src/runs/background/async-execution.ts +86 -21
- package/dist/extensions/pi-subagents/src/runs/background/async-job-tracker.ts +24 -13
- package/dist/extensions/pi-subagents/src/runs/background/async-resume.ts +7 -5
- package/dist/extensions/pi-subagents/src/runs/background/async-status.ts +18 -2
- package/dist/extensions/pi-subagents/src/runs/background/chain-append.ts +48 -5
- package/dist/extensions/pi-subagents/src/runs/background/control-channel.ts +68 -1
- package/dist/extensions/pi-subagents/src/runs/background/notify.ts +56 -5
- package/dist/extensions/pi-subagents/src/runs/background/result-watcher.ts +92 -11
- package/dist/extensions/pi-subagents/src/runs/background/run-status.ts +29 -3
- package/dist/extensions/pi-subagents/src/runs/background/subagent-runner.ts +388 -29
- package/dist/extensions/pi-subagents/src/runs/foreground/async-stop-action.ts +65 -0
- package/dist/extensions/pi-subagents/src/runs/foreground/chain-clarify.ts +3 -3
- package/dist/extensions/pi-subagents/src/runs/foreground/chain-execution.ts +214 -60
- package/dist/extensions/pi-subagents/src/runs/foreground/execution.ts +546 -252
- package/dist/extensions/pi-subagents/src/runs/foreground/foreground-control.ts +42 -0
- package/dist/extensions/pi-subagents/src/runs/foreground/subagent-executor.ts +553 -154
- package/dist/extensions/pi-subagents/src/runs/shared/acceptance.ts +19 -13
- package/dist/extensions/pi-subagents/src/runs/shared/capability-ceiling.ts +51 -19
- package/dist/extensions/pi-subagents/src/runs/shared/chain-outputs.ts +3 -1
- package/dist/extensions/pi-subagents/src/runs/shared/dynamic-fanout.ts +1 -1
- package/dist/extensions/pi-subagents/src/runs/shared/mcp-direct-tool-allowlist.ts +44 -11
- package/dist/extensions/pi-subagents/src/runs/shared/model-fallback.ts +8 -0
- package/dist/extensions/pi-subagents/src/runs/shared/nested-events.ts +97 -20
- package/dist/extensions/pi-subagents/src/runs/shared/parallel-utils.ts +43 -12
- package/dist/extensions/pi-subagents/src/runs/shared/pi-args.ts +52 -4
- package/dist/extensions/pi-subagents/src/runs/shared/process-signal.ts +19 -0
- package/dist/extensions/pi-subagents/src/runs/shared/run-history.ts +45 -9
- package/dist/extensions/pi-subagents/src/runs/shared/runtime-acknowledged-extensions.ts +71 -0
- package/dist/extensions/pi-subagents/src/runs/shared/single-output.ts +63 -9
- package/dist/extensions/pi-subagents/src/runs/shared/subagent-prompt-runtime.ts +31 -1
- package/dist/extensions/pi-subagents/src/runs/shared/subagent-startup-retry.ts +101 -0
- package/dist/extensions/pi-subagents/src/runs/shared/task-intent.ts +22 -1
- package/dist/extensions/pi-subagents/src/runs/shared/usage-budget.ts +65 -0
- package/dist/extensions/pi-subagents/src/runs/shared/workflow-graph.ts +26 -1
- package/dist/extensions/pi-subagents/src/shared/settings.ts +17 -1
- package/dist/extensions/pi-subagents/src/shared/types.ts +196 -12
- package/dist/extensions/pi-subagents/src/shared/utils.ts +102 -5
- package/dist/extensions/pi-subagents/src/slash/delegation-adapters.ts +10 -1
- package/dist/extensions/pi-subagents/src/slash/slash-commands.ts +46 -4
- package/dist/extensions/pi-subagents/src/slash/slash-live-state.ts +5 -3
- package/dist/extensions/pi-subagents/src/tui/fleet-status.ts +87 -24
- package/dist/extensions/pi-subagents/src/tui/fleet.ts +182 -9
- package/dist/extensions/pi-subagents/src/tui/render.ts +55 -34
- package/dist/extensions/pi-subagents/src/watchdog/register-main.ts +14 -7
- package/dist/extensions/pi-subagents/src/watchdog/review.ts +5 -4
- package/dist/extensions/pi-subagents/src/watchdog/runtime.ts +170 -17
- package/dist/extensions/pi-subagents/src/watchdog/scope.ts +62 -0
- package/dist/extensions/pi-subagents/src/watchdog/settings.ts +41 -1
- package/dist/extensions/pi-subagents/src/watchdog/types.ts +10 -0
- package/dist/extensions/pi-subagents/test/e2e/real-session-subagent.test.ts +113 -8
- package/dist/extensions/pi-subagents/test/integration/async-execution.test.ts +419 -47
- package/dist/extensions/pi-subagents/test/integration/async-job-tracker.test.ts +84 -0
- package/dist/extensions/pi-subagents/test/integration/async-status.test.ts +4 -2
- package/dist/extensions/pi-subagents/test/integration/chain-clarify.test.ts +51 -2
- package/dist/extensions/pi-subagents/test/integration/chain-execution.test.ts +62 -22
- package/dist/extensions/pi-subagents/test/integration/detect-error.test.ts +48 -0
- package/dist/extensions/pi-subagents/test/integration/fork-context-execution.test.ts +8 -6
- package/dist/extensions/pi-subagents/test/integration/intercom-result-delivery.test.ts +231 -19
- package/dist/extensions/pi-subagents/test/integration/parallel-execution.test.ts +48 -7
- package/dist/extensions/pi-subagents/test/integration/render-fork-badge.test.ts +44 -0
- package/dist/extensions/pi-subagents/test/integration/result-watcher.test.ts +199 -17
- package/dist/extensions/pi-subagents/test/integration/single-execution.test.ts +898 -16
- package/dist/extensions/pi-subagents/test/integration/slash-commands.test.ts +112 -23
- package/dist/extensions/pi-subagents/test/support/mock-pi-script.mjs +17 -5
- package/dist/extensions/pi-subagents/test/support/mock-pi.ts +2 -0
- package/dist/extensions/pi-subagents/test/support/real-session-runner.ts +18 -2
- package/dist/extensions/pi-subagents/test/support/register-loader.mjs +3 -3
- package/dist/extensions/pi-subagents/test/unit/acceptance.test.ts +3 -1
- package/dist/extensions/pi-subagents/test/unit/agent-disabled.test.ts +1 -1
- package/dist/extensions/pi-subagents/test/unit/agent-frontmatter.test.ts +198 -6
- package/dist/extensions/pi-subagents/test/unit/agent-management.test.ts +161 -1
- package/dist/extensions/pi-subagents/test/unit/agent-overrides.test.ts +47 -2
- package/dist/extensions/pi-subagents/test/unit/async-recovery-descriptor.test.ts +60 -0
- package/dist/extensions/pi-subagents/test/unit/async-resume.test.ts +8 -0
- package/dist/extensions/pi-subagents/test/unit/builtin-agent-documentation.test.ts +63 -0
- package/dist/extensions/pi-subagents/test/unit/capability-ceiling-agent-allowlist.test.ts +136 -0
- package/dist/extensions/pi-subagents/test/unit/capability-ceiling.test.ts +1 -1
- package/dist/extensions/pi-subagents/test/unit/chain-append.test.ts +6 -0
- package/dist/extensions/pi-subagents/test/unit/chain-validation.test.ts +1 -1
- package/dist/extensions/pi-subagents/test/unit/completion-guard.test.ts +48 -48
- package/dist/extensions/pi-subagents/test/unit/config-dir-runtime.test.ts +23 -0
- package/dist/extensions/pi-subagents/test/unit/control-channel.test.ts +27 -0
- package/dist/extensions/pi-subagents/test/unit/delegation-api.test.ts +28 -2
- package/dist/extensions/pi-subagents/test/unit/dynamic-fanout.test.ts +1 -0
- package/dist/extensions/pi-subagents/test/unit/fleet-status.test.ts +176 -8
- package/dist/extensions/pi-subagents/test/unit/fleet.test.ts +164 -5
- package/dist/extensions/pi-subagents/test/unit/foreground-control.test.ts +41 -1
- package/dist/extensions/pi-subagents/test/unit/index-child-registration.test.ts +17 -12
- package/dist/extensions/pi-subagents/test/unit/intercom-bridge.test.ts +18 -2
- package/dist/extensions/pi-subagents/test/unit/nested-control.test.ts +20 -1
- package/dist/extensions/pi-subagents/test/unit/nested-events.test.ts +30 -2
- package/dist/extensions/pi-subagents/test/unit/notify.test.ts +39 -2
- package/dist/extensions/pi-subagents/test/unit/parallel-utils.test.ts +22 -0
- package/dist/extensions/pi-subagents/test/unit/pi-args.test.ts +103 -0
- package/dist/extensions/pi-subagents/test/unit/pi-coding-agent-dir.test.ts +18 -0
- package/dist/extensions/pi-subagents/test/unit/preflight.test.ts +48 -0
- package/dist/extensions/pi-subagents/test/unit/render-helpers.test.ts +13 -1
- package/dist/extensions/pi-subagents/test/unit/result-intercom.test.ts +29 -4
- package/dist/extensions/pi-subagents/test/unit/rpc.test.ts +223 -4
- package/dist/extensions/pi-subagents/test/unit/run-status.test.ts +30 -0
- package/dist/extensions/pi-subagents/test/unit/runtime-acknowledged-extensions.test.ts +52 -0
- package/dist/extensions/pi-subagents/test/unit/schemas.test.ts +46 -2
- package/dist/extensions/pi-subagents/test/unit/single-output.test.ts +91 -1
- package/dist/extensions/pi-subagents/test/unit/skills-fallback.test.ts +1 -1
- package/dist/extensions/pi-subagents/test/unit/steering-action.test.ts +1 -1
- package/dist/extensions/pi-subagents/test/unit/streamed-progress-bounds.test.ts +78 -0
- package/dist/extensions/pi-subagents/test/unit/subagent-prompt-runtime.test.ts +41 -0
- package/dist/extensions/pi-subagents/test/unit/subagent-startup-retry.test.ts +77 -0
- package/dist/extensions/pi-subagents/test/unit/task-aware-routing.test.ts +213 -0
- package/dist/extensions/pi-subagents/test/unit/task-intent.test.ts +26 -1
- package/dist/extensions/pi-subagents/test/unit/tool-description.test.ts +61 -10
- package/dist/extensions/pi-subagents/test/unit/total-cost.test.ts +1 -0
- package/dist/extensions/pi-subagents/test/unit/watchdog-runtime.test.ts +210 -1
- package/dist/extensions/pi-subagents/test/unit/watchdog-scope.test.ts +33 -0
- package/dist/extensions/pi-subagents/test/unit/watchdog-settings.test.ts +32 -0
- package/dist/extensions/pi-subagents/test/unit/writer-budget-guidance.test.ts +1 -1
- package/dist/main.d.ts.map +1 -1
- package/dist/main.js +43 -0
- package/dist/main.js.map +1 -1
- package/dist/modes/interactive/components/custom-message.d.ts +3 -1
- package/dist/modes/interactive/components/custom-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/custom-message.js +10 -2
- package/dist/modes/interactive/components/custom-message.js.map +1 -1
- package/dist/modes/interactive/components/extension-editor.d.ts +1 -2
- package/dist/modes/interactive/components/extension-editor.d.ts.map +1 -1
- package/dist/modes/interactive/components/extension-editor.js +16 -46
- package/dist/modes/interactive/components/extension-editor.js.map +1 -1
- package/dist/modes/interactive/components/model-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/model-selector.js +4 -1
- package/dist/modes/interactive/components/model-selector.js.map +1 -1
- package/dist/modes/interactive/components/scoped-models-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/scoped-models-selector.js +22 -13
- package/dist/modes/interactive/components/scoped-models-selector.js.map +1 -1
- package/dist/modes/interactive/external-editor.d.ts +12 -0
- package/dist/modes/interactive/external-editor.d.ts.map +1 -0
- package/dist/modes/interactive/external-editor.js +37 -0
- package/dist/modes/interactive/external-editor.js.map +1 -0
- package/dist/modes/interactive/interactive-mode.d.ts +1 -1
- package/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
- package/dist/modes/interactive/interactive-mode.js +72 -64
- package/dist/modes/interactive/interactive-mode.js.map +1 -1
- package/dist/modes/rpc/rpc-mode.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-mode.js +14 -0
- package/dist/modes/rpc/rpc-mode.js.map +1 -1
- package/dist/skills/ponytail/SKILL.md +1 -3
- package/dist/utils/clipboard.d.ts.map +1 -1
- package/dist/utils/clipboard.js +19 -8
- package/dist/utils/clipboard.js.map +1 -1
- package/dist/utils/version-check.d.ts.map +1 -1
- package/dist/utils/version-check.js +1 -1
- package/dist/utils/version-check.js.map +1 -1
- package/docs/compaction.md +1 -1
- package/docs/custom-provider.md +14 -5
- package/docs/environment-variables.md +86 -0
- package/docs/extensions.md +15 -5
- package/docs/index.md +1 -0
- package/docs/models.md +9 -2
- package/docs/plans/subagent-delegation/phase-0-correctness.md +265 -0
- package/docs/plans/subagent-delegation/phase-1-behavioral-contract.md +486 -0
- package/docs/plans/subagent-delegation/phase-2-context-controls.md +282 -0
- package/docs/plans/subagent-delegation/phase-3-advisory-routing.md +362 -0
- package/docs/plans/subagent-delegation/phase-4-optional-enforcement.md +381 -0
- package/docs/providers.md +21 -2
- package/docs/rpc.md +23 -6
- package/docs/session-format.md +2 -0
- package/docs/settings.md +1 -1
- package/docs/usage.md +0 -13
- package/examples/extensions/custom-compaction.ts +5 -2
- package/examples/extensions/custom-provider-anthropic/index.ts +9 -3
- package/examples/extensions/custom-provider-anthropic/package-lock.json +2 -2
- package/examples/extensions/custom-provider-anthropic/package.json +1 -1
- package/examples/extensions/custom-provider-gitlab-duo/package.json +1 -1
- package/examples/extensions/gondolin/package-lock.json +2 -2
- package/examples/extensions/gondolin/package.json +1 -1
- package/examples/extensions/handoff.ts +11 -3
- package/examples/extensions/message-renderer.ts +3 -3
- package/examples/extensions/sandbox/package-lock.json +2 -2
- package/examples/extensions/sandbox/package.json +1 -1
- package/examples/extensions/summarize.ts +5 -2
- package/examples/extensions/with-deps/package-lock.json +2 -2
- package/examples/extensions/with-deps/package.json +1 -1
- package/examples/sdk/12-full-control.ts +3 -1
- package/package.json +16 -7
- package/dist/extensions/caveman/caveman-instructions.cjs +0 -11
- package/dist/extensions/caveman/index.js +0 -118
- package/dist/extensions/caveman/package.json +0 -8
- package/dist/extensions/caveman/test/extension.test.js +0 -203
- package/dist/extensions/caveman/test/helpers.test.js +0 -58
- package/dist/skills/caveman/SKILL.md +0 -50
|
@@ -0,0 +1,281 @@
|
|
|
1
|
+
# Pi Subagents: Prompting And Roles
|
|
2
|
+
|
|
3
|
+
This file is a detailed reference loaded from `skills/pi-subagents/SKILL.md`.
|
|
4
|
+
|
|
5
|
+
## Capability ceilings
|
|
6
|
+
|
|
7
|
+
Parent extensions may register a session-scoped, out-of-band ceiling through `pi-subagents/capability-ceiling`. Child tools and eligible canonical agent names are intersected with every active registration and inherited snapshot; `denyExtensions` removes ambient/provider extension loading while retaining package protocol runtime. `{ action: "list" }` marks non-allowlisted agents as restricted, and launch rejects them before spawn. Do not add a model-visible ceiling field or rely on unrestricted role selection for enforcement. Restricted schedules are rejected until their ceiling can be persisted safely.
|
|
8
|
+
|
|
9
|
+
## When to Use
|
|
10
|
+
|
|
11
|
+
- **Complex work orchestration**: use Fable mode as the default parent-agent loop for complex work. Complex means the task has multiple moving parts, unclear acceptance, cross-cutting code, meaningful user-visible impact, expensive or irreversible validation, broad review surface, or the user asks for orchestration. Lightweight one-off delegation can stay lightweight.
|
|
12
|
+
- **Advisory review**: use fresh-context `commentator` agents for adversarial code review, or fork to `commentator` when inherited decisions and drift matter
|
|
13
|
+
- **Implementation handoff**: have `commentator` advise, then `builder` implement only after an approved direction
|
|
14
|
+
- **Recon and planning**: use `explorer`, then `architect`
|
|
15
|
+
- **Parallel exploration**: run multiple non-conflicting tasks concurrently
|
|
16
|
+
- **Regular skill specialists**: when discovery shows proactive skill subagent suggestions and the current work is broad enough, launch a small fresh-context fanout that asks one subagent per relevant regularly used skill to apply that skill's perspective to the task
|
|
17
|
+
- **Long-running work**: launch async/background runs and inspect them later. For mutation-capable work, bound the delivery slice and elapsed runtime, then request checkpoints after active tool work returns. Reserve hard turn and tool-call caps for explicitly read-only children.
|
|
18
|
+
- **Subagent control**: watch needs-attention signals and soft-interrupt only when a delegated run is genuinely blocked
|
|
19
|
+
- **Agent authoring**: create, update, or override agents and chains for a project
|
|
20
|
+
|
|
21
|
+
## Tool vs Slash Commands
|
|
22
|
+
|
|
23
|
+
Agents can use the `subagent(...)` tool directly for execution, management, status, and control.
|
|
24
|
+
Humans often use the slash-command layer instead:
|
|
25
|
+
|
|
26
|
+
- `/run` — launch a single agent
|
|
27
|
+
- `/chain` — launch a chain of steps
|
|
28
|
+
- `/parallel` — launch top-level parallel tasks
|
|
29
|
+
- `/run-chain` — launch a saved `.chain.md` or `.chain.json` workflow
|
|
30
|
+
- `/subagents` — interactive admin for inspecting agents and editing model, thinking, or system prompt
|
|
31
|
+
- `/subagents-stop [run-id]` — stop a current-session top-level async run; opens a selector when no id is given
|
|
32
|
+
- `/subagents-detach [run-id]` — detach an active foreground single-subagent run without terminating its child
|
|
33
|
+
- `/subagent-cost` — show parent plus child token usage and cost for the session
|
|
34
|
+
- `/subagents-fleet` — open the live fleet inspector with per-child controls; `Ctrl+Alt+F` opens it during an active foreground turn, `↑↓`/`jk` selects children, `PgUp`/`PgDn` scrolls transcript detail, `s` steers the selected live async child, and `D` stops its top-level async run after confirmation
|
|
35
|
+
- `/subagents-watchdog` — inspect or configure the opt-in adversarial change watchdog (model, on/off, recommend-model, check)
|
|
36
|
+
- `/subagents-doctor` — diagnose setup, discovery, async paths, and intercom bridge state
|
|
37
|
+
- `/subagents-models [agent]` — show the live runtime-loaded builtin model mapping
|
|
38
|
+
- `/subagents-profiles`, `/subagents-load-profile`, `/subagents-refresh-provider-models`, `/subagents-generate-profiles`, `/subagents-check-profile` — manage model profiles and provider catalogs
|
|
39
|
+
- `/prompt-workflow` and `/chain-prompts` — run prompt templates through native subagent single/chain workflows
|
|
40
|
+
|
|
41
|
+
Prefer the tool when you are writing agent logic. Prefer the slash commands when
|
|
42
|
+
you are guiding a human through an interactive flow.
|
|
43
|
+
|
|
44
|
+
Packaged prompt shortcuts are also available for repeatable workflows. Treat them as reusable orchestration recipes, not just human slash commands. When the user asks for one of these shapes, or when the workflow clearly fits, apply the same pattern directly with `subagent(...)` and other tools:
|
|
45
|
+
- `/parallel-review` — fresh-context commentators with distinct review angles, then synthesis
|
|
46
|
+
- `/review-loop` — parent-orchestrated builder, fresh-commentator, and fix-builder cycles until clean or capped
|
|
47
|
+
- `/parallel-research` — combine `researcher` and `explorer` for external evidence plus local code context
|
|
48
|
+
- `/parallel-context-build` — parallel `explorer` passes that produce planning handoff context and meta-prompts
|
|
49
|
+
- `/parallel-handoff-plan` — external-reference research plus local `explorer` passes, followed by a synthesis handoff plan and implementation-ready meta-prompt
|
|
50
|
+
- `/gather-context-and-clarify` — explorer/research first, then ask the user clarifying questions with `interview`
|
|
51
|
+
- `/parallel-cleanup` — two fresh-context commentators (deslop + verbosity passes) for an adversarial cleanup review of the current diff
|
|
52
|
+
|
|
53
|
+
## Applying Prompt Techniques Without Slash Commands
|
|
54
|
+
|
|
55
|
+
The prompt templates in `prompts/` encode workflows the parent agent can run on demand. If the user provides a URL, issue, PR, plan, local file, screenshot, or freeform target, treat that target as the primary scope: read or fetch it before launching children, then include it explicitly in every child task. Do not depend on the parent conversation history when the recipe calls for fresh context.
|
|
56
|
+
|
|
57
|
+
### Parallel review technique
|
|
58
|
+
|
|
59
|
+
Use this when the user wants adversarial review of a diff, plan, issue, file, or implemented work. Launch fresh-context `commentator` agents with distinct angles generated from the actual target. Common angles are correctness/regressions, tests/validation, and simplicity/maintainability; adapt for TypeScript, UI, security, docs, or large structural changes. commentators should inspect files and diffs directly, return concise evidence-backed findings with file/line references, and avoid edits unless the user explicitly asks for a writer pass. The parent synthesizes fixes worth doing now, optional improvements, and feedback to ignore/defer before applying anything.
|
|
60
|
+
|
|
61
|
+
### Proactive skill-specialist technique
|
|
62
|
+
|
|
63
|
+
Use this when `{ action: "list" }` reports proactive skill subagent suggestions and the user's task would benefit from perspectives the parent regularly uses. These suggestions are conservative: a skill is recommended only when it is available and referenced repeatedly by configured agents or saved chains. Treat the list as an opt-in hint for the current task, not a command to always fan out.
|
|
64
|
+
|
|
65
|
+
Default guardrails:
|
|
66
|
+
- Keep the fanout small: usually one or two skill-specialist children, never more than the listed recommendations or configured cap.
|
|
67
|
+
- Prefer `context: "fresh"` and include only the files, diff, plan, URL, or request details each child needs. Use forked context only when private/session history is essential and appropriate to share.
|
|
68
|
+
- Use read-only agents for analysis/review unless implementation was explicitly requested; do not create several writers in the same worktree.
|
|
69
|
+
- Skip proactive skill subagents for tiny questions, direct commands, highly private requests, or when the user asks not to delegate.
|
|
70
|
+
- Make cost and concurrency visible by using an ordinary `subagent(...)` call rather than hidden/background automation.
|
|
71
|
+
|
|
72
|
+
Example shape:
|
|
73
|
+
|
|
74
|
+
```typescript
|
|
75
|
+
subagent({
|
|
76
|
+
tasks: [
|
|
77
|
+
{ agent: "commentator", task: "Apply the available 'deslop' skill to review the current diff for concrete cleanup findings only. Do not modify files.", skill: "deslop" },
|
|
78
|
+
{ agent: "commentator", task: "Apply the available 'accessibility' skill to review the UI changes for concrete issues only. Do not modify files.", skill: "accessibility" }
|
|
79
|
+
],
|
|
80
|
+
context: "fresh",
|
|
81
|
+
concurrency: 2
|
|
82
|
+
})
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
### Review-loop technique
|
|
86
|
+
|
|
87
|
+
Use this when the user wants implementation or current diff review to continue until commentators stop finding fixes worth doing now. Keep the loop in the parent session: one async `builder` implements or fixes, fresh-context `commentator` agents inspect the actual repo and diff, the parent synthesizes accepted fixes, and one async forked `builder` applies them. The parent can express the sequence up front as an async/background chain when the workflow is known, or continue with explicit follow-up subagent runs after each async completion. For an initial chain, pass `async: true` so the main chat is unblocked; do not set `clarify: true` unless the user explicitly wants the foreground clarify UI. Treat an async implementation builder handoff as an intermediate state, not final completion, unless the user explicitly asked for builder-only work, review-only output, or to stop after implementation. Stop when commentators find no blockers or fixes worth doing now, remaining feedback is optional or deferred, an unapproved product/scope/architecture decision appears, or the max review-round cap is reached. Default to 3 review rounds unless the user sets a different cap. Do not loop for optional polish, and do not let children launch subagents or decide the loop outcome.
|
|
88
|
+
|
|
89
|
+
As a conservative orchestration policy, do not pass `turnBudget` or a hard `toolBudget` to an implementation builder, fix builder, commentator with edit authority, or other mutation-capable child. The default tool budget blocks read/search tools rather than mutation tools, but count limits still do not measure delivery safety. Use a narrow task plus an outer elapsed deadline with enough margin, then request a checkpoint after the current tool returns. The checkpoint should report changed files, build/test state, remaining work, and commit or PR state. An elapsed timeout is not a mutation-safe boundary and must not be used as the checkpoint trigger.
|
|
90
|
+
|
|
91
|
+
### Parallel research technique
|
|
92
|
+
|
|
93
|
+
Use this when the question needs both external evidence and local implications. Combine `researcher` for official docs, specs, ecosystem behavior, recent changes, benchmarks, and primary sources with `explorer` for repository files, patterns, constraints, tests, and likely integration points. Give each child a distinct angle: external evidence, local code context, and practical tradeoffs. Ask for source links or file ranges, confidence level, gaps, and decision implications. Do not ask these children to edit unless implementation was explicitly requested.
|
|
94
|
+
|
|
95
|
+
### Parallel context-build technique
|
|
96
|
+
|
|
97
|
+
Use this before planning or implementation when a stronger handoff is needed. Run a chain with one parallel step of `explorer` agents rather than top-level parallel tasks, so relative output files live under the temporary chain directory. Give every task a distinct output path such as `context-build/request-and-scope.md`, `context-build/codebase-and-patterns.md`, and `context-build/validation-and-risks.md`. Choose two or three builders: request/scope, codebase/patterns, and validation/risks. Each builder must read every relevant file needed to understand its slice, follow imports/callers/tests/docs/config, conduct tool-available web research when needed, and include a compact `meta-prompt` section. The parent synthesizes the outputs into important context, recommended next meta-prompt, open questions, assumptions, and artifact paths.
|
|
98
|
+
|
|
99
|
+
Example shape:
|
|
100
|
+
|
|
101
|
+
```typescript
|
|
102
|
+
subagent({
|
|
103
|
+
chain: [{
|
|
104
|
+
parallel: [
|
|
105
|
+
{ agent: "explorer", task: "Build request/scope context for: ...", output: "context-build/request-and-scope.md" },
|
|
106
|
+
{ agent: "explorer", task: "Build codebase/pattern context for: ...", output: "context-build/codebase-and-patterns.md" },
|
|
107
|
+
{ agent: "explorer", task: "Build validation/risk context for: ...", output: "context-build/validation-and-risks.md" }
|
|
108
|
+
]
|
|
109
|
+
}],
|
|
110
|
+
context: "fresh"
|
|
111
|
+
})
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
### Parallel handoff-plan technique
|
|
115
|
+
|
|
116
|
+
Use this when the user needs a solution brief or implementation-ready handoff from an external reference plus local code context, such as “study this library behavior, inspect our codebase, then produce a builder prompt.” Run a chain with a first parallel group and a second synthesis `explorer` step. The first group usually includes `researcher` for external projects/docs/prompt guidance and `explorer` for local code context; add a second `explorer` for implementation strategy only when the scope is large enough to benefit. Use distinct output paths under `handoff/`, then have the synthesis `explorer` read those outputs and write `handoff/final-handoff-plan.md` with the recommended approach, likely files, constraints, non-goals, validation, risks, unresolved questions, and final compact implementation-ready meta-prompt.
|
|
117
|
+
|
|
118
|
+
Example shape:
|
|
119
|
+
|
|
120
|
+
```typescript
|
|
121
|
+
subagent({
|
|
122
|
+
chain: [
|
|
123
|
+
{ parallel: [
|
|
124
|
+
{ agent: "researcher", task: "Research the external reference and transferable implementation ideas for: ...", output: "handoff/external-reference.md" },
|
|
125
|
+
{ agent: "explorer", task: "Build local codebase context for: ...", output: "handoff/local-context.md" },
|
|
126
|
+
{ agent: "explorer", task: "Compare evidence and propose implementation strategy for: ...", output: "handoff/implementation-strategy.md" }
|
|
127
|
+
] },
|
|
128
|
+
{ agent: "explorer", task: "Read {previous} and synthesize the final handoff plan and implementation-ready meta-prompt.", output: "handoff/final-handoff-plan.md" }
|
|
129
|
+
],
|
|
130
|
+
context: "fresh"
|
|
131
|
+
})
|
|
132
|
+
```
|
|
133
|
+
|
|
134
|
+
### Gather-context-and-clarify technique
|
|
135
|
+
|
|
136
|
+
Use this at the start of non-trivial work. Launch `explorer` for local context and `researcher` only when external docs, recent sources, ecosystem context, or primary evidence would materially improve understanding. Ask children for concise findings plus remaining clarification questions. Then synthesize what is known and use `interview` to ask the unresolved questions needed for shared understanding before planning or implementing.
|
|
137
|
+
|
|
138
|
+
### Parallel cleanup technique
|
|
139
|
+
|
|
140
|
+
Use this after implementation when the user wants cleanup review or when a final pass would reduce AI-slop. Launch two fresh-context `commentator` tasks with `output: false` and `progress: false`: one deslop pass and one verbosity pass. If the `deslop` or `verbosity-cleaner` skills are available, pass the relevant skill to that commentator; otherwise inline the criteria. Both commentators are review-only and should flag concrete issues with severity, file/line references, and smallest safe fixes. Phrase the constraint as “Do not modify project/source files; returning findings through the configured output artifact is allowed” when you use `output` or `outputMode: "file-only"`. The parent decides what to apply and asks before making changes unless cleanup was already authorized.
|
|
141
|
+
|
|
142
|
+
### Staged fix orchestration technique
|
|
143
|
+
|
|
144
|
+
Use this when a broad diff has known commentator findings across several items and the user wants the parent to “orchestrate subagents like a boss.” Keep the active worktree safe with a three-stage chain:
|
|
145
|
+
|
|
146
|
+
1. A parallel read-only planning fanout, one architect/commentator per issue cluster. Each child inspects the real diff and returns exact files, line refs, proposed fixes, and focused validation. They must not edit.
|
|
147
|
+
2. One writer builder. It receives the architect summaries through `{previous}`, the parent’s accepted scope, stop rules, and verification contract. It is the only child allowed to edit the active worktree.
|
|
148
|
+
3. A parallel read-only validation fanout. Validators inspect the builder diff from fresh context with distinct angles, report pass/fail, remaining blockers, and missing verification.
|
|
149
|
+
|
|
150
|
+
Prefer `async: true`, `context: "fresh"` for architects/validators, `outputMode: "file-only"` for large summaries, and per-stage output names that will not collide. Add `phase` and `label` to make async status readable, and use `as` plus `{outputs.name}` when a later step needs a specific earlier result instead of the whole `{previous}` blob. Use this pattern instead of launching several writer builders into a dirty worktree. Include non-blocking suggestions in the writer prompt only when they are small, safe, and do not expand product scope; otherwise record them as deferred.
|
|
151
|
+
|
|
152
|
+
When the first step can return a structured target list, prefer dynamic fanout instead of hand-authoring a static parallel group. Use `outputSchema` and `as` on the producer, then an `expand` step with `from: { output, path }`, an explicit `maxItems`, one `parallel` child template, and `collect.as`. Item templates may use `{item}` or a named item such as `{target.path}`. Do not use dynamic fanout for prose outputs, nested fanout, dynamic agent selection, reducers, `when` conditions, or arbitrary expressions; `.chain.md` does not support this syntax, so use direct JSON or a saved `.chain.json`.
|
|
153
|
+
|
|
154
|
+
Example shape:
|
|
155
|
+
|
|
156
|
+
```typescript
|
|
157
|
+
subagent({
|
|
158
|
+
async: true,
|
|
159
|
+
context: "fresh",
|
|
160
|
+
chain: [
|
|
161
|
+
{ parallel: [
|
|
162
|
+
{ agent: "commentator", phase: "Planning", label: "Deploy docs", as: "deployPlan", task: "Plan fixes for deploy docs/workflow. Inspect the current diff. Do not modify project/source files; returning findings via the configured output artifact is allowed.", output: "plans/deploy.md", outputMode: "file-only" },
|
|
163
|
+
{ agent: "commentator", phase: "Planning", label: "Scheduler contract", as: "schedulerPlan", task: "Plan fixes for scheduler contract. Inspect the current diff. Do not modify project/source files; returning findings via the configured output artifact is allowed.", output: "plans/scheduler.md", outputMode: "file-only" },
|
|
164
|
+
{ agent: "commentator", phase: "Planning", label: "Sandbox/security", as: "sandboxPlan", task: "Plan fixes for sandbox/security. Inspect the current diff. Do not modify project/source files; returning findings via the configured output artifact is allowed.", output: "plans/sandbox.md", outputMode: "file-only" }
|
|
165
|
+
], concurrency: 3 },
|
|
166
|
+
{ agent: "builder", phase: "Implementation", label: "Apply accepted fixes", as: "workerResult", task: "Apply only the accepted fixes from these planning summaries. You are the sole writer for the active worktree. Run focused validation and report changed files, commands, failures, and remaining issues.\n\nDeploy plan:\n{outputs.deployPlan}\n\nScheduler plan:\n{outputs.schedulerPlan}\n\nSandbox plan:\n{outputs.sandboxPlan}", output: "builder/fixes.md", outputMode: "file-only", progress: true },
|
|
167
|
+
{ parallel: [
|
|
168
|
+
{ agent: "commentator", phase: "Validation", label: "Deploy/scheduler validation", task: "Validate the post-builder diff for deploy and scheduler fixes. Start from the builder result: {outputs.workerResult}. Do not modify project/source files; returning findings via the configured output artifact is allowed.", output: "validation/deploy-scheduler.md", outputMode: "file-only" },
|
|
169
|
+
{ agent: "commentator", phase: "Validation", label: "Sandbox validation", task: "Validate the post-builder diff for sandbox/security fixes. Start from the builder result: {outputs.workerResult}. Do not modify project/source files; returning findings via the configured output artifact is allowed.", output: "validation/sandbox.md", outputMode: "file-only" }
|
|
170
|
+
], concurrency: 2 }
|
|
171
|
+
]
|
|
172
|
+
})
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
## Builtin Agents
|
|
176
|
+
|
|
177
|
+
Builtin agents load at the lowest priority. Project agents override user agents,
|
|
178
|
+
and user/project agents override builtins with the same name.
|
|
179
|
+
|
|
180
|
+
| Agent | Purpose | Model | Typical output / role |
|
|
181
|
+
|-------|---------|-------|------------------------|
|
|
182
|
+
| `architect` | Creates implementation plans | inherits default | Read-only planning; returns the complete plan in its final response |
|
|
183
|
+
| `builder` | Implementation and approved commentator handoffs | inherits default | Single-writer implementation with decision escalation |
|
|
184
|
+
| `commentator` | Review specialist | inherits default | Review-only findings in its final response; no edit/write tools |
|
|
185
|
+
| `explorer` | Fast codebase recon | inherits default | Read-only recon findings in its final response |
|
|
186
|
+
| `recapper` | Current-state handoff specialist | inherits default | Fork-context handoff; returns a self-contained handoff in its final response |
|
|
187
|
+
| `researcher` | Sourced research brief generator | inherits default | Read-only brief in its final response |
|
|
188
|
+
|
|
189
|
+
Only `architect` and `recapper` resolve to forked context when a launch omits `context`; `builder`, `commentator`, `explorer`, and `researcher` default to fresh context. Read-only builtins return their output in the final response; output files are written only when the caller configures output persistence.
|
|
190
|
+
|
|
191
|
+
Explicit `tools` is an allowlist, but ambient extension discovery remains possible unless `extensions`, `subagentOnlyExtensions`, or a capability ceiling constrains it; naming a tool alone does not load its provider. To give a child an extension tool, name it in `tools` and load its provider via `extensions`, a path-like `tools` entry, or `subagentOnlyExtensions`. Custom agents without an `extensions` field follow `subagents.defaultExtensions` when set.
|
|
192
|
+
|
|
193
|
+
Builtin agents inherit the current Pi default model unless a run, user setting, project setting, or `subagents.defaultModel` overrides `model`. Set `subagents.defaultModel` when subagents should use a different default model than the parent session. Override builtin defaults before copying full agent files when a small tweak is enough.
|
|
194
|
+
|
|
195
|
+
Set `subagents.defaultThinking` to apply a shared thinking level to builtin, package, user, and project agents whose frontmatter leaves `thinking` unset. Project settings win over user settings; explicit frontmatter (including `thinking: false`), `agentOverrides.<name>.thinking`, and per-run overrides remain more specific. This setting affects child agents only and does not change the parent session's default thinking level.
|
|
196
|
+
|
|
197
|
+
```json
|
|
198
|
+
{
|
|
199
|
+
"subagents": {
|
|
200
|
+
"defaultThinking": "medium"
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
```
|
|
204
|
+
|
|
205
|
+
For one run, use inline config:
|
|
206
|
+
|
|
207
|
+
```text
|
|
208
|
+
/run commentator[model=anthropic/claude-sonnet-4] "Review this diff"
|
|
209
|
+
```
|
|
210
|
+
|
|
211
|
+
For persistent tweaks, edit `subagents.agentOverrides` in user or project settings. User overrides apply everywhere. Project overrides apply only in that repo and win over user overrides. Use `/subagents-models` or `subagent({ action: "models" })` to inspect the live mapping after settings and overrides load.
|
|
212
|
+
|
|
213
|
+
Model ids do not have to be exact. Separator variations (`claude-haiku-4.5` vs `claude-haiku-4-5`), case (`Claude-Sonnet-4`), and optional trailing date stamps (`claude-haiku-4-5-20251001`) all resolve to the same registry model. Exact `provider/id` wins; a qualified `provider/model` never switches providers. To constrain subagents to a budget or compliance profile, set `subagents.modelScope: { enforce: true, allow: ["anthropic/*", "openai/gpt-5-*"] }` in user or project settings. Out-of-scope models you pass explicitly error and abort; models inherited from frontmatter, `subagents.defaultModel`, agent frontmatter, or the parent session only warn.
|
|
214
|
+
|
|
215
|
+
For model fleets, use the profile commands instead of hand-editing repeated overrides: `/subagents-refresh-provider-models <provider>`, `/subagents-generate-profiles <provider>`, `/subagents-load-profile <name>`, and `/subagents-check-profile <name>`. Profiles live under `~/.selesai/agent/profiles/pi-subagents/` and replace only `settings.subagents` when loaded.
|
|
216
|
+
|
|
217
|
+
## Prompting role subagents
|
|
218
|
+
|
|
219
|
+
Builtin role agents inherit the current Pi default model unless you override them. When launching them, write the task prompt as a compact contract, not a long procedural script. Define the destination and let the role choose the efficient path.
|
|
220
|
+
|
|
221
|
+
A strong subagent prompt usually includes:
|
|
222
|
+
- **Goal**: the concrete outcome the child should produce.
|
|
223
|
+
- **Context/evidence**: relevant plan paths, files, diffs, decisions, or user constraints already approved.
|
|
224
|
+
- **Success criteria**: what must be true before the child can finish.
|
|
225
|
+
- **Hard constraints**: true invariants only, such as no edits for review-only tasks, one writer thread, child must not run subagents unless it is an explicitly assigned `tools: subagent` fanout child, or escalation for unapproved decisions.
|
|
226
|
+
- **Validation**: targeted checks to run, or the next-best check when validation is impossible.
|
|
227
|
+
- **Output**: the expected summary shape, artifact path, or finding format.
|
|
228
|
+
- **Stop rules**: when to ask via `intercom`, when to stop after enough evidence, and when not to keep searching.
|
|
229
|
+
|
|
230
|
+
Avoid carrying over old prompt habits that over-specify every step. Use `must`, `always`, and `never` for real invariants; for judgment calls, give decision rules. For example, tell a commentator to inspect the staged diff directly and report only evidence-backed findings, rather than prescribing every file or command. Tell a researcher the retrieval budget: start with broad targeted searches, fetch only the strongest sources, search again only when a required fact is missing, then stop.
|
|
231
|
+
|
|
232
|
+
For implementation handoffs, name the approved scope and success criteria more clearly than the process. Good prompts say what to change, what not to change, where the evidence lives, how to validate, and when to escalate. They should not ask the child to create another subagent plan or continue the parent conversation.
|
|
233
|
+
|
|
234
|
+
Settings locations:
|
|
235
|
+
- User scope: `~/.selesai/agent/settings.json`
|
|
236
|
+
- Project scope: `.selesai/settings.json`
|
|
237
|
+
|
|
238
|
+
Direct settings example:
|
|
239
|
+
|
|
240
|
+
```json
|
|
241
|
+
{
|
|
242
|
+
"subagents": {
|
|
243
|
+
"agentOverrides": {
|
|
244
|
+
"commentator": {
|
|
245
|
+
"model": "anthropic/claude-sonnet-4",
|
|
246
|
+
"thinking": "high",
|
|
247
|
+
"fallbackModels": ["openai/gpt-5-mini"],
|
|
248
|
+
"acceptanceRole": "read-only"
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
```
|
|
254
|
+
|
|
255
|
+
Useful override fields: `description`, `model`, `fallbackModels`, `thinking`,
|
|
256
|
+
`systemPromptMode`, `inheritProjectContext`, `inheritSkills`, `defaultContext`,
|
|
257
|
+
`acceptanceRole`, `disabled`, `skills`, `tools`, `extensions`, and `systemPrompt`.
|
|
258
|
+
`description` replaces the discovered description for builtin and custom agents
|
|
259
|
+
in `list` output, which is useful for deployment-specific routing notes.
|
|
260
|
+
Use `acceptanceRole: false` to clear an override. Create a user or project
|
|
261
|
+
agent with the same name only when you want a substantially different agent.
|
|
262
|
+
|
|
263
|
+
### Recommended model tiering (optional)
|
|
264
|
+
|
|
265
|
+
When several providers are available, route agents by task shape instead of one model for everything:
|
|
266
|
+
|
|
267
|
+
1. **Fast workhorse** — cheapest capable model at low thinking for recon, lookups, and mechanical edits (for example on `explorer`).
|
|
268
|
+
2. **Standard well-scoped** — mid-tier model at medium thinking for most delegations: routine multi-file edits, focused reviews, straightforward implementation (for example on `builder` and `commentator`).
|
|
269
|
+
3. **Deep but bounded** — top reasoning model at high thinking only for hard tasks that arrive with explicit goals and completion criteria; these models loop on vague goals (for example on `architect` and commentator-style agents).
|
|
270
|
+
4. **Taste and intent** — a model that reads human intent well for ambiguous work: UX/design judgment, product tradeoffs, planning from vague requirements, writing quality.
|
|
271
|
+
|
|
272
|
+
Routing rule: use tiers 1–3 when the task is well-scoped; use tier 4 when scoping or judging is the task itself. Give tier-4 agents cross-provider `fallbackModels` so subscription usage limits degrade gracefully; fallback triggers automatically on rate-limit and overload errors. Note that forked context over an Anthropic parent transcript with signed thinking blocks forces the child's thinking off, so intent-tier agents work best with fresh context.
|
|
273
|
+
|
|
274
|
+
If a provider rejects model IDs with thinking suffixes, use
|
|
275
|
+
`subagents.disableThinking: true` in user or project settings to clear bundled
|
|
276
|
+
builtin thinking defaults globally. A higher-precedence per-agent `thinking`
|
|
277
|
+
override can opt one builtin back in. Existing custom-agent frontmatter remains authoritative.
|
|
278
|
+
|
|
279
|
+
Set `subagents.defaultExtensions` to give agents without an `extensions` field a shared child extension allowlist. Omit it to preserve ambient extension discovery, set it to `[]` to disable ambient extensions by default, or use `agentOverrides.<name>.extensions` for one agent. Explicit custom-agent frontmatter still wins.
|
|
280
|
+
|
|
281
|
+
Tool description modes live in `~/.selesai/agent/extensions/subagent/config.json`, not `subagents` settings. Set `toolDescriptionMode` to `compact` to reduce tool-description prompt cost while keeping the execution, async/`subagent_wait`, child-safety, one-writer, management/action, and artifact/status guardrails. Set it to `custom` to read `subagent-tool-description.md` from the project config dir or agent dir; invalid custom files fall back to full mode and the safety guidance is still appended.
|
|
@@ -19,6 +19,7 @@ import {
|
|
|
19
19
|
mergeBuiltinAgentOverride,
|
|
20
20
|
removeBuiltinAgentOverride,
|
|
21
21
|
removeBuiltinAgentOverrideFields,
|
|
22
|
+
resolveAgentName,
|
|
22
23
|
} from "./agents.ts";
|
|
23
24
|
import { serializeAgent } from "./agent-serializer.ts";
|
|
24
25
|
import { mergeAgentsForScope } from "./agent-selection.ts";
|
|
@@ -27,18 +28,20 @@ import { discoverAvailableSkills, resolveSkills } from "./skills.ts";
|
|
|
27
28
|
import {
|
|
28
29
|
buildProactiveSkillSubagentRecommendationLines,
|
|
29
30
|
} from "./proactive-skills.ts";
|
|
31
|
+
import { formatTaskAwareAgentRecommendation, recommendTaskAwareAgent } from "./task-aware-routing.ts";
|
|
30
32
|
import { parseFrontmatter } from "./frontmatter.ts";
|
|
31
33
|
import { toModelInfo } from "../shared/model-info.ts";
|
|
32
34
|
import { resolveSubagentModelOverride, type ParentModel } from "../runs/shared/model-fallback.ts";
|
|
33
35
|
import { validateToolBudgetConfig } from "../runs/shared/tool-budget.ts";
|
|
34
36
|
import { resolveTurnBudgetConfig } from "../runs/shared/turn-budget.ts";
|
|
35
37
|
import { validateAcceptanceInput } from "../runs/shared/acceptance.ts";
|
|
36
|
-
import type { AcceptanceInput, Details, ExtensionConfig, ToolBudgetConfig } from "../shared/types.ts";
|
|
38
|
+
import type { AcceptanceInput, CatalogAgentMetadata, Details, ExtensionConfig, ToolBudgetConfig } from "../shared/types.ts";
|
|
37
39
|
import { getProjectConfigDir } from "../shared/utils.ts";
|
|
40
|
+
import { capabilityCeilingAgentRestrictionSources, isAgentAllowedByCapabilityCeiling, resolveCurrentSubagentCapabilityCeiling } from "../runs/shared/capability-ceiling.ts";
|
|
38
41
|
|
|
39
42
|
type ManagementAction = "list" | "get" | "models" | "create" | "update" | "delete" | "eject" | "disable" | "enable" | "reset";
|
|
40
43
|
type ManagementScope = "user" | "project";
|
|
41
|
-
type ManagementContext = Pick<ExtensionContext, "cwd" | "modelRegistry"> & { model?: ExtensionContext["model"]; config?: ExtensionConfig };
|
|
44
|
+
type ManagementContext = Pick<ExtensionContext, "cwd" | "modelRegistry"> & { model?: ExtensionContext["model"]; config?: ExtensionConfig; currentSessionId?: string };
|
|
42
45
|
|
|
43
46
|
interface ManagementParams {
|
|
44
47
|
action?: string;
|
|
@@ -46,10 +49,12 @@ interface ManagementParams {
|
|
|
46
49
|
chainName?: string;
|
|
47
50
|
agentScope?: string;
|
|
48
51
|
config?: unknown;
|
|
52
|
+
/** Optional advisory intent for action:'list' only; never launches work. */
|
|
53
|
+
task?: string;
|
|
49
54
|
}
|
|
50
55
|
|
|
51
|
-
function result(text: string, isError = false): AgentToolResult<Details> {
|
|
52
|
-
return { content: [{ type: "text", text }], isError, details: { mode: "management", results: [] } };
|
|
56
|
+
function result(text: string, isError = false, extraDetails: Partial<Details> = {}): AgentToolResult<Details> {
|
|
57
|
+
return { content: [{ type: "text", text }], isError, details: { mode: "management", results: [], ...extraDetails } };
|
|
53
58
|
}
|
|
54
59
|
|
|
55
60
|
function parseCsv(value: string): string[] {
|
|
@@ -113,8 +118,13 @@ function findAgents(name: string, cwd: string, scope: AgentScope = "both"): Agen
|
|
|
113
118
|
const d = discoverAgentsAll(cwd);
|
|
114
119
|
const raw = name.trim();
|
|
115
120
|
const sanitized = sanitizeName(raw);
|
|
116
|
-
|
|
117
|
-
|
|
121
|
+
const scoped = mergeAgentsForScope(scope, d.user, d.project, d.builtin, d.package);
|
|
122
|
+
let resolved = resolveAgentName(raw, scoped);
|
|
123
|
+
if (!resolved.agent && !resolved.error && sanitized !== raw) resolved = resolveAgentName(sanitized, scoped);
|
|
124
|
+
if (resolved.agent) return scoped.filter((agent) => agent.name === resolved.agent!.name).sort((a, b) => a.source.localeCompare(b.source));
|
|
125
|
+
return scoped
|
|
126
|
+
.filter((agent) => Boolean(resolveAgentName(raw, [agent]).agent)
|
|
127
|
+
|| (sanitized !== raw && Boolean(resolveAgentName(sanitized, [agent]).agent)))
|
|
118
128
|
.sort((a, b) => a.source.localeCompare(b.source));
|
|
119
129
|
}
|
|
120
130
|
|
|
@@ -128,15 +138,20 @@ function findChains(name: string, cwd: string, scope: AgentScope = "both"): Chai
|
|
|
128
138
|
|
|
129
139
|
const AGENT_SOURCE_PRECEDENCE: Record<AgentSource, number> = { builtin: 0, package: 1, user: 2, project: 3 };
|
|
130
140
|
|
|
131
|
-
// Returns the highest-precedence
|
|
132
|
-
// matching mergeAgentsForScope for "both"
|
|
133
|
-
|
|
134
|
-
function pickEffectiveAgent(d: ReturnType<typeof discoverAgentsAll>, name: string): AgentConfig | undefined {
|
|
141
|
+
// Returns the highest-precedence definition for a resolved canonical name (project > user > package > builtin),
|
|
142
|
+
// matching mergeAgentsForScope for "both", including disabled agents so disable/enable can locate hidden targets.
|
|
143
|
+
function resolveEffectiveAgent(d: ReturnType<typeof discoverAgentsAll>, name: string): { agent?: AgentConfig; error?: string } {
|
|
135
144
|
const raw = name.trim();
|
|
136
|
-
const
|
|
137
|
-
|
|
138
|
-
if (
|
|
139
|
-
|
|
145
|
+
const candidates = allAgents(d);
|
|
146
|
+
let resolved = resolveAgentName(raw, candidates);
|
|
147
|
+
if (!resolved.agent && !resolved.error) {
|
|
148
|
+
const sanitized = sanitizeName(raw);
|
|
149
|
+
if (sanitized !== raw) resolved = resolveAgentName(sanitized, candidates);
|
|
150
|
+
}
|
|
151
|
+
if (resolved.error) return { error: resolved.error };
|
|
152
|
+
if (!resolved.agent) return {};
|
|
153
|
+
const matches = candidates.filter((agent) => agent.name === resolved.agent!.name);
|
|
154
|
+
return { agent: matches.reduce((best, agent) => (AGENT_SOURCE_PRECEDENCE[agent.source] > AGENT_SOURCE_PRECEDENCE[best.source] ? agent : best)) };
|
|
140
155
|
}
|
|
141
156
|
|
|
142
157
|
function nameExistsInScope(cwd: string, scope: ManagementScope, name: string, excludePath?: string): boolean {
|
|
@@ -156,8 +171,9 @@ function isMutableSource(source: AgentSource): source is ManagementScope {
|
|
|
156
171
|
|
|
157
172
|
function unknownChainAgents(cwd: string, steps: ChainStepConfig[]): string[] {
|
|
158
173
|
const d = discoverAgentsAll(cwd);
|
|
159
|
-
const
|
|
160
|
-
return [...new Set(steps.map((s) => s.agent).filter((
|
|
174
|
+
const agents = allAgents(d);
|
|
175
|
+
return [...new Set(steps.map((s) => s.agent).filter((agentName): agentName is string => typeof agentName === "string" && !resolveAgentName(agentName, agents).agent))]
|
|
176
|
+
.sort((a, b) => a.localeCompare(b));
|
|
161
177
|
}
|
|
162
178
|
|
|
163
179
|
function chainStepWarnings(ctx: ManagementContext, steps: ChainStepConfig[]): string[] {
|
|
@@ -251,6 +267,7 @@ export function preservedAgentFrontmatterFields(agent: AgentConfig, cfg: Record<
|
|
|
251
267
|
if (hasKey(cfg, "name")) changed("name");
|
|
252
268
|
if (hasKey(cfg, "package")) changed("package");
|
|
253
269
|
if (hasKey(cfg, "description")) changed("description");
|
|
270
|
+
if (hasKey(cfg, "aliases")) changed("alias", "aliases");
|
|
254
271
|
if (hasKey(cfg, "systemPrompt")) changed("systemPrompt");
|
|
255
272
|
if (hasKey(cfg, "model")) changed("model");
|
|
256
273
|
if (hasKey(cfg, "fallbackModels")) changed("fallbackModels");
|
|
@@ -370,6 +387,16 @@ function parseTools(raw: string): { tools?: string[]; mcpDirectTools?: string[]
|
|
|
370
387
|
}
|
|
371
388
|
|
|
372
389
|
function applyAgentConfig(target: AgentConfig, cfg: Record<string, unknown>): string | undefined {
|
|
390
|
+
if (hasKey(cfg, "aliases")) {
|
|
391
|
+
if (cfg.aliases === false || cfg.aliases === "") target.aliases = undefined;
|
|
392
|
+
else if (typeof cfg.aliases === "string") {
|
|
393
|
+
const aliases = parseCsv(cfg.aliases).filter((alias) => alias !== target.name);
|
|
394
|
+
target.aliases = aliases.length ? aliases : undefined;
|
|
395
|
+
} else if (Array.isArray(cfg.aliases) && cfg.aliases.every((entry) => typeof entry === "string")) {
|
|
396
|
+
const aliases = [...new Set(cfg.aliases.map((entry) => entry.trim()).filter(Boolean).filter((alias) => alias !== target.name))];
|
|
397
|
+
target.aliases = aliases.length ? aliases : undefined;
|
|
398
|
+
} else return "config.aliases must be a comma-separated string, string array, or false when provided.";
|
|
399
|
+
}
|
|
373
400
|
if (hasKey(cfg, "systemPrompt")) {
|
|
374
401
|
if (cfg.systemPrompt === false || cfg.systemPrompt === "") target.systemPrompt = "";
|
|
375
402
|
else if (typeof cfg.systemPrompt === "string") target.systemPrompt = cfg.systemPrompt;
|
|
@@ -513,13 +540,17 @@ function applyAgentConfig(target: AgentConfig, cfg: Record<string, unknown>): st
|
|
|
513
540
|
return undefined;
|
|
514
541
|
}
|
|
515
542
|
|
|
516
|
-
function resolveTarget<T extends { source: AgentSource; filePath: string }>(
|
|
543
|
+
function resolveTarget<T extends { name: string; source: AgentSource; filePath: string }>(
|
|
517
544
|
kind: "agent" | "chain",
|
|
518
545
|
name: string,
|
|
519
546
|
matches: T[],
|
|
520
547
|
cwd: string,
|
|
521
548
|
scopeHint?: string,
|
|
522
549
|
): T | AgentToolResult<Details> {
|
|
550
|
+
const distinctNames = [...new Set(matches.map((m) => m.name))];
|
|
551
|
+
if (distinctNames.length > 1) {
|
|
552
|
+
return result(`Ambiguous ${kind} alias or name '${name}': ${distinctNames.sort((a, b) => a.localeCompare(b)).join(", ")}`, true);
|
|
553
|
+
}
|
|
523
554
|
const mutable = matches.filter((m): m is T & { source: ManagementScope } => isMutableSource(m.source));
|
|
524
555
|
if (mutable.length === 0) {
|
|
525
556
|
if (matches.length > 0) {
|
|
@@ -557,13 +588,19 @@ function renamePath(
|
|
|
557
588
|
return { filePath };
|
|
558
589
|
}
|
|
559
590
|
|
|
591
|
+
/** Effective declared tools: normal tools plus mcp:-prefixed direct MCP tools. */
|
|
592
|
+
function effectiveAgentTools(agent: AgentConfig): string[] {
|
|
593
|
+
return [...(agent.tools ?? []), ...(agent.mcpDirectTools ?? []).map((t) => `mcp:${t}`)];
|
|
594
|
+
}
|
|
595
|
+
|
|
560
596
|
function formatAgentDetail(agent: AgentConfig): string {
|
|
561
|
-
const tools =
|
|
597
|
+
const tools = effectiveAgentTools(agent);
|
|
562
598
|
const lines: string[] = [`Agent: ${agent.name} (${agent.source})`, `Path: ${agent.filePath}`, `Description: ${agent.description}`];
|
|
563
599
|
if (agent.packageName) {
|
|
564
600
|
lines.push(`Local name: ${frontmatterNameForConfig(agent)}`);
|
|
565
601
|
lines.push(`Package: ${agent.packageName}`);
|
|
566
602
|
}
|
|
603
|
+
if (agent.aliases?.length) lines.push(`Aliases: ${agent.aliases.join(", ")}`);
|
|
567
604
|
if (agent.model) lines.push(`Model: ${agent.model}`);
|
|
568
605
|
if (agent.fallbackModels?.length) lines.push(`Fallback models: ${agent.fallbackModels.join(", ")}`);
|
|
569
606
|
if (tools.length) lines.push(`Tools: ${tools.join(", ")}`);
|
|
@@ -643,12 +680,43 @@ function formatChainDetail(chain: ChainConfig): string {
|
|
|
643
680
|
return lines.join("\n");
|
|
644
681
|
}
|
|
645
682
|
|
|
683
|
+
function formatCatalogAgentLine(agent: AgentConfig): string {
|
|
684
|
+
const parts: string[] = [agent.source, `context: ${agent.defaultContext ?? "fresh"}`];
|
|
685
|
+
if (agent.acceptanceRole) parts.push(`role: ${agent.acceptanceRole}`);
|
|
686
|
+
if (agent.aliases?.length) parts.push(`aliases: ${agent.aliases.join(", ")}`);
|
|
687
|
+
const tools = effectiveAgentTools(agent);
|
|
688
|
+
if (tools.length) parts.push(`tools: ${tools.join(", ")}`);
|
|
689
|
+
return `- ${agent.name} (${parts.join(", ")}): ${agent.description}`;
|
|
690
|
+
}
|
|
691
|
+
|
|
692
|
+
function catalogAgentMetadata(
|
|
693
|
+
agent: AgentConfig,
|
|
694
|
+
executable: boolean,
|
|
695
|
+
restrictionSources: string[] | undefined,
|
|
696
|
+
): CatalogAgentMetadata {
|
|
697
|
+
return {
|
|
698
|
+
name: agent.name,
|
|
699
|
+
source: agent.source,
|
|
700
|
+
description: agent.description,
|
|
701
|
+
executable,
|
|
702
|
+
...(restrictionSources?.length ? { restrictionSources } : {}),
|
|
703
|
+
...(agent.aliases?.length ? { aliases: [...agent.aliases] } : {}),
|
|
704
|
+
defaultContext: agent.defaultContext ?? "fresh",
|
|
705
|
+
...(agent.acceptanceRole ? { acceptanceRole: agent.acceptanceRole } : {}),
|
|
706
|
+
tools: effectiveAgentTools(agent),
|
|
707
|
+
};
|
|
708
|
+
}
|
|
709
|
+
|
|
646
710
|
export function handleList(params: ManagementParams, ctx: ManagementContext): AgentToolResult<Details> {
|
|
647
711
|
const scope = normalizeListScope(params.agentScope) ?? "both";
|
|
648
712
|
const d = discoverAgentsAll(ctx.cwd);
|
|
649
713
|
const scopedAgents = mergeAgentsForScope(scope, d.user, d.project, d.builtin, d.package)
|
|
650
714
|
.sort((a, b) => a.name.localeCompare(b.name));
|
|
651
|
-
const
|
|
715
|
+
const capabilityCeiling = resolveCurrentSubagentCapabilityCeiling(ctx.currentSessionId);
|
|
716
|
+
const visibleAgents = scopedAgents.filter((a) => !a.disabled);
|
|
717
|
+
const agents = visibleAgents.filter((a) => isAgentAllowedByCapabilityCeiling(a.name, capabilityCeiling));
|
|
718
|
+
const restrictedAgents = visibleAgents.filter((a) => !isAgentAllowedByCapabilityCeiling(a.name, capabilityCeiling));
|
|
719
|
+
const restrictedSources = capabilityCeilingAgentRestrictionSources(capabilityCeiling);
|
|
652
720
|
const chains = d.chains.filter((c) => scope === "both" || c.source === "package" || c.source === scope).sort((a, b) => a.name.localeCompare(b.name));
|
|
653
721
|
const diagnostics = d.chainDiagnostics.filter((entry) => scope === "both" || entry.source === scope);
|
|
654
722
|
const proactiveSuggestions = buildProactiveSkillSubagentRecommendationLines({
|
|
@@ -657,18 +725,35 @@ export function handleList(params: ManagementParams, ctx: ManagementContext): Ag
|
|
|
657
725
|
config: ctx.config?.proactiveSkillSubagents,
|
|
658
726
|
discoverAvailableSkills: () => discoverAvailableSkills(ctx.cwd),
|
|
659
727
|
});
|
|
728
|
+
const taskAdvice = params.task?.trim()
|
|
729
|
+
? formatTaskAwareAgentRecommendation(recommendTaskAwareAgent({ task: params.task, agents, capabilityCeiling }))
|
|
730
|
+
: [];
|
|
660
731
|
const lines = [
|
|
661
732
|
"Executable agents:",
|
|
662
|
-
...(agents.length
|
|
663
|
-
|
|
664
|
-
|
|
733
|
+
...(agents.length ? agents.map(formatCatalogAgentLine) : ["- (none)"]),
|
|
734
|
+
...(restrictedAgents.length ? [
|
|
735
|
+
"",
|
|
736
|
+
`Restricted agents (not executable in this session${restrictedSources?.length ? `; capability ceiling: ${restrictedSources.join(", ")}` : ""}):`,
|
|
737
|
+
...restrictedAgents.map(formatCatalogAgentLine),
|
|
738
|
+
] : []),
|
|
665
739
|
"",
|
|
666
740
|
"Chains:",
|
|
667
741
|
...(chains.length ? chains.map((c) => `- ${c.name} (${c.source}): ${c.description}`) : ["- (none)"]),
|
|
668
742
|
...(proactiveSuggestions.length ? ["", ...proactiveSuggestions] : []),
|
|
743
|
+
...(taskAdvice.length ? ["", ...taskAdvice] : []),
|
|
669
744
|
...(diagnostics.length ? ["", "Chain diagnostics:", ...diagnostics.map((entry) => `- ${entry.filePath}: ${entry.error}`)] : []),
|
|
670
745
|
];
|
|
671
|
-
return result(lines.join("\n")
|
|
746
|
+
return result(lines.join("\n"), false, {
|
|
747
|
+
catalog: {
|
|
748
|
+
version: 1,
|
|
749
|
+
agents: [
|
|
750
|
+
...agents.map((a) => catalogAgentMetadata(a, true, undefined)),
|
|
751
|
+
...restrictedAgents.map((a) => catalogAgentMetadata(a, false, restrictedSources)),
|
|
752
|
+
],
|
|
753
|
+
chains: chains.map((c) => ({ name: c.name, source: c.source, description: c.description })),
|
|
754
|
+
...(restrictedSources?.length ? { capabilityCeilingSources: restrictedSources } : {}),
|
|
755
|
+
},
|
|
756
|
+
});
|
|
672
757
|
}
|
|
673
758
|
|
|
674
759
|
function formatModelSource(agent: AgentConfig, currentModel: ParentModel | undefined): string {
|
|
@@ -760,12 +845,13 @@ function handleGet(params: ManagementParams, ctx: ManagementContext): AgentToolR
|
|
|
760
845
|
const blocks: string[] = [];
|
|
761
846
|
let anyFound = false;
|
|
762
847
|
if (params.agent) {
|
|
763
|
-
const
|
|
764
|
-
const
|
|
765
|
-
|
|
766
|
-
|
|
767
|
-
|
|
768
|
-
|
|
848
|
+
const matches = findAgents(params.agent, ctx.cwd, scope);
|
|
849
|
+
const distinctNames = [...new Set(matches.map((agent) => agent.name))];
|
|
850
|
+
if (distinctNames.length > 1) {
|
|
851
|
+
const msg = `Ambiguous agent alias or name '${params.agent}': ${distinctNames.sort((a, b) => a.localeCompare(b)).join(", ")}`;
|
|
852
|
+
if (!hasBoth) return result(msg, true);
|
|
853
|
+
blocks.push(msg);
|
|
854
|
+
} else if (!matches.length) {
|
|
769
855
|
const msg = `Agent '${params.agent}' not found. Available: ${availableNames(ctx.cwd, "agent").join(", ") || "none"}.`;
|
|
770
856
|
if (!hasBoth) return result(msg, true);
|
|
771
857
|
blocks.push(msg);
|
|
@@ -1027,13 +1113,14 @@ function handleDisable(params: ManagementParams, ctx: ManagementContext): AgentT
|
|
|
1027
1113
|
if (scope === "project" && d.projectSettingsPath === null) {
|
|
1028
1114
|
return result("Project override is not available here: no project config root (.pi or .agents) was found above the cwd. Use agentScope: 'user' or run from inside a project.", true);
|
|
1029
1115
|
}
|
|
1030
|
-
const effective =
|
|
1031
|
-
if (
|
|
1116
|
+
const effective = resolveEffectiveAgent(d, raw);
|
|
1117
|
+
if (effective.error) return result(effective.error, true);
|
|
1118
|
+
if (!effective.agent) {
|
|
1032
1119
|
return result(`Agent '${raw}' not found. Available: ${availableNames(ctx.cwd, "agent").join(", ") || "none"}.`, true);
|
|
1033
1120
|
}
|
|
1034
|
-
const runtimeName = effective.name;
|
|
1121
|
+
const runtimeName = effective.agent.name;
|
|
1035
1122
|
const settingsPath = mergeBuiltinAgentOverride(ctx.cwd, runtimeName, scope, { disabled: true });
|
|
1036
|
-
const after =
|
|
1123
|
+
const after = resolveEffectiveAgent(discoverAgentsAll(ctx.cwd), raw).agent;
|
|
1037
1124
|
if (after?.disabled === true) {
|
|
1038
1125
|
return result(`Disabled agent '${runtimeName}' via ${scope} settings override at ${settingsPath}. It is now hidden from runtime discovery and { action: "list" }.`);
|
|
1039
1126
|
}
|
|
@@ -1050,13 +1137,14 @@ function handleEnable(params: ManagementParams, ctx: ManagementContext): AgentTo
|
|
|
1050
1137
|
if (scope === "project" && d.projectSettingsPath === null) {
|
|
1051
1138
|
return result("Project override is not available here: no project config root (.pi or .agents) was found above the cwd. Use agentScope: 'user' or run from inside a project.", true);
|
|
1052
1139
|
}
|
|
1053
|
-
const effective =
|
|
1054
|
-
if (
|
|
1140
|
+
const effective = resolveEffectiveAgent(d, raw);
|
|
1141
|
+
if (effective.error) return result(effective.error, true);
|
|
1142
|
+
if (!effective.agent) {
|
|
1055
1143
|
return result(`Agent '${raw}' not found. Available: ${availableNames(ctx.cwd, "agent").join(", ") || "none"}.`, true);
|
|
1056
1144
|
}
|
|
1057
|
-
const runtimeName = effective.name;
|
|
1145
|
+
const runtimeName = effective.agent.name;
|
|
1058
1146
|
const { path: settingsPath, removed } = removeBuiltinAgentOverrideFields(ctx.cwd, runtimeName, scope, ["disabled"]);
|
|
1059
|
-
const after =
|
|
1147
|
+
const after = resolveEffectiveAgent(discoverAgentsAll(ctx.cwd), raw).agent;
|
|
1060
1148
|
if (after && after.disabled !== true) {
|
|
1061
1149
|
if (removed) return result(`Enabled agent '${runtimeName}' (removed disabled override at ${settingsPath}).`);
|
|
1062
1150
|
return result(`Agent '${runtimeName}' is already enabled.`);
|
|
@@ -5,6 +5,8 @@ export const KNOWN_FIELDS = new Set([
|
|
|
5
5
|
"name",
|
|
6
6
|
"package",
|
|
7
7
|
"description",
|
|
8
|
+
"alias",
|
|
9
|
+
"aliases",
|
|
8
10
|
"tools",
|
|
9
11
|
"model",
|
|
10
12
|
"fallbackModels",
|
|
@@ -50,6 +52,8 @@ export function serializeAgent(config: AgentConfig, options: SerializeAgentOptio
|
|
|
50
52
|
lines.push(`name: ${frontmatterNameForConfig(config)}`);
|
|
51
53
|
if (config.packageName) lines.push(`package: ${config.packageName}`);
|
|
52
54
|
lines.push(`description: ${config.description}`);
|
|
55
|
+
const aliasesValue = joinComma(config.aliases);
|
|
56
|
+
if (aliasesValue || preserve("alias", "aliases")) lines.push(`aliases: ${aliasesValue ?? ""}`);
|
|
53
57
|
|
|
54
58
|
const tools = [
|
|
55
59
|
...(config.tools ?? []),
|