@kortix/ui 0.14.11 → 0.14.13
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/dist/_vendor/kortix-shared.js +521 -7045
- package/dist/_vendor/shared/app-config.d.ts +8 -0
- package/dist/_vendor/shared/artifact-annotations.d.ts +708 -0
- package/dist/_vendor/shared/artifact-comments.d.ts +327 -0
- package/dist/_vendor/shared/index.d.ts +3 -1
- package/dist/_vendor/shared/my-kortix-agent.d.ts +40 -0
- package/dist/_vendor/shared/peer-message-prompt.d.ts +35 -0
- package/dist/_vendor/shared/pixel-mark.d.ts +11 -0
- package/dist/_vendor/shared/prompt-attachments.d.ts +1 -0
- package/dist/_vendor/shared/reminder-prompt.d.ts +8 -2
- package/dist/_vendor/shared/runtime-versions.d.ts +8 -0
- package/dist/artifacts/artifact-frame.d.ts +1 -0
- package/dist/artifacts/artifact-frame.js +18 -5
- package/dist/artifacts/frame-policy.d.ts +1 -1
- package/dist/artifacts/frame-policy.js +10 -5
- package/dist/browser/browser-panel.d.ts +2 -1
- package/dist/browser/browser-panel.js +12 -2
- package/dist/customize/agents/agent-access-text.d.ts +16 -0
- package/dist/customize/agents/agent-access-text.js +54 -0
- package/dist/customize/agents/agent-approval-rules.d.ts +8 -0
- package/dist/customize/agents/agent-approval-rules.js +26 -0
- package/dist/customize/agents/agent-authority-card.js +4 -1
- package/dist/customize/agents/agent-cover-card.d.ts +4 -1
- package/dist/customize/agents/agent-cover-card.js +2 -2
- package/dist/customize/agents/agent-detail-aside.d.ts +1 -2
- package/dist/customize/agents/agent-detail-aside.js +8 -11
- package/dist/customize/agents/agent-drives-section.d.ts +23 -7
- package/dist/customize/agents/agent-drives-section.js +107 -41
- package/dist/customize/agents/agent-instructions.d.ts +11 -0
- package/dist/customize/agents/agent-instructions.js +114 -0
- package/dist/customize/agents/agent-model-view.d.ts +17 -0
- package/dist/customize/agents/agent-model-view.js +67 -0
- package/dist/customize/agents/agent-overview.d.ts +53 -0
- package/dist/customize/agents/agent-overview.js +242 -0
- package/dist/customize/agents/agent-page-chrome.d.ts +128 -0
- package/dist/customize/agents/agent-page-chrome.js +145 -0
- package/dist/customize/agents/agent-page.d.ts +13 -1
- package/dist/customize/agents/agent-page.js +478 -367
- package/dist/customize/agents/agent-pin-button.d.ts +10 -0
- package/dist/customize/agents/agent-pin-button.js +20 -0
- package/dist/customize/agents/agent-policy-sets-section.d.ts +16 -0
- package/dist/customize/agents/agent-policy-sets-section.js +80 -0
- package/dist/customize/agents/agent-policy-sets.js +1 -1
- package/dist/customize/agents/agent-section-rail.d.ts +21 -0
- package/dist/customize/agents/agent-section-rail.js +23 -0
- package/dist/customize/agents/agent-share-control.d.ts +4 -3
- package/dist/customize/agents/agent-share-control.js +15 -16
- package/dist/customize/agents/{agent-people-section.d.ts → agent-share-dialog.d.ts} +3 -1
- package/dist/customize/agents/{agent-people-section.js → agent-share-dialog.js} +21 -21
- package/dist/customize/agents/agent-tabs.d.ts +95 -0
- package/dist/customize/agents/agent-tabs.js +199 -0
- package/dist/customize/agents/agents-page.d.ts +0 -21
- package/dist/customize/agents/agents-page.js +104 -118
- package/dist/customize/agents/connectors-required.d.ts +16 -0
- package/dist/customize/agents/connectors-required.js +19 -0
- package/dist/customize/agents/create-agent-modal.d.ts +19 -0
- package/dist/customize/agents/create-agent-modal.js +94 -0
- package/dist/customize/connectors/agent-access.d.ts +4 -4
- package/dist/customize/connectors/agent-access.js +7 -10
- package/dist/customize/connectors/connector-identity.d.ts +12 -0
- package/dist/customize/connectors/connector-identity.js +15 -2
- package/dist/customize/connectors/connector-routes.js +2 -2
- package/dist/customize/connectors/connectors-page.d.ts +14 -1
- package/dist/customize/connectors/connectors-page.js +101 -32
- package/dist/customize/connectors/detail/app-page.js +1 -1
- package/dist/customize/connectors/detail/connector-agents.js +0 -3
- package/dist/customize/connectors/detail/connector-page.d.ts +1 -1
- package/dist/customize/connectors/detail/connector-page.js +5 -2
- package/dist/customize/connectors/detail/connector-policy-sets.js +1 -1
- package/dist/customize/connectors/detail/connector-triggers.js +2 -2
- package/dist/customize/connectors/use-agent-access.d.ts +7 -5
- package/dist/customize/connectors/use-agent-access.js +2 -6
- package/dist/customize/models/models-page.d.ts +7 -1
- package/dist/customize/models/models-page.js +2 -2
- package/dist/customize/project-settings/project-admin-sections.d.ts +63 -0
- package/dist/customize/project-settings/project-admin-sections.js +80 -0
- package/dist/customize/project-settings/project-settings-page.d.ts +1 -1
- package/dist/customize/project-settings/project-settings-page.js +4 -13
- package/dist/customize/project-settings/project-settings-sections.d.ts +5 -5
- package/dist/customize/project-settings/project-settings-sections.js +6 -20
- package/dist/customize/providers/provider-accordion.js +29 -17
- package/dist/customize/providers/provider-connect.js +1 -1
- package/dist/customize/providers/provider-sheet.d.ts +4 -1
- package/dist/customize/providers/provider-sheet.js +15 -5
- package/dist/customize/secrets/secrets-page.d.ts +5 -1
- package/dist/customize/secrets/secrets-page.js +2 -2
- package/dist/customize/sections/gateway-view.d.ts +10 -2
- package/dist/customize/sections/gateway-view.js +16 -4
- package/dist/customize/sections/llm-provider/chatgpt-subscription-connect.d.ts +12 -5
- package/dist/customize/sections/llm-provider/chatgpt-subscription-connect.js +131 -8
- package/dist/customize/sections/llm-provider/claude-code-step.d.ts +10 -0
- package/dist/customize/sections/llm-provider/claude-code-step.js +32 -0
- package/dist/customize/sections/llm-provider/models-tab.js +5 -1
- package/dist/customize/sections/view/account-secret-resources-panel.d.ts +5 -3
- package/dist/customize/sections/view/account-secret-resources-panel.js +122 -19
- package/dist/customize/sections/view/agent-editor-access-fields.d.ts +1 -1
- package/dist/customize/sections/view/agent-editor-access-fields.js +8 -4
- package/dist/customize/sections/view/agent-editor-basics-fields.d.ts +4 -1
- package/dist/customize/sections/view/agent-editor-basics-fields.js +33 -4
- package/dist/customize/sections/view/agent-editor-catalog.d.ts +2 -2
- package/dist/customize/sections/view/agent-editor-catalog.js +10 -12
- package/dist/customize/sections/view/agent-editor-primitives.d.ts +1 -1
- package/dist/customize/sections/view/agent-editor-primitives.js +4 -4
- package/dist/customize/sections/view/agent-editor.d.ts +37 -26
- package/dist/customize/sections/view/agent-editor.js +19 -19
- package/dist/customize/sections/view/grant-mode-field.d.ts +8 -20
- package/dist/customize/sections/view/grant-mode-field.js +31 -57
- package/dist/customize/sections/view/permission-editor.d.ts +3 -1
- package/dist/customize/sections/view/permission-editor.js +19 -10
- package/dist/customize/sections/view/review-view.d.ts +8 -0
- package/dist/customize/sections/view/review-view.js +12 -1
- package/dist/customize/sections/view/secret-delivery.js +1 -4
- package/dist/customize/sections/view/secrets-view.d.ts +7 -1
- package/dist/customize/sections/view/secrets-view.js +42 -6
- package/dist/customize/settings/rail.js +2 -8
- package/dist/customize/settings/settings-tabs.d.ts +2 -2
- package/dist/customize/settings/settings-tabs.js +17 -19
- package/dist/customize/settings/tabs/experimental-tab.d.ts +3 -0
- package/dist/customize/settings/tabs/experimental-tab.js +6 -1
- package/dist/customize/settings/tabs/sandbox-tab.d.ts +4 -6
- package/dist/customize/settings/tabs/sandbox-tab.js +9 -9
- package/dist/customize/shared/access-list.d.ts +39 -0
- package/dist/customize/shared/access-list.js +62 -0
- package/dist/customize/shared/agent-resource-scope.d.ts +87 -0
- package/dist/customize/shared/agent-resource-scope.js +123 -0
- package/dist/customize/shared/capability-library.d.ts +41 -0
- package/dist/customize/shared/capability-library.js +271 -0
- package/dist/customize/shared/capability-page-shell.d.ts +18 -1
- package/dist/customize/shared/capability-page-shell.js +21 -1
- package/dist/customize/shared/catalog/catalog-space-tabs.d.ts +14 -0
- package/dist/customize/shared/catalog/catalog-space-tabs.js +20 -0
- package/dist/customize/shared/customize-tab-bar.d.ts +13 -0
- package/dist/customize/shared/customize-tab-bar.js +95 -0
- package/dist/customize/shared/entity/entity-modal.d.ts +17 -1
- package/dist/customize/shared/entity/entity-modal.js +10 -9
- package/dist/customize/shared/leave-guard.d.ts +23 -0
- package/dist/customize/shared/leave-guard.js +87 -0
- package/dist/customize/shared/standalone-settings-nav.js +4 -1
- package/dist/customize/shared/tool-rules.d.ts +11 -0
- package/dist/customize/shared/tool-rules.js +29 -0
- package/dist/customize/skills/builtin-skill-modal.d.ts +6 -0
- package/dist/customize/skills/builtin-skill-modal.js +41 -0
- package/dist/customize/skills/skills-page.d.ts +21 -18
- package/dist/customize/skills/skills-page.js +16 -110
- package/dist/customize/triggers/runtime-triggers.d.ts +17 -0
- package/dist/customize/triggers/runtime-triggers.js +57 -0
- package/dist/customize/triggers/schedule/event-trigger-copy.js +2 -2
- package/dist/customize/triggers/schedule/post-to-field.js +2 -2
- package/dist/customize/triggers/schedule/schedule-copy.d.ts +11 -6
- package/dist/customize/triggers/schedule/schedule-copy.js +29 -8
- package/dist/customize/triggers/schedule/schedule-detail-sheet.js +7 -3
- package/dist/customize/triggers/schedule/trigger-composer-logic.d.ts +26 -1
- package/dist/customize/triggers/schedule/trigger-composer-logic.js +64 -3
- package/dist/customize/triggers/schedule/trigger-composer.js +57 -20
- package/dist/customize/triggers/schedule/trigger-edit-logic.js +18 -5
- package/dist/customize/triggers/schedule/trigger-filter.d.ts +10 -0
- package/dist/customize/triggers/schedule/trigger-filter.js +16 -0
- package/dist/customize/triggers/schedule/trigger-runs-panel.js +1 -0
- package/dist/customize/triggers/schedule/trigger-toast.js +2 -1
- package/dist/customize/triggers/schedule/use-trigger-mutations.d.ts +1 -1
- package/dist/customize/triggers/schedule/use-trigger-mutations.js +1 -1
- package/dist/customize/triggers/schedule/when-app.d.ts +15 -0
- package/dist/customize/triggers/schedule/when-app.js +21 -0
- package/dist/customize/triggers/schedule/when-change-request.d.ts +10 -0
- package/dist/customize/triggers/schedule/when-change-request.js +15 -0
- package/dist/customize/triggers/schedule-view.d.ts +17 -3
- package/dist/customize/triggers/schedule-view.js +46 -16
- package/dist/customize/triggers/triggers-page.d.ts +3 -3
- package/dist/customize/triggers/triggers-page.js +2 -2
- package/dist/customize/use-configure-thread.d.ts +8 -2
- package/dist/customize/use-configure-thread.js +30 -18
- package/dist/files/project/components/change-request-detail-dialog.js +2 -3
- package/dist/files/project/components/drive-explorer.js +6 -5
- package/dist/files/project/explorer-source.d.ts +3 -0
- package/dist/files/project/upload-batch.d.ts +3 -3
- package/dist/files/project/upload-batch.js +7 -6
- package/dist/files/runtime/sandbox-explorer-source.js +3 -3
- package/dist/i18n/en.d.ts +1331 -53
- package/dist/i18n/en.js +1423 -145
- package/dist/i18n/ui-catalog/remaining-ui-translation-keys.generated.js +16 -7
- package/dist/internal/auth/auth-primitives.d.ts +1 -3
- package/dist/internal/auth/auth-primitives.js +2 -2
- package/dist/internal/billing/session-cost-format.d.ts +1 -0
- package/dist/internal/billing/session-cost-format.js +11 -0
- package/dist/internal/components/agent-mark.d.ts +12 -1
- package/dist/internal/components/agent-mark.js +34 -11
- package/dist/internal/components/nav-rail.d.ts +22 -0
- package/dist/internal/components/nav-rail.js +16 -0
- package/dist/internal/components/repository-disconnected.js +2 -2
- package/dist/internal/goals/goal-meta.d.ts +15 -1
- package/dist/internal/goals/goal-meta.js +42 -2
- package/dist/internal/hooks/projects/use-agent-config.d.ts +11 -7
- package/dist/internal/hooks/projects/use-agent-config.js +28 -11
- package/dist/internal/hooks/use-slash-focus.d.ts +7 -1
- package/dist/internal/hooks/use-slash-focus.js +9 -3
- package/dist/internal/layout/project-capability-nav.d.ts +24 -0
- package/dist/internal/layout/project-capability-nav.js +86 -0
- package/dist/internal/layout/project-page-header.d.ts +1 -1
- package/dist/internal/layout/project-page-header.js +1 -1
- package/dist/internal/layout/project-settings-nav.d.ts +3 -2
- package/dist/internal/layout/project-settings-nav.js +5 -3
- package/dist/internal/lib/browser-noise/rules/extensions.js +3 -0
- package/dist/internal/lib/browser-noise/rules/old-browsers.js +1 -1
- package/dist/internal/lib/capability-tab-routes.d.ts +34 -3
- package/dist/internal/lib/capability-tab-routes.js +76 -8
- package/dist/internal/lib/manifest-health.d.ts +10 -0
- package/dist/internal/lib/manifest-health.js +20 -0
- package/dist/internal/lib/pixel-mark.d.ts +4 -1
- package/dist/internal/lib/pixel-mark.js +33 -6
- package/dist/internal/lib/project-actions.d.ts +1 -1
- package/dist/internal/lib/project-actions.js +0 -4
- package/dist/internal/lib/provider-branding.js +2 -0
- package/dist/internal/lib/space-scope.d.ts +29 -0
- package/dist/internal/lib/space-scope.js +28 -0
- package/dist/internal/lib/use-project-feature-flags.js +3 -3
- package/dist/internal/lib/web-notifications.d.ts +74 -8
- package/dist/internal/lib/web-notifications.js +243 -117
- package/dist/internal/notifications/notification-rows.d.ts +14 -7
- package/dist/internal/notifications/notification-rows.js +21 -14
- package/dist/internal/notifications/session-toast-cards.d.ts +2 -2
- package/dist/internal/reminders/reminder-format.d.ts +6 -2
- package/dist/internal/reminders/reminder-format.js +7 -1
- package/dist/internal/stores/active-space-store.d.ts +35 -0
- package/dist/internal/stores/active-space-store.js +29 -0
- package/dist/internal/stores/kortix-computer-store.d.ts +2 -1
- package/dist/internal/stores/kortix-computer-store.js +18 -7
- package/dist/internal/stores/pinned-agents-store.d.ts +26 -0
- package/dist/internal/stores/pinned-agents-store.js +20 -0
- package/dist/internal/stores/session-panel-memory-store.js +3 -0
- package/dist/internal/stores/turn-attention-store.d.ts +5 -4
- package/dist/lib/routes.d.ts +16 -1
- package/dist/lib/routes.js +15 -3
- package/dist/markdown/doc-editor/doc-embed.d.ts +31 -0
- package/dist/markdown/doc-editor/doc-embed.js +168 -0
- package/dist/markdown/doc-editor/doc-extensions.d.ts +26 -0
- package/dist/markdown/doc-editor/doc-extensions.js +149 -0
- package/dist/markdown/doc-editor/doc-menus.d.ts +9 -0
- package/dist/markdown/doc-editor/doc-menus.js +56 -0
- package/dist/markdown/doc-editor/markdown.d.ts +12 -0
- package/dist/markdown/doc-editor/markdown.js +140 -0
- package/dist/markdown/genui/components/inline.d.ts +1 -1
- package/dist/primitives/badge.d.ts +1 -1
- package/dist/primitives/button.d.ts +1 -1
- package/dist/primitives/pixel-kortix-mark.d.ts +5 -4
- package/dist/primitives/pixel-kortix-mark.js +5 -15
- package/dist/primitives/tag.d.ts +1 -1
- package/dist/primitives/textarea.js +14 -0
- package/dist/primitives/toast.d.ts +2 -0
- package/dist/primitives/toast.js +4 -2
- package/dist/providers/ui-provider.d.ts +16 -0
- package/dist/session/actions/session-label.d.ts +1 -1
- package/dist/session/actions/session-label.js +3 -3
- package/dist/session/agents/agent-model.d.ts +92 -0
- package/dist/session/agents/agent-model.js +123 -0
- package/dist/session/agents/agent-state-mark.d.ts +10 -0
- package/dist/session/agents/agent-state-mark.js +22 -0
- package/dist/session/agents/agent-strip.d.ts +58 -0
- package/dist/session/agents/agent-strip.js +259 -0
- package/dist/session/agents/held-messages.d.ts +33 -0
- package/dist/session/agents/held-messages.js +50 -0
- package/dist/session/agents/legacy-subagent-chat.d.ts +11 -0
- package/dist/session/agents/legacy-subagent-chat.js +19 -0
- package/dist/session/agents/session-peek.d.ts +20 -0
- package/dist/session/agents/session-peek.js +67 -0
- package/dist/session/agents/session-prompt.d.ts +13 -0
- package/dist/session/agents/session-prompt.js +18 -0
- package/dist/session/agents/steer-session.d.ts +13 -0
- package/dist/session/agents/steer-session.js +29 -0
- package/dist/session/agents/subagent-dialog-content.d.ts +11 -0
- package/dist/session/agents/subagent-dialog-content.js +115 -0
- package/dist/session/agents/subagent-view.d.ts +8 -0
- package/dist/session/agents/subagent-view.js +18 -0
- package/dist/session/agents/tasks-panel.d.ts +13 -0
- package/dist/session/agents/tasks-panel.js +41 -0
- package/dist/session/agents/workflow-run-controls.d.ts +43 -0
- package/dist/session/agents/workflow-run-controls.js +141 -0
- package/dist/session/composer/ComposerCard.d.ts +1 -1
- package/dist/session/composer/ComposerCard.js +3 -3
- package/dist/session/composer/agent-selector.js +13 -19
- package/dist/session/composer/composer-underbar.d.ts +3 -1
- package/dist/session/composer/composer-underbar.js +2 -2
- package/dist/session/composer/composer.d.ts +5 -0
- package/dist/session/composer/composer.js +16 -10
- package/dist/session/composer/editor/composer-editor.js +19 -8
- package/dist/session/composer/editor/ultracode.d.ts +34 -0
- package/dist/session/composer/editor/ultracode.js +127 -0
- package/dist/session/composer/index.d.ts +1 -0
- package/dist/session/composer/index.js +1 -0
- package/dist/session/composer/send-blockers.d.ts +1 -11
- package/dist/session/composer/send-blockers.js +1 -11
- package/dist/session/composer/session-composer-readiness.d.ts +1 -28
- package/dist/session/composer/session-composer-readiness.js +5 -16
- package/dist/session/header/reminder-parts.d.ts +1 -1
- package/dist/session/header/session-site-header.js +6 -3
- package/dist/session/header/subagent-hover-card.d.ts +0 -2
- package/dist/session/header/subagent-hover-card.js +1 -4
- package/dist/session/models/claude-connection-slot.d.ts +11 -0
- package/dist/session/models/claude-connection-slot.js +30 -0
- package/dist/session/models/model-availability.d.ts +3 -1
- package/dist/session/models/model-availability.js +3 -0
- package/dist/session/models/model-selector.js +11 -12
- package/dist/session/models/model-tags.d.ts +9 -0
- package/dist/session/models/model-tags.js +8 -0
- package/dist/session/panel/easy/detail-view.js +7 -0
- package/dist/session/panel/easy/easy-panel.js +1 -1
- package/dist/session/panel/easy/step-icon.js +5 -1
- package/dist/session/panel/mobile-tool-drawer.js +7 -3
- package/dist/session/panel/open-session-quick-view.js +1 -1
- package/dist/session/panel/session-action-panel-column.js +1 -1
- package/dist/session/panel/session-desktop.js +41 -14
- package/dist/session/panel/session-panel-provider.d.ts +1 -1
- package/dist/session/panel/session-panel-provider.js +7 -11
- package/dist/session/prompts/question-prompt.js +3 -1
- package/dist/session/status/session-error-banner.js +4 -1
- package/dist/session/thread/session-chat.js +286 -296
- package/dist/session/thread/session-context-modal.js +29 -10
- package/dist/session/thread/session-context-spawned-sessions.d.ts +13 -0
- package/dist/session/thread/session-context-spawned-sessions.js +44 -0
- package/dist/session/thread/session-context-sub-sessions.js +3 -8
- package/dist/session/thread/transcript.d.ts +3 -0
- package/dist/session/thread/transcript.js +32 -8
- package/dist/session/tool/shared/full-view-action.d.ts +29 -0
- package/dist/session/tool/shared/full-view-action.js +43 -0
- package/dist/session/tool/tool-part-renderer.js +10 -2
- package/dist/session/tool/tools/agent-message-tool.js +2 -2
- package/dist/session/tool/tools/agent-spawn-tool.js +2 -2
- package/dist/session/tool/tools/agent-status-tool.js +2 -2
- package/dist/session/tool/tools/kortix-action-tool.d.ts +2 -0
- package/dist/session/tool/tools/kortix-action-tool.js +148 -0
- package/dist/session/tool/tools/kortix-tool-card.d.ts +83 -0
- package/dist/session/tool/tools/kortix-tool-card.js +186 -0
- package/dist/session/tool/tools/multi-agent-tool-bodies.d.ts +11 -0
- package/dist/session/tool/tools/multi-agent-tool-bodies.js +141 -0
- package/dist/session/tool/tools/multi-agent-tool-data.d.ts +63 -0
- package/dist/session/tool/tools/multi-agent-tool-data.js +118 -0
- package/dist/session/tool/tools/multi-agent-tools.d.ts +9 -0
- package/dist/session/tool/tools/multi-agent-tools.js +38 -0
- package/dist/session/tool/tools/question-tool.js +1 -1
- package/dist/session/tool/tools/register.d.ts +3 -0
- package/dist/session/tool/tools/register.js +3 -0
- package/dist/session/tool/tools/session-spawn-tool.js +2 -2
- package/dist/session/tool/tools/task-tool.d.ts +1 -1
- package/dist/session/tool/tools/task-tool.js +29 -41
- package/dist/session/tool/tools/workflow-progress.d.ts +34 -0
- package/dist/session/tool/tools/workflow-progress.js +186 -0
- package/dist/session/tool/tools/workflow-run.d.ts +128 -0
- package/dist/session/tool/tools/workflow-run.js +251 -0
- package/dist/session/tool/tools/workflow-tool.d.ts +9 -0
- package/dist/session/tool/tools/workflow-tool.js +253 -0
- package/dist/session/turn/notice-batch-group.d.ts +12 -0
- package/dist/session/turn/notice-batch-group.js +17 -0
- package/dist/session/turn/peer-message-row.d.ts +14 -0
- package/dist/session/turn/peer-message-row.js +57 -0
- package/dist/session/turn/subagent-notice-row.d.ts +4 -0
- package/dist/session/turn/subagent-notice-row.js +50 -0
- package/dist/session/turn/subagent-notice.d.ts +58 -0
- package/dist/session/turn/subagent-notice.js +111 -0
- package/dist/session/turn/user-message.d.ts +5 -4
- package/dist/session/turn/user-message.js +31 -10
- package/dist/styles/tokens.css +2 -0
- package/dist/styles.css +1 -1
- package/dist/terminal/session-terminal-connect-bar.js +1 -1
- package/dist/workspace/admin/project-admin-dashboard.d.ts +53 -0
- package/dist/workspace/admin/project-admin-dashboard.js +252 -0
- package/dist/workspace/admin/project-admin-nav.d.ts +20 -0
- package/dist/workspace/admin/project-admin-nav.js +41 -0
- package/dist/workspace/home/welcome-body.js +25 -3
- package/dist/workspace/index.d.ts +6 -2
- package/dist/workspace/index.js +12 -2
- package/dist/workspace/layout/new-session-create.js +3 -3
- package/dist/workspace/layout/project-home.js +3 -3
- package/dist/workspace/memory/memory-labels.js +5 -0
- package/dist/workspace/repository-disconnected.js +2 -2
- package/dist/workspace/sessions/board-dispatch.d.ts +52 -0
- package/dist/workspace/sessions/board-dispatch.js +110 -0
- package/dist/workspace/sessions/board-grouping.d.ts +63 -0
- package/dist/workspace/sessions/board-grouping.js +141 -0
- package/dist/workspace/sessions/board-peek.d.ts +15 -0
- package/dist/workspace/sessions/board-peek.js +54 -0
- package/dist/workspace/sessions/board-state-mark.d.ts +15 -0
- package/dist/workspace/sessions/board-state-mark.js +24 -0
- package/dist/workspace/sessions/project-sessions-view.js +42 -31
- package/dist/workspace/sessions/sessions-board.d.ts +12 -0
- package/dist/workspace/sessions/sessions-board.js +214 -0
- package/dist/workspace/sidebar/footer/project-manifest-issues-alert.d.ts +46 -0
- package/dist/workspace/sidebar/footer/project-manifest-issues-alert.js +85 -0
- package/dist/workspace/sidebar/footer/sidebar-alert.js +1 -1
- package/dist/workspace/sidebar/new-agent-modal-provider.d.ts +12 -0
- package/dist/workspace/sidebar/new-agent-modal-provider.js +19 -0
- package/dist/workspace/sidebar/project-nav-items.d.ts +3 -1
- package/dist/workspace/sidebar/project-nav-items.js +53 -5
- package/dist/workspace/sidebar/project-session-list.js +35 -12
- package/dist/workspace/sidebar/project-sidebar.js +6 -3
- package/dist/workspace/sidebar/session-filter-menu.js +2 -1
- package/dist/workspace/space/space-blocks.d.ts +25 -0
- package/dist/workspace/space/space-blocks.js +124 -0
- package/dist/workspace/space/space-filter-tabs.d.ts +17 -0
- package/dist/workspace/space/space-filter-tabs.js +31 -0
- package/dist/workspace/space/space-page.d.ts +24 -0
- package/dist/workspace/space/space-page.js +157 -0
- package/dist/workspace/space/space-room.d.ts +20 -0
- package/dist/workspace/space/space-room.js +27 -0
- package/dist/workspace/space/space-tab-menu.d.ts +14 -0
- package/dist/workspace/space/space-tab-menu.js +127 -0
- package/dist/workspace/space/space-tab-panels.d.ts +9 -0
- package/dist/workspace/space/space-tab-panels.js +203 -0
- package/dist/workspace/space/space-templates.d.ts +34 -0
- package/dist/workspace/space/space-templates.js +71 -0
- package/dist/workspace/space/use-space-filter.d.ts +10 -0
- package/dist/workspace/space/use-space-filter.js +40 -0
- package/dist/workspace/space/use-space-manifest.d.ts +8 -0
- package/dist/workspace/space/use-space-manifest.js +27 -0
- package/dist/workspace/spaces/space-timeline.js +2 -2
- package/package.json +56 -53
- package/skills/kortix-ui/SKILL.md +1 -1
- package/skills/kortix-ui/references/custom-dashboard.md +10 -4
- package/skills/kortix-ui/references/modules.md +11 -9
- package/dist/_vendor/shared/meta-agent.d.ts +0 -7
- package/dist/customize/agents/agent-grant-pages.d.ts +0 -37
- package/dist/customize/agents/agent-grant-pages.js +0 -226
- package/dist/customize/agents/agent-triggers-section.d.ts +0 -17
- package/dist/customize/agents/agent-triggers-section.js +0 -109
- package/dist/customize/migrate-to-v2/index.d.ts +0 -5
- package/dist/customize/migrate-to-v2/index.js +0 -5
- package/dist/customize/migrate-to-v2/migration-prompt.d.ts +0 -16
- package/dist/customize/migrate-to-v2/migration-prompt.js +0 -59
- package/dist/customize/migrate-to-v2/upgrade-defs.d.ts +0 -30
- package/dist/customize/migrate-to-v2/upgrade-defs.js +0 -43
- package/dist/customize/migrate-to-v2/upgrade-view.d.ts +0 -32
- package/dist/customize/migrate-to-v2/upgrade-view.js +0 -152
- package/dist/customize/migrate-to-v2/use-run-upgrade.d.ts +0 -18
- package/dist/customize/migrate-to-v2/use-run-upgrade.js +0 -16
- package/dist/customize/shared/capability-tabs.d.ts +0 -3
- package/dist/customize/shared/capability-tabs.js +0 -137
- package/dist/customize/skills/skill-scope.d.ts +0 -14
- package/dist/customize/skills/skill-scope.js +0 -18
- package/dist/internal/lib/manifest-version.d.ts +0 -21
- package/dist/internal/lib/manifest-version.js +0 -55
- package/dist/session/composer/hooks/use-composer-escape-stop.d.ts +0 -6
- package/dist/session/composer/hooks/use-composer-escape-stop.js +0 -28
- package/dist/session/thread/sub-session-modal-content.d.ts +0 -8
- package/dist/session/thread/sub-session-modal-content.js +0 -23
- package/dist/session/thread/sub-session-modal.d.ts +0 -2
- package/dist/session/thread/sub-session-modal.js +0 -14
- package/dist/workspace/sidebar/footer/project-manifest-upgrade-alert.d.ts +0 -13
- package/dist/workspace/sidebar/footer/project-manifest-upgrade-alert.js +0 -48
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The `data` of a multi-agent tool result, parsed defensively for its card body.
|
|
3
|
+
*
|
|
4
|
+
* The shapes are in `packages/api-contract/src/multi-agent.ts` (`PeerMessageSendResult`,
|
|
5
|
+
* `ReachableAgents`, `SessionTask`). `@kortix/ui` does not depend on that package, so
|
|
6
|
+
* only the fields a card draws are mirrored here, and every one is checked. A value
|
|
7
|
+
* that does not parse is `null`: the card then draws its own rows, as every platform
|
|
8
|
+
* card does.
|
|
9
|
+
*/
|
|
10
|
+
const PEER_STATUSES = new Set(['delivered', 'held', 'refused', 'denied', 'expired', 'dropped']);
|
|
11
|
+
const BOARD_STATES = new Set(['working', 'needs_input', 'idle', 'completed', 'failed', 'stopped']);
|
|
12
|
+
const TASK_STATUSES = new Set(['pending', 'in_progress', 'completed']);
|
|
13
|
+
/** A card body is a short list; a longer one is the tool's mistake, not a page to render. */
|
|
14
|
+
const MAX_ROWS = 50;
|
|
15
|
+
const isObject = (value) => typeof value === 'object' && value !== null && !Array.isArray(value);
|
|
16
|
+
const text = (value) => (typeof value === 'string' && value.trim() ? value.trim() : null);
|
|
17
|
+
const positiveInt = (value) => typeof value === 'number' && Number.isInteger(value) && value > 0 ? value : null;
|
|
18
|
+
const handle = (value) => text(value)?.replace(/^@/, '') ?? null;
|
|
19
|
+
/** `send_message`: `PeerMessageSendResult`. */
|
|
20
|
+
export function parsePeerSend(data) {
|
|
21
|
+
if (!isObject(data) || !PEER_STATUSES.has(data.status))
|
|
22
|
+
return null;
|
|
23
|
+
const message = isObject(data.message) ? data.message : null;
|
|
24
|
+
const to = isObject(data.to) ? handle(data.to.handle) : null;
|
|
25
|
+
return {
|
|
26
|
+
status: data.status,
|
|
27
|
+
to: to ?? (message ? handle(message.to_handle) : null),
|
|
28
|
+
message: message ? text(message.message) : null,
|
|
29
|
+
summary: message ? text(message.summary) : null,
|
|
30
|
+
note: text(data.note),
|
|
31
|
+
};
|
|
32
|
+
}
|
|
33
|
+
function agentRow(value) {
|
|
34
|
+
if (!isObject(value))
|
|
35
|
+
return null;
|
|
36
|
+
const name = handle(value.handle);
|
|
37
|
+
const sessionId = text(value.session_id);
|
|
38
|
+
if (!name || !sessionId)
|
|
39
|
+
return null;
|
|
40
|
+
return {
|
|
41
|
+
handle: name,
|
|
42
|
+
sessionId,
|
|
43
|
+
title: text(value.title),
|
|
44
|
+
agentName: text(value.agent_name),
|
|
45
|
+
relation: text(value.relation) ?? 'session',
|
|
46
|
+
state: BOARD_STATES.has(value.state) ? value.state : null,
|
|
47
|
+
canReceive: value.can_receive !== false,
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
/** `list_agents`: `ReachableAgents` (the asking session itself is left out). */
|
|
51
|
+
export function parseReachable(data) {
|
|
52
|
+
if (!isObject(data) || !Array.isArray(data.agents))
|
|
53
|
+
return null;
|
|
54
|
+
const rows = [];
|
|
55
|
+
for (const entry of data.agents.slice(0, MAX_ROWS)) {
|
|
56
|
+
const row = agentRow(entry);
|
|
57
|
+
if (row && row.relation !== 'self')
|
|
58
|
+
rows.push(row);
|
|
59
|
+
}
|
|
60
|
+
return rows;
|
|
61
|
+
}
|
|
62
|
+
function taskRow(value) {
|
|
63
|
+
if (!isObject(value))
|
|
64
|
+
return null;
|
|
65
|
+
const seq = positiveInt(value.seq);
|
|
66
|
+
const subject = text(value.subject);
|
|
67
|
+
if (seq === null || !subject || !TASK_STATUSES.has(value.status))
|
|
68
|
+
return null;
|
|
69
|
+
const blockedBy = Array.isArray(value.blocked_by)
|
|
70
|
+
? value.blocked_by.map(positiveInt).filter((n) => n !== null)
|
|
71
|
+
: [];
|
|
72
|
+
return {
|
|
73
|
+
seq,
|
|
74
|
+
subject,
|
|
75
|
+
status: value.status,
|
|
76
|
+
owner: handle(value.owner_handle),
|
|
77
|
+
blockedBy,
|
|
78
|
+
blocked: value.blocked === true,
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
/** `task_*`: one `SessionTask`, or `{ tasks: SessionTask[] }`. */
|
|
82
|
+
export function parseTasks(data) {
|
|
83
|
+
if (!isObject(data))
|
|
84
|
+
return null;
|
|
85
|
+
if (Array.isArray(data.tasks)) {
|
|
86
|
+
return data.tasks
|
|
87
|
+
.slice(0, MAX_ROWS)
|
|
88
|
+
.map(taskRow)
|
|
89
|
+
.filter((row) => row !== null);
|
|
90
|
+
}
|
|
91
|
+
if (isObject(data.task)) {
|
|
92
|
+
const row = taskRow(data.task);
|
|
93
|
+
return row ? [row] : null;
|
|
94
|
+
}
|
|
95
|
+
const row = taskRow(data);
|
|
96
|
+
return row ? [row] : null;
|
|
97
|
+
}
|
|
98
|
+
/** `task_stop`: the child it stopped, or null. */
|
|
99
|
+
export function parseStoppedChild(data) {
|
|
100
|
+
if (!isObject(data) || typeof data.stopped !== 'boolean')
|
|
101
|
+
return null;
|
|
102
|
+
const sessionId = text(data.sessionId);
|
|
103
|
+
if (!sessionId)
|
|
104
|
+
return null;
|
|
105
|
+
return { sessionId, handle: handle(data.handle), title: text(data.title), stopped: data.stopped };
|
|
106
|
+
}
|
|
107
|
+
/**
|
|
108
|
+
* True when a running call's input has the shape of pi's `task_*` tools
|
|
109
|
+
* (apps/kortix-sandbox-agent-server/src/harness/pi/extensions/team-tasks.ts):
|
|
110
|
+
* `task_create { subject, … }`, `task_get { seq }`, `task_update { seq, … }`.
|
|
111
|
+
* The older plugin tools that share these names take neither. pi's
|
|
112
|
+
* `task_list {}` has no input to tell: its output decides once it settles.
|
|
113
|
+
*/
|
|
114
|
+
export function looksLikeTeamTaskInput(input) {
|
|
115
|
+
if (!isObject(input))
|
|
116
|
+
return false;
|
|
117
|
+
return typeof input.subject === 'string' || typeof input.seq === 'number';
|
|
118
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { ToolProps } from '../shared/types.js';
|
|
2
|
+
/**
|
|
3
|
+
* `task_create`, `task_list`, `task_get` and `task_update` name two tools: pi's
|
|
4
|
+
* team task tools (flag `agent_teams`), which answer with a `KortixToolResult`
|
|
5
|
+
* card, and the older plugin tools of a transcript from before pi, which render
|
|
6
|
+
* their own rows. The output decides; a call still running decides by its input
|
|
7
|
+
* (pi's take a `subject`, a task number, a status or an owner).
|
|
8
|
+
*/
|
|
9
|
+
export declare function isTeamTaskCall(call: ToolProps['call']): boolean;
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import { partError, partInput, partRawOutput, partStatus } from '../shared/infrastructure.js';
|
|
4
|
+
import { ToolRegistry } from '../shared/registry.js';
|
|
5
|
+
import { AgentSpawnTool } from './agent-spawn-tool.js';
|
|
6
|
+
import { AgentTaskUpdateTool } from './agent-task-update-tool.js';
|
|
7
|
+
import { KortixActionTool } from './kortix-action-tool.js';
|
|
8
|
+
import { parseKortixToolResult } from './kortix-tool-card.js';
|
|
9
|
+
import { looksLikeTeamTaskInput } from './multi-agent-tool-data.js';
|
|
10
|
+
import { TaskListTool } from './task-list-tool.js';
|
|
11
|
+
/**
|
|
12
|
+
* `task_create`, `task_list`, `task_get` and `task_update` name two tools: pi's
|
|
13
|
+
* team task tools (flag `agent_teams`), which answer with a `KortixToolResult`
|
|
14
|
+
* card, and the older plugin tools of a transcript from before pi, which render
|
|
15
|
+
* their own rows. The output decides; a call still running decides by its input
|
|
16
|
+
* (pi's take a `subject`, a task number, a status or an owner).
|
|
17
|
+
*/
|
|
18
|
+
export function isTeamTaskCall(call) {
|
|
19
|
+
const status = partStatus(call);
|
|
20
|
+
if (status === 'completed' || status === 'error') {
|
|
21
|
+
const raw = status === 'error' ? (partError(call) ?? '') : partRawOutput(call);
|
|
22
|
+
return parseKortixToolResult(raw, call.name) !== null;
|
|
23
|
+
}
|
|
24
|
+
return looksLikeTeamTaskInput(partInput(call));
|
|
25
|
+
}
|
|
26
|
+
function teamTaskTool(legacy) {
|
|
27
|
+
function TeamTaskTool(props) {
|
|
28
|
+
const Component = isTeamTaskCall(props.call) ? KortixActionTool : legacy;
|
|
29
|
+
return _jsx(Component, { ...props });
|
|
30
|
+
}
|
|
31
|
+
TeamTaskTool.displayName = `TeamTaskTool(${legacy.displayName ?? legacy.name})`;
|
|
32
|
+
return TeamTaskTool;
|
|
33
|
+
}
|
|
34
|
+
// Registered after the older tools (`register.ts` imports this file last), so these win their keys.
|
|
35
|
+
ToolRegistry.register('task-create', teamTaskTool(AgentSpawnTool));
|
|
36
|
+
ToolRegistry.register('task-update', teamTaskTool(AgentTaskUpdateTool));
|
|
37
|
+
ToolRegistry.register('task-list', teamTaskTool(TaskListTool));
|
|
38
|
+
ToolRegistry.register('task-get', teamTaskTool(TaskListTool));
|
|
@@ -23,7 +23,7 @@ function AnswerText({ answers, options, }) {
|
|
|
23
23
|
}
|
|
24
24
|
function QuestionAnswerBlock({ question, index, answers, }) {
|
|
25
25
|
const fallback = question.header?.trim() || `Question ${index + 1}`;
|
|
26
|
-
return (_jsxs("div", { className: "space-y-1.5", children: [_jsx("div", { className: cn('text-foreground
|
|
26
|
+
return (_jsxs("div", { className: "space-y-1.5", children: [_jsx("div", { className: cn('text-foreground text-xs text-pretty [&_p]:whitespace-pre-line', MD_FLUSH_CLASSES), children: _jsx(UnifiedMarkdown, { content: question.question || question.header || fallback, trust: "agent" }) }), _jsx(AnswerText, { answers: answers, options: question.options })] }));
|
|
27
27
|
}
|
|
28
28
|
export function QuestionTool({ call, defaultOpen, forceOpen, locked, hasActiveQuestion, }) {
|
|
29
29
|
const tI18nHardcoded = useTranslations('hardcodedUi');
|
|
@@ -16,6 +16,7 @@ import './glob-tool.js';
|
|
|
16
16
|
import './grep-tool.js';
|
|
17
17
|
import './image-gen-tool.js';
|
|
18
18
|
import './image-search-tool.js';
|
|
19
|
+
import './kortix-action-tool.js';
|
|
19
20
|
import './list-tool.js';
|
|
20
21
|
import './memory-search-tool.js';
|
|
21
22
|
import './memory-tool.js';
|
|
@@ -52,4 +53,6 @@ import './triggers-tool.js';
|
|
|
52
53
|
import './video-gen-tool.js';
|
|
53
54
|
import './web-fetch-tool.js';
|
|
54
55
|
import './web-search-tool.js';
|
|
56
|
+
import './workflow-tool.js';
|
|
55
57
|
import './write-tool.js';
|
|
58
|
+
import './multi-agent-tools.js';
|
|
@@ -16,6 +16,7 @@ import './glob-tool.js';
|
|
|
16
16
|
import './grep-tool.js';
|
|
17
17
|
import './image-gen-tool.js';
|
|
18
18
|
import './image-search-tool.js';
|
|
19
|
+
import './kortix-action-tool.js';
|
|
19
20
|
import './list-tool.js';
|
|
20
21
|
import './memory-search-tool.js';
|
|
21
22
|
import './memory-tool.js';
|
|
@@ -52,4 +53,6 @@ import './triggers-tool.js';
|
|
|
52
53
|
import './video-gen-tool.js';
|
|
53
54
|
import './web-fetch-tool.js';
|
|
54
55
|
import './web-search-tool.js';
|
|
56
|
+
import './workflow-tool.js';
|
|
55
57
|
import './write-tool.js';
|
|
58
|
+
import './multi-agent-tools.js';
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
3
|
import { Button } from '../../../primitives/button.js';
|
|
4
|
-
import {
|
|
4
|
+
import { SubagentDialog } from '../../agents/subagent-view.js';
|
|
5
5
|
import { partInput, partStatus } from '../shared/infrastructure.js';
|
|
6
6
|
import { ToolRegistry } from '../shared/registry.js';
|
|
7
7
|
import { SubAgentActivity, SubAgentStatusBanner, useSubAgentThread, } from '../shared/sub-agent.js';
|
|
@@ -49,7 +49,7 @@ export function SessionSpawnTool({ call, forceOpen }) {
|
|
|
49
49
|
if (hasPreview)
|
|
50
50
|
setModalOpen(true);
|
|
51
51
|
};
|
|
52
|
-
return (_jsxs(_Fragment, { children: [_jsxs("div", { "data-component": "tool-trigger", className: cn('group text-muted-foreground/70 flex max-w-full items-center gap-1.5 py-0.5 text-xs transition-colors select-none', '[&>span:first-child>svg]:text-muted-foreground/50 [&>span:first-child>svg]:size-3.5'), children: [_jsx("span", { className: "shrink-0", children: _jsx(Cpu, {}) }), _jsxs("button", { type: "button", disabled: !hasPreview, onClick: openPreview, className: cn('flex min-w-0 flex-1 items-center gap-1.5 overflow-hidden text-left', hasPreview ? 'cursor-pointer' : 'cursor-default'), children: [_jsxs("span", { className: "shrink-0 whitespace-nowrap", children: [tI18nComplete.raw('text2ee7054bf895'), " ", agentName] }), subtitle && (_jsx("span", { className: "text-muted-foreground min-w-0 truncate font-mono text-xs", children: subtitle })), isRunning && (_jsx("span", { className: "ml-auto size-2 shrink-0 animate-pulse rounded-full bg-current opacity-50" })), isCompleted && childCalls.length > 0 && (_jsxs("span", { className: "text-muted-foreground/60 ml-auto shrink-0 font-mono text-xs whitespace-nowrap", children: [childCalls.length, " ", tI18nComplete.raw('textb7595e2a8639')] }))] }), childHref && (_jsx(Button, { asChild: true, variant: "ghost", size: "xs", className: "h-6 shrink-0 gap-1 px-1.5 text-xs", children: _jsxs(Link, { href: childHref, prefetch: true, children: [tI18nComplete.raw('textb205bb47f81a'), _jsx(ExternalLink, { className: "size-3" })] }) }))] }), forceOpen && childCalls.length > 0 && (_jsx(SubAgentActivity, { childSessionId: childSessionId, calls: childCalls })), _jsx(SubAgentStatusBanner, { childSessionId: childSessionId, childThread: childThread }), childSessionId && (_jsx(
|
|
52
|
+
return (_jsxs(_Fragment, { children: [_jsxs("div", { "data-component": "tool-trigger", className: cn('group text-muted-foreground/70 flex max-w-full items-center gap-1.5 py-0.5 text-xs transition-colors select-none', '[&>span:first-child>svg]:text-muted-foreground/50 [&>span:first-child>svg]:size-3.5'), children: [_jsx("span", { className: "shrink-0", children: _jsx(Cpu, {}) }), _jsxs("button", { type: "button", disabled: !hasPreview, onClick: openPreview, className: cn('flex min-w-0 flex-1 items-center gap-1.5 overflow-hidden text-left', hasPreview ? 'cursor-pointer' : 'cursor-default'), children: [_jsxs("span", { className: "shrink-0 whitespace-nowrap", children: [tI18nComplete.raw('text2ee7054bf895'), " ", agentName] }), subtitle && (_jsx("span", { className: "text-muted-foreground min-w-0 truncate font-mono text-xs", children: subtitle })), isRunning && (_jsx("span", { className: "ml-auto size-2 shrink-0 animate-pulse rounded-full bg-current opacity-50" })), isCompleted && childCalls.length > 0 && (_jsxs("span", { className: "text-muted-foreground/60 ml-auto shrink-0 font-mono text-xs whitespace-nowrap", children: [childCalls.length, " ", tI18nComplete.raw('textb7595e2a8639')] }))] }), childHref && (_jsx(Button, { asChild: true, variant: "ghost", size: "xs", className: "h-6 shrink-0 gap-1 px-1.5 text-xs", children: _jsxs(Link, { href: childHref, prefetch: true, children: [tI18nComplete.raw('textb205bb47f81a'), _jsx(ExternalLink, { className: "size-3" })] }) }))] }), forceOpen && childCalls.length > 0 && (_jsx(SubAgentActivity, { childSessionId: childSessionId, calls: childCalls })), _jsx(SubAgentStatusBanner, { childSessionId: childSessionId, childThread: childThread }), childSessionId && (_jsx(SubagentDialog, { open: modalOpen, onOpenChange: setModalOpen, sessionId: childSessionId, title: tI18nComplete('textc65feb0006ea', {
|
|
53
53
|
value0: agentName,
|
|
54
54
|
value1: label ? tI18nComplete('textb581fd88ea24', { value0: label }) : '',
|
|
55
55
|
}) }))] }));
|
|
@@ -2,7 +2,7 @@ import type { ToolProps } from '../shared/types.js';
|
|
|
2
2
|
/**
|
|
3
3
|
* A task call is a disclosure row: what the sub-agent is doing, in place.
|
|
4
4
|
*
|
|
5
|
-
* This row used to be a plain button that opened `
|
|
5
|
+
* This row used to be a plain button that opened `SubagentDialog` on any
|
|
6
6
|
* click. That put the only view of a running sub-agent behind a modal — the
|
|
7
7
|
* reader had to leave the transcript to learn what the agent they just
|
|
8
8
|
* dispatched was up to, and had to close it again to get back — while the
|
|
@@ -1,59 +1,35 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
-
import {
|
|
4
|
-
import { BasicTool, firstMeaningfulLine, partInput, partStatus, partError, } from '../shared/infrastructure.js';
|
|
3
|
+
import { SubagentDialog } from '../../agents/subagent-view.js';
|
|
4
|
+
import { BasicTool, firstMeaningfulLine, partInput, partMetadata, partStatus, partError, } from '../shared/infrastructure.js';
|
|
5
5
|
import { ToolRegistry } from '../shared/registry.js';
|
|
6
6
|
import { SubAgentActivity, SubAgentStatusBanner, useSubAgentThread, } from '../shared/sub-agent.js';
|
|
7
7
|
import { ToolError } from '../tool-error.js';
|
|
8
|
+
import { FullViewAction } from '../shared/full-view-action.js';
|
|
8
9
|
import { useTranslations } from '../../../i18n/index.js';
|
|
9
|
-
import { cn } from '../../../lib/utils.js';
|
|
10
10
|
import { getChildSessionId, getToolInfo } from '../../../internal/session-types/index.js';
|
|
11
11
|
import { KanbanIcon as SquareKanban } from '@phosphor-icons/react';
|
|
12
12
|
import { useCallback, useMemo, useState } from 'react';
|
|
13
13
|
import { subAgentCalls } from '@kortix/sdk';
|
|
14
|
+
import { useSessionStateStore } from '@kortix/sdk/react';
|
|
14
15
|
/**
|
|
15
|
-
*
|
|
16
|
-
*
|
|
17
|
-
*
|
|
18
|
-
* was wrong twice over. It sat at the body's left margin — the chain's icon
|
|
19
|
-
* gutter — so it read as one more step in the sub-agent's list rather than as
|
|
20
|
-
* an action on the agent. And it was reachable only by expanding the row, which
|
|
21
|
-
* is backwards for a sub-agent that has not produced a step yet: that is the
|
|
22
|
-
* one moment the full view is the ONLY thing there is to look at.
|
|
23
|
-
*
|
|
24
|
-
* A `span role="button"`, not a `<button>`. This node renders inside the
|
|
25
|
-
* disclosure's trigger, and `DisclosureTrigger` clones that trigger into its own
|
|
26
|
-
* `role="button"` element — a button nested in a button is invalid HTML. The
|
|
27
|
-
* subtitle link in `InlineTriggerTitle` is the same shape for the same reason.
|
|
28
|
-
* Both activation paths `stopPropagation` so reaching the full view does not
|
|
29
|
-
* also toggle the row underneath it.
|
|
30
|
-
*
|
|
31
|
-
* Visible label "Full view", accessible name "Open full view". The row already
|
|
32
|
-
* carries a title plus a live subtitle that has to truncate, so the right edge
|
|
33
|
-
* gets the two words that matter; the longer name rides on `aria-label` and
|
|
34
|
-
* `title`, and it CONTAINS the visible text, so WCAG 2.5.3 (Label in Name)
|
|
35
|
-
* holds.
|
|
36
|
-
*
|
|
37
|
-
* Always visible, never hover-revealed: a hover-only affordance does not exist
|
|
38
|
-
* on touch, and this is the only route to a running sub-agent's full transcript.
|
|
16
|
+
* Whether a background hand-off's child still works. The child's status is
|
|
17
|
+
* known while this tab streams it; without it, a child whose last reply has
|
|
18
|
+
* completed is not working, and any other child is taken as still at work.
|
|
39
19
|
*/
|
|
40
|
-
function
|
|
41
|
-
const
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
e.preventDefault();
|
|
49
|
-
e.stopPropagation();
|
|
50
|
-
onOpen();
|
|
51
|
-
}, className: cn('text-muted-foreground/60 hover:text-foreground', 'flex cursor-pointer items-center gap-1 whitespace-nowrap', 'underline-offset-2 transition-colors hover:underline'), children: tI18nComplete.raw('textdcc839a4015c') }));
|
|
20
|
+
function useBackgroundWorking(childSessionId, childThread) {
|
|
21
|
+
const childStatus = useSessionStateStore((s) => (childSessionId ? s.sessionStatus[childSessionId] : undefined));
|
|
22
|
+
if (childStatus?.type === 'busy' || childStatus?.type === 'retry')
|
|
23
|
+
return true;
|
|
24
|
+
if (childStatus?.type === 'idle')
|
|
25
|
+
return false;
|
|
26
|
+
const last = childThread?.messages.findLast((m) => m.role === 'assistant');
|
|
27
|
+
return !last || last.completed_at === null;
|
|
52
28
|
}
|
|
53
29
|
/**
|
|
54
30
|
* A task call is a disclosure row: what the sub-agent is doing, in place.
|
|
55
31
|
*
|
|
56
|
-
* This row used to be a plain button that opened `
|
|
32
|
+
* This row used to be a plain button that opened `SubagentDialog` on any
|
|
57
33
|
* click. That put the only view of a running sub-agent behind a modal — the
|
|
58
34
|
* reader had to leave the transcript to learn what the agent they just
|
|
59
35
|
* dispatched was up to, and had to close it again to get back — while the
|
|
@@ -74,6 +50,7 @@ function FullViewAction({ onOpen }) {
|
|
|
74
50
|
*/
|
|
75
51
|
export function TaskTool({ call, defaultOpen, forceOpen, locked }) {
|
|
76
52
|
const tI18nComplete = useTranslations('hardcodedUi.i18nComplete');
|
|
53
|
+
const tAgent = useTranslations('tools.agent');
|
|
77
54
|
const input = partInput(call);
|
|
78
55
|
const status = partStatus(call);
|
|
79
56
|
const subagentType = input.subagent_type || 'general';
|
|
@@ -88,6 +65,10 @@ export function TaskTool({ call, defaultOpen, forceOpen, locked }) {
|
|
|
88
65
|
const childSessionId = useMemo(() => getChildSessionId(call), [call]);
|
|
89
66
|
const childThread = useSubAgentThread(childSessionId);
|
|
90
67
|
const childCalls = useMemo(() => subAgentCalls(childThread), [childThread]);
|
|
68
|
+
// `agent(…, { background: true })` returns as soon as the child exists. The call is
|
|
69
|
+
// over; the work goes on in the child's own session, and the row says so.
|
|
70
|
+
const background = partMetadata(call).background === true;
|
|
71
|
+
const backgroundWorking = useBackgroundWorking(background ? childSessionId : undefined, childThread);
|
|
91
72
|
const [modalOpen, setModalOpen] = useState(false);
|
|
92
73
|
const openModal = useCallback(() => setModalOpen(true), []);
|
|
93
74
|
const isRunning = status === 'running' || status === 'pending';
|
|
@@ -105,6 +86,11 @@ export function TaskTool({ call, defaultOpen, forceOpen, locked }) {
|
|
|
105
86
|
return info.title + (info.subtitle ? ` · ${info.subtitle}` : '');
|
|
106
87
|
}, [childCalls]);
|
|
107
88
|
const subtitle = isRunning ? (lastActivity ?? description) : description || undefined;
|
|
89
|
+
const backgroundLabel = background && childSessionId && !errorText
|
|
90
|
+
? backgroundWorking
|
|
91
|
+
? tAgent('backgroundWorking')
|
|
92
|
+
: tAgent('backgroundSession')
|
|
93
|
+
: undefined;
|
|
108
94
|
/**
|
|
109
95
|
* Whether this row can show the sub-agent's work WITHOUT leaving the
|
|
110
96
|
* transcript.
|
|
@@ -121,6 +107,7 @@ export function TaskTool({ call, defaultOpen, forceOpen, locked }) {
|
|
|
121
107
|
return (_jsxs(_Fragment, { children: [_jsx(BasicTool, { icon: _jsx(SquareKanban, { className: "size-3.5 shrink-0" }), trigger: {
|
|
122
108
|
title: tI18nComplete('text9471197a871a', { value0: subagentType }),
|
|
123
109
|
subtitle,
|
|
110
|
+
args: backgroundLabel ? [backgroundLabel] : undefined,
|
|
124
111
|
}, defaultOpen: defaultOpen, forceOpen: forceOpen, locked: locked, badge: isCompleted && childCalls.length > 0 ? `${childCalls.length} steps` : undefined, triggerAction: childSessionId ? _jsx(FullViewAction, { onOpen: openModal }) : undefined,
|
|
125
112
|
// A click on an agent row always leads somewhere. With steps in hand
|
|
126
113
|
// the row is a disclosure and opens them in place; with the child
|
|
@@ -132,9 +119,10 @@ export function TaskTool({ call, defaultOpen, forceOpen, locked }) {
|
|
|
132
119
|
// failure reason, which `ClickableToolRow` would drop, and the reason
|
|
133
120
|
// must stay readable on the row exactly as the generic error card
|
|
134
121
|
// showed it (KRTX-1746). The child thread stays one `View` away.
|
|
135
|
-
onClick: childSessionId && !hasInlineSteps && !errorText ? openModal : undefined, children: (errorText || hasInlineSteps) ? (_jsxs(_Fragment, { children: [errorText ? _jsx(ToolError, { error: errorText, toolName: call.name }) : undefined, hasInlineSteps ? (_jsx(SubAgentActivity, { childSessionId: childSessionId, calls: childCalls })) : undefined] })) : undefined }), _jsx(SubAgentStatusBanner, { childSessionId: childSessionId, childThread: childThread }), childSessionId && (_jsx(
|
|
122
|
+
onClick: childSessionId && !hasInlineSteps && !errorText ? openModal : undefined, children: (errorText || hasInlineSteps) ? (_jsxs(_Fragment, { children: [errorText ? _jsx(ToolError, { error: errorText, toolName: call.name }) : undefined, hasInlineSteps ? (_jsx(SubAgentActivity, { childSessionId: childSessionId, calls: childCalls })) : undefined] })) : undefined }), _jsx(SubAgentStatusBanner, { childSessionId: childSessionId, childThread: childThread }), childSessionId && (_jsx(SubagentDialog, { open: modalOpen, onOpenChange: setModalOpen, sessionId: childSessionId, title: tI18nComplete('text7decbfdbacee', {
|
|
136
123
|
value0: subagentType,
|
|
137
124
|
value1: description ? tI18nComplete('textb581fd88ea24', { value0: description }) : '',
|
|
138
125
|
}) }))] }));
|
|
139
126
|
}
|
|
127
|
+
// pi's `agent` (`task` is its deprecated alias) reaches this row through its kind (`toolKind`).
|
|
140
128
|
ToolRegistry.register('task', TaskTool);
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { type WorkflowAgentStatus, type WorkflowPhaseStatus, type WorkflowRun, type WorkflowRunAgent } from './workflow-run.js';
|
|
2
|
+
/**
|
|
3
|
+
* One status mark for a run, a phase or an agent: a spinner while it works, else the
|
|
4
|
+
* outcome. The glyph is decoration; the word beside it is for a screen reader.
|
|
5
|
+
*/
|
|
6
|
+
export declare function StateMark({ status, label, }: {
|
|
7
|
+
status: WorkflowPhaseStatus | WorkflowAgentStatus;
|
|
8
|
+
label: string;
|
|
9
|
+
}): import("react").JSX.Element;
|
|
10
|
+
/** The script's newest `log()` lines, muted, above the phases. */
|
|
11
|
+
export declare function WorkflowLogs({ logs }: {
|
|
12
|
+
logs: string[];
|
|
13
|
+
}): import("react").JSX.Element | null;
|
|
14
|
+
export interface AgentStopState {
|
|
15
|
+
/** Whether a row's agent can be stopped from here at all (a project, a live run). */
|
|
16
|
+
enabled: boolean;
|
|
17
|
+
/** Session ids whose stop is in flight. */
|
|
18
|
+
pending: ReadonlySet<string>;
|
|
19
|
+
stop: (agent: WorkflowRunAgent) => void;
|
|
20
|
+
/** Claude Code's `r`: stop a running agent and start it again with the same prompt. Absent: no Restart. */
|
|
21
|
+
restart?: {
|
|
22
|
+
/** The agent session whose restart is in flight. */
|
|
23
|
+
pending?: string;
|
|
24
|
+
run: (agent: WorkflowRunAgent) => void;
|
|
25
|
+
};
|
|
26
|
+
}
|
|
27
|
+
export declare function WorkflowProgress({ run, live, now, onOpen, stop, }: {
|
|
28
|
+
run: WorkflowRun;
|
|
29
|
+
/** The run is under way in this call: elapsed time ticks and running rows can be stopped. */
|
|
30
|
+
live: boolean;
|
|
31
|
+
now: number;
|
|
32
|
+
onOpen: (agent: WorkflowRunAgent) => void;
|
|
33
|
+
stop: AgentStopState;
|
|
34
|
+
}): import("react").JSX.Element | null;
|
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { Button } from '../../../primitives/button.js';
|
|
4
|
+
import { CountBadge } from '../../../primitives/count-badge.js';
|
|
5
|
+
import { Hint } from '../../../primitives/hint.js';
|
|
6
|
+
import Loading from '../../../primitives/loading.js';
|
|
7
|
+
import { Tabs, TabsListCompact, TabsTriggerCompact } from '../../../primitives/tabs.js';
|
|
8
|
+
import { useToolIndent } from '../shared/infrastructure.js';
|
|
9
|
+
import { OutputBlock } from '../shared/output-block.js';
|
|
10
|
+
import { ToolResultCard } from '../shared/result-card.js';
|
|
11
|
+
import { useTranslations } from '../../../i18n/index.js';
|
|
12
|
+
import { cn } from '../../../lib/utils.js';
|
|
13
|
+
import { ArrowClockwiseIcon, CaretRightIcon, CheckIcon, CircleDashedIcon, MinusIcon, SquareIcon, WarningIcon, } from '@phosphor-icons/react';
|
|
14
|
+
import { useCallback, useId, useMemo, useState } from 'react';
|
|
15
|
+
import { AGENT_FILTERS, agentMatches, countAgents, elapsedMs, formatElapsed, groupAgents, structuredSummary, } from './workflow-run.js';
|
|
16
|
+
/**
|
|
17
|
+
* The body of a workflow card: Claude Code's `/workflows` progress view, in the chat.
|
|
18
|
+
*
|
|
19
|
+
* The script's newest `log()` lines, then one group per phase with its agent count
|
|
20
|
+
* and state (a phase the script declared but has not reached is listed, greyed), and
|
|
21
|
+
* under each phase one dense row per agent. More than {@link FILTER_FROM} agents get a
|
|
22
|
+
* status filter (`f` cycles it, as in Claude Code); ↑ and ↓ move between rows, Enter
|
|
23
|
+
* opens the focused agent's session. A phase longer than {@link CAP_FROM} rows shows its
|
|
24
|
+
* first {@link GROUP_CAP} and a "Show all" button, inside one scroll container for the run.
|
|
25
|
+
*
|
|
26
|
+
* Nothing moves while the run updates: rows append in start order, every number is
|
|
27
|
+
* `tabular-nums`, the elapsed column and the Stop slot keep a fixed width.
|
|
28
|
+
*/
|
|
29
|
+
/** More agents than this get the status filter. */
|
|
30
|
+
const FILTER_FROM = 8;
|
|
31
|
+
/** A group with more rows than this (Claude Code's "Large workflow" line) is capped… */
|
|
32
|
+
const CAP_FROM = 25;
|
|
33
|
+
/** …to this many rows and a "Show all" button. */
|
|
34
|
+
const GROUP_CAP = 20;
|
|
35
|
+
/**
|
|
36
|
+
* One status mark for a run, a phase or an agent: a spinner while it works, else the
|
|
37
|
+
* outcome. The glyph is decoration; the word beside it is for a screen reader.
|
|
38
|
+
*/
|
|
39
|
+
export function StateMark({ status, label, }) {
|
|
40
|
+
return (_jsxs(_Fragment, { children: [status === 'starting' || status === 'running' ? (
|
|
41
|
+
// `Loading` paints itself `text-background` inside a button; an agent row is one.
|
|
42
|
+
_jsx(Loading, { className: "text-muted-foreground in-[button]:text-muted-foreground size-3 shrink-0" })) : status === 'done' ? (_jsx(CheckIcon, { "aria-hidden": true, className: "text-kortix-green size-3 shrink-0" })) : status === 'failed' ? (_jsx(WarningIcon, { weight: "fill", "aria-hidden": true, className: "text-kortix-red size-3 shrink-0" })) : status === 'pending' ? (_jsx(CircleDashedIcon, { "aria-hidden": true, className: "text-muted-foreground size-3 shrink-0" })) : (_jsx(MinusIcon, { "aria-hidden": true, className: "text-muted-foreground size-3 shrink-0" })), _jsx("span", { className: "sr-only", children: label })] }));
|
|
43
|
+
}
|
|
44
|
+
/** The script's newest `log()` lines, muted, above the phases. */
|
|
45
|
+
export function WorkflowLogs({ logs }) {
|
|
46
|
+
const t = useTranslations('tools.workflow');
|
|
47
|
+
const indent = useToolIndent();
|
|
48
|
+
if (logs.length === 0)
|
|
49
|
+
return null;
|
|
50
|
+
return (_jsx("ol", { "aria-label": t('logLabel'), className: cn('text-muted-foreground space-y-0.5 text-xs text-pretty wrap-anywhere', indent && 'mt-1.5', indent), children: logs.map((line, index) => (
|
|
51
|
+
// Lines repeat and carry no id; the list is the newest 5, replaced whole.
|
|
52
|
+
_jsx("li", { children: line }, `${index}:${line}`))) }));
|
|
53
|
+
}
|
|
54
|
+
export function WorkflowProgress({ run, live, now, onOpen, stop, }) {
|
|
55
|
+
const t = useTranslations('tools.workflow');
|
|
56
|
+
const [filter, setFilter] = useState('all');
|
|
57
|
+
const [collapsed, setCollapsed] = useState(() => new Set());
|
|
58
|
+
const [uncapped, setUncapped] = useState(() => new Set());
|
|
59
|
+
const groups = useMemo(() => groupAgents(run), [run]);
|
|
60
|
+
const counts = useMemo(() => countAgents(run.agents), [run.agents]);
|
|
61
|
+
const showFilter = run.agents.length > FILTER_FROM;
|
|
62
|
+
const active = showFilter ? filter : 'all';
|
|
63
|
+
// The elapsed column exists only when some agent reports when it started.
|
|
64
|
+
const timed = run.agents.some((agent) => agent.startedAt !== undefined);
|
|
65
|
+
const toggle = useCallback((setter, key) => setter((previous) => {
|
|
66
|
+
const next = new Set(previous);
|
|
67
|
+
if (next.has(key))
|
|
68
|
+
next.delete(key);
|
|
69
|
+
else
|
|
70
|
+
next.add(key);
|
|
71
|
+
return next;
|
|
72
|
+
}), []);
|
|
73
|
+
const cycleFilter = useCallback((step) => {
|
|
74
|
+
setFilter((current) => {
|
|
75
|
+
const index = AGENT_FILTERS.indexOf(current);
|
|
76
|
+
return AGENT_FILTERS[(index + step + AGENT_FILTERS.length) % AGENT_FILTERS.length];
|
|
77
|
+
});
|
|
78
|
+
}, []);
|
|
79
|
+
const onKeyDown = useCallback((event) => {
|
|
80
|
+
if (event.defaultPrevented || event.altKey || event.ctrlKey || event.metaKey)
|
|
81
|
+
return;
|
|
82
|
+
const target = event.target;
|
|
83
|
+
if (target.closest('input, textarea, [contenteditable="true"]'))
|
|
84
|
+
return;
|
|
85
|
+
if (event.key === 'ArrowDown' || event.key === 'ArrowUp') {
|
|
86
|
+
const rows = Array.from(event.currentTarget.querySelectorAll('[data-workflow-row]'));
|
|
87
|
+
const index = rows.indexOf(target.closest('[data-workflow-row]'));
|
|
88
|
+
if (index === -1)
|
|
89
|
+
return;
|
|
90
|
+
const next = rows[index + (event.key === 'ArrowDown' ? 1 : -1)];
|
|
91
|
+
if (!next)
|
|
92
|
+
return;
|
|
93
|
+
event.preventDefault();
|
|
94
|
+
next.focus();
|
|
95
|
+
}
|
|
96
|
+
else if ((event.key === 'f' || event.key === 'F') && showFilter) {
|
|
97
|
+
event.preventDefault();
|
|
98
|
+
cycleFilter(event.shiftKey ? -1 : 1);
|
|
99
|
+
}
|
|
100
|
+
}, [showFilter, cycleFilter]);
|
|
101
|
+
const visible = groups
|
|
102
|
+
.map((group) => ({ group, agents: group.agents.filter((agent) => agentMatches(agent, active)) }))
|
|
103
|
+
// Under a filter, a group with no matching agent (a pending phase included) is left out.
|
|
104
|
+
.filter(({ agents }) => active === 'all' || agents.length > 0);
|
|
105
|
+
const nothing = active !== 'all' && visible.every(({ agents }) => agents.length === 0);
|
|
106
|
+
if (groups.length === 0)
|
|
107
|
+
return null;
|
|
108
|
+
return (_jsxs("div", { role: "group", "aria-label": t('agentsLabel'), onKeyDown: onKeyDown, children: [showFilter && (_jsx(FilterBar, { filter: active, counts: counts, onChange: setFilter })), _jsx(ToolResultCard, { bodyClassName: "py-0.5", children: nothing ? (_jsx("p", { className: "text-muted-foreground px-2 py-1 text-xs", children: t(`filterEmpty.${active}`) })) : (_jsx("ul", { children: visible.map(({ group, agents }) => {
|
|
109
|
+
const key = group.phase?.title ?? '';
|
|
110
|
+
const rows = (_jsx(AgentRows, { agents: agents, capped: agents.length > CAP_FROM && !uncapped.has(key), onShowAll: () => toggle(setUncapped, key), live: live, now: now, timed: timed, onOpen: onOpen, stop: stop }));
|
|
111
|
+
if (!group.phase)
|
|
112
|
+
return _jsx("li", { children: rows }, "loose");
|
|
113
|
+
const open = !collapsed.has(key);
|
|
114
|
+
return (_jsxs("li", { children: [_jsx(PhaseHeader, { group: group, shown: agents.length, filtered: active !== 'all', open: open, onToggle: () => toggle(setCollapsed, key) }), open && agents.length > 0 && _jsx("div", { className: "pl-5", children: rows })] }, `phase:${key}`));
|
|
115
|
+
}) })) })] }));
|
|
116
|
+
}
|
|
117
|
+
function FilterBar({ filter, counts, onChange, }) {
|
|
118
|
+
const t = useTranslations('tools.workflow');
|
|
119
|
+
const indent = useToolIndent();
|
|
120
|
+
const tally = {
|
|
121
|
+
all: counts.total,
|
|
122
|
+
running: counts.running,
|
|
123
|
+
failed: counts.failed,
|
|
124
|
+
done: counts.done,
|
|
125
|
+
};
|
|
126
|
+
return (_jsx(Tabs, { value: filter, onValueChange: (value) => onChange(value), className: cn(indent && 'mt-1.5', indent), children: _jsx(TabsListCompact, { "aria-label": t('filter.label'), children: AGENT_FILTERS.map((value) => (_jsxs(TabsTriggerCompact, { value: value, className: "gap-1.5", children: [t(`filter.${value}`), _jsx(CountBadge, { count: tally[value] })] }, value))) }) }));
|
|
127
|
+
}
|
|
128
|
+
function PhaseHeader({ group, shown, filtered, open, onToggle, }) {
|
|
129
|
+
const t = useTranslations('tools.workflow');
|
|
130
|
+
const phase = group.phase;
|
|
131
|
+
const pending = phase.status === 'pending';
|
|
132
|
+
const tally = countAgents(group.agents);
|
|
133
|
+
const detail = pending
|
|
134
|
+
? t('status.pending')
|
|
135
|
+
: group.agents.length === 0
|
|
136
|
+
? undefined
|
|
137
|
+
: filtered
|
|
138
|
+
? t('agents', { count: shown })
|
|
139
|
+
: [
|
|
140
|
+
phase.status === 'running' ? t('progress', { done: tally.done, total: tally.total }) : t('agents', { count: tally.total }),
|
|
141
|
+
tally.failed > 0 ? t('failedSuffix', { count: tally.failed }) : undefined,
|
|
142
|
+
]
|
|
143
|
+
.filter(Boolean)
|
|
144
|
+
.join(' · ');
|
|
145
|
+
const body = (_jsxs(_Fragment, { children: [_jsx(StateMark, { status: phase.status, label: t(`status.${phase.status}`) }), _jsx("span", { className: cn('min-w-0 truncate font-medium', pending ? 'text-muted-foreground' : 'text-foreground'), title: phase.title, children: phase.title }), detail && _jsx("span", { className: "text-muted-foreground shrink-0 tabular-nums", children: detail })] }));
|
|
146
|
+
const rowClass = 'flex w-full min-w-0 items-center gap-2 rounded-sm px-2 py-1 text-left text-xs';
|
|
147
|
+
// A phase with no rows has nothing to fold: a plain line, not a control.
|
|
148
|
+
if (group.agents.length === 0)
|
|
149
|
+
return _jsx("div", { className: rowClass, children: body });
|
|
150
|
+
return (_jsxs("button", { type: "button", "data-workflow-row": true, "aria-expanded": open, onClick: onToggle, className: cn(rowClass, 'hover:bg-muted/40 cursor-pointer'), children: [body, _jsx(CaretRightIcon, { "aria-hidden": true, className: cn('text-muted-foreground ml-auto size-3 shrink-0 transition-transform motion-reduce:transition-none', open && 'rotate-90') })] }));
|
|
151
|
+
}
|
|
152
|
+
function AgentRows({ agents, capped, onShowAll, ...row }) {
|
|
153
|
+
const t = useTranslations('tools.workflow');
|
|
154
|
+
const shown = capped ? agents.slice(0, GROUP_CAP) : agents;
|
|
155
|
+
return (_jsxs("ul", { children: [shown.map((agent) => (_jsx(AgentRow, { agent: agent, ...row }, agent.id))), capped && (_jsx("li", { children: _jsx("button", { type: "button", "data-workflow-row": true, onClick: onShowAll, className: "text-muted-foreground hover:text-foreground w-full cursor-pointer rounded-sm px-2 py-1 text-left text-xs", children: t('showAll', { count: agents.length }) }) }))] }));
|
|
156
|
+
}
|
|
157
|
+
/** `kortix/claude-sonnet-4.6` reads `claude-sonnet-4.6`; the row's title keeps the whole id. */
|
|
158
|
+
function shortModel(model) {
|
|
159
|
+
return model.slice(model.lastIndexOf('/') + 1) || model;
|
|
160
|
+
}
|
|
161
|
+
function AgentRow({ agent, live, now, timed, onOpen, stop, }) {
|
|
162
|
+
const t = useTranslations('tools.workflow');
|
|
163
|
+
const tm = useTranslations('multiAgent.workflow');
|
|
164
|
+
const describedBy = useId();
|
|
165
|
+
const [jsonOpen, setJsonOpen] = useState(false);
|
|
166
|
+
const statusLabel = t(`status.${agent.status}`);
|
|
167
|
+
const working = agent.status === 'starting' || agent.status === 'running';
|
|
168
|
+
const structured = agent.structured && agent.summary ? structuredSummary(agent.summary) : undefined;
|
|
169
|
+
const meta = [
|
|
170
|
+
agent.agent,
|
|
171
|
+
agent.model ? shortModel(agent.model) : undefined,
|
|
172
|
+
agent.attempt && agent.attempt > 1 ? t('retry', { count: agent.attempt - 1 }) : undefined,
|
|
173
|
+
agent.cached ? t('cached') : undefined,
|
|
174
|
+
].filter((part) => !!part);
|
|
175
|
+
const elapsed = elapsedMs(agent, live && working, now);
|
|
176
|
+
const summary = agent.summary ?? (agent.status === 'running' ? '' : statusLabel);
|
|
177
|
+
const head = (_jsxs(_Fragment, { children: [_jsx(StateMark, { status: agent.status, label: statusLabel }), _jsx("span", { className: "text-foreground min-w-0 shrink truncate", title: agent.label, children: agent.label }), meta.length > 0 && (_jsx("span", { className: "text-muted-foreground max-w-[40%] shrink-0 truncate", title: agent.model ? [agent.agent, agent.model].filter(Boolean).join(' · ') : undefined, children: meta.join(' · ') })), _jsx("span", { id: describedBy, className: "text-muted-foreground min-w-0 flex-1 truncate", title: structured ? undefined : agent.summary, children: structured ? _jsx("span", { className: "sr-only", children: statusLabel }) : summary })] }));
|
|
178
|
+
const headClass = 'flex min-w-0 flex-1 items-center gap-2 rounded-sm px-2 py-1 text-left';
|
|
179
|
+
const canStop = stop.enabled && live && working && !!agent.sessionId;
|
|
180
|
+
const stopping = !!agent.sessionId && stop.pending.has(agent.sessionId);
|
|
181
|
+
return (_jsxs("li", { children: [_jsxs("div", { className: cn('flex min-w-0 items-center gap-1 rounded-sm text-xs', agent.sessionId && 'hover:bg-muted/40'), children: [agent.sessionId ? (_jsx("button", { type: "button", "data-workflow-row": true, "aria-label": t('openAgent', { label: agent.label }), "aria-describedby": describedBy, onClick: () => onOpen(agent), className: cn(headClass, 'cursor-pointer'), children: head })) : (_jsx("div", { className: headClass, children: head })), structured && (_jsxs("button", { type: "button", "data-workflow-row": true, "aria-expanded": jsonOpen, onClick: () => setJsonOpen((open) => !open), className: "text-muted-foreground hover:text-foreground flex shrink-0 cursor-pointer items-center gap-1 rounded-sm px-1 py-1 tabular-nums", children: [structured.kind === 'object'
|
|
182
|
+
? t('jsonKeys', { count: structured.keys })
|
|
183
|
+
: structured.kind === 'array'
|
|
184
|
+
? t('jsonItems', { count: structured.items })
|
|
185
|
+
: t('json'), _jsx(CaretRightIcon, { "aria-hidden": true, className: cn('size-3 shrink-0 transition-transform motion-reduce:transition-none', jsonOpen && 'rotate-90') })] })), timed && (_jsx("span", { className: "text-muted-foreground min-w-12 shrink-0 pr-1 text-right tabular-nums", children: elapsed !== undefined ? formatElapsed(elapsed) : '' })), live && stop.enabled && stop.restart && (_jsx("span", { className: "flex size-6 shrink-0 items-center justify-center", children: stop.restart.pending && stop.restart.pending === agent.sessionId ? (_jsx(Loading, { className: "text-muted-foreground size-3" })) : canStop && !stopping ? (_jsx(Hint, { label: tm('restartHint'), side: "top", sideOffset: 4, alignOffset: 0, children: _jsx(Button, { type: "button", variant: "ghost", size: "icon-xs", "aria-label": tm('restartAgent', { label: agent.label }), onClick: () => stop.restart?.run(agent), className: "text-muted-foreground hover:text-foreground", children: _jsx(ArrowClockwiseIcon, { className: "size-3" }) }) })) : null })), live && stop.enabled && (_jsx("span", { className: "flex size-6 shrink-0 items-center justify-center", children: stopping && working ? (_jsx(Loading, { className: "text-muted-foreground size-3" })) : canStop ? (_jsx(Hint, { label: t('stopHint'), side: "top", sideOffset: 4, alignOffset: 0, children: _jsx(Button, { type: "button", variant: "ghost", size: "icon-xs", "aria-label": t('stopAgent', { label: agent.label }), onClick: () => stop.stop(agent), className: "text-muted-foreground hover:text-foreground", children: _jsx(SquareIcon, { weight: "fill", className: "size-2.5" }) }) })) : null }))] }), structured && jsonOpen && (_jsx("div", { className: "pr-1 pb-1 pl-7", children: _jsx(OutputBlock, { text: structured.pretty }) }))] }));
|
|
186
|
+
}
|