@bastani/atomic 0.8.11 → 0.8.12
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 +43 -0
- package/dist/builtin/intercom/package.json +1 -1
- package/dist/builtin/mcp/package.json +1 -1
- package/dist/builtin/subagents/CHANGELOG.md +3 -0
- package/dist/builtin/subagents/package.json +1 -1
- package/dist/builtin/subagents/src/agents/agent-serializer.ts +3 -2
- package/dist/builtin/subagents/src/agents/agents.ts +1 -1
- package/dist/builtin/subagents/src/extension/index.ts +597 -471
- package/dist/builtin/subagents/src/runs/background/async-job-tracker.ts +16 -8
- package/dist/builtin/subagents/src/runs/background/subagent-runner.ts +9 -13
- package/dist/builtin/subagents/src/runs/foreground/execution.ts +7 -3
- package/dist/builtin/subagents/src/shared/formatters.ts +8 -3
- package/dist/builtin/subagents/src/slash/slash-commands.ts +625 -468
- package/dist/builtin/subagents/src/tui/render.ts +342 -158
- package/dist/builtin/web-access/package.json +1 -1
- package/dist/builtin/workflows/package.json +1 -1
- package/dist/builtin/workflows/src/runs/foreground/executor.ts +15 -4
- package/dist/builtin/workflows/src/runs/foreground/stage-control-registry.ts +75 -33
- package/dist/builtin/workflows/src/shared/store-types.ts +3 -4
- package/dist/builtin/workflows/src/shared/store.ts +2 -3
- package/dist/builtin/workflows/src/tui/graph-view.ts +12 -1
- package/dist/builtin/workflows/src/tui/stage-chat-view.ts +1 -2
- package/dist/builtin/workflows/src/tui/status-helpers.ts +1 -1
- package/dist/bun/cli.d.ts.map +1 -1
- package/dist/bun/cli.js.map +1 -1
- package/dist/cli/args.d.ts +1 -1
- package/dist/cli/args.d.ts.map +1 -1
- package/dist/cli/args.js.map +1 -1
- package/dist/cli/config-selector.d.ts +2 -2
- package/dist/cli/config-selector.d.ts.map +1 -1
- package/dist/cli/config-selector.js.map +1 -1
- package/dist/cli/file-processor.d.ts.map +1 -1
- package/dist/cli/file-processor.js.map +1 -1
- package/dist/cli/initial-message.d.ts +1 -1
- package/dist/cli/initial-message.d.ts.map +1 -1
- package/dist/cli/initial-message.js.map +1 -1
- package/dist/cli/list-models.d.ts +1 -1
- package/dist/cli/list-models.d.ts.map +1 -1
- package/dist/cli/list-models.js.map +1 -1
- package/dist/cli/session-picker.d.ts +1 -1
- package/dist/cli/session-picker.d.ts.map +1 -1
- package/dist/cli/session-picker.js.map +1 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +2 -6
- package/dist/cli.js.map +1 -1
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +45 -22
- package/dist/config.js.map +1 -1
- package/dist/core/agent-session-runtime.d.ts +9 -9
- package/dist/core/agent-session-runtime.d.ts.map +1 -1
- package/dist/core/agent-session-runtime.js +2 -3
- package/dist/core/agent-session-runtime.js.map +1 -1
- package/dist/core/agent-session-services.d.ts +7 -7
- package/dist/core/agent-session-services.d.ts.map +1 -1
- package/dist/core/agent-session-services.js.map +1 -1
- package/dist/core/agent-session.d.ts +10 -10
- package/dist/core/agent-session.d.ts.map +1 -1
- package/dist/core/agent-session.js.map +1 -1
- package/dist/core/atomic-guide-command.d.ts.map +1 -1
- package/dist/core/atomic-guide-command.js.map +1 -1
- package/dist/core/auth-guidance.d.ts.map +1 -1
- package/dist/core/auth-guidance.js.map +1 -1
- package/dist/core/auth-storage.d.ts +1 -1
- package/dist/core/auth-storage.d.ts.map +1 -1
- package/dist/core/auth-storage.js +1 -1
- package/dist/core/auth-storage.js.map +1 -1
- package/dist/core/bash-executor.d.ts +1 -1
- package/dist/core/bash-executor.d.ts.map +1 -1
- package/dist/core/bash-executor.js.map +1 -1
- package/dist/core/builtin-packages.d.ts.map +1 -1
- package/dist/core/builtin-packages.js.map +1 -1
- package/dist/core/compaction/branch-summarization.d.ts +3 -3
- package/dist/core/compaction/branch-summarization.d.ts.map +1 -1
- package/dist/core/compaction/branch-summarization.js.map +1 -1
- package/dist/core/compaction/compaction.d.ts +2 -2
- package/dist/core/compaction/compaction.d.ts.map +1 -1
- package/dist/core/compaction/compaction.js.map +1 -1
- package/dist/core/compaction/index.d.ts +3 -3
- package/dist/core/compaction/index.d.ts.map +1 -1
- package/dist/core/compaction/index.js.map +1 -1
- package/dist/core/exec.d.ts.map +1 -1
- package/dist/core/exec.js.map +1 -1
- package/dist/core/export-html/index.d.ts +1 -1
- package/dist/core/export-html/index.d.ts.map +1 -1
- package/dist/core/export-html/index.js.map +1 -1
- package/dist/core/export-html/tool-renderer.d.ts +2 -2
- package/dist/core/export-html/tool-renderer.d.ts.map +1 -1
- package/dist/core/export-html/tool-renderer.js.map +1 -1
- package/dist/core/extensions/index.d.ts +8 -8
- package/dist/core/extensions/index.d.ts.map +1 -1
- package/dist/core/extensions/index.js.map +1 -1
- package/dist/core/extensions/loader.d.ts +3 -3
- package/dist/core/extensions/loader.d.ts.map +1 -1
- package/dist/core/extensions/loader.js.map +1 -1
- package/dist/core/extensions/runner.d.ts +6 -6
- package/dist/core/extensions/runner.d.ts.map +1 -1
- package/dist/core/extensions/runner.js.map +1 -1
- package/dist/core/extensions/types.d.ts +20 -20
- package/dist/core/extensions/types.d.ts.map +1 -1
- package/dist/core/extensions/types.js.map +1 -1
- package/dist/core/extensions/wrapper.d.ts +2 -2
- package/dist/core/extensions/wrapper.d.ts.map +1 -1
- package/dist/core/extensions/wrapper.js.map +1 -1
- package/dist/core/footer-data-provider.d.ts.map +1 -1
- package/dist/core/footer-data-provider.js.map +1 -1
- package/dist/core/http-dispatcher.d.ts +32 -0
- package/dist/core/http-dispatcher.d.ts.map +1 -0
- package/dist/core/http-dispatcher.js +43 -0
- package/dist/core/http-dispatcher.js.map +1 -0
- package/dist/core/index.d.ts +8 -8
- package/dist/core/index.d.ts.map +1 -1
- package/dist/core/index.js.map +1 -1
- package/dist/core/keybindings.d.ts.map +1 -1
- package/dist/core/keybindings.js.map +1 -1
- package/dist/core/model-registry.d.ts +4 -4
- 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 -1
- package/dist/core/model-resolver.d.ts.map +1 -1
- package/dist/core/model-resolver.js.map +1 -1
- package/dist/core/package-manager.d.ts +1 -1
- package/dist/core/package-manager.d.ts.map +1 -1
- package/dist/core/package-manager.js +10 -11
- package/dist/core/package-manager.js.map +1 -1
- package/dist/core/prompt-templates.d.ts +1 -1
- package/dist/core/prompt-templates.d.ts.map +1 -1
- package/dist/core/prompt-templates.js.map +1 -1
- package/dist/core/resolve-config-value.d.ts.map +1 -1
- package/dist/core/resolve-config-value.js.map +1 -1
- package/dist/core/resource-loader.d.ts +9 -9
- package/dist/core/resource-loader.d.ts.map +1 -1
- package/dist/core/resource-loader.js.map +1 -1
- package/dist/core/sdk.d.ts +13 -13
- package/dist/core/sdk.d.ts.map +1 -1
- package/dist/core/sdk.js.map +1 -1
- package/dist/core/session-manager.d.ts +1 -1
- package/dist/core/session-manager.d.ts.map +1 -1
- package/dist/core/session-manager.js.map +1 -1
- package/dist/core/settings-manager.d.ts +3 -0
- package/dist/core/settings-manager.d.ts.map +1 -1
- package/dist/core/settings-manager.js +21 -0
- package/dist/core/settings-manager.js.map +1 -1
- package/dist/core/skills.d.ts +2 -2
- package/dist/core/skills.d.ts.map +1 -1
- package/dist/core/skills.js.map +1 -1
- package/dist/core/slash-commands.d.ts +1 -1
- package/dist/core/slash-commands.d.ts.map +1 -1
- package/dist/core/slash-commands.js.map +1 -1
- package/dist/core/source-info.d.ts +1 -1
- package/dist/core/source-info.d.ts.map +1 -1
- package/dist/core/source-info.js.map +1 -1
- package/dist/core/system-prompt.d.ts +1 -1
- package/dist/core/system-prompt.d.ts.map +1 -1
- package/dist/core/system-prompt.js +7 -8
- package/dist/core/system-prompt.js.map +1 -1
- package/dist/core/telemetry.d.ts +1 -1
- package/dist/core/telemetry.d.ts.map +1 -1
- package/dist/core/telemetry.js.map +1 -1
- package/dist/core/timings.d.ts.map +1 -1
- package/dist/core/timings.js.map +1 -1
- package/dist/core/tools/ask-user-question/ask-user-question.d.ts +4 -4
- package/dist/core/tools/ask-user-question/ask-user-question.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/ask-user-question.js.map +1 -1
- package/dist/core/tools/ask-user-question/index.d.ts +1 -1
- package/dist/core/tools/ask-user-question/index.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/index.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/build-questionnaire.d.ts +5 -5
- package/dist/core/tools/ask-user-question/state/build-questionnaire.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/build-questionnaire.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/key-router.d.ts +2 -2
- package/dist/core/tools/ask-user-question/state/key-router.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/key-router.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/questionnaire-session.d.ts +3 -3
- package/dist/core/tools/ask-user-question/state/questionnaire-session.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/questionnaire-session.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/row-intent.d.ts +2 -2
- package/dist/core/tools/ask-user-question/state/row-intent.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/row-intent.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/contract.d.ts +6 -6
- package/dist/core/tools/ask-user-question/state/selectors/contract.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/contract.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/derivations.d.ts +2 -2
- package/dist/core/tools/ask-user-question/state/selectors/derivations.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/derivations.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/focus.d.ts +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/focus.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/focus.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/projections.d.ts +8 -8
- package/dist/core/tools/ask-user-question/state/selectors/projections.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/selectors/projections.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/state-reducer.d.ts +4 -4
- package/dist/core/tools/ask-user-question/state/state-reducer.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/state-reducer.js.map +1 -1
- package/dist/core/tools/ask-user-question/state/state.d.ts +2 -2
- package/dist/core/tools/ask-user-question/state/state.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/state/state.js.map +1 -1
- package/dist/core/tools/ask-user-question/tool/format-answer.d.ts +1 -1
- package/dist/core/tools/ask-user-question/tool/format-answer.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/tool/format-answer.js.map +1 -1
- package/dist/core/tools/ask-user-question/tool/response-envelope.d.ts +1 -1
- package/dist/core/tools/ask-user-question/tool/response-envelope.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/tool/response-envelope.js.map +1 -1
- package/dist/core/tools/ask-user-question/tool/types.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/tool/types.js.map +1 -1
- package/dist/core/tools/ask-user-question/tool/validate-questionnaire.d.ts +1 -1
- package/dist/core/tools/ask-user-question/tool/validate-questionnaire.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/tool/validate-questionnaire.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/body-residual-spacer.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/body-residual-spacer.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/component-binding.d.ts +4 -4
- package/dist/core/tools/ask-user-question/view/component-binding.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/component-binding.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/chat-row-view.d.ts +2 -2
- package/dist/core/tools/ask-user-question/view/components/chat-row-view.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/chat-row-view.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/multi-select-view.d.ts +4 -4
- package/dist/core/tools/ask-user-question/view/components/multi-select-view.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/multi-select-view.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/option-list-view.d.ts +2 -2
- package/dist/core/tools/ask-user-question/view/components/option-list-view.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/option-list-view.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/preview/markdown-content-cache.d.ts +2 -2
- package/dist/core/tools/ask-user-question/view/components/preview/markdown-content-cache.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/preview/markdown-content-cache.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/preview/preview-block-renderer.d.ts +3 -3
- package/dist/core/tools/ask-user-question/view/components/preview/preview-block-renderer.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/preview/preview-block-renderer.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/preview/preview-layout-decider.d.ts +2 -2
- package/dist/core/tools/ask-user-question/view/components/preview/preview-layout-decider.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/preview/preview-layout-decider.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/preview/preview-pane.d.ts +8 -8
- package/dist/core/tools/ask-user-question/view/components/preview/preview-pane.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/preview/preview-pane.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/submit-picker.d.ts +3 -3
- package/dist/core/tools/ask-user-question/view/components/submit-picker.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/submit-picker.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/tab-bar.d.ts +3 -3
- package/dist/core/tools/ask-user-question/view/components/tab-bar.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/components/tab-bar.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/dialog-builder.d.ts +8 -8
- package/dist/core/tools/ask-user-question/view/dialog-builder.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/dialog-builder.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/props-adapter.d.ts +5 -5
- package/dist/core/tools/ask-user-question/view/props-adapter.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/props-adapter.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/tab-components.d.ts +4 -4
- package/dist/core/tools/ask-user-question/view/tab-components.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/tab-components.js.map +1 -1
- package/dist/core/tools/ask-user-question/view/tab-content-strategy.d.ts +9 -9
- package/dist/core/tools/ask-user-question/view/tab-content-strategy.d.ts.map +1 -1
- package/dist/core/tools/ask-user-question/view/tab-content-strategy.js +2 -2
- package/dist/core/tools/ask-user-question/view/tab-content-strategy.js.map +1 -1
- package/dist/core/tools/bash.d.ts +2 -2
- package/dist/core/tools/bash.d.ts.map +1 -1
- package/dist/core/tools/bash.js +9 -1
- package/dist/core/tools/bash.js.map +1 -1
- package/dist/core/tools/edit-diff.d.ts.map +1 -1
- package/dist/core/tools/edit-diff.js.map +1 -1
- package/dist/core/tools/edit.d.ts +2 -2
- package/dist/core/tools/edit.d.ts.map +1 -1
- package/dist/core/tools/edit.js.map +1 -1
- package/dist/core/tools/find.d.ts +2 -2
- package/dist/core/tools/find.d.ts.map +1 -1
- package/dist/core/tools/find.js.map +1 -1
- package/dist/core/tools/grep.d.ts +2 -2
- package/dist/core/tools/grep.d.ts.map +1 -1
- package/dist/core/tools/grep.js.map +1 -1
- package/dist/core/tools/index.d.ts +19 -19
- package/dist/core/tools/index.d.ts.map +1 -1
- package/dist/core/tools/index.js.map +1 -1
- package/dist/core/tools/ls.d.ts +2 -2
- package/dist/core/tools/ls.d.ts.map +1 -1
- package/dist/core/tools/ls.js.map +1 -1
- package/dist/core/tools/output-accumulator.d.ts +1 -1
- package/dist/core/tools/output-accumulator.d.ts.map +1 -1
- package/dist/core/tools/output-accumulator.js.map +1 -1
- package/dist/core/tools/read.d.ts +2 -2
- package/dist/core/tools/read.d.ts.map +1 -1
- package/dist/core/tools/read.js.map +1 -1
- package/dist/core/tools/render-utils.d.ts +1 -1
- package/dist/core/tools/render-utils.d.ts.map +1 -1
- package/dist/core/tools/render-utils.js.map +1 -1
- package/dist/core/tools/todos.d.ts +1 -1
- package/dist/core/tools/todos.d.ts.map +1 -1
- package/dist/core/tools/todos.js.map +1 -1
- package/dist/core/tools/tool-definition-wrapper.d.ts +1 -1
- package/dist/core/tools/tool-definition-wrapper.d.ts.map +1 -1
- package/dist/core/tools/tool-definition-wrapper.js.map +1 -1
- package/dist/core/tools/write.d.ts +1 -1
- package/dist/core/tools/write.d.ts.map +1 -1
- package/dist/core/tools/write.js.map +1 -1
- package/dist/index.d.ts +30 -29
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/main.d.ts +1 -1
- package/dist/main.d.ts.map +1 -1
- package/dist/main.js +2 -0
- package/dist/main.js.map +1 -1
- package/dist/migrations.d.ts.map +1 -1
- package/dist/migrations.js.map +1 -1
- package/dist/modes/index.d.ts +5 -5
- package/dist/modes/index.d.ts.map +1 -1
- package/dist/modes/index.js.map +1 -1
- package/dist/modes/interactive/components/armin.d.ts.map +1 -1
- package/dist/modes/interactive/components/armin.js.map +1 -1
- package/dist/modes/interactive/components/assistant-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/assistant-message.js.map +1 -1
- package/dist/modes/interactive/components/atomic-banner.d.ts +1 -1
- package/dist/modes/interactive/components/atomic-banner.d.ts.map +1 -1
- package/dist/modes/interactive/components/atomic-banner.js.map +1 -1
- package/dist/modes/interactive/components/bash-execution.d.ts +1 -1
- package/dist/modes/interactive/components/bash-execution.d.ts.map +1 -1
- package/dist/modes/interactive/components/bash-execution.js.map +1 -1
- package/dist/modes/interactive/components/bordered-loader.d.ts +1 -1
- package/dist/modes/interactive/components/bordered-loader.d.ts.map +1 -1
- package/dist/modes/interactive/components/bordered-loader.js.map +1 -1
- package/dist/modes/interactive/components/branch-summary-message.d.ts +1 -1
- package/dist/modes/interactive/components/branch-summary-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/branch-summary-message.js.map +1 -1
- package/dist/modes/interactive/components/chat-message-renderer.d.ts +3 -3
- package/dist/modes/interactive/components/chat-message-renderer.d.ts.map +1 -1
- package/dist/modes/interactive/components/chat-message-renderer.js +1 -1
- package/dist/modes/interactive/components/chat-message-renderer.js.map +1 -1
- package/dist/modes/interactive/components/chat-transcript.d.ts.map +1 -1
- package/dist/modes/interactive/components/chat-transcript.js.map +1 -1
- package/dist/modes/interactive/components/compaction-summary-message.d.ts +1 -1
- package/dist/modes/interactive/components/compaction-summary-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/compaction-summary-message.js.map +1 -1
- package/dist/modes/interactive/components/config-selector.d.ts +2 -2
- package/dist/modes/interactive/components/config-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/config-selector.js.map +1 -1
- package/dist/modes/interactive/components/countdown-timer.d.ts +2 -2
- package/dist/modes/interactive/components/countdown-timer.d.ts.map +1 -1
- package/dist/modes/interactive/components/countdown-timer.js.map +1 -1
- package/dist/modes/interactive/components/custom-editor.d.ts +1 -1
- package/dist/modes/interactive/components/custom-editor.d.ts.map +1 -1
- package/dist/modes/interactive/components/custom-editor.js.map +1 -1
- package/dist/modes/interactive/components/custom-message.d.ts +2 -2
- package/dist/modes/interactive/components/custom-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/custom-message.js.map +1 -1
- package/dist/modes/interactive/components/daxnuts.d.ts.map +1 -1
- package/dist/modes/interactive/components/daxnuts.js.map +1 -1
- package/dist/modes/interactive/components/diff.d.ts.map +1 -1
- package/dist/modes/interactive/components/diff.js.map +1 -1
- package/dist/modes/interactive/components/dynamic-border.d.ts.map +1 -1
- package/dist/modes/interactive/components/dynamic-border.js.map +1 -1
- package/dist/modes/interactive/components/earendil-announcement.d.ts.map +1 -1
- package/dist/modes/interactive/components/earendil-announcement.js.map +1 -1
- package/dist/modes/interactive/components/extension-editor.d.ts +1 -1
- package/dist/modes/interactive/components/extension-editor.d.ts.map +1 -1
- package/dist/modes/interactive/components/extension-editor.js.map +1 -1
- package/dist/modes/interactive/components/extension-input.d.ts.map +1 -1
- package/dist/modes/interactive/components/extension-input.js.map +1 -1
- package/dist/modes/interactive/components/extension-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/extension-selector.js.map +1 -1
- package/dist/modes/interactive/components/footer.d.ts +3 -3
- package/dist/modes/interactive/components/footer.d.ts.map +1 -1
- package/dist/modes/interactive/components/footer.js +1 -1
- package/dist/modes/interactive/components/footer.js.map +1 -1
- package/dist/modes/interactive/components/index.d.ts +34 -34
- package/dist/modes/interactive/components/index.d.ts.map +1 -1
- package/dist/modes/interactive/components/index.js.map +1 -1
- package/dist/modes/interactive/components/keybinding-hints.d.ts.map +1 -1
- package/dist/modes/interactive/components/keybinding-hints.js.map +1 -1
- package/dist/modes/interactive/components/login-dialog.d.ts +1 -1
- package/dist/modes/interactive/components/login-dialog.d.ts.map +1 -1
- package/dist/modes/interactive/components/login-dialog.js +1 -1
- package/dist/modes/interactive/components/login-dialog.js.map +1 -1
- package/dist/modes/interactive/components/model-selector.d.ts +2 -2
- package/dist/modes/interactive/components/model-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/model-selector.js.map +1 -1
- package/dist/modes/interactive/components/oauth-selector.d.ts +1 -1
- package/dist/modes/interactive/components/oauth-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/oauth-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.map +1 -1
- package/dist/modes/interactive/components/session-selector-search.d.ts +1 -1
- package/dist/modes/interactive/components/session-selector-search.d.ts.map +1 -1
- package/dist/modes/interactive/components/session-selector-search.js.map +1 -1
- package/dist/modes/interactive/components/session-selector.d.ts +3 -3
- package/dist/modes/interactive/components/session-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/session-selector.js.map +1 -1
- package/dist/modes/interactive/components/settings-selector.d.ts +3 -1
- package/dist/modes/interactive/components/settings-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/settings-selector.js +13 -0
- package/dist/modes/interactive/components/settings-selector.js.map +1 -1
- package/dist/modes/interactive/components/show-images-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/show-images-selector.js.map +1 -1
- package/dist/modes/interactive/components/skill-invocation-message.d.ts +1 -1
- package/dist/modes/interactive/components/skill-invocation-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/skill-invocation-message.js.map +1 -1
- package/dist/modes/interactive/components/theme-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/theme-selector.js.map +1 -1
- package/dist/modes/interactive/components/thinking-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/thinking-selector.js.map +1 -1
- package/dist/modes/interactive/components/tool-execution.d.ts +1 -1
- package/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
- package/dist/modes/interactive/components/tool-execution.js.map +1 -1
- package/dist/modes/interactive/components/tree-selector.d.ts +1 -1
- package/dist/modes/interactive/components/tree-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/tree-selector.js.map +1 -1
- package/dist/modes/interactive/components/user-message-selector.d.ts.map +1 -1
- package/dist/modes/interactive/components/user-message-selector.js.map +1 -1
- package/dist/modes/interactive/components/user-message.d.ts.map +1 -1
- package/dist/modes/interactive/components/user-message.js.map +1 -1
- package/dist/modes/interactive/components/working-status.d.ts.map +1 -1
- package/dist/modes/interactive/components/working-status.js.map +1 -1
- package/dist/modes/interactive/interactive-mode.d.ts +2 -2
- package/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
- package/dist/modes/interactive/interactive-mode.js +7 -1
- package/dist/modes/interactive/interactive-mode.js.map +1 -1
- package/dist/modes/interactive/theme/theme.d.ts +1 -1
- package/dist/modes/interactive/theme/theme.d.ts.map +1 -1
- package/dist/modes/interactive/theme/theme.js.map +1 -1
- package/dist/modes/print-mode.d.ts +1 -1
- package/dist/modes/print-mode.d.ts.map +1 -1
- package/dist/modes/print-mode.js.map +1 -1
- package/dist/modes/rpc/rpc-client.d.ts +5 -5
- package/dist/modes/rpc/rpc-client.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-client.js +1 -1
- package/dist/modes/rpc/rpc-client.js.map +1 -1
- package/dist/modes/rpc/rpc-mode.d.ts +2 -2
- package/dist/modes/rpc/rpc-mode.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-mode.js.map +1 -1
- package/dist/modes/rpc/rpc-types.d.ts +4 -4
- package/dist/modes/rpc/rpc-types.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-types.js.map +1 -1
- package/dist/package-manager-cli.d.ts.map +1 -1
- package/dist/package-manager-cli.js +22 -6
- package/dist/package-manager-cli.js.map +1 -1
- package/dist/utils/changelog.d.ts +1 -1
- package/dist/utils/changelog.d.ts.map +1 -1
- package/dist/utils/changelog.js.map +1 -1
- package/dist/utils/child-process.d.ts +5 -2
- package/dist/utils/child-process.d.ts.map +1 -1
- package/dist/utils/child-process.js +9 -7
- package/dist/utils/child-process.js.map +1 -1
- package/dist/utils/clipboard-image.d.ts.map +1 -1
- package/dist/utils/clipboard-image.js.map +1 -1
- package/dist/utils/clipboard.d.ts.map +1 -1
- package/dist/utils/clipboard.js.map +1 -1
- package/dist/utils/exif-orientation.d.ts +1 -1
- package/dist/utils/exif-orientation.d.ts.map +1 -1
- package/dist/utils/exif-orientation.js.map +1 -1
- package/dist/utils/image-convert.d.ts.map +1 -1
- package/dist/utils/image-convert.js.map +1 -1
- package/dist/utils/image-resize.d.ts.map +1 -1
- package/dist/utils/image-resize.js.map +1 -1
- package/dist/utils/shell.d.ts.map +1 -1
- package/dist/utils/shell.js.map +1 -1
- package/dist/utils/syntax-highlight.d.ts.map +1 -1
- package/dist/utils/syntax-highlight.js.map +1 -1
- package/dist/utils/tools-manager.d.ts.map +1 -1
- package/dist/utils/tools-manager.js.map +1 -1
- package/dist/utils/version-check.d.ts.map +1 -1
- package/dist/utils/version-check.js.map +1 -1
- package/dist/utils/windows-self-update.d.ts +3 -0
- package/dist/utils/windows-self-update.d.ts.map +1 -0
- package/dist/utils/windows-self-update.js +78 -0
- package/dist/utils/windows-self-update.js.map +1 -0
- package/docs/compaction.md +5 -5
- package/docs/custom-provider.md +2 -2
- package/docs/development.md +22 -16
- package/docs/docs.json +6 -2
- package/docs/extensions.md +25 -25
- package/docs/index.md +11 -14
- package/docs/keybindings.md +5 -5
- package/docs/models.md +6 -6
- package/docs/packages.md +55 -48
- package/docs/prompt-templates.md +5 -5
- package/docs/providers.md +10 -10
- package/docs/quickstart.md +32 -30
- package/docs/rpc.md +9 -9
- package/docs/sdk.md +1 -1
- package/docs/session-format.md +3 -3
- package/docs/sessions.md +11 -11
- package/docs/settings.md +18 -15
- package/docs/shell-aliases.md +2 -2
- package/docs/skills.md +11 -11
- package/docs/terminal-setup.md +8 -8
- package/docs/termux.md +6 -6
- package/docs/themes.md +10 -10
- package/docs/tui.md +5 -4
- package/docs/usage.md +50 -50
- package/docs/windows.md +2 -2
- package/docs/workflows.md +695 -0
- package/examples/extensions/custom-provider-gitlab-duo/test.ts +1 -1
- package/examples/extensions/doom-overlay/doom-component.ts +2 -2
- package/examples/extensions/doom-overlay/index.ts +3 -3
- package/examples/extensions/overlay-qa-tests.ts +116 -33
- package/examples/extensions/overlay-test.ts +9 -3
- package/examples/extensions/plan-mode/index.ts +1 -1
- package/examples/extensions/subagent/index.ts +1159 -903
- package/package.json +6 -4
- package/dist/builtin/workflows/skills/workflow/SKILL.md +0 -322
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/advanced-evaluation.md +0 -404
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/bdi-mental-states.md +0 -313
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/context-compression.md +0 -274
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/context-degradation.md +0 -208
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/context-fundamentals.md +0 -203
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/context-optimization.md +0 -197
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/evaluation.md +0 -253
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/filesystem-context.md +0 -289
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/hosted-agents.md +0 -262
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/memory-systems.md +0 -221
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/multi-agent-patterns.md +0 -259
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/project-development.md +0 -293
- package/dist/builtin/workflows/skills/workflow/references/context-engineering/tool-design.md +0 -273
- package/dist/builtin/workflows/skills/workflow/references/context-engineering.md +0 -23
- package/dist/builtin/workflows/skills/workflow/references/design-checklist.md +0 -83
- package/dist/builtin/workflows/skills/workflow/references/running-workflows.md +0 -159
- package/dist/builtin/workflows/skills/workflow/references/sdk-authoring.md +0 -260
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"chat-message-renderer.d.ts","sourceRoot":"","sources":["../../../../src/modes/interactive/components/chat-message-renderer.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AssistantMessage, ToolResultMessage } from \"@earendil-works/pi-ai\";\nimport type { AgentMessage } from \"@earendil-works/pi-agent-core\";\nimport { Container, Text, type Component, type MarkdownTheme, type TUI } from \"@earendil-works/pi-tui\";\nimport type { TSchema } from \"typebox\";\nimport type { MessageRenderer, ToolDefinition } from \"../../../core/extensions/types.js\";\nimport type {\n BashExecutionMessage,\n BranchSummaryMessage,\n CompactionSummaryMessage,\n CustomMessage,\n} from \"../../../core/messages.js\";\nimport { parseSkillBlock } from \"../../../core/agent-session.js\";\nimport { getMarkdownTheme, theme } from \"../theme/theme.js\";\nimport { AssistantMessageComponent } from \"./assistant-message.js\";\nimport { BashExecutionComponent } from \"./bash-execution.js\";\nimport { BranchSummaryMessageComponent } from \"./branch-summary-message.js\";\nimport { CompactionSummaryMessageComponent } from \"./compaction-summary-message.js\";\nimport { CustomMessageComponent } from \"./custom-message.js\";\nimport { SkillInvocationMessageComponent } from \"./skill-invocation-message.js\";\nimport { ToolExecutionComponent } from \"./tool-execution.js\";\nimport { UserMessageComponent } from \"./user-message.js\";\n\nexport type ChatMessageEntry =\n | { role: \"assistant\"; kind: \"assistant\"; message: AssistantMessage }\n | {\n role: \"tool\";\n kind: \"tool\";\n toolName: string;\n toolCallId: string;\n args: unknown;\n result?: ToolResultMessage;\n isPartial?: boolean;\n }\n | { role: \"tool\"; kind: \"bashExecution\"; message: BashExecutionMessage }\n | { role: \"user\"; kind: \"user\"; text: string }\n | { role: \"custom\"; kind: \"custom\"; message: CustomMessage<unknown> }\n | { role: \"summary\"; kind: \"branchSummary\"; message: BranchSummaryMessage }\n | { role: \"summary\"; kind: \"compactionSummary\"; message: CompactionSummaryMessage }\n | { role: \"system\"; kind: \"system\"; text: string };\n\nexport interface ChatMessageRenderOptions {\n ui: Pick<TUI, \"requestRender\">;\n cwd: string;\n markdownTheme?: MarkdownTheme;\n hideThinkingBlock?: boolean;\n hiddenThinkingLabel?: string;\n toolOutputExpanded?: boolean;\n showImages?: boolean;\n imageWidthCells?: number;\n getToolDefinition?: (toolName: string) => ToolDefinition<TSchema, unknown> | undefined;\n getCustomMessageRenderer?: (customType: string) => MessageRenderer | undefined;\n}\n\nexport function chatEntriesFromAgentMessages(\n messages: readonly AgentMessage[],\n): ChatMessageEntry[] {\n const entries: ChatMessageEntry[] = [];\n const pendingTools = new Map<string, Extract<ChatMessageEntry, { kind: \"tool\" }>>();\n\n for (const message of messages) {\n switch (message.role) {\n case \"assistant\": {\n entries.push({ role: \"assistant\", kind: \"assistant\", message });\n for (const content of message.content) {\n if (content.type !== \"toolCall\") continue;\n const toolEntry: ChatMessageEntry = {\n role: \"tool\",\n kind: \"tool\",\n toolName: content.name,\n toolCallId: content.id,\n args: content.arguments,\n isPartial: true,\n };\n entries.push(toolEntry);\n pendingTools.set(content.id, toolEntry);\n }\n if (message.stopReason === \"aborted\" || message.stopReason === \"error\") {\n const errorText = message.stopReason === \"aborted\"\n ? message.errorMessage || \"Operation aborted\"\n : message.errorMessage || \"Unknown error\";\n for (const toolEntry of pendingTools.values()) {\n toolEntry.result = {\n role: \"toolResult\",\n toolCallId: toolEntry.toolCallId,\n toolName: toolEntry.toolName,\n content: [{ type: \"text\", text: errorText }],\n isError: true,\n timestamp: message.timestamp,\n };\n toolEntry.isPartial = false;\n }\n pendingTools.clear();\n }\n break;\n }\n case \"toolResult\": {\n const toolEntry = pendingTools.get(message.toolCallId);\n if (toolEntry) {\n toolEntry.result = message;\n toolEntry.isPartial = false;\n pendingTools.delete(message.toolCallId);\n } else {\n entries.push({\n role: \"tool\",\n kind: \"tool\",\n toolName: message.toolName,\n toolCallId: message.toolCallId,\n args: {},\n result: message,\n isPartial: false,\n });\n }\n break;\n }\n case \"user\": {\n const text = getMessageText(message);\n if (text) entries.push({ role: \"user\", kind: \"user\", text });\n break;\n }\n case \"bashExecution\":\n entries.push({ role: \"tool\", kind: \"bashExecution\", message });\n break;\n case \"custom\":\n if (message.display) entries.push({ role: \"custom\", kind: \"custom\", message });\n break;\n case \"branchSummary\":\n entries.push({ role: \"summary\", kind: \"branchSummary\", message });\n break;\n case \"compactionSummary\":\n entries.push({ role: \"summary\", kind: \"compactionSummary\", message });\n break;\n default: {\n const role = (message as { role: string }).role;\n entries.push({ role: \"system\", kind: \"system\", text: role });\n break;\n }\n }\n }\n\n return entries;\n}\n\nexport interface LiveChatEventLike {\n readonly type?: unknown;\n readonly message?: unknown;\n readonly assistantMessageEvent?: { readonly type?: unknown; readonly delta?: unknown };\n readonly toolCallId?: unknown;\n readonly toolName?: unknown;\n readonly args?: unknown;\n readonly partialResult?: unknown;\n readonly result?: unknown;\n readonly isError?: unknown;\n}\n\ntype LiveChatEntry = ChatMessageEntry | { role: string };\n\nexport class LiveChatEntriesController {\n private streamingAssistantIndex: number | undefined;\n private pendingToolIndexes = new Map<string, number>();\n\n constructor(private readonly entries: LiveChatEntry[]) {}\n\n appendMessages(messages: readonly AgentMessage[]): void {\n this.entries.push(...chatEntriesFromAgentMessages(messages));\n this.reindexPendingTools();\n }\n\n appendUserText(text: string): void {\n this.entries.push({ role: \"user\", kind: \"user\", text });\n }\n\n applyEvent(event: LiveChatEventLike): boolean {\n const type = String(event.type ?? \"\");\n switch (type) {\n case \"message_start\":\n return this.handleMessageStart(event.message);\n case \"message_update\":\n return this.handleMessageUpdate(event);\n case \"message_end\":\n return this.handleMessageEnd(event.message);\n case \"tool_execution_start\":\n return this.upsertToolEntry({\n toolCallId: typeof event.toolCallId === \"string\" ? event.toolCallId : undefined,\n toolName: typeof event.toolName === \"string\" ? event.toolName : \"tool\",\n args: event.args,\n isPartial: true,\n });\n case \"tool_execution_update\": {\n const toolCallId = typeof event.toolCallId === \"string\" ? event.toolCallId : undefined;\n if (!toolCallId) return false;\n return this.updateToolResult(toolCallId, event.partialResult, true, false);\n }\n case \"tool_execution_end\": {\n const toolCallId = typeof event.toolCallId === \"string\" ? event.toolCallId : undefined;\n if (!toolCallId) return false;\n return this.updateToolResult(toolCallId, event.result, false, event.isError === true);\n }\n default:\n return false;\n }\n }\n\n pendingToolIds(): string[] {\n return [...this.pendingToolIndexes.keys()];\n }\n\n clearPendingTools(): void {\n this.pendingToolIndexes.clear();\n }\n\n private handleMessageStart(message: unknown): boolean {\n if (!isAgentMessageLike(message)) return false;\n if (message.role === \"assistant\") {\n this.streamingAssistantIndex = undefined;\n return this.updateAssistantMessage(message as AssistantMessage);\n }\n const entries = chatEntriesFromAgentMessages([message as AgentMessage]);\n if (entries.length === 0) return false;\n this.entries.push(...entries);\n this.reindexPendingTools();\n return true;\n }\n\n private handleMessageUpdate(event: LiveChatEventLike): boolean {\n const message = event.message;\n let changed = false;\n const snapshotHasPayload = isAgentMessageLike(message) &&\n message.role === \"assistant\" &&\n assistantContentHasRenderablePayload((message as { content?: unknown }).content);\n if (isAgentMessageLike(message) && message.role === \"assistant\" && snapshotHasPayload) {\n changed = this.updateAssistantMessage(message as AssistantMessage) || changed;\n }\n const assistantEvent = event.assistantMessageEvent;\n const streamType = String(assistantEvent?.type ?? \"\");\n const delta = typeof assistantEvent?.delta === \"string\" ? assistantEvent.delta : \"\";\n if (!changed && streamType === \"text_delta\" && delta) {\n changed = this.appendAssistantTextDelta(delta);\n } else if (!changed && streamType === \"thinking_delta\" && delta) {\n changed = this.appendAssistantThinkingDelta(delta);\n }\n return changed;\n }\n\n private handleMessageEnd(message: unknown): boolean {\n if (!isAgentMessageLike(message) || message.role !== \"assistant\") return false;\n const changed = this.updateAssistantMessage(message as AssistantMessage);\n const stopReason = typeof message.stopReason === \"string\" ? message.stopReason : \"\";\n if (stopReason === \"aborted\" || stopReason === \"error\") {\n const errorText = typeof message.errorMessage === \"string\" && message.errorMessage\n ? message.errorMessage\n : stopReason === \"aborted\"\n ? \"Operation aborted\"\n : \"Unknown error\";\n for (const toolCallId of this.pendingToolIds()) {\n this.updateToolResult(toolCallId, { content: [{ type: \"text\", text: errorText }] }, false, true);\n }\n this.clearPendingTools();\n }\n this.streamingAssistantIndex = undefined;\n return changed || true;\n }\n\n private updateAssistantMessage(message: AssistantMessage): boolean {\n if (this.streamingAssistantIndex !== undefined && this.isAssistantEntry(this.entries[this.streamingAssistantIndex])) {\n this.entries[this.streamingAssistantIndex] = {\n ...(this.entries[this.streamingAssistantIndex] as Extract<ChatMessageEntry, { kind: \"assistant\" }>),\n message,\n };\n } else {\n this.entries.push({ role: \"assistant\", kind: \"assistant\", message });\n this.streamingAssistantIndex = this.entries.length - 1;\n }\n for (const content of message.content) {\n if (content.type !== \"toolCall\") continue;\n this.upsertToolEntry({\n toolCallId: content.id,\n toolName: content.name,\n args: content.arguments,\n isPartial: true,\n });\n }\n return true;\n }\n\n private appendAssistantTextDelta(delta: string): boolean {\n const current = this.currentStreamingAssistantMessage();\n const content = current ? [...current.content] : [];\n const lastText = [...content].reverse().find((item) => item.type === \"text\");\n if (lastText && lastText.type === \"text\") lastText.text += delta;\n else content.push({ type: \"text\", text: delta });\n return this.updateAssistantMessage({\n ...(current ?? minimalAssistantMessage()),\n content,\n });\n }\n\n private appendAssistantThinkingDelta(delta: string): boolean {\n const current = this.currentStreamingAssistantMessage();\n const content = current ? [...current.content] : [];\n const lastThinking = [...content].reverse().find((item) => item.type === \"thinking\");\n if (lastThinking && lastThinking.type === \"thinking\") lastThinking.thinking += delta;\n else content.push({ type: \"thinking\", thinking: delta });\n return this.updateAssistantMessage({\n ...(current ?? minimalAssistantMessage()),\n content,\n });\n }\n\n private currentStreamingAssistantMessage(): AssistantMessage | undefined {\n const entry = this.streamingAssistantIndex !== undefined ? this.entries[this.streamingAssistantIndex] : undefined;\n return this.isAssistantEntry(entry) ? entry.message : undefined;\n }\n\n private upsertToolEntry(update: {\n toolCallId?: string;\n toolName: string;\n args?: unknown;\n isPartial: boolean;\n }): boolean {\n const toolCallId = update.toolCallId ?? `live-${update.toolName}`;\n const index = this.pendingToolIndexes.get(toolCallId) ?? this.findToolEntryIndex(toolCallId, update.toolName);\n const previous = index >= 0 ? this.entries[index] : undefined;\n const previousTool = this.isToolEntry(previous) ? previous : undefined;\n const next: ChatMessageEntry = {\n role: \"tool\",\n kind: \"tool\",\n toolName: previousTool?.toolName ?? update.toolName,\n toolCallId,\n args: update.args ?? previousTool?.args ?? {},\n result: previousTool?.result,\n isPartial: update.isPartial,\n };\n if (index >= 0) this.entries[index] = next;\n else this.entries.push(next);\n this.pendingToolIndexes.set(toolCallId, index >= 0 ? index : this.entries.length - 1);\n return true;\n }\n\n private updateToolResult(toolCallId: string, result: unknown, isPartial: boolean, isError: boolean): boolean {\n const index = this.pendingToolIndexes.get(toolCallId) ?? this.findToolEntryIndex(toolCallId);\n if (index < 0) return false;\n const entry = this.entries[index];\n if (!this.isToolEntry(entry)) return false;\n const resultObject = toolResultFromUnknown(result, entry.toolName, toolCallId, isError);\n this.entries[index] = { ...entry, result: resultObject, isPartial };\n if (!isPartial) this.pendingToolIndexes.delete(toolCallId);\n return true;\n }\n\n private findToolEntryIndex(toolCallId: string, toolName?: string): number {\n for (let i = this.entries.length - 1; i >= 0; i--) {\n const entry = this.entries[i];\n if (!this.isToolEntry(entry)) continue;\n if (entry.toolCallId === toolCallId || (toolName && entry.toolName === toolName && entry.isPartial !== false)) return i;\n }\n return -1;\n }\n\n private reindexPendingTools(): void {\n this.pendingToolIndexes.clear();\n for (let i = 0; i < this.entries.length; i++) {\n const entry = this.entries[i];\n if (this.isToolEntry(entry) && entry.isPartial !== false) this.pendingToolIndexes.set(entry.toolCallId, i);\n }\n }\n\n private isAssistantEntry(entry: LiveChatEntry | undefined): entry is Extract<ChatMessageEntry, { kind: \"assistant\" }> {\n return isChatMessageEntry(entry) && entry.kind === \"assistant\";\n }\n\n private isToolEntry(entry: LiveChatEntry | undefined): entry is Extract<ChatMessageEntry, { kind: \"tool\" }> {\n return isChatMessageEntry(entry) && entry.kind === \"tool\";\n }\n}\n\nfunction isChatMessageEntry(entry: LiveChatEntry | undefined): entry is ChatMessageEntry {\n return entry !== undefined && \"kind\" in entry;\n}\n\nfunction isAgentMessageLike(message: unknown): message is AgentMessage & { stopReason?: unknown; errorMessage?: unknown } {\n return message !== null && typeof message === \"object\" && \"role\" in message;\n}\n\nfunction assistantContentHasRenderablePayload(content: unknown): boolean {\n if (typeof content === \"string\") return content.length > 0;\n if (!Array.isArray(content)) return false;\n return content.some((item) => {\n if (typeof item === \"string\") return item.length > 0;\n if (item == null || typeof item !== \"object\") return false;\n const obj = item as { type?: unknown; text?: unknown; thinking?: unknown };\n return (obj.type === \"text\" && typeof obj.text === \"string\" && obj.text.length > 0) ||\n (obj.type === \"thinking\" && typeof obj.thinking === \"string\" && obj.thinking.length > 0) ||\n obj.type === \"toolCall\";\n });\n}\n\nfunction minimalAssistantMessage(): AssistantMessage {\n return {\n role: \"assistant\",\n content: [],\n stopReason: \"stop\",\n } as unknown as AssistantMessage;\n}\n\nfunction toolResultFromUnknown(\n result: unknown,\n toolName: string,\n toolCallId: string,\n isError: boolean,\n): ToolResultMessage {\n if (result !== null && typeof result === \"object\" && \"content\" in result) {\n const candidate = result as { content?: unknown; details?: unknown };\n const content = Array.isArray(candidate.content) ? candidate.content : [];\n return {\n role: \"toolResult\",\n toolCallId,\n toolName,\n content: content as ToolResultMessage[\"content\"],\n details: candidate.details,\n isError,\n timestamp: Date.now(),\n };\n }\n return {\n role: \"toolResult\",\n toolCallId,\n toolName,\n content: typeof result === \"string\" ? [{ type: \"text\", text: result }] : [],\n isError,\n timestamp: Date.now(),\n };\n}\n\nexport function renderChatMessageEntry(\n entry: ChatMessageEntry,\n options: ChatMessageRenderOptions,\n): Component {\n const messageEntry = entry as ChatMessageEntry;\n const markdownTheme = options.markdownTheme ?? getMarkdownTheme();\n\n switch (messageEntry.kind) {\n case \"assistant\":\n return new AssistantMessageComponent(\n messageEntry.message,\n options.hideThinkingBlock ?? false,\n markdownTheme,\n options.hiddenThinkingLabel ?? \"Thinking...\",\n );\n case \"tool\": {\n const component = new ToolExecutionComponent(\n messageEntry.toolName,\n messageEntry.toolCallId,\n messageEntry.args,\n {\n showImages: options.showImages ?? true,\n imageWidthCells: options.imageWidthCells,\n },\n options.getToolDefinition?.(messageEntry.toolName),\n options.ui as TUI,\n options.cwd,\n );\n component.setExpanded(options.toolOutputExpanded ?? false);\n if (messageEntry.result) component.updateResult(messageEntry.result, messageEntry.isPartial ?? false);\n return component;\n }\n case \"bashExecution\": {\n const component = new BashExecutionComponent(\n messageEntry.message.command,\n options.ui as TUI,\n messageEntry.message.excludeFromContext,\n );\n if (messageEntry.message.output) component.appendOutput(messageEntry.message.output);\n component.setComplete(\n messageEntry.message.exitCode,\n messageEntry.message.cancelled,\n messageEntry.message.truncated\n ? ({ truncated: true } as Parameters<BashExecutionComponent[\"setComplete\"]>[2])\n : undefined,\n messageEntry.message.fullOutputPath,\n );\n return component;\n }\n case \"user\":\n return userMessageComponent(messageEntry.text, markdownTheme, options.toolOutputExpanded ?? false);\n case \"custom\": {\n const component = new CustomMessageComponent(\n messageEntry.message,\n options.getCustomMessageRenderer?.(messageEntry.message.customType),\n markdownTheme,\n );\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"branchSummary\": {\n const component = new BranchSummaryMessageComponent(messageEntry.message, markdownTheme);\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"compactionSummary\": {\n const component = new CompactionSummaryMessageComponent(messageEntry.message, markdownTheme);\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"system\":\n return new Text(theme.fg(\"dim\", messageEntry.text), 1, 0);\n }\n}\n\nfunction userMessageComponent(text: string, markdownTheme: MarkdownTheme, expanded: boolean): Component {\n const skillBlock = parseSkillBlock(text);\n if (!skillBlock) return new UserMessageComponent(text, markdownTheme);\n\n const container = new Container();\n const skillComponent = new SkillInvocationMessageComponent(skillBlock, markdownTheme);\n skillComponent.setExpanded(expanded);\n container.addChild(skillComponent);\n if (skillBlock.userMessage) {\n container.addChild(new UserMessageComponent(skillBlock.userMessage, markdownTheme));\n }\n return container;\n}\n\nfunction getMessageText(message: Extract<AgentMessage, { role: \"user\" }>): string {\n return messageContentText(message.content).trim();\n}\n\nfunction messageContentText(content: unknown): string {\n if (typeof content === \"string\") return content;\n if (!Array.isArray(content)) return \"\";\n const parts: string[] = [];\n for (const item of content) {\n if (item == null) continue;\n if (typeof item === \"string\") {\n parts.push(item);\n continue;\n }\n if (typeof item !== \"object\") continue;\n const text = (item as { text?: unknown }).text;\n if (typeof text === \"string\") parts.push(text);\n }\n return parts.join(\"\");\n}\n"]}
|
|
1
|
+
{"version":3,"file":"chat-message-renderer.d.ts","sourceRoot":"","sources":["../../../../src/modes/interactive/components/chat-message-renderer.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AssistantMessage, ToolResultMessage } from \"@earendil-works/pi-ai\";\nimport type { AgentMessage } from \"@earendil-works/pi-agent-core\";\nimport { Container, Text, type Component, type MarkdownTheme, type TUI } from \"@earendil-works/pi-tui\";\nimport type { TSchema } from \"typebox\";\nimport type { MessageRenderer, ToolDefinition } from \"../../../core/extensions/types.ts\";\nimport type {\n BashExecutionMessage,\n BranchSummaryMessage,\n CompactionSummaryMessage,\n CustomMessage,\n} from \"../../../core/messages.ts\";\nimport { parseSkillBlock } from \"../../../core/agent-session.ts\";\nimport { getMarkdownTheme, theme } from \"../theme/theme.ts\";\nimport { AssistantMessageComponent } from \"./assistant-message.ts\";\nimport { BashExecutionComponent } from \"./bash-execution.ts\";\nimport { BranchSummaryMessageComponent } from \"./branch-summary-message.ts\";\nimport { CompactionSummaryMessageComponent } from \"./compaction-summary-message.ts\";\nimport { CustomMessageComponent } from \"./custom-message.ts\";\nimport { SkillInvocationMessageComponent } from \"./skill-invocation-message.ts\";\nimport { ToolExecutionComponent } from \"./tool-execution.ts\";\nimport { UserMessageComponent } from \"./user-message.ts\";\n\nexport type ChatMessageEntry =\n | { role: \"assistant\"; kind: \"assistant\"; message: AssistantMessage }\n | {\n role: \"tool\";\n kind: \"tool\";\n toolName: string;\n toolCallId: string;\n args: unknown;\n result?: ToolResultMessage;\n isPartial?: boolean;\n }\n | { role: \"tool\"; kind: \"bashExecution\"; message: BashExecutionMessage }\n | { role: \"user\"; kind: \"user\"; text: string }\n | { role: \"custom\"; kind: \"custom\"; message: CustomMessage<unknown> }\n | { role: \"summary\"; kind: \"branchSummary\"; message: BranchSummaryMessage }\n | { role: \"summary\"; kind: \"compactionSummary\"; message: CompactionSummaryMessage }\n | { role: \"system\"; kind: \"system\"; text: string };\n\nexport interface ChatMessageRenderOptions {\n ui: Pick<TUI, \"requestRender\">;\n cwd: string;\n markdownTheme?: MarkdownTheme;\n hideThinkingBlock?: boolean;\n hiddenThinkingLabel?: string;\n toolOutputExpanded?: boolean;\n showImages?: boolean;\n imageWidthCells?: number;\n getToolDefinition?: (toolName: string) => ToolDefinition<TSchema, unknown> | undefined;\n getCustomMessageRenderer?: (customType: string) => MessageRenderer | undefined;\n}\n\nexport function chatEntriesFromAgentMessages(\n messages: readonly AgentMessage[],\n): ChatMessageEntry[] {\n const entries: ChatMessageEntry[] = [];\n const pendingTools = new Map<string, Extract<ChatMessageEntry, { kind: \"tool\" }>>();\n\n for (const message of messages) {\n switch (message.role) {\n case \"assistant\": {\n entries.push({ role: \"assistant\", kind: \"assistant\", message });\n for (const content of message.content) {\n if (content.type !== \"toolCall\") continue;\n const toolEntry: ChatMessageEntry = {\n role: \"tool\",\n kind: \"tool\",\n toolName: content.name,\n toolCallId: content.id,\n args: content.arguments,\n isPartial: true,\n };\n entries.push(toolEntry);\n pendingTools.set(content.id, toolEntry);\n }\n if (message.stopReason === \"aborted\" || message.stopReason === \"error\") {\n const errorText = message.stopReason === \"aborted\"\n ? message.errorMessage || \"Operation aborted\"\n : message.errorMessage || \"Unknown error\";\n for (const toolEntry of pendingTools.values()) {\n toolEntry.result = {\n role: \"toolResult\",\n toolCallId: toolEntry.toolCallId,\n toolName: toolEntry.toolName,\n content: [{ type: \"text\", text: errorText }],\n isError: true,\n timestamp: message.timestamp,\n };\n toolEntry.isPartial = false;\n }\n pendingTools.clear();\n }\n break;\n }\n case \"toolResult\": {\n const toolEntry = pendingTools.get(message.toolCallId);\n if (toolEntry) {\n toolEntry.result = message;\n toolEntry.isPartial = false;\n pendingTools.delete(message.toolCallId);\n } else {\n entries.push({\n role: \"tool\",\n kind: \"tool\",\n toolName: message.toolName,\n toolCallId: message.toolCallId,\n args: {},\n result: message,\n isPartial: false,\n });\n }\n break;\n }\n case \"user\": {\n const text = getMessageText(message);\n if (text) entries.push({ role: \"user\", kind: \"user\", text });\n break;\n }\n case \"bashExecution\":\n entries.push({ role: \"tool\", kind: \"bashExecution\", message });\n break;\n case \"custom\":\n if (message.display) entries.push({ role: \"custom\", kind: \"custom\", message });\n break;\n case \"branchSummary\":\n entries.push({ role: \"summary\", kind: \"branchSummary\", message });\n break;\n case \"compactionSummary\":\n entries.push({ role: \"summary\", kind: \"compactionSummary\", message });\n break;\n default: {\n const role = (message as { role: string }).role;\n entries.push({ role: \"system\", kind: \"system\", text: role });\n break;\n }\n }\n }\n\n return entries;\n}\n\nexport interface LiveChatEventLike {\n readonly type?: unknown;\n readonly message?: unknown;\n readonly assistantMessageEvent?: { readonly type?: unknown; readonly delta?: unknown };\n readonly toolCallId?: unknown;\n readonly toolName?: unknown;\n readonly args?: unknown;\n readonly partialResult?: unknown;\n readonly result?: unknown;\n readonly isError?: unknown;\n}\n\ntype LiveChatEntry = ChatMessageEntry | { role: string };\n\nexport class LiveChatEntriesController {\n private streamingAssistantIndex: number | undefined;\n private pendingToolIndexes = new Map<string, number>();\n\n declare private readonly entries: LiveChatEntry[];\n\n constructor(entries: LiveChatEntry[]) {\n this.entries = entries;\n\t}\n\n appendMessages(messages: readonly AgentMessage[]): void {\n this.entries.push(...chatEntriesFromAgentMessages(messages));\n this.reindexPendingTools();\n }\n\n appendUserText(text: string): void {\n this.entries.push({ role: \"user\", kind: \"user\", text });\n }\n\n applyEvent(event: LiveChatEventLike): boolean {\n const type = String(event.type ?? \"\");\n switch (type) {\n case \"message_start\":\n return this.handleMessageStart(event.message);\n case \"message_update\":\n return this.handleMessageUpdate(event);\n case \"message_end\":\n return this.handleMessageEnd(event.message);\n case \"tool_execution_start\":\n return this.upsertToolEntry({\n toolCallId: typeof event.toolCallId === \"string\" ? event.toolCallId : undefined,\n toolName: typeof event.toolName === \"string\" ? event.toolName : \"tool\",\n args: event.args,\n isPartial: true,\n });\n case \"tool_execution_update\": {\n const toolCallId = typeof event.toolCallId === \"string\" ? event.toolCallId : undefined;\n if (!toolCallId) return false;\n return this.updateToolResult(toolCallId, event.partialResult, true, false);\n }\n case \"tool_execution_end\": {\n const toolCallId = typeof event.toolCallId === \"string\" ? event.toolCallId : undefined;\n if (!toolCallId) return false;\n return this.updateToolResult(toolCallId, event.result, false, event.isError === true);\n }\n default:\n return false;\n }\n }\n\n pendingToolIds(): string[] {\n return [...this.pendingToolIndexes.keys()];\n }\n\n clearPendingTools(): void {\n this.pendingToolIndexes.clear();\n }\n\n private handleMessageStart(message: unknown): boolean {\n if (!isAgentMessageLike(message)) return false;\n if (message.role === \"assistant\") {\n this.streamingAssistantIndex = undefined;\n return this.updateAssistantMessage(message as AssistantMessage);\n }\n const entries = chatEntriesFromAgentMessages([message as AgentMessage]);\n if (entries.length === 0) return false;\n this.entries.push(...entries);\n this.reindexPendingTools();\n return true;\n }\n\n private handleMessageUpdate(event: LiveChatEventLike): boolean {\n const message = event.message;\n let changed = false;\n const snapshotHasPayload = isAgentMessageLike(message) &&\n message.role === \"assistant\" &&\n assistantContentHasRenderablePayload((message as { content?: unknown }).content);\n if (isAgentMessageLike(message) && message.role === \"assistant\" && snapshotHasPayload) {\n changed = this.updateAssistantMessage(message as AssistantMessage) || changed;\n }\n const assistantEvent = event.assistantMessageEvent;\n const streamType = String(assistantEvent?.type ?? \"\");\n const delta = typeof assistantEvent?.delta === \"string\" ? assistantEvent.delta : \"\";\n if (!changed && streamType === \"text_delta\" && delta) {\n changed = this.appendAssistantTextDelta(delta);\n } else if (!changed && streamType === \"thinking_delta\" && delta) {\n changed = this.appendAssistantThinkingDelta(delta);\n }\n return changed;\n }\n\n private handleMessageEnd(message: unknown): boolean {\n if (!isAgentMessageLike(message) || message.role !== \"assistant\") return false;\n const changed = this.updateAssistantMessage(message as AssistantMessage);\n const stopReason = typeof message.stopReason === \"string\" ? message.stopReason : \"\";\n if (stopReason === \"aborted\" || stopReason === \"error\") {\n const errorText = typeof message.errorMessage === \"string\" && message.errorMessage\n ? message.errorMessage\n : stopReason === \"aborted\"\n ? \"Operation aborted\"\n : \"Unknown error\";\n for (const toolCallId of this.pendingToolIds()) {\n this.updateToolResult(toolCallId, { content: [{ type: \"text\", text: errorText }] }, false, true);\n }\n this.clearPendingTools();\n }\n this.streamingAssistantIndex = undefined;\n return changed || true;\n }\n\n private updateAssistantMessage(message: AssistantMessage): boolean {\n if (this.streamingAssistantIndex !== undefined && this.isAssistantEntry(this.entries[this.streamingAssistantIndex])) {\n this.entries[this.streamingAssistantIndex] = {\n ...(this.entries[this.streamingAssistantIndex] as Extract<ChatMessageEntry, { kind: \"assistant\" }>),\n message,\n };\n } else {\n this.entries.push({ role: \"assistant\", kind: \"assistant\", message });\n this.streamingAssistantIndex = this.entries.length - 1;\n }\n for (const content of message.content) {\n if (content.type !== \"toolCall\") continue;\n this.upsertToolEntry({\n toolCallId: content.id,\n toolName: content.name,\n args: content.arguments,\n isPartial: true,\n });\n }\n return true;\n }\n\n private appendAssistantTextDelta(delta: string): boolean {\n const current = this.currentStreamingAssistantMessage();\n const content = current ? [...current.content] : [];\n const lastText = [...content].reverse().find((item) => item.type === \"text\");\n if (lastText && lastText.type === \"text\") lastText.text += delta;\n else content.push({ type: \"text\", text: delta });\n return this.updateAssistantMessage({\n ...(current ?? minimalAssistantMessage()),\n content,\n });\n }\n\n private appendAssistantThinkingDelta(delta: string): boolean {\n const current = this.currentStreamingAssistantMessage();\n const content = current ? [...current.content] : [];\n const lastThinking = [...content].reverse().find((item) => item.type === \"thinking\");\n if (lastThinking && lastThinking.type === \"thinking\") lastThinking.thinking += delta;\n else content.push({ type: \"thinking\", thinking: delta });\n return this.updateAssistantMessage({\n ...(current ?? minimalAssistantMessage()),\n content,\n });\n }\n\n private currentStreamingAssistantMessage(): AssistantMessage | undefined {\n const entry = this.streamingAssistantIndex !== undefined ? this.entries[this.streamingAssistantIndex] : undefined;\n return this.isAssistantEntry(entry) ? entry.message : undefined;\n }\n\n private upsertToolEntry(update: {\n toolCallId?: string;\n toolName: string;\n args?: unknown;\n isPartial: boolean;\n }): boolean {\n const toolCallId = update.toolCallId ?? `live-${update.toolName}`;\n const index = this.pendingToolIndexes.get(toolCallId) ?? this.findToolEntryIndex(toolCallId, update.toolName);\n const previous = index >= 0 ? this.entries[index] : undefined;\n const previousTool = this.isToolEntry(previous) ? previous : undefined;\n const next: ChatMessageEntry = {\n role: \"tool\",\n kind: \"tool\",\n toolName: previousTool?.toolName ?? update.toolName,\n toolCallId,\n args: update.args ?? previousTool?.args ?? {},\n result: previousTool?.result,\n isPartial: update.isPartial,\n };\n if (index >= 0) this.entries[index] = next;\n else this.entries.push(next);\n this.pendingToolIndexes.set(toolCallId, index >= 0 ? index : this.entries.length - 1);\n return true;\n }\n\n private updateToolResult(toolCallId: string, result: unknown, isPartial: boolean, isError: boolean): boolean {\n const index = this.pendingToolIndexes.get(toolCallId) ?? this.findToolEntryIndex(toolCallId);\n if (index < 0) return false;\n const entry = this.entries[index];\n if (!this.isToolEntry(entry)) return false;\n const resultObject = toolResultFromUnknown(result, entry.toolName, toolCallId, isError);\n this.entries[index] = { ...entry, result: resultObject, isPartial };\n if (!isPartial) this.pendingToolIndexes.delete(toolCallId);\n return true;\n }\n\n private findToolEntryIndex(toolCallId: string, toolName?: string): number {\n for (let i = this.entries.length - 1; i >= 0; i--) {\n const entry = this.entries[i];\n if (!this.isToolEntry(entry)) continue;\n if (entry.toolCallId === toolCallId || (toolName && entry.toolName === toolName && entry.isPartial !== false)) return i;\n }\n return -1;\n }\n\n private reindexPendingTools(): void {\n this.pendingToolIndexes.clear();\n for (let i = 0; i < this.entries.length; i++) {\n const entry = this.entries[i];\n if (this.isToolEntry(entry) && entry.isPartial !== false) this.pendingToolIndexes.set(entry.toolCallId, i);\n }\n }\n\n private isAssistantEntry(entry: LiveChatEntry | undefined): entry is Extract<ChatMessageEntry, { kind: \"assistant\" }> {\n return isChatMessageEntry(entry) && entry.kind === \"assistant\";\n }\n\n private isToolEntry(entry: LiveChatEntry | undefined): entry is Extract<ChatMessageEntry, { kind: \"tool\" }> {\n return isChatMessageEntry(entry) && entry.kind === \"tool\";\n }\n}\n\nfunction isChatMessageEntry(entry: LiveChatEntry | undefined): entry is ChatMessageEntry {\n return entry !== undefined && \"kind\" in entry;\n}\n\nfunction isAgentMessageLike(message: unknown): message is AgentMessage & { stopReason?: unknown; errorMessage?: unknown } {\n return message !== null && typeof message === \"object\" && \"role\" in message;\n}\n\nfunction assistantContentHasRenderablePayload(content: unknown): boolean {\n if (typeof content === \"string\") return content.length > 0;\n if (!Array.isArray(content)) return false;\n return content.some((item) => {\n if (typeof item === \"string\") return item.length > 0;\n if (item == null || typeof item !== \"object\") return false;\n const obj = item as { type?: unknown; text?: unknown; thinking?: unknown };\n return (obj.type === \"text\" && typeof obj.text === \"string\" && obj.text.length > 0) ||\n (obj.type === \"thinking\" && typeof obj.thinking === \"string\" && obj.thinking.length > 0) ||\n obj.type === \"toolCall\";\n });\n}\n\nfunction minimalAssistantMessage(): AssistantMessage {\n return {\n role: \"assistant\",\n content: [],\n stopReason: \"stop\",\n } as unknown as AssistantMessage;\n}\n\nfunction toolResultFromUnknown(\n result: unknown,\n toolName: string,\n toolCallId: string,\n isError: boolean,\n): ToolResultMessage {\n if (result !== null && typeof result === \"object\" && \"content\" in result) {\n const candidate = result as { content?: unknown; details?: unknown };\n const content = Array.isArray(candidate.content) ? candidate.content : [];\n return {\n role: \"toolResult\",\n toolCallId,\n toolName,\n content: content as ToolResultMessage[\"content\"],\n details: candidate.details,\n isError,\n timestamp: Date.now(),\n };\n }\n return {\n role: \"toolResult\",\n toolCallId,\n toolName,\n content: typeof result === \"string\" ? [{ type: \"text\", text: result }] : [],\n isError,\n timestamp: Date.now(),\n };\n}\n\nexport function renderChatMessageEntry(\n entry: ChatMessageEntry,\n options: ChatMessageRenderOptions,\n): Component {\n const messageEntry = entry as ChatMessageEntry;\n const markdownTheme = options.markdownTheme ?? getMarkdownTheme();\n\n switch (messageEntry.kind) {\n case \"assistant\":\n return new AssistantMessageComponent(\n messageEntry.message,\n options.hideThinkingBlock ?? false,\n markdownTheme,\n options.hiddenThinkingLabel ?? \"Thinking...\",\n );\n case \"tool\": {\n const component = new ToolExecutionComponent(\n messageEntry.toolName,\n messageEntry.toolCallId,\n messageEntry.args,\n {\n showImages: options.showImages ?? true,\n imageWidthCells: options.imageWidthCells,\n },\n options.getToolDefinition?.(messageEntry.toolName),\n options.ui as TUI,\n options.cwd,\n );\n component.setExpanded(options.toolOutputExpanded ?? false);\n if (messageEntry.result) component.updateResult(messageEntry.result, messageEntry.isPartial ?? false);\n return component;\n }\n case \"bashExecution\": {\n const component = new BashExecutionComponent(\n messageEntry.message.command,\n options.ui as TUI,\n messageEntry.message.excludeFromContext,\n );\n if (messageEntry.message.output) component.appendOutput(messageEntry.message.output);\n component.setComplete(\n messageEntry.message.exitCode,\n messageEntry.message.cancelled,\n messageEntry.message.truncated\n ? ({ truncated: true } as Parameters<BashExecutionComponent[\"setComplete\"]>[2])\n : undefined,\n messageEntry.message.fullOutputPath,\n );\n return component;\n }\n case \"user\":\n return userMessageComponent(messageEntry.text, markdownTheme, options.toolOutputExpanded ?? false);\n case \"custom\": {\n const component = new CustomMessageComponent(\n messageEntry.message,\n options.getCustomMessageRenderer?.(messageEntry.message.customType),\n markdownTheme,\n );\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"branchSummary\": {\n const component = new BranchSummaryMessageComponent(messageEntry.message, markdownTheme);\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"compactionSummary\": {\n const component = new CompactionSummaryMessageComponent(messageEntry.message, markdownTheme);\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"system\":\n return new Text(theme.fg(\"dim\", messageEntry.text), 1, 0);\n }\n}\n\nfunction userMessageComponent(text: string, markdownTheme: MarkdownTheme, expanded: boolean): Component {\n const skillBlock = parseSkillBlock(text);\n if (!skillBlock) return new UserMessageComponent(text, markdownTheme);\n\n const container = new Container();\n const skillComponent = new SkillInvocationMessageComponent(skillBlock, markdownTheme);\n skillComponent.setExpanded(expanded);\n container.addChild(skillComponent);\n if (skillBlock.userMessage) {\n container.addChild(new UserMessageComponent(skillBlock.userMessage, markdownTheme));\n }\n return container;\n}\n\nfunction getMessageText(message: Extract<AgentMessage, { role: \"user\" }>): string {\n return messageContentText(message.content).trim();\n}\n\nfunction messageContentText(content: unknown): string {\n if (typeof content === \"string\") return content;\n if (!Array.isArray(content)) return \"\";\n const parts: string[] = [];\n for (const item of content) {\n if (item == null) continue;\n if (typeof item === \"string\") {\n parts.push(item);\n continue;\n }\n if (typeof item !== \"object\") continue;\n const text = (item as { text?: unknown }).text;\n if (typeof text === \"string\") parts.push(text);\n }\n return parts.join(\"\");\n}\n"]}
|
|
@@ -99,8 +99,8 @@ export function chatEntriesFromAgentMessages(messages) {
|
|
|
99
99
|
}
|
|
100
100
|
export class LiveChatEntriesController {
|
|
101
101
|
constructor(entries) {
|
|
102
|
-
this.entries = entries;
|
|
103
102
|
this.pendingToolIndexes = new Map();
|
|
103
|
+
this.entries = entries;
|
|
104
104
|
}
|
|
105
105
|
appendMessages(messages) {
|
|
106
106
|
this.entries.push(...chatEntriesFromAgentMessages(messages));
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"chat-message-renderer.js","sourceRoot":"","sources":["../../../../src/modes/interactive/components/chat-message-renderer.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AssistantMessage, ToolResultMessage } from \"@earendil-works/pi-ai\";\nimport type { AgentMessage } from \"@earendil-works/pi-agent-core\";\nimport { Container, Text, type Component, type MarkdownTheme, type TUI } from \"@earendil-works/pi-tui\";\nimport type { TSchema } from \"typebox\";\nimport type { MessageRenderer, ToolDefinition } from \"../../../core/extensions/types.js\";\nimport type {\n BashExecutionMessage,\n BranchSummaryMessage,\n CompactionSummaryMessage,\n CustomMessage,\n} from \"../../../core/messages.js\";\nimport { parseSkillBlock } from \"../../../core/agent-session.js\";\nimport { getMarkdownTheme, theme } from \"../theme/theme.js\";\nimport { AssistantMessageComponent } from \"./assistant-message.js\";\nimport { BashExecutionComponent } from \"./bash-execution.js\";\nimport { BranchSummaryMessageComponent } from \"./branch-summary-message.js\";\nimport { CompactionSummaryMessageComponent } from \"./compaction-summary-message.js\";\nimport { CustomMessageComponent } from \"./custom-message.js\";\nimport { SkillInvocationMessageComponent } from \"./skill-invocation-message.js\";\nimport { ToolExecutionComponent } from \"./tool-execution.js\";\nimport { UserMessageComponent } from \"./user-message.js\";\n\nexport type ChatMessageEntry =\n | { role: \"assistant\"; kind: \"assistant\"; message: AssistantMessage }\n | {\n role: \"tool\";\n kind: \"tool\";\n toolName: string;\n toolCallId: string;\n args: unknown;\n result?: ToolResultMessage;\n isPartial?: boolean;\n }\n | { role: \"tool\"; kind: \"bashExecution\"; message: BashExecutionMessage }\n | { role: \"user\"; kind: \"user\"; text: string }\n | { role: \"custom\"; kind: \"custom\"; message: CustomMessage<unknown> }\n | { role: \"summary\"; kind: \"branchSummary\"; message: BranchSummaryMessage }\n | { role: \"summary\"; kind: \"compactionSummary\"; message: CompactionSummaryMessage }\n | { role: \"system\"; kind: \"system\"; text: string };\n\nexport interface ChatMessageRenderOptions {\n ui: Pick<TUI, \"requestRender\">;\n cwd: string;\n markdownTheme?: MarkdownTheme;\n hideThinkingBlock?: boolean;\n hiddenThinkingLabel?: string;\n toolOutputExpanded?: boolean;\n showImages?: boolean;\n imageWidthCells?: number;\n getToolDefinition?: (toolName: string) => ToolDefinition<TSchema, unknown> | undefined;\n getCustomMessageRenderer?: (customType: string) => MessageRenderer | undefined;\n}\n\nexport function chatEntriesFromAgentMessages(\n messages: readonly AgentMessage[],\n): ChatMessageEntry[] {\n const entries: ChatMessageEntry[] = [];\n const pendingTools = new Map<string, Extract<ChatMessageEntry, { kind: \"tool\" }>>();\n\n for (const message of messages) {\n switch (message.role) {\n case \"assistant\": {\n entries.push({ role: \"assistant\", kind: \"assistant\", message });\n for (const content of message.content) {\n if (content.type !== \"toolCall\") continue;\n const toolEntry: ChatMessageEntry = {\n role: \"tool\",\n kind: \"tool\",\n toolName: content.name,\n toolCallId: content.id,\n args: content.arguments,\n isPartial: true,\n };\n entries.push(toolEntry);\n pendingTools.set(content.id, toolEntry);\n }\n if (message.stopReason === \"aborted\" || message.stopReason === \"error\") {\n const errorText = message.stopReason === \"aborted\"\n ? message.errorMessage || \"Operation aborted\"\n : message.errorMessage || \"Unknown error\";\n for (const toolEntry of pendingTools.values()) {\n toolEntry.result = {\n role: \"toolResult\",\n toolCallId: toolEntry.toolCallId,\n toolName: toolEntry.toolName,\n content: [{ type: \"text\", text: errorText }],\n isError: true,\n timestamp: message.timestamp,\n };\n toolEntry.isPartial = false;\n }\n pendingTools.clear();\n }\n break;\n }\n case \"toolResult\": {\n const toolEntry = pendingTools.get(message.toolCallId);\n if (toolEntry) {\n toolEntry.result = message;\n toolEntry.isPartial = false;\n pendingTools.delete(message.toolCallId);\n } else {\n entries.push({\n role: \"tool\",\n kind: \"tool\",\n toolName: message.toolName,\n toolCallId: message.toolCallId,\n args: {},\n result: message,\n isPartial: false,\n });\n }\n break;\n }\n case \"user\": {\n const text = getMessageText(message);\n if (text) entries.push({ role: \"user\", kind: \"user\", text });\n break;\n }\n case \"bashExecution\":\n entries.push({ role: \"tool\", kind: \"bashExecution\", message });\n break;\n case \"custom\":\n if (message.display) entries.push({ role: \"custom\", kind: \"custom\", message });\n break;\n case \"branchSummary\":\n entries.push({ role: \"summary\", kind: \"branchSummary\", message });\n break;\n case \"compactionSummary\":\n entries.push({ role: \"summary\", kind: \"compactionSummary\", message });\n break;\n default: {\n const role = (message as { role: string }).role;\n entries.push({ role: \"system\", kind: \"system\", text: role });\n break;\n }\n }\n }\n\n return entries;\n}\n\nexport interface LiveChatEventLike {\n readonly type?: unknown;\n readonly message?: unknown;\n readonly assistantMessageEvent?: { readonly type?: unknown; readonly delta?: unknown };\n readonly toolCallId?: unknown;\n readonly toolName?: unknown;\n readonly args?: unknown;\n readonly partialResult?: unknown;\n readonly result?: unknown;\n readonly isError?: unknown;\n}\n\ntype LiveChatEntry = ChatMessageEntry | { role: string };\n\nexport class LiveChatEntriesController {\n private streamingAssistantIndex: number | undefined;\n private pendingToolIndexes = new Map<string, number>();\n\n constructor(private readonly entries: LiveChatEntry[]) {}\n\n appendMessages(messages: readonly AgentMessage[]): void {\n this.entries.push(...chatEntriesFromAgentMessages(messages));\n this.reindexPendingTools();\n }\n\n appendUserText(text: string): void {\n this.entries.push({ role: \"user\", kind: \"user\", text });\n }\n\n applyEvent(event: LiveChatEventLike): boolean {\n const type = String(event.type ?? \"\");\n switch (type) {\n case \"message_start\":\n return this.handleMessageStart(event.message);\n case \"message_update\":\n return this.handleMessageUpdate(event);\n case \"message_end\":\n return this.handleMessageEnd(event.message);\n case \"tool_execution_start\":\n return this.upsertToolEntry({\n toolCallId: typeof event.toolCallId === \"string\" ? event.toolCallId : undefined,\n toolName: typeof event.toolName === \"string\" ? event.toolName : \"tool\",\n args: event.args,\n isPartial: true,\n });\n case \"tool_execution_update\": {\n const toolCallId = typeof event.toolCallId === \"string\" ? event.toolCallId : undefined;\n if (!toolCallId) return false;\n return this.updateToolResult(toolCallId, event.partialResult, true, false);\n }\n case \"tool_execution_end\": {\n const toolCallId = typeof event.toolCallId === \"string\" ? event.toolCallId : undefined;\n if (!toolCallId) return false;\n return this.updateToolResult(toolCallId, event.result, false, event.isError === true);\n }\n default:\n return false;\n }\n }\n\n pendingToolIds(): string[] {\n return [...this.pendingToolIndexes.keys()];\n }\n\n clearPendingTools(): void {\n this.pendingToolIndexes.clear();\n }\n\n private handleMessageStart(message: unknown): boolean {\n if (!isAgentMessageLike(message)) return false;\n if (message.role === \"assistant\") {\n this.streamingAssistantIndex = undefined;\n return this.updateAssistantMessage(message as AssistantMessage);\n }\n const entries = chatEntriesFromAgentMessages([message as AgentMessage]);\n if (entries.length === 0) return false;\n this.entries.push(...entries);\n this.reindexPendingTools();\n return true;\n }\n\n private handleMessageUpdate(event: LiveChatEventLike): boolean {\n const message = event.message;\n let changed = false;\n const snapshotHasPayload = isAgentMessageLike(message) &&\n message.role === \"assistant\" &&\n assistantContentHasRenderablePayload((message as { content?: unknown }).content);\n if (isAgentMessageLike(message) && message.role === \"assistant\" && snapshotHasPayload) {\n changed = this.updateAssistantMessage(message as AssistantMessage) || changed;\n }\n const assistantEvent = event.assistantMessageEvent;\n const streamType = String(assistantEvent?.type ?? \"\");\n const delta = typeof assistantEvent?.delta === \"string\" ? assistantEvent.delta : \"\";\n if (!changed && streamType === \"text_delta\" && delta) {\n changed = this.appendAssistantTextDelta(delta);\n } else if (!changed && streamType === \"thinking_delta\" && delta) {\n changed = this.appendAssistantThinkingDelta(delta);\n }\n return changed;\n }\n\n private handleMessageEnd(message: unknown): boolean {\n if (!isAgentMessageLike(message) || message.role !== \"assistant\") return false;\n const changed = this.updateAssistantMessage(message as AssistantMessage);\n const stopReason = typeof message.stopReason === \"string\" ? message.stopReason : \"\";\n if (stopReason === \"aborted\" || stopReason === \"error\") {\n const errorText = typeof message.errorMessage === \"string\" && message.errorMessage\n ? message.errorMessage\n : stopReason === \"aborted\"\n ? \"Operation aborted\"\n : \"Unknown error\";\n for (const toolCallId of this.pendingToolIds()) {\n this.updateToolResult(toolCallId, { content: [{ type: \"text\", text: errorText }] }, false, true);\n }\n this.clearPendingTools();\n }\n this.streamingAssistantIndex = undefined;\n return changed || true;\n }\n\n private updateAssistantMessage(message: AssistantMessage): boolean {\n if (this.streamingAssistantIndex !== undefined && this.isAssistantEntry(this.entries[this.streamingAssistantIndex])) {\n this.entries[this.streamingAssistantIndex] = {\n ...(this.entries[this.streamingAssistantIndex] as Extract<ChatMessageEntry, { kind: \"assistant\" }>),\n message,\n };\n } else {\n this.entries.push({ role: \"assistant\", kind: \"assistant\", message });\n this.streamingAssistantIndex = this.entries.length - 1;\n }\n for (const content of message.content) {\n if (content.type !== \"toolCall\") continue;\n this.upsertToolEntry({\n toolCallId: content.id,\n toolName: content.name,\n args: content.arguments,\n isPartial: true,\n });\n }\n return true;\n }\n\n private appendAssistantTextDelta(delta: string): boolean {\n const current = this.currentStreamingAssistantMessage();\n const content = current ? [...current.content] : [];\n const lastText = [...content].reverse().find((item) => item.type === \"text\");\n if (lastText && lastText.type === \"text\") lastText.text += delta;\n else content.push({ type: \"text\", text: delta });\n return this.updateAssistantMessage({\n ...(current ?? minimalAssistantMessage()),\n content,\n });\n }\n\n private appendAssistantThinkingDelta(delta: string): boolean {\n const current = this.currentStreamingAssistantMessage();\n const content = current ? [...current.content] : [];\n const lastThinking = [...content].reverse().find((item) => item.type === \"thinking\");\n if (lastThinking && lastThinking.type === \"thinking\") lastThinking.thinking += delta;\n else content.push({ type: \"thinking\", thinking: delta });\n return this.updateAssistantMessage({\n ...(current ?? minimalAssistantMessage()),\n content,\n });\n }\n\n private currentStreamingAssistantMessage(): AssistantMessage | undefined {\n const entry = this.streamingAssistantIndex !== undefined ? this.entries[this.streamingAssistantIndex] : undefined;\n return this.isAssistantEntry(entry) ? entry.message : undefined;\n }\n\n private upsertToolEntry(update: {\n toolCallId?: string;\n toolName: string;\n args?: unknown;\n isPartial: boolean;\n }): boolean {\n const toolCallId = update.toolCallId ?? `live-${update.toolName}`;\n const index = this.pendingToolIndexes.get(toolCallId) ?? this.findToolEntryIndex(toolCallId, update.toolName);\n const previous = index >= 0 ? this.entries[index] : undefined;\n const previousTool = this.isToolEntry(previous) ? previous : undefined;\n const next: ChatMessageEntry = {\n role: \"tool\",\n kind: \"tool\",\n toolName: previousTool?.toolName ?? update.toolName,\n toolCallId,\n args: update.args ?? previousTool?.args ?? {},\n result: previousTool?.result,\n isPartial: update.isPartial,\n };\n if (index >= 0) this.entries[index] = next;\n else this.entries.push(next);\n this.pendingToolIndexes.set(toolCallId, index >= 0 ? index : this.entries.length - 1);\n return true;\n }\n\n private updateToolResult(toolCallId: string, result: unknown, isPartial: boolean, isError: boolean): boolean {\n const index = this.pendingToolIndexes.get(toolCallId) ?? this.findToolEntryIndex(toolCallId);\n if (index < 0) return false;\n const entry = this.entries[index];\n if (!this.isToolEntry(entry)) return false;\n const resultObject = toolResultFromUnknown(result, entry.toolName, toolCallId, isError);\n this.entries[index] = { ...entry, result: resultObject, isPartial };\n if (!isPartial) this.pendingToolIndexes.delete(toolCallId);\n return true;\n }\n\n private findToolEntryIndex(toolCallId: string, toolName?: string): number {\n for (let i = this.entries.length - 1; i >= 0; i--) {\n const entry = this.entries[i];\n if (!this.isToolEntry(entry)) continue;\n if (entry.toolCallId === toolCallId || (toolName && entry.toolName === toolName && entry.isPartial !== false)) return i;\n }\n return -1;\n }\n\n private reindexPendingTools(): void {\n this.pendingToolIndexes.clear();\n for (let i = 0; i < this.entries.length; i++) {\n const entry = this.entries[i];\n if (this.isToolEntry(entry) && entry.isPartial !== false) this.pendingToolIndexes.set(entry.toolCallId, i);\n }\n }\n\n private isAssistantEntry(entry: LiveChatEntry | undefined): entry is Extract<ChatMessageEntry, { kind: \"assistant\" }> {\n return isChatMessageEntry(entry) && entry.kind === \"assistant\";\n }\n\n private isToolEntry(entry: LiveChatEntry | undefined): entry is Extract<ChatMessageEntry, { kind: \"tool\" }> {\n return isChatMessageEntry(entry) && entry.kind === \"tool\";\n }\n}\n\nfunction isChatMessageEntry(entry: LiveChatEntry | undefined): entry is ChatMessageEntry {\n return entry !== undefined && \"kind\" in entry;\n}\n\nfunction isAgentMessageLike(message: unknown): message is AgentMessage & { stopReason?: unknown; errorMessage?: unknown } {\n return message !== null && typeof message === \"object\" && \"role\" in message;\n}\n\nfunction assistantContentHasRenderablePayload(content: unknown): boolean {\n if (typeof content === \"string\") return content.length > 0;\n if (!Array.isArray(content)) return false;\n return content.some((item) => {\n if (typeof item === \"string\") return item.length > 0;\n if (item == null || typeof item !== \"object\") return false;\n const obj = item as { type?: unknown; text?: unknown; thinking?: unknown };\n return (obj.type === \"text\" && typeof obj.text === \"string\" && obj.text.length > 0) ||\n (obj.type === \"thinking\" && typeof obj.thinking === \"string\" && obj.thinking.length > 0) ||\n obj.type === \"toolCall\";\n });\n}\n\nfunction minimalAssistantMessage(): AssistantMessage {\n return {\n role: \"assistant\",\n content: [],\n stopReason: \"stop\",\n } as unknown as AssistantMessage;\n}\n\nfunction toolResultFromUnknown(\n result: unknown,\n toolName: string,\n toolCallId: string,\n isError: boolean,\n): ToolResultMessage {\n if (result !== null && typeof result === \"object\" && \"content\" in result) {\n const candidate = result as { content?: unknown; details?: unknown };\n const content = Array.isArray(candidate.content) ? candidate.content : [];\n return {\n role: \"toolResult\",\n toolCallId,\n toolName,\n content: content as ToolResultMessage[\"content\"],\n details: candidate.details,\n isError,\n timestamp: Date.now(),\n };\n }\n return {\n role: \"toolResult\",\n toolCallId,\n toolName,\n content: typeof result === \"string\" ? [{ type: \"text\", text: result }] : [],\n isError,\n timestamp: Date.now(),\n };\n}\n\nexport function renderChatMessageEntry(\n entry: ChatMessageEntry,\n options: ChatMessageRenderOptions,\n): Component {\n const messageEntry = entry as ChatMessageEntry;\n const markdownTheme = options.markdownTheme ?? getMarkdownTheme();\n\n switch (messageEntry.kind) {\n case \"assistant\":\n return new AssistantMessageComponent(\n messageEntry.message,\n options.hideThinkingBlock ?? false,\n markdownTheme,\n options.hiddenThinkingLabel ?? \"Thinking...\",\n );\n case \"tool\": {\n const component = new ToolExecutionComponent(\n messageEntry.toolName,\n messageEntry.toolCallId,\n messageEntry.args,\n {\n showImages: options.showImages ?? true,\n imageWidthCells: options.imageWidthCells,\n },\n options.getToolDefinition?.(messageEntry.toolName),\n options.ui as TUI,\n options.cwd,\n );\n component.setExpanded(options.toolOutputExpanded ?? false);\n if (messageEntry.result) component.updateResult(messageEntry.result, messageEntry.isPartial ?? false);\n return component;\n }\n case \"bashExecution\": {\n const component = new BashExecutionComponent(\n messageEntry.message.command,\n options.ui as TUI,\n messageEntry.message.excludeFromContext,\n );\n if (messageEntry.message.output) component.appendOutput(messageEntry.message.output);\n component.setComplete(\n messageEntry.message.exitCode,\n messageEntry.message.cancelled,\n messageEntry.message.truncated\n ? ({ truncated: true } as Parameters<BashExecutionComponent[\"setComplete\"]>[2])\n : undefined,\n messageEntry.message.fullOutputPath,\n );\n return component;\n }\n case \"user\":\n return userMessageComponent(messageEntry.text, markdownTheme, options.toolOutputExpanded ?? false);\n case \"custom\": {\n const component = new CustomMessageComponent(\n messageEntry.message,\n options.getCustomMessageRenderer?.(messageEntry.message.customType),\n markdownTheme,\n );\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"branchSummary\": {\n const component = new BranchSummaryMessageComponent(messageEntry.message, markdownTheme);\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"compactionSummary\": {\n const component = new CompactionSummaryMessageComponent(messageEntry.message, markdownTheme);\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"system\":\n return new Text(theme.fg(\"dim\", messageEntry.text), 1, 0);\n }\n}\n\nfunction userMessageComponent(text: string, markdownTheme: MarkdownTheme, expanded: boolean): Component {\n const skillBlock = parseSkillBlock(text);\n if (!skillBlock) return new UserMessageComponent(text, markdownTheme);\n\n const container = new Container();\n const skillComponent = new SkillInvocationMessageComponent(skillBlock, markdownTheme);\n skillComponent.setExpanded(expanded);\n container.addChild(skillComponent);\n if (skillBlock.userMessage) {\n container.addChild(new UserMessageComponent(skillBlock.userMessage, markdownTheme));\n }\n return container;\n}\n\nfunction getMessageText(message: Extract<AgentMessage, { role: \"user\" }>): string {\n return messageContentText(message.content).trim();\n}\n\nfunction messageContentText(content: unknown): string {\n if (typeof content === \"string\") return content;\n if (!Array.isArray(content)) return \"\";\n const parts: string[] = [];\n for (const item of content) {\n if (item == null) continue;\n if (typeof item === \"string\") {\n parts.push(item);\n continue;\n }\n if (typeof item !== \"object\") continue;\n const text = (item as { text?: unknown }).text;\n if (typeof text === \"string\") parts.push(text);\n }\n return parts.join(\"\");\n}\n"]}
|
|
1
|
+
{"version":3,"file":"chat-message-renderer.js","sourceRoot":"","sources":["../../../../src/modes/interactive/components/chat-message-renderer.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AssistantMessage, ToolResultMessage } from \"@earendil-works/pi-ai\";\nimport type { AgentMessage } from \"@earendil-works/pi-agent-core\";\nimport { Container, Text, type Component, type MarkdownTheme, type TUI } from \"@earendil-works/pi-tui\";\nimport type { TSchema } from \"typebox\";\nimport type { MessageRenderer, ToolDefinition } from \"../../../core/extensions/types.ts\";\nimport type {\n BashExecutionMessage,\n BranchSummaryMessage,\n CompactionSummaryMessage,\n CustomMessage,\n} from \"../../../core/messages.ts\";\nimport { parseSkillBlock } from \"../../../core/agent-session.ts\";\nimport { getMarkdownTheme, theme } from \"../theme/theme.ts\";\nimport { AssistantMessageComponent } from \"./assistant-message.ts\";\nimport { BashExecutionComponent } from \"./bash-execution.ts\";\nimport { BranchSummaryMessageComponent } from \"./branch-summary-message.ts\";\nimport { CompactionSummaryMessageComponent } from \"./compaction-summary-message.ts\";\nimport { CustomMessageComponent } from \"./custom-message.ts\";\nimport { SkillInvocationMessageComponent } from \"./skill-invocation-message.ts\";\nimport { ToolExecutionComponent } from \"./tool-execution.ts\";\nimport { UserMessageComponent } from \"./user-message.ts\";\n\nexport type ChatMessageEntry =\n | { role: \"assistant\"; kind: \"assistant\"; message: AssistantMessage }\n | {\n role: \"tool\";\n kind: \"tool\";\n toolName: string;\n toolCallId: string;\n args: unknown;\n result?: ToolResultMessage;\n isPartial?: boolean;\n }\n | { role: \"tool\"; kind: \"bashExecution\"; message: BashExecutionMessage }\n | { role: \"user\"; kind: \"user\"; text: string }\n | { role: \"custom\"; kind: \"custom\"; message: CustomMessage<unknown> }\n | { role: \"summary\"; kind: \"branchSummary\"; message: BranchSummaryMessage }\n | { role: \"summary\"; kind: \"compactionSummary\"; message: CompactionSummaryMessage }\n | { role: \"system\"; kind: \"system\"; text: string };\n\nexport interface ChatMessageRenderOptions {\n ui: Pick<TUI, \"requestRender\">;\n cwd: string;\n markdownTheme?: MarkdownTheme;\n hideThinkingBlock?: boolean;\n hiddenThinkingLabel?: string;\n toolOutputExpanded?: boolean;\n showImages?: boolean;\n imageWidthCells?: number;\n getToolDefinition?: (toolName: string) => ToolDefinition<TSchema, unknown> | undefined;\n getCustomMessageRenderer?: (customType: string) => MessageRenderer | undefined;\n}\n\nexport function chatEntriesFromAgentMessages(\n messages: readonly AgentMessage[],\n): ChatMessageEntry[] {\n const entries: ChatMessageEntry[] = [];\n const pendingTools = new Map<string, Extract<ChatMessageEntry, { kind: \"tool\" }>>();\n\n for (const message of messages) {\n switch (message.role) {\n case \"assistant\": {\n entries.push({ role: \"assistant\", kind: \"assistant\", message });\n for (const content of message.content) {\n if (content.type !== \"toolCall\") continue;\n const toolEntry: ChatMessageEntry = {\n role: \"tool\",\n kind: \"tool\",\n toolName: content.name,\n toolCallId: content.id,\n args: content.arguments,\n isPartial: true,\n };\n entries.push(toolEntry);\n pendingTools.set(content.id, toolEntry);\n }\n if (message.stopReason === \"aborted\" || message.stopReason === \"error\") {\n const errorText = message.stopReason === \"aborted\"\n ? message.errorMessage || \"Operation aborted\"\n : message.errorMessage || \"Unknown error\";\n for (const toolEntry of pendingTools.values()) {\n toolEntry.result = {\n role: \"toolResult\",\n toolCallId: toolEntry.toolCallId,\n toolName: toolEntry.toolName,\n content: [{ type: \"text\", text: errorText }],\n isError: true,\n timestamp: message.timestamp,\n };\n toolEntry.isPartial = false;\n }\n pendingTools.clear();\n }\n break;\n }\n case \"toolResult\": {\n const toolEntry = pendingTools.get(message.toolCallId);\n if (toolEntry) {\n toolEntry.result = message;\n toolEntry.isPartial = false;\n pendingTools.delete(message.toolCallId);\n } else {\n entries.push({\n role: \"tool\",\n kind: \"tool\",\n toolName: message.toolName,\n toolCallId: message.toolCallId,\n args: {},\n result: message,\n isPartial: false,\n });\n }\n break;\n }\n case \"user\": {\n const text = getMessageText(message);\n if (text) entries.push({ role: \"user\", kind: \"user\", text });\n break;\n }\n case \"bashExecution\":\n entries.push({ role: \"tool\", kind: \"bashExecution\", message });\n break;\n case \"custom\":\n if (message.display) entries.push({ role: \"custom\", kind: \"custom\", message });\n break;\n case \"branchSummary\":\n entries.push({ role: \"summary\", kind: \"branchSummary\", message });\n break;\n case \"compactionSummary\":\n entries.push({ role: \"summary\", kind: \"compactionSummary\", message });\n break;\n default: {\n const role = (message as { role: string }).role;\n entries.push({ role: \"system\", kind: \"system\", text: role });\n break;\n }\n }\n }\n\n return entries;\n}\n\nexport interface LiveChatEventLike {\n readonly type?: unknown;\n readonly message?: unknown;\n readonly assistantMessageEvent?: { readonly type?: unknown; readonly delta?: unknown };\n readonly toolCallId?: unknown;\n readonly toolName?: unknown;\n readonly args?: unknown;\n readonly partialResult?: unknown;\n readonly result?: unknown;\n readonly isError?: unknown;\n}\n\ntype LiveChatEntry = ChatMessageEntry | { role: string };\n\nexport class LiveChatEntriesController {\n private streamingAssistantIndex: number | undefined;\n private pendingToolIndexes = new Map<string, number>();\n\n declare private readonly entries: LiveChatEntry[];\n\n constructor(entries: LiveChatEntry[]) {\n this.entries = entries;\n\t}\n\n appendMessages(messages: readonly AgentMessage[]): void {\n this.entries.push(...chatEntriesFromAgentMessages(messages));\n this.reindexPendingTools();\n }\n\n appendUserText(text: string): void {\n this.entries.push({ role: \"user\", kind: \"user\", text });\n }\n\n applyEvent(event: LiveChatEventLike): boolean {\n const type = String(event.type ?? \"\");\n switch (type) {\n case \"message_start\":\n return this.handleMessageStart(event.message);\n case \"message_update\":\n return this.handleMessageUpdate(event);\n case \"message_end\":\n return this.handleMessageEnd(event.message);\n case \"tool_execution_start\":\n return this.upsertToolEntry({\n toolCallId: typeof event.toolCallId === \"string\" ? event.toolCallId : undefined,\n toolName: typeof event.toolName === \"string\" ? event.toolName : \"tool\",\n args: event.args,\n isPartial: true,\n });\n case \"tool_execution_update\": {\n const toolCallId = typeof event.toolCallId === \"string\" ? event.toolCallId : undefined;\n if (!toolCallId) return false;\n return this.updateToolResult(toolCallId, event.partialResult, true, false);\n }\n case \"tool_execution_end\": {\n const toolCallId = typeof event.toolCallId === \"string\" ? event.toolCallId : undefined;\n if (!toolCallId) return false;\n return this.updateToolResult(toolCallId, event.result, false, event.isError === true);\n }\n default:\n return false;\n }\n }\n\n pendingToolIds(): string[] {\n return [...this.pendingToolIndexes.keys()];\n }\n\n clearPendingTools(): void {\n this.pendingToolIndexes.clear();\n }\n\n private handleMessageStart(message: unknown): boolean {\n if (!isAgentMessageLike(message)) return false;\n if (message.role === \"assistant\") {\n this.streamingAssistantIndex = undefined;\n return this.updateAssistantMessage(message as AssistantMessage);\n }\n const entries = chatEntriesFromAgentMessages([message as AgentMessage]);\n if (entries.length === 0) return false;\n this.entries.push(...entries);\n this.reindexPendingTools();\n return true;\n }\n\n private handleMessageUpdate(event: LiveChatEventLike): boolean {\n const message = event.message;\n let changed = false;\n const snapshotHasPayload = isAgentMessageLike(message) &&\n message.role === \"assistant\" &&\n assistantContentHasRenderablePayload((message as { content?: unknown }).content);\n if (isAgentMessageLike(message) && message.role === \"assistant\" && snapshotHasPayload) {\n changed = this.updateAssistantMessage(message as AssistantMessage) || changed;\n }\n const assistantEvent = event.assistantMessageEvent;\n const streamType = String(assistantEvent?.type ?? \"\");\n const delta = typeof assistantEvent?.delta === \"string\" ? assistantEvent.delta : \"\";\n if (!changed && streamType === \"text_delta\" && delta) {\n changed = this.appendAssistantTextDelta(delta);\n } else if (!changed && streamType === \"thinking_delta\" && delta) {\n changed = this.appendAssistantThinkingDelta(delta);\n }\n return changed;\n }\n\n private handleMessageEnd(message: unknown): boolean {\n if (!isAgentMessageLike(message) || message.role !== \"assistant\") return false;\n const changed = this.updateAssistantMessage(message as AssistantMessage);\n const stopReason = typeof message.stopReason === \"string\" ? message.stopReason : \"\";\n if (stopReason === \"aborted\" || stopReason === \"error\") {\n const errorText = typeof message.errorMessage === \"string\" && message.errorMessage\n ? message.errorMessage\n : stopReason === \"aborted\"\n ? \"Operation aborted\"\n : \"Unknown error\";\n for (const toolCallId of this.pendingToolIds()) {\n this.updateToolResult(toolCallId, { content: [{ type: \"text\", text: errorText }] }, false, true);\n }\n this.clearPendingTools();\n }\n this.streamingAssistantIndex = undefined;\n return changed || true;\n }\n\n private updateAssistantMessage(message: AssistantMessage): boolean {\n if (this.streamingAssistantIndex !== undefined && this.isAssistantEntry(this.entries[this.streamingAssistantIndex])) {\n this.entries[this.streamingAssistantIndex] = {\n ...(this.entries[this.streamingAssistantIndex] as Extract<ChatMessageEntry, { kind: \"assistant\" }>),\n message,\n };\n } else {\n this.entries.push({ role: \"assistant\", kind: \"assistant\", message });\n this.streamingAssistantIndex = this.entries.length - 1;\n }\n for (const content of message.content) {\n if (content.type !== \"toolCall\") continue;\n this.upsertToolEntry({\n toolCallId: content.id,\n toolName: content.name,\n args: content.arguments,\n isPartial: true,\n });\n }\n return true;\n }\n\n private appendAssistantTextDelta(delta: string): boolean {\n const current = this.currentStreamingAssistantMessage();\n const content = current ? [...current.content] : [];\n const lastText = [...content].reverse().find((item) => item.type === \"text\");\n if (lastText && lastText.type === \"text\") lastText.text += delta;\n else content.push({ type: \"text\", text: delta });\n return this.updateAssistantMessage({\n ...(current ?? minimalAssistantMessage()),\n content,\n });\n }\n\n private appendAssistantThinkingDelta(delta: string): boolean {\n const current = this.currentStreamingAssistantMessage();\n const content = current ? [...current.content] : [];\n const lastThinking = [...content].reverse().find((item) => item.type === \"thinking\");\n if (lastThinking && lastThinking.type === \"thinking\") lastThinking.thinking += delta;\n else content.push({ type: \"thinking\", thinking: delta });\n return this.updateAssistantMessage({\n ...(current ?? minimalAssistantMessage()),\n content,\n });\n }\n\n private currentStreamingAssistantMessage(): AssistantMessage | undefined {\n const entry = this.streamingAssistantIndex !== undefined ? this.entries[this.streamingAssistantIndex] : undefined;\n return this.isAssistantEntry(entry) ? entry.message : undefined;\n }\n\n private upsertToolEntry(update: {\n toolCallId?: string;\n toolName: string;\n args?: unknown;\n isPartial: boolean;\n }): boolean {\n const toolCallId = update.toolCallId ?? `live-${update.toolName}`;\n const index = this.pendingToolIndexes.get(toolCallId) ?? this.findToolEntryIndex(toolCallId, update.toolName);\n const previous = index >= 0 ? this.entries[index] : undefined;\n const previousTool = this.isToolEntry(previous) ? previous : undefined;\n const next: ChatMessageEntry = {\n role: \"tool\",\n kind: \"tool\",\n toolName: previousTool?.toolName ?? update.toolName,\n toolCallId,\n args: update.args ?? previousTool?.args ?? {},\n result: previousTool?.result,\n isPartial: update.isPartial,\n };\n if (index >= 0) this.entries[index] = next;\n else this.entries.push(next);\n this.pendingToolIndexes.set(toolCallId, index >= 0 ? index : this.entries.length - 1);\n return true;\n }\n\n private updateToolResult(toolCallId: string, result: unknown, isPartial: boolean, isError: boolean): boolean {\n const index = this.pendingToolIndexes.get(toolCallId) ?? this.findToolEntryIndex(toolCallId);\n if (index < 0) return false;\n const entry = this.entries[index];\n if (!this.isToolEntry(entry)) return false;\n const resultObject = toolResultFromUnknown(result, entry.toolName, toolCallId, isError);\n this.entries[index] = { ...entry, result: resultObject, isPartial };\n if (!isPartial) this.pendingToolIndexes.delete(toolCallId);\n return true;\n }\n\n private findToolEntryIndex(toolCallId: string, toolName?: string): number {\n for (let i = this.entries.length - 1; i >= 0; i--) {\n const entry = this.entries[i];\n if (!this.isToolEntry(entry)) continue;\n if (entry.toolCallId === toolCallId || (toolName && entry.toolName === toolName && entry.isPartial !== false)) return i;\n }\n return -1;\n }\n\n private reindexPendingTools(): void {\n this.pendingToolIndexes.clear();\n for (let i = 0; i < this.entries.length; i++) {\n const entry = this.entries[i];\n if (this.isToolEntry(entry) && entry.isPartial !== false) this.pendingToolIndexes.set(entry.toolCallId, i);\n }\n }\n\n private isAssistantEntry(entry: LiveChatEntry | undefined): entry is Extract<ChatMessageEntry, { kind: \"assistant\" }> {\n return isChatMessageEntry(entry) && entry.kind === \"assistant\";\n }\n\n private isToolEntry(entry: LiveChatEntry | undefined): entry is Extract<ChatMessageEntry, { kind: \"tool\" }> {\n return isChatMessageEntry(entry) && entry.kind === \"tool\";\n }\n}\n\nfunction isChatMessageEntry(entry: LiveChatEntry | undefined): entry is ChatMessageEntry {\n return entry !== undefined && \"kind\" in entry;\n}\n\nfunction isAgentMessageLike(message: unknown): message is AgentMessage & { stopReason?: unknown; errorMessage?: unknown } {\n return message !== null && typeof message === \"object\" && \"role\" in message;\n}\n\nfunction assistantContentHasRenderablePayload(content: unknown): boolean {\n if (typeof content === \"string\") return content.length > 0;\n if (!Array.isArray(content)) return false;\n return content.some((item) => {\n if (typeof item === \"string\") return item.length > 0;\n if (item == null || typeof item !== \"object\") return false;\n const obj = item as { type?: unknown; text?: unknown; thinking?: unknown };\n return (obj.type === \"text\" && typeof obj.text === \"string\" && obj.text.length > 0) ||\n (obj.type === \"thinking\" && typeof obj.thinking === \"string\" && obj.thinking.length > 0) ||\n obj.type === \"toolCall\";\n });\n}\n\nfunction minimalAssistantMessage(): AssistantMessage {\n return {\n role: \"assistant\",\n content: [],\n stopReason: \"stop\",\n } as unknown as AssistantMessage;\n}\n\nfunction toolResultFromUnknown(\n result: unknown,\n toolName: string,\n toolCallId: string,\n isError: boolean,\n): ToolResultMessage {\n if (result !== null && typeof result === \"object\" && \"content\" in result) {\n const candidate = result as { content?: unknown; details?: unknown };\n const content = Array.isArray(candidate.content) ? candidate.content : [];\n return {\n role: \"toolResult\",\n toolCallId,\n toolName,\n content: content as ToolResultMessage[\"content\"],\n details: candidate.details,\n isError,\n timestamp: Date.now(),\n };\n }\n return {\n role: \"toolResult\",\n toolCallId,\n toolName,\n content: typeof result === \"string\" ? [{ type: \"text\", text: result }] : [],\n isError,\n timestamp: Date.now(),\n };\n}\n\nexport function renderChatMessageEntry(\n entry: ChatMessageEntry,\n options: ChatMessageRenderOptions,\n): Component {\n const messageEntry = entry as ChatMessageEntry;\n const markdownTheme = options.markdownTheme ?? getMarkdownTheme();\n\n switch (messageEntry.kind) {\n case \"assistant\":\n return new AssistantMessageComponent(\n messageEntry.message,\n options.hideThinkingBlock ?? false,\n markdownTheme,\n options.hiddenThinkingLabel ?? \"Thinking...\",\n );\n case \"tool\": {\n const component = new ToolExecutionComponent(\n messageEntry.toolName,\n messageEntry.toolCallId,\n messageEntry.args,\n {\n showImages: options.showImages ?? true,\n imageWidthCells: options.imageWidthCells,\n },\n options.getToolDefinition?.(messageEntry.toolName),\n options.ui as TUI,\n options.cwd,\n );\n component.setExpanded(options.toolOutputExpanded ?? false);\n if (messageEntry.result) component.updateResult(messageEntry.result, messageEntry.isPartial ?? false);\n return component;\n }\n case \"bashExecution\": {\n const component = new BashExecutionComponent(\n messageEntry.message.command,\n options.ui as TUI,\n messageEntry.message.excludeFromContext,\n );\n if (messageEntry.message.output) component.appendOutput(messageEntry.message.output);\n component.setComplete(\n messageEntry.message.exitCode,\n messageEntry.message.cancelled,\n messageEntry.message.truncated\n ? ({ truncated: true } as Parameters<BashExecutionComponent[\"setComplete\"]>[2])\n : undefined,\n messageEntry.message.fullOutputPath,\n );\n return component;\n }\n case \"user\":\n return userMessageComponent(messageEntry.text, markdownTheme, options.toolOutputExpanded ?? false);\n case \"custom\": {\n const component = new CustomMessageComponent(\n messageEntry.message,\n options.getCustomMessageRenderer?.(messageEntry.message.customType),\n markdownTheme,\n );\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"branchSummary\": {\n const component = new BranchSummaryMessageComponent(messageEntry.message, markdownTheme);\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"compactionSummary\": {\n const component = new CompactionSummaryMessageComponent(messageEntry.message, markdownTheme);\n component.setExpanded(options.toolOutputExpanded ?? false);\n return component;\n }\n case \"system\":\n return new Text(theme.fg(\"dim\", messageEntry.text), 1, 0);\n }\n}\n\nfunction userMessageComponent(text: string, markdownTheme: MarkdownTheme, expanded: boolean): Component {\n const skillBlock = parseSkillBlock(text);\n if (!skillBlock) return new UserMessageComponent(text, markdownTheme);\n\n const container = new Container();\n const skillComponent = new SkillInvocationMessageComponent(skillBlock, markdownTheme);\n skillComponent.setExpanded(expanded);\n container.addChild(skillComponent);\n if (skillBlock.userMessage) {\n container.addChild(new UserMessageComponent(skillBlock.userMessage, markdownTheme));\n }\n return container;\n}\n\nfunction getMessageText(message: Extract<AgentMessage, { role: \"user\" }>): string {\n return messageContentText(message.content).trim();\n}\n\nfunction messageContentText(content: unknown): string {\n if (typeof content === \"string\") return content;\n if (!Array.isArray(content)) return \"\";\n const parts: string[] = [];\n for (const item of content) {\n if (item == null) continue;\n if (typeof item === \"string\") {\n parts.push(item);\n continue;\n }\n if (typeof item !== \"object\") continue;\n const text = (item as { text?: unknown }).text;\n if (typeof text === \"string\") parts.push(text);\n }\n return parts.join(\"\");\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"chat-transcript.d.ts","sourceRoot":"","sources":["../../../../src/modes/interactive/components/chat-transcript.ts"],"names":[],"mappings":"AAAA,OAAO,EAEL,KAAK,SAAS,EACd,SAAS,EAEV,MAAM,wBAAwB,CAAC;AAEhC;;;;;;GAMG;AACH,MAAM,MAAM,kBAAkB,GAC1B,WAAW,GACX,UAAU,GACV,MAAM,GACN,MAAM,GACN,QAAQ,GACR,QAAQ,GACR,QAAQ,GACR,SAAS,CAAC;AAEd,MAAM,WAAW,uBAAuB;IACtC,QAAQ,CAAC,IAAI,EAAE,kBAAkB,CAAC;CACnC;AAED,MAAM,MAAM,sBAAsB,CAAC,MAAM,SAAS,uBAAuB,IAAI,CAC3E,KAAK,EAAE,MAAM,KACV,SAAS,CAAC;AAEf,wBAAgB,sBAAsB,CACpC,SAAS,EAAE,SAAS,EACpB,SAAS,EAAE,SAAS,EACpB,IAAI,EAAE,kBAAkB,GACvB,IAAI,CAKN;AAYD;;;;;;;GAOG;AACH,qBAAa,uBAAuB,CAAC,MAAM,SAAS,uBAAuB,CACzE,YAAW,SAAS;
|
|
1
|
+
{"version":3,"file":"chat-transcript.d.ts","sourceRoot":"","sources":["../../../../src/modes/interactive/components/chat-transcript.ts"],"names":[],"mappings":"AAAA,OAAO,EAEL,KAAK,SAAS,EACd,SAAS,EAEV,MAAM,wBAAwB,CAAC;AAEhC;;;;;;GAMG;AACH,MAAM,MAAM,kBAAkB,GAC1B,WAAW,GACX,UAAU,GACV,MAAM,GACN,MAAM,GACN,QAAQ,GACR,QAAQ,GACR,QAAQ,GACR,SAAS,CAAC;AAEd,MAAM,WAAW,uBAAuB;IACtC,QAAQ,CAAC,IAAI,EAAE,kBAAkB,CAAC;CACnC;AAED,MAAM,MAAM,sBAAsB,CAAC,MAAM,SAAS,uBAAuB,IAAI,CAC3E,KAAK,EAAE,MAAM,KACV,SAAS,CAAC;AAEf,wBAAgB,sBAAsB,CACpC,SAAS,EAAE,SAAS,EACpB,SAAS,EAAE,SAAS,EACpB,IAAI,EAAE,kBAAkB,GACvB,IAAI,CAKN;AAYD;;;;;;;GAOG;AACH,qBAAa,uBAAuB,CAAC,MAAM,SAAS,uBAAuB,CACzE,YAAW,SAAS;IAEpB,iBAAyB,OAAO,CAAoB;IACpD,iBAAyB,WAAW,CAAiC;IAErE,YACE,OAAO,EAAE,SAAS,MAAM,EAAE,EAC1B,WAAW,EAAE,sBAAsB,CAAC,MAAM,CAAC,EAI7C;IAEA,MAAM,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,EAAE,CAM9B;IAED,UAAU,IAAI,IAAI,CAAG;CACtB;AAID;;;;;;GAMG;AACH,qBAAa,2BAA4B,YAAW,SAAS;IAC3D,OAAO,CAAC,UAAU,CAA4B;IAC9C,OAAO,CAAC,WAAW,CAAK;IACxB,OAAO,CAAC,gBAAgB,CAAK;IAC7B,OAAO,CAAC,aAAa,CAAK;IAC1B,OAAO,CAAC,SAAS,CAAK;IACtB,OAAO,CAAC,SAAS,CAAK;IAEtB,aAAa,CAAC,UAAU,EAAE,SAAS,SAAS,EAAE,GAAG,IAAI,CAEpD;IAED,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAGjC;IAED,mBAAmB,IAAI,MAAM,CAE5B;IAED,YAAY,IAAI,MAAM,CAErB;IAED,cAAc,IAAI,IAAI,CAErB;IAED,WAAW,IAAI,IAAI,CAElB;IAED,QAAQ,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI,CAMhC;IAED,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAwBjC;IAED,MAAM,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,EAAE,CAe9B;IAED,UAAU,IAAI,IAAI,CAEjB;IAED,OAAO,CAAC,QAAQ;IAIhB,OAAO,CAAC,WAAW;CAGpB;AAED,qBAAa,iCAAiC,CAAC,MAAM,SAAS,uBAAuB,CACnF,YAAW,SAAS;IAEpB,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAqC;IAC9D,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAkC;IAE7D,YACE,OAAO,EAAE,SAAS,MAAM,EAAE,EAC1B,WAAW,EAAE,sBAAsB,CAAC,MAAM,CAAC,EAI5C;IAED,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAEjC;IAED,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAEjC;IAED,MAAM,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,EAAE,CAE9B;IAED,UAAU,IAAI,IAAI,CAEjB;IAED,mBAAmB,IAAI,MAAM,CAE5B;IAED,YAAY,IAAI,MAAM,CAErB;IAED,cAAc,IAAI,IAAI,CAErB;CACF","sourcesContent":["import {\n matchesKey,\n type Component,\n Container,\n Spacer,\n} from \"@earendil-works/pi-tui\";\n\n/**\n * Roles that participate in pi's chat spacing contract.\n *\n * Assistant turns own their leading whitespace internally, and tool rows attach\n * directly under the assistant/tool-call row they belong to. User-like rows get\n * one blank line when they are not the first row in the transcript.\n */\nexport type ChatTranscriptRole =\n | \"assistant\"\n | \"thinking\"\n | \"tool\"\n | \"user\"\n | \"custom\"\n | \"notice\"\n | \"system\"\n | \"summary\";\n\nexport interface ChatTranscriptEntryLike {\n readonly role: ChatTranscriptRole;\n}\n\nexport type ChatTranscriptRenderer<TEntry extends ChatTranscriptEntryLike> = (\n entry: TEntry,\n) => Component;\n\nexport function addChatTranscriptEntry(\n container: Container,\n component: Component,\n role: ChatTranscriptRole,\n): void {\n if (needsLeadingSpacer(role) && container.children.length > 0) {\n container.addChild(new Spacer(1));\n }\n container.addChild(component);\n}\n\nfunction needsLeadingSpacer(role: ChatTranscriptRole): boolean {\n return (\n role === \"user\" ||\n role === \"custom\" ||\n role === \"notice\" ||\n role === \"system\" ||\n role === \"summary\"\n );\n}\n\n/**\n * Reusable pi chat transcript scaffold for extension surfaces.\n *\n * This intentionally mirrors InteractiveMode.addMessageToChat spacing without\n * coupling consumers to a full AgentSession. Extension UIs can bring their own\n * message model while still rendering inside the same Container/Spacer rhythm\n * as the main chat.\n */\nexport class ChatTranscriptComponent<TEntry extends ChatTranscriptEntryLike>\n implements Component\n{\n declare private readonly entries: readonly TEntry[];\n declare private readonly renderEntry: ChatTranscriptRenderer<TEntry>;\n\n constructor(\n entries: readonly TEntry[],\n renderEntry: ChatTranscriptRenderer<TEntry>,\n ) {\n this.entries = entries;\n this.renderEntry = renderEntry;\n\t}\n\n render(width: number): string[] {\n const container = new Container();\n for (const entry of this.entries) {\n addChatTranscriptEntry(container, this.renderEntry(entry), entry.role);\n }\n return container.render(width);\n }\n\n invalidate(): void {}\n}\n\nconst DEFAULT_SCROLL_STEP_ROWS = 4;\n\n/**\n * Sticky-bottom, scrollable viewport for chat-like component stacks.\n *\n * Pi's main interactive chat gets terminal scrollback for free. Extension\n * overlays render into a fixed rectangle, so they need an explicit viewport\n * with the same sticky-bottom default plus keyboard and mouse history controls.\n */\nexport class ScrollableComponentViewport implements Component {\n private components: readonly Component[] = [];\n private visibleRows = 1;\n private scrollFromBottom = 0;\n private lastLineCount = 0;\n private lastWidth = 0;\n private maxScroll = 0;\n\n setComponents(components: readonly Component[]): void {\n this.components = components;\n }\n\n setVisibleRows(rows: number): void {\n this.visibleRows = Math.max(1, Math.floor(rows));\n this.clampScroll();\n }\n\n getScrollFromBottom(): number {\n return this.scrollFromBottom;\n }\n\n getMaxScroll(): number {\n return this.maxScroll;\n }\n\n scrollToBottom(): void {\n this.scrollFromBottom = 0;\n }\n\n scrollToTop(): void {\n this.scrollFromBottom = this.maxScroll;\n }\n\n scrollBy(deltaRows: number): void {\n // Positive deltas move toward newer content; negative deltas move up\n // into older history. Store the offset from the sticky bottom so new\n // streaming output can keep following when the offset is zero.\n this.scrollFromBottom -= deltaRows;\n this.clampScroll();\n }\n\n handleInput(data: string): boolean {\n const wheelDeltaRows = mouseWheelDeltaRows(data);\n if (wheelDeltaRows !== 0) {\n this.scrollBy(wheelDeltaRows);\n return true;\n }\n if (isMouseSequence(data)) return true;\n if (matchesKey(data, \"pageUp\")) {\n this.scrollBy(-this.pageSize());\n return true;\n }\n if (matchesKey(data, \"pageDown\")) {\n this.scrollBy(this.pageSize());\n return true;\n }\n if (matchesKey(data, \"home\")) {\n this.scrollToTop();\n return true;\n }\n if (matchesKey(data, \"end\")) {\n this.scrollToBottom();\n return true;\n }\n return false;\n }\n\n render(width: number): string[] {\n const allLines = this.components.flatMap((component) => component.render(width));\n const maxScroll = Math.max(0, allLines.length - this.visibleRows);\n if (this.scrollFromBottom > 0 && this.lastWidth === width && allLines.length > this.lastLineCount) {\n this.scrollFromBottom += allLines.length - this.lastLineCount;\n }\n this.lastLineCount = allLines.length;\n this.lastWidth = width;\n this.maxScroll = maxScroll;\n this.clampScroll();\n\n const start = Math.max(0, maxScroll - this.scrollFromBottom);\n const visible = allLines.slice(start, start + this.visibleRows);\n while (visible.length < this.visibleRows) visible.push(\" \".repeat(width));\n return visible;\n }\n\n invalidate(): void {\n for (const component of this.components) component.invalidate();\n }\n\n private pageSize(): number {\n return Math.max(4, this.visibleRows - 2);\n }\n\n private clampScroll(): void {\n this.scrollFromBottom = Math.max(0, Math.min(this.maxScroll, this.scrollFromBottom));\n }\n}\n\nexport class ScrollableChatTranscriptComponent<TEntry extends ChatTranscriptEntryLike>\n implements Component\n{\n private readonly viewport = new ScrollableComponentViewport();\n private readonly transcript: ChatTranscriptComponent<TEntry>;\n\n constructor(\n entries: readonly TEntry[],\n renderEntry: ChatTranscriptRenderer<TEntry>,\n ) {\n this.transcript = new ChatTranscriptComponent(entries, renderEntry);\n this.viewport.setComponents([this.transcript]);\n }\n\n setVisibleRows(rows: number): void {\n this.viewport.setVisibleRows(rows);\n }\n\n handleInput(data: string): boolean {\n return this.viewport.handleInput(data);\n }\n\n render(width: number): string[] {\n return this.viewport.render(width);\n }\n\n invalidate(): void {\n this.viewport.invalidate();\n }\n\n getScrollFromBottom(): number {\n return this.viewport.getScrollFromBottom();\n }\n\n getMaxScroll(): number {\n return this.viewport.getMaxScroll();\n }\n\n scrollToBottom(): void {\n this.viewport.scrollToBottom();\n }\n}\n\nfunction mouseWheelDeltaRows(data: string): number {\n const sgr = data.match(/^\\x1b\\[<(\\d+);\\d+;\\d+M$/);\n if (sgr) return wheelDeltaForButtonCode(Number.parseInt(sgr[1]!, 10));\n if (data.startsWith(\"\\x1b[M\") && data.length >= 6) {\n return wheelDeltaForButtonCode(data.charCodeAt(3) - 32);\n }\n return 0;\n}\n\nfunction wheelDeltaForButtonCode(code: number): number {\n if ((code & 64) === 0) return 0;\n const direction = code & 3;\n if (direction === 0) return -DEFAULT_SCROLL_STEP_ROWS;\n if (direction === 1) return DEFAULT_SCROLL_STEP_ROWS;\n return 0;\n}\n\nfunction isMouseSequence(data: string): boolean {\n return /^\\x1b\\[<\\d+;\\d+;\\d+[mM]$/.test(data) || data.startsWith(\"\\x1b[M\");\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"chat-transcript.js","sourceRoot":"","sources":["../../../../src/modes/interactive/components/chat-transcript.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n matchesKey,\n type Component,\n Container,\n Spacer,\n} from \"@earendil-works/pi-tui\";\n\n/**\n * Roles that participate in pi's chat spacing contract.\n *\n * Assistant turns own their leading whitespace internally, and tool rows attach\n * directly under the assistant/tool-call row they belong to. User-like rows get\n * one blank line when they are not the first row in the transcript.\n */\nexport type ChatTranscriptRole =\n | \"assistant\"\n | \"thinking\"\n | \"tool\"\n | \"user\"\n | \"custom\"\n | \"notice\"\n | \"system\"\n | \"summary\";\n\nexport interface ChatTranscriptEntryLike {\n readonly role: ChatTranscriptRole;\n}\n\nexport type ChatTranscriptRenderer<TEntry extends ChatTranscriptEntryLike> = (\n entry: TEntry,\n) => Component;\n\nexport function addChatTranscriptEntry(\n container: Container,\n component: Component,\n role: ChatTranscriptRole,\n): void {\n if (needsLeadingSpacer(role) && container.children.length > 0) {\n container.addChild(new Spacer(1));\n }\n container.addChild(component);\n}\n\nfunction needsLeadingSpacer(role: ChatTranscriptRole): boolean {\n return (\n role === \"user\" ||\n role === \"custom\" ||\n role === \"notice\" ||\n role === \"system\" ||\n role === \"summary\"\n );\n}\n\n/**\n * Reusable pi chat transcript scaffold for extension surfaces.\n *\n * This intentionally mirrors InteractiveMode.addMessageToChat spacing without\n * coupling consumers to a full AgentSession. Extension UIs can bring their own\n * message model while still rendering inside the same Container/Spacer rhythm\n * as the main chat.\n */\nexport class ChatTranscriptComponent<TEntry extends ChatTranscriptEntryLike>\n implements Component\n{\n constructor(\n private readonly entries: readonly TEntry[],\n private readonly renderEntry: ChatTranscriptRenderer<TEntry>,\n ) {}\n\n render(width: number): string[] {\n const container = new Container();\n for (const entry of this.entries) {\n addChatTranscriptEntry(container, this.renderEntry(entry), entry.role);\n }\n return container.render(width);\n }\n\n invalidate(): void {}\n}\n\nconst DEFAULT_SCROLL_STEP_ROWS = 4;\n\n/**\n * Sticky-bottom, scrollable viewport for chat-like component stacks.\n *\n * Pi's main interactive chat gets terminal scrollback for free. Extension\n * overlays render into a fixed rectangle, so they need an explicit viewport\n * with the same sticky-bottom default plus keyboard and mouse history controls.\n */\nexport class ScrollableComponentViewport implements Component {\n private components: readonly Component[] = [];\n private visibleRows = 1;\n private scrollFromBottom = 0;\n private lastLineCount = 0;\n private lastWidth = 0;\n private maxScroll = 0;\n\n setComponents(components: readonly Component[]): void {\n this.components = components;\n }\n\n setVisibleRows(rows: number): void {\n this.visibleRows = Math.max(1, Math.floor(rows));\n this.clampScroll();\n }\n\n getScrollFromBottom(): number {\n return this.scrollFromBottom;\n }\n\n getMaxScroll(): number {\n return this.maxScroll;\n }\n\n scrollToBottom(): void {\n this.scrollFromBottom = 0;\n }\n\n scrollToTop(): void {\n this.scrollFromBottom = this.maxScroll;\n }\n\n scrollBy(deltaRows: number): void {\n // Positive deltas move toward newer content; negative deltas move up\n // into older history. Store the offset from the sticky bottom so new\n // streaming output can keep following when the offset is zero.\n this.scrollFromBottom -= deltaRows;\n this.clampScroll();\n }\n\n handleInput(data: string): boolean {\n const wheelDeltaRows = mouseWheelDeltaRows(data);\n if (wheelDeltaRows !== 0) {\n this.scrollBy(wheelDeltaRows);\n return true;\n }\n if (isMouseSequence(data)) return true;\n if (matchesKey(data, \"pageUp\")) {\n this.scrollBy(-this.pageSize());\n return true;\n }\n if (matchesKey(data, \"pageDown\")) {\n this.scrollBy(this.pageSize());\n return true;\n }\n if (matchesKey(data, \"home\")) {\n this.scrollToTop();\n return true;\n }\n if (matchesKey(data, \"end\")) {\n this.scrollToBottom();\n return true;\n }\n return false;\n }\n\n render(width: number): string[] {\n const allLines = this.components.flatMap((component) => component.render(width));\n const maxScroll = Math.max(0, allLines.length - this.visibleRows);\n if (this.scrollFromBottom > 0 && this.lastWidth === width && allLines.length > this.lastLineCount) {\n this.scrollFromBottom += allLines.length - this.lastLineCount;\n }\n this.lastLineCount = allLines.length;\n this.lastWidth = width;\n this.maxScroll = maxScroll;\n this.clampScroll();\n\n const start = Math.max(0, maxScroll - this.scrollFromBottom);\n const visible = allLines.slice(start, start + this.visibleRows);\n while (visible.length < this.visibleRows) visible.push(\" \".repeat(width));\n return visible;\n }\n\n invalidate(): void {\n for (const component of this.components) component.invalidate();\n }\n\n private pageSize(): number {\n return Math.max(4, this.visibleRows - 2);\n }\n\n private clampScroll(): void {\n this.scrollFromBottom = Math.max(0, Math.min(this.maxScroll, this.scrollFromBottom));\n }\n}\n\nexport class ScrollableChatTranscriptComponent<TEntry extends ChatTranscriptEntryLike>\n implements Component\n{\n private readonly viewport = new ScrollableComponentViewport();\n private readonly transcript: ChatTranscriptComponent<TEntry>;\n\n constructor(\n entries: readonly TEntry[],\n renderEntry: ChatTranscriptRenderer<TEntry>,\n ) {\n this.transcript = new ChatTranscriptComponent(entries, renderEntry);\n this.viewport.setComponents([this.transcript]);\n }\n\n setVisibleRows(rows: number): void {\n this.viewport.setVisibleRows(rows);\n }\n\n handleInput(data: string): boolean {\n return this.viewport.handleInput(data);\n }\n\n render(width: number): string[] {\n return this.viewport.render(width);\n }\n\n invalidate(): void {\n this.viewport.invalidate();\n }\n\n getScrollFromBottom(): number {\n return this.viewport.getScrollFromBottom();\n }\n\n getMaxScroll(): number {\n return this.viewport.getMaxScroll();\n }\n\n scrollToBottom(): void {\n this.viewport.scrollToBottom();\n }\n}\n\nfunction mouseWheelDeltaRows(data: string): number {\n const sgr = data.match(/^\\x1b\\[<(\\d+);\\d+;\\d+M$/);\n if (sgr) return wheelDeltaForButtonCode(Number.parseInt(sgr[1]!, 10));\n if (data.startsWith(\"\\x1b[M\") && data.length >= 6) {\n return wheelDeltaForButtonCode(data.charCodeAt(3) - 32);\n }\n return 0;\n}\n\nfunction wheelDeltaForButtonCode(code: number): number {\n if ((code & 64) === 0) return 0;\n const direction = code & 3;\n if (direction === 0) return -DEFAULT_SCROLL_STEP_ROWS;\n if (direction === 1) return DEFAULT_SCROLL_STEP_ROWS;\n return 0;\n}\n\nfunction isMouseSequence(data: string): boolean {\n return /^\\x1b\\[<\\d+;\\d+;\\d+[mM]$/.test(data) || data.startsWith(\"\\x1b[M\");\n}\n"]}
|
|
1
|
+
{"version":3,"file":"chat-transcript.js","sourceRoot":"","sources":["../../../../src/modes/interactive/components/chat-transcript.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n matchesKey,\n type Component,\n Container,\n Spacer,\n} from \"@earendil-works/pi-tui\";\n\n/**\n * Roles that participate in pi's chat spacing contract.\n *\n * Assistant turns own their leading whitespace internally, and tool rows attach\n * directly under the assistant/tool-call row they belong to. User-like rows get\n * one blank line when they are not the first row in the transcript.\n */\nexport type ChatTranscriptRole =\n | \"assistant\"\n | \"thinking\"\n | \"tool\"\n | \"user\"\n | \"custom\"\n | \"notice\"\n | \"system\"\n | \"summary\";\n\nexport interface ChatTranscriptEntryLike {\n readonly role: ChatTranscriptRole;\n}\n\nexport type ChatTranscriptRenderer<TEntry extends ChatTranscriptEntryLike> = (\n entry: TEntry,\n) => Component;\n\nexport function addChatTranscriptEntry(\n container: Container,\n component: Component,\n role: ChatTranscriptRole,\n): void {\n if (needsLeadingSpacer(role) && container.children.length > 0) {\n container.addChild(new Spacer(1));\n }\n container.addChild(component);\n}\n\nfunction needsLeadingSpacer(role: ChatTranscriptRole): boolean {\n return (\n role === \"user\" ||\n role === \"custom\" ||\n role === \"notice\" ||\n role === \"system\" ||\n role === \"summary\"\n );\n}\n\n/**\n * Reusable pi chat transcript scaffold for extension surfaces.\n *\n * This intentionally mirrors InteractiveMode.addMessageToChat spacing without\n * coupling consumers to a full AgentSession. Extension UIs can bring their own\n * message model while still rendering inside the same Container/Spacer rhythm\n * as the main chat.\n */\nexport class ChatTranscriptComponent<TEntry extends ChatTranscriptEntryLike>\n implements Component\n{\n declare private readonly entries: readonly TEntry[];\n declare private readonly renderEntry: ChatTranscriptRenderer<TEntry>;\n\n constructor(\n entries: readonly TEntry[],\n renderEntry: ChatTranscriptRenderer<TEntry>,\n ) {\n this.entries = entries;\n this.renderEntry = renderEntry;\n\t}\n\n render(width: number): string[] {\n const container = new Container();\n for (const entry of this.entries) {\n addChatTranscriptEntry(container, this.renderEntry(entry), entry.role);\n }\n return container.render(width);\n }\n\n invalidate(): void {}\n}\n\nconst DEFAULT_SCROLL_STEP_ROWS = 4;\n\n/**\n * Sticky-bottom, scrollable viewport for chat-like component stacks.\n *\n * Pi's main interactive chat gets terminal scrollback for free. Extension\n * overlays render into a fixed rectangle, so they need an explicit viewport\n * with the same sticky-bottom default plus keyboard and mouse history controls.\n */\nexport class ScrollableComponentViewport implements Component {\n private components: readonly Component[] = [];\n private visibleRows = 1;\n private scrollFromBottom = 0;\n private lastLineCount = 0;\n private lastWidth = 0;\n private maxScroll = 0;\n\n setComponents(components: readonly Component[]): void {\n this.components = components;\n }\n\n setVisibleRows(rows: number): void {\n this.visibleRows = Math.max(1, Math.floor(rows));\n this.clampScroll();\n }\n\n getScrollFromBottom(): number {\n return this.scrollFromBottom;\n }\n\n getMaxScroll(): number {\n return this.maxScroll;\n }\n\n scrollToBottom(): void {\n this.scrollFromBottom = 0;\n }\n\n scrollToTop(): void {\n this.scrollFromBottom = this.maxScroll;\n }\n\n scrollBy(deltaRows: number): void {\n // Positive deltas move toward newer content; negative deltas move up\n // into older history. Store the offset from the sticky bottom so new\n // streaming output can keep following when the offset is zero.\n this.scrollFromBottom -= deltaRows;\n this.clampScroll();\n }\n\n handleInput(data: string): boolean {\n const wheelDeltaRows = mouseWheelDeltaRows(data);\n if (wheelDeltaRows !== 0) {\n this.scrollBy(wheelDeltaRows);\n return true;\n }\n if (isMouseSequence(data)) return true;\n if (matchesKey(data, \"pageUp\")) {\n this.scrollBy(-this.pageSize());\n return true;\n }\n if (matchesKey(data, \"pageDown\")) {\n this.scrollBy(this.pageSize());\n return true;\n }\n if (matchesKey(data, \"home\")) {\n this.scrollToTop();\n return true;\n }\n if (matchesKey(data, \"end\")) {\n this.scrollToBottom();\n return true;\n }\n return false;\n }\n\n render(width: number): string[] {\n const allLines = this.components.flatMap((component) => component.render(width));\n const maxScroll = Math.max(0, allLines.length - this.visibleRows);\n if (this.scrollFromBottom > 0 && this.lastWidth === width && allLines.length > this.lastLineCount) {\n this.scrollFromBottom += allLines.length - this.lastLineCount;\n }\n this.lastLineCount = allLines.length;\n this.lastWidth = width;\n this.maxScroll = maxScroll;\n this.clampScroll();\n\n const start = Math.max(0, maxScroll - this.scrollFromBottom);\n const visible = allLines.slice(start, start + this.visibleRows);\n while (visible.length < this.visibleRows) visible.push(\" \".repeat(width));\n return visible;\n }\n\n invalidate(): void {\n for (const component of this.components) component.invalidate();\n }\n\n private pageSize(): number {\n return Math.max(4, this.visibleRows - 2);\n }\n\n private clampScroll(): void {\n this.scrollFromBottom = Math.max(0, Math.min(this.maxScroll, this.scrollFromBottom));\n }\n}\n\nexport class ScrollableChatTranscriptComponent<TEntry extends ChatTranscriptEntryLike>\n implements Component\n{\n private readonly viewport = new ScrollableComponentViewport();\n private readonly transcript: ChatTranscriptComponent<TEntry>;\n\n constructor(\n entries: readonly TEntry[],\n renderEntry: ChatTranscriptRenderer<TEntry>,\n ) {\n this.transcript = new ChatTranscriptComponent(entries, renderEntry);\n this.viewport.setComponents([this.transcript]);\n }\n\n setVisibleRows(rows: number): void {\n this.viewport.setVisibleRows(rows);\n }\n\n handleInput(data: string): boolean {\n return this.viewport.handleInput(data);\n }\n\n render(width: number): string[] {\n return this.viewport.render(width);\n }\n\n invalidate(): void {\n this.viewport.invalidate();\n }\n\n getScrollFromBottom(): number {\n return this.viewport.getScrollFromBottom();\n }\n\n getMaxScroll(): number {\n return this.viewport.getMaxScroll();\n }\n\n scrollToBottom(): void {\n this.viewport.scrollToBottom();\n }\n}\n\nfunction mouseWheelDeltaRows(data: string): number {\n const sgr = data.match(/^\\x1b\\[<(\\d+);\\d+;\\d+M$/);\n if (sgr) return wheelDeltaForButtonCode(Number.parseInt(sgr[1]!, 10));\n if (data.startsWith(\"\\x1b[M\") && data.length >= 6) {\n return wheelDeltaForButtonCode(data.charCodeAt(3) - 32);\n }\n return 0;\n}\n\nfunction wheelDeltaForButtonCode(code: number): number {\n if ((code & 64) === 0) return 0;\n const direction = code & 3;\n if (direction === 0) return -DEFAULT_SCROLL_STEP_ROWS;\n if (direction === 1) return DEFAULT_SCROLL_STEP_ROWS;\n return 0;\n}\n\nfunction isMouseSequence(data: string): boolean {\n return /^\\x1b\\[<\\d+;\\d+;\\d+[mM]$/.test(data) || data.startsWith(\"\\x1b[M\");\n}\n"]}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Box, type MarkdownTheme } from "@earendil-works/pi-tui";
|
|
2
|
-
import type { CompactionSummaryMessage } from "../../../core/messages.
|
|
2
|
+
import type { CompactionSummaryMessage } from "../../../core/messages.ts";
|
|
3
3
|
/**
|
|
4
4
|
* Component that renders a compaction message with collapsed/expanded state.
|
|
5
5
|
* Uses same background color as custom messages for visual consistency.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"compaction-summary-message.d.ts","sourceRoot":"","sources":["../../../../src/modes/interactive/components/compaction-summary-message.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAY,KAAK,aAAa,EAAgB,MAAM,wBAAwB,CAAC;AACzF,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,2BAA2B,CAAC;AAI1E;;;GAGG;AACH,qBAAa,iCAAkC,SAAQ,GAAG;IACzD,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,OAAO,CAA2B;IAC1C,OAAO,CAAC,aAAa,CAAgB;IAErC,YAAY,OAAO,EAAE,wBAAwB,EAAE,aAAa,GAAE,aAAkC,EAK/F;IAED,WAAW,CAAC,QAAQ,EAAE,OAAO,GAAG,IAAI,CAGnC;IAEQ,UAAU,IAAI,IAAI,CAG1B;IAED,OAAO,CAAC,aAAa;CA2BrB","sourcesContent":["import { Box, Markdown, type MarkdownTheme, Spacer, Text } from \"@earendil-works/pi-tui\";\nimport type { CompactionSummaryMessage } from \"../../../core/messages.
|
|
1
|
+
{"version":3,"file":"compaction-summary-message.d.ts","sourceRoot":"","sources":["../../../../src/modes/interactive/components/compaction-summary-message.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAY,KAAK,aAAa,EAAgB,MAAM,wBAAwB,CAAC;AACzF,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,2BAA2B,CAAC;AAI1E;;;GAGG;AACH,qBAAa,iCAAkC,SAAQ,GAAG;IACzD,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,OAAO,CAA2B;IAC1C,OAAO,CAAC,aAAa,CAAgB;IAErC,YAAY,OAAO,EAAE,wBAAwB,EAAE,aAAa,GAAE,aAAkC,EAK/F;IAED,WAAW,CAAC,QAAQ,EAAE,OAAO,GAAG,IAAI,CAGnC;IAEQ,UAAU,IAAI,IAAI,CAG1B;IAED,OAAO,CAAC,aAAa;CA2BrB","sourcesContent":["import { Box, Markdown, type MarkdownTheme, Spacer, Text } from \"@earendil-works/pi-tui\";\nimport type { CompactionSummaryMessage } from \"../../../core/messages.ts\";\nimport { getMarkdownTheme, theme } from \"../theme/theme.ts\";\nimport { keyText } from \"./keybinding-hints.ts\";\n\n/**\n * Component that renders a compaction message with collapsed/expanded state.\n * Uses same background color as custom messages for visual consistency.\n */\nexport class CompactionSummaryMessageComponent extends Box {\n\tprivate expanded = false;\n\tprivate message: CompactionSummaryMessage;\n\tprivate markdownTheme: MarkdownTheme;\n\n\tconstructor(message: CompactionSummaryMessage, markdownTheme: MarkdownTheme = getMarkdownTheme()) {\n\t\tsuper(1, 1, (t) => theme.bg(\"customMessageBg\", t));\n\t\tthis.message = message;\n\t\tthis.markdownTheme = markdownTheme;\n\t\tthis.updateDisplay();\n\t}\n\n\tsetExpanded(expanded: boolean): void {\n\t\tthis.expanded = expanded;\n\t\tthis.updateDisplay();\n\t}\n\n\toverride invalidate(): void {\n\t\tsuper.invalidate();\n\t\tthis.updateDisplay();\n\t}\n\n\tprivate updateDisplay(): void {\n\t\tthis.clear();\n\n\t\tconst tokenStr = this.message.tokensBefore.toLocaleString();\n\t\tconst label = theme.fg(\"customMessageLabel\", `\\x1b[1m[compaction]\\x1b[22m`);\n\t\tthis.addChild(new Text(label, 0, 0));\n\t\tthis.addChild(new Spacer(1));\n\n\t\tif (this.expanded) {\n\t\t\tconst header = `**Compacted from ${tokenStr} tokens**\\n\\n`;\n\t\t\tthis.addChild(\n\t\t\t\tnew Markdown(header + this.message.summary, 0, 0, this.markdownTheme, {\n\t\t\t\t\tcolor: (text: string) => theme.fg(\"customMessageText\", text),\n\t\t\t\t}),\n\t\t\t);\n\t\t} else {\n\t\t\tthis.addChild(\n\t\t\t\tnew Text(\n\t\t\t\t\ttheme.fg(\"customMessageText\", `Compacted from ${tokenStr} tokens (`) +\n\t\t\t\t\t\ttheme.fg(\"dim\", keyText(\"app.tools.expand\")) +\n\t\t\t\t\t\ttheme.fg(\"customMessageText\", \" Expand)\"),\n\t\t\t\t\t0,\n\t\t\t\t\t0,\n\t\t\t\t),\n\t\t\t);\n\t\t}\n\t}\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"compaction-summary-message.js","sourceRoot":"","sources":["../../../../src/modes/interactive/components/compaction-summary-message.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,QAAQ,EAAsB,MAAM,EAAE,IAAI,EAAE,MAAM,wBAAwB,CAAC;AAEzF,OAAO,EAAE,gBAAgB,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAC;AAC5D,OAAO,EAAE,OAAO,EAAE,MAAM,uBAAuB,CAAC;AAEhD;;;GAGG;AACH,MAAM,OAAO,iCAAkC,SAAQ,GAAG;IAKzD,YAAY,OAAiC,EAAE,aAAa,GAAkB,gBAAgB,EAAE;QAC/F,KAAK,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,KAAK,CAAC,EAAE,CAAC,iBAAiB,EAAE,CAAC,CAAC,CAAC,CAAC;QAL5C,aAAQ,GAAG,KAAK,CAAC;QAMxB,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACvB,IAAI,CAAC,aAAa,GAAG,aAAa,CAAC;QACnC,IAAI,CAAC,aAAa,EAAE,CAAC;IACtB,CAAC;IAED,WAAW,CAAC,QAAiB;QAC5B,IAAI,CAAC,QAAQ,GAAG,QAAQ,CAAC;QACzB,IAAI,CAAC,aAAa,EAAE,CAAC;IACtB,CAAC;IAEQ,UAAU;QAClB,KAAK,CAAC,UAAU,EAAE,CAAC;QACnB,IAAI,CAAC,aAAa,EAAE,CAAC;IACtB,CAAC;IAEO,aAAa;QACpB,IAAI,CAAC,KAAK,EAAE,CAAC;QAEb,MAAM,QAAQ,GAAG,IAAI,CAAC,OAAO,CAAC,YAAY,CAAC,cAAc,EAAE,CAAC;QAC5D,MAAM,KAAK,GAAG,KAAK,CAAC,EAAE,CAAC,oBAAoB,EAAE,6BAA6B,CAAC,CAAC;QAC5E,IAAI,CAAC,QAAQ,CAAC,IAAI,IAAI,CAAC,KAAK,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;QACrC,IAAI,CAAC,QAAQ,CAAC,IAAI,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC;QAE7B,IAAI,IAAI,CAAC,QAAQ,EAAE,CAAC;YACnB,MAAM,MAAM,GAAG,oBAAoB,QAAQ,eAAe,CAAC;YAC3D,IAAI,CAAC,QAAQ,CACZ,IAAI,QAAQ,CAAC,MAAM,GAAG,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,CAAC,EAAE,CAAC,EAAE,IAAI,CAAC,aAAa,EAAE;gBACrE,KAAK,EAAE,CAAC,IAAY,EAAE,EAAE,CAAC,KAAK,CAAC,EAAE,CAAC,mBAAmB,EAAE,IAAI,CAAC;aAC5D,CAAC,CACF,CAAC;QACH,CAAC;aAAM,CAAC;YACP,IAAI,CAAC,QAAQ,CACZ,IAAI,IAAI,CACP,KAAK,CAAC,EAAE,CAAC,mBAAmB,EAAE,kBAAkB,QAAQ,WAAW,CAAC;gBACnE,KAAK,CAAC,EAAE,CAAC,KAAK,EAAE,OAAO,CAAC,kBAAkB,CAAC,CAAC;gBAC5C,KAAK,CAAC,EAAE,CAAC,mBAAmB,EAAE,UAAU,CAAC,EAC1C,CAAC,EACD,CAAC,CACD,CACD,CAAC;QACH,CAAC;IACF,CAAC;CACD","sourcesContent":["import { Box, Markdown, type MarkdownTheme, Spacer, Text } from \"@earendil-works/pi-tui\";\nimport type { CompactionSummaryMessage } from \"../../../core/messages.
|
|
1
|
+
{"version":3,"file":"compaction-summary-message.js","sourceRoot":"","sources":["../../../../src/modes/interactive/components/compaction-summary-message.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,GAAG,EAAE,QAAQ,EAAsB,MAAM,EAAE,IAAI,EAAE,MAAM,wBAAwB,CAAC;AAEzF,OAAO,EAAE,gBAAgB,EAAE,KAAK,EAAE,MAAM,mBAAmB,CAAC;AAC5D,OAAO,EAAE,OAAO,EAAE,MAAM,uBAAuB,CAAC;AAEhD;;;GAGG;AACH,MAAM,OAAO,iCAAkC,SAAQ,GAAG;IAKzD,YAAY,OAAiC,EAAE,aAAa,GAAkB,gBAAgB,EAAE;QAC/F,KAAK,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,KAAK,CAAC,EAAE,CAAC,iBAAiB,EAAE,CAAC,CAAC,CAAC,CAAC;QAL5C,aAAQ,GAAG,KAAK,CAAC;QAMxB,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACvB,IAAI,CAAC,aAAa,GAAG,aAAa,CAAC;QACnC,IAAI,CAAC,aAAa,EAAE,CAAC;IACtB,CAAC;IAED,WAAW,CAAC,QAAiB;QAC5B,IAAI,CAAC,QAAQ,GAAG,QAAQ,CAAC;QACzB,IAAI,CAAC,aAAa,EAAE,CAAC;IACtB,CAAC;IAEQ,UAAU;QAClB,KAAK,CAAC,UAAU,EAAE,CAAC;QACnB,IAAI,CAAC,aAAa,EAAE,CAAC;IACtB,CAAC;IAEO,aAAa;QACpB,IAAI,CAAC,KAAK,EAAE,CAAC;QAEb,MAAM,QAAQ,GAAG,IAAI,CAAC,OAAO,CAAC,YAAY,CAAC,cAAc,EAAE,CAAC;QAC5D,MAAM,KAAK,GAAG,KAAK,CAAC,EAAE,CAAC,oBAAoB,EAAE,6BAA6B,CAAC,CAAC;QAC5E,IAAI,CAAC,QAAQ,CAAC,IAAI,IAAI,CAAC,KAAK,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;QACrC,IAAI,CAAC,QAAQ,CAAC,IAAI,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC;QAE7B,IAAI,IAAI,CAAC,QAAQ,EAAE,CAAC;YACnB,MAAM,MAAM,GAAG,oBAAoB,QAAQ,eAAe,CAAC;YAC3D,IAAI,CAAC,QAAQ,CACZ,IAAI,QAAQ,CAAC,MAAM,GAAG,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,CAAC,EAAE,CAAC,EAAE,IAAI,CAAC,aAAa,EAAE;gBACrE,KAAK,EAAE,CAAC,IAAY,EAAE,EAAE,CAAC,KAAK,CAAC,EAAE,CAAC,mBAAmB,EAAE,IAAI,CAAC;aAC5D,CAAC,CACF,CAAC;QACH,CAAC;aAAM,CAAC;YACP,IAAI,CAAC,QAAQ,CACZ,IAAI,IAAI,CACP,KAAK,CAAC,EAAE,CAAC,mBAAmB,EAAE,kBAAkB,QAAQ,WAAW,CAAC;gBACnE,KAAK,CAAC,EAAE,CAAC,KAAK,EAAE,OAAO,CAAC,kBAAkB,CAAC,CAAC;gBAC5C,KAAK,CAAC,EAAE,CAAC,mBAAmB,EAAE,UAAU,CAAC,EAC1C,CAAC,EACD,CAAC,CACD,CACD,CAAC;QACH,CAAC;IACF,CAAC;CACD","sourcesContent":["import { Box, Markdown, type MarkdownTheme, Spacer, Text } from \"@earendil-works/pi-tui\";\nimport type { CompactionSummaryMessage } from \"../../../core/messages.ts\";\nimport { getMarkdownTheme, theme } from \"../theme/theme.ts\";\nimport { keyText } from \"./keybinding-hints.ts\";\n\n/**\n * Component that renders a compaction message with collapsed/expanded state.\n * Uses same background color as custom messages for visual consistency.\n */\nexport class CompactionSummaryMessageComponent extends Box {\n\tprivate expanded = false;\n\tprivate message: CompactionSummaryMessage;\n\tprivate markdownTheme: MarkdownTheme;\n\n\tconstructor(message: CompactionSummaryMessage, markdownTheme: MarkdownTheme = getMarkdownTheme()) {\n\t\tsuper(1, 1, (t) => theme.bg(\"customMessageBg\", t));\n\t\tthis.message = message;\n\t\tthis.markdownTheme = markdownTheme;\n\t\tthis.updateDisplay();\n\t}\n\n\tsetExpanded(expanded: boolean): void {\n\t\tthis.expanded = expanded;\n\t\tthis.updateDisplay();\n\t}\n\n\toverride invalidate(): void {\n\t\tsuper.invalidate();\n\t\tthis.updateDisplay();\n\t}\n\n\tprivate updateDisplay(): void {\n\t\tthis.clear();\n\n\t\tconst tokenStr = this.message.tokensBefore.toLocaleString();\n\t\tconst label = theme.fg(\"customMessageLabel\", `\\x1b[1m[compaction]\\x1b[22m`);\n\t\tthis.addChild(new Text(label, 0, 0));\n\t\tthis.addChild(new Spacer(1));\n\n\t\tif (this.expanded) {\n\t\t\tconst header = `**Compacted from ${tokenStr} tokens**\\n\\n`;\n\t\t\tthis.addChild(\n\t\t\t\tnew Markdown(header + this.message.summary, 0, 0, this.markdownTheme, {\n\t\t\t\t\tcolor: (text: string) => theme.fg(\"customMessageText\", text),\n\t\t\t\t}),\n\t\t\t);\n\t\t} else {\n\t\t\tthis.addChild(\n\t\t\t\tnew Text(\n\t\t\t\t\ttheme.fg(\"customMessageText\", `Compacted from ${tokenStr} tokens (`) +\n\t\t\t\t\t\ttheme.fg(\"dim\", keyText(\"app.tools.expand\")) +\n\t\t\t\t\t\ttheme.fg(\"customMessageText\", \" Expand)\"),\n\t\t\t\t\t0,\n\t\t\t\t\t0,\n\t\t\t\t),\n\t\t\t);\n\t\t}\n\t}\n}\n"]}
|
|
@@ -2,8 +2,8 @@
|
|
|
2
2
|
* TUI component for managing package resources (enable/disable)
|
|
3
3
|
*/
|
|
4
4
|
import { type Component, Container, type Focusable } from "@earendil-works/pi-tui";
|
|
5
|
-
import type { PathMetadata, ResolvedPaths } from "../../../core/package-manager.
|
|
6
|
-
import type { SettingsManager } from "../../../core/settings-manager.
|
|
5
|
+
import type { PathMetadata, ResolvedPaths } from "../../../core/package-manager.ts";
|
|
6
|
+
import type { SettingsManager } from "../../../core/settings-manager.ts";
|
|
7
7
|
type ResourceType = "extensions" | "skills" | "prompts" | "themes";
|
|
8
8
|
interface ResourceItem {
|
|
9
9
|
path: string;
|