@pellux/goodvibes-agent 0.1.0
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/.goodvibes/GOODVIBES.md +35 -0
- package/.goodvibes/agents/reviewer.md +48 -0
- package/.goodvibes/skills/add-provider/SKILL.md +199 -0
- package/CHANGELOG.md +25 -0
- package/README.md +74 -0
- package/bin/goodvibes-agent.ts +2 -0
- package/docs/README.md +23 -0
- package/docs/deployment-and-services.md +57 -0
- package/docs/getting-started.md +53 -0
- package/docs/release-and-publishing.md +46 -0
- package/package.json +134 -0
- package/scripts/check-bun.sh +20 -0
- package/src/audio/player.ts +156 -0
- package/src/audio/spoken-turn-controller.ts +203 -0
- package/src/audio/spoken-turn-model-routing.ts +117 -0
- package/src/audio/spoken-turn-wiring.ts +44 -0
- package/src/audio/text-chunker.ts +110 -0
- package/src/cli/bundle-command.ts +227 -0
- package/src/cli/completion.ts +90 -0
- package/src/cli/config-overrides.ts +159 -0
- package/src/cli/endpoints.ts +63 -0
- package/src/cli/entrypoint.ts +172 -0
- package/src/cli/help.ts +299 -0
- package/src/cli/index.ts +11 -0
- package/src/cli/management-commands.ts +426 -0
- package/src/cli/management.ts +744 -0
- package/src/cli/network-posture.ts +46 -0
- package/src/cli/package-verification.ts +123 -0
- package/src/cli/parser.ts +369 -0
- package/src/cli/provider-auth-routes.ts +22 -0
- package/src/cli/provider-classification.ts +107 -0
- package/src/cli/redaction.ts +105 -0
- package/src/cli/service-command.ts +26 -0
- package/src/cli/service-posture.ts +482 -0
- package/src/cli/status.ts +383 -0
- package/src/cli/surface-command.ts +247 -0
- package/src/cli/tui-startup.ts +32 -0
- package/src/cli/types.ts +69 -0
- package/src/cli-flags.ts +21 -0
- package/src/config/goodvibes-home-audit.ts +465 -0
- package/src/config/index.ts +57 -0
- package/src/config/provider-model.ts +23 -0
- package/src/config/secret-config.ts +119 -0
- package/src/config/secrets.ts +71 -0
- package/src/config/surface.ts +1 -0
- package/src/core/composer-state.ts +61 -0
- package/src/core/conversation-rendering.ts +359 -0
- package/src/core/conversation.ts +551 -0
- package/src/core/history.ts +45 -0
- package/src/core/orchestrator.ts +7 -0
- package/src/core/system-message-router.ts +171 -0
- package/src/daemon/cli.ts +55 -0
- package/src/daemon/safe-serve.ts +61 -0
- package/src/input/agent-workspace.ts +428 -0
- package/src/input/autocomplete.ts +96 -0
- package/src/input/bookmark-modal.ts +115 -0
- package/src/input/command-args-hint.ts +36 -0
- package/src/input/command-registry.ts +329 -0
- package/src/input/commands/agent-externalized-tui.ts +73 -0
- package/src/input/commands/agent-workspace-runtime.ts +17 -0
- package/src/input/commands/branch-runtime.ts +72 -0
- package/src/input/commands/cloudflare-runtime.ts +370 -0
- package/src/input/commands/config.ts +18 -0
- package/src/input/commands/control-room-runtime.ts +255 -0
- package/src/input/commands/conversation-runtime.ts +207 -0
- package/src/input/commands/discovery-runtime.ts +52 -0
- package/src/input/commands/eval.ts +204 -0
- package/src/input/commands/experience-runtime.ts +278 -0
- package/src/input/commands/guidance-runtime.ts +106 -0
- package/src/input/commands/health-runtime.ts +434 -0
- package/src/input/commands/hooks-runtime.ts +148 -0
- package/src/input/commands/incident-runtime.ts +95 -0
- package/src/input/commands/integration-runtime.ts +394 -0
- package/src/input/commands/intelligence-runtime.ts +223 -0
- package/src/input/commands/knowledge.ts +531 -0
- package/src/input/commands/local-auth-runtime.ts +105 -0
- package/src/input/commands/local-provider-runtime.ts +170 -0
- package/src/input/commands/local-runtime.ts +392 -0
- package/src/input/commands/local-setup-review.ts +199 -0
- package/src/input/commands/local-setup-transfer.ts +135 -0
- package/src/input/commands/local-setup.ts +282 -0
- package/src/input/commands/managed-runtime.ts +209 -0
- package/src/input/commands/marketplace-runtime.ts +290 -0
- package/src/input/commands/mcp-runtime.ts +432 -0
- package/src/input/commands/memory-product-runtime.ts +111 -0
- package/src/input/commands/memory.ts +151 -0
- package/src/input/commands/notify-runtime.ts +83 -0
- package/src/input/commands/onboarding-runtime.ts +14 -0
- package/src/input/commands/operator-panel-runtime.ts +146 -0
- package/src/input/commands/operator-runtime.ts +392 -0
- package/src/input/commands/planning-runtime.ts +205 -0
- package/src/input/commands/platform-access-runtime.ts +422 -0
- package/src/input/commands/platform-services-runtime.ts +246 -0
- package/src/input/commands/policy-dispatch.ts +339 -0
- package/src/input/commands/policy.ts +17 -0
- package/src/input/commands/product-runtime.ts +351 -0
- package/src/input/commands/profile-sync-runtime.ts +99 -0
- package/src/input/commands/provider-accounts-runtime.ts +113 -0
- package/src/input/commands/provider.ts +363 -0
- package/src/input/commands/qrcode-runtime.ts +20 -0
- package/src/input/commands/quit-shared.ts +162 -0
- package/src/input/commands/recall-bundle.ts +132 -0
- package/src/input/commands/recall-capture.ts +152 -0
- package/src/input/commands/recall-query.ts +229 -0
- package/src/input/commands/recall-review.ts +98 -0
- package/src/input/commands/recall-shared.ts +22 -0
- package/src/input/commands/remote-runtime-pool.ts +106 -0
- package/src/input/commands/remote-runtime-setup.ts +199 -0
- package/src/input/commands/remote-runtime.ts +431 -0
- package/src/input/commands/replay-runtime.ts +18 -0
- package/src/input/commands/runtime-services.ts +291 -0
- package/src/input/commands/schedule-runtime.ts +91 -0
- package/src/input/commands/services-runtime.ts +209 -0
- package/src/input/commands/session-content.ts +408 -0
- package/src/input/commands/session-workflow.ts +464 -0
- package/src/input/commands/session.ts +375 -0
- package/src/input/commands/settings-sync-runtime.ts +174 -0
- package/src/input/commands/share-runtime.ts +119 -0
- package/src/input/commands/shell-core.ts +307 -0
- package/src/input/commands/skills-runtime.ts +221 -0
- package/src/input/commands/subscription-runtime.ts +434 -0
- package/src/input/commands/tasks-runtime.ts +230 -0
- package/src/input/commands/teamwork-runtime.ts +339 -0
- package/src/input/commands/teleport-runtime.ts +57 -0
- package/src/input/commands/tts-runtime.ts +29 -0
- package/src/input/commands/work-plan-runtime.ts +169 -0
- package/src/input/commands.ts +131 -0
- package/src/input/feed-context-factory.ts +254 -0
- package/src/input/file-picker.ts +192 -0
- package/src/input/handler-command-route.ts +180 -0
- package/src/input/handler-content-actions.ts +497 -0
- package/src/input/handler-feed-routes.ts +648 -0
- package/src/input/handler-feed.ts +452 -0
- package/src/input/handler-interactions.ts +281 -0
- package/src/input/handler-modal-routes.ts +418 -0
- package/src/input/handler-modal-stack.ts +263 -0
- package/src/input/handler-modal-token-routes.ts +329 -0
- package/src/input/handler-onboarding-cloudflare.ts +391 -0
- package/src/input/handler-onboarding.ts +620 -0
- package/src/input/handler-picker-routes.ts +472 -0
- package/src/input/handler-prompt-buffer.ts +320 -0
- package/src/input/handler-shortcuts.ts +213 -0
- package/src/input/handler-ui-state.ts +372 -0
- package/src/input/handler.ts +729 -0
- package/src/input/input-history.ts +297 -0
- package/src/input/keybindings.ts +292 -0
- package/src/input/mcp-workspace.ts +554 -0
- package/src/input/model-picker-provider-filter.ts +28 -0
- package/src/input/model-picker-types.ts +137 -0
- package/src/input/model-picker.ts +797 -0
- package/src/input/onboarding/handler-onboarding-routes.ts +125 -0
- package/src/input/onboarding/onboarding-runtime-status.ts +87 -0
- package/src/input/onboarding/onboarding-wizard-apply.ts +277 -0
- package/src/input/onboarding/onboarding-wizard-cloudflare-step.ts +494 -0
- package/src/input/onboarding/onboarding-wizard-cloudflare.ts +204 -0
- package/src/input/onboarding/onboarding-wizard-constants.ts +158 -0
- package/src/input/onboarding/onboarding-wizard-external-surface-extra-specs.ts +130 -0
- package/src/input/onboarding/onboarding-wizard-external-surfaces.ts +762 -0
- package/src/input/onboarding/onboarding-wizard-helpers.ts +167 -0
- package/src/input/onboarding/onboarding-wizard-rules.ts +256 -0
- package/src/input/onboarding/onboarding-wizard-state.ts +365 -0
- package/src/input/onboarding/onboarding-wizard-steps.ts +798 -0
- package/src/input/onboarding/onboarding-wizard-types.ts +195 -0
- package/src/input/onboarding/onboarding-wizard.ts +711 -0
- package/src/input/panel-integration-actions.ts +78 -0
- package/src/input/profile-picker-modal.ts +222 -0
- package/src/input/search.ts +100 -0
- package/src/input/selection-modal.ts +163 -0
- package/src/input/selection.ts +135 -0
- package/src/input/session-picker-modal.ts +136 -0
- package/src/input/settings-modal-behavior.ts +37 -0
- package/src/input/settings-modal-secrets.ts +41 -0
- package/src/input/settings-modal-subscriptions.ts +95 -0
- package/src/input/settings-modal-types.ts +91 -0
- package/src/input/settings-modal.ts +793 -0
- package/src/input/submission-intent.ts +17 -0
- package/src/input/submission-router.ts +59 -0
- package/src/input/tts-settings-actions.ts +100 -0
- package/src/main.ts +792 -0
- package/src/mcp/runtime-reload.ts +81 -0
- package/src/panels/agent-inspector-panel.ts +521 -0
- package/src/panels/agent-inspector-shared.ts +94 -0
- package/src/panels/agent-logs-panel.ts +559 -0
- package/src/panels/agent-logs-shared.ts +129 -0
- package/src/panels/approval-panel.ts +150 -0
- package/src/panels/automation-control-panel.ts +212 -0
- package/src/panels/base-panel.ts +254 -0
- package/src/panels/builtin/agent.ts +117 -0
- package/src/panels/builtin/development.ts +31 -0
- package/src/panels/builtin/knowledge.ts +26 -0
- package/src/panels/builtin/operations.ts +349 -0
- package/src/panels/builtin/session.ts +129 -0
- package/src/panels/builtin/shared.ts +274 -0
- package/src/panels/builtin-panels.ts +23 -0
- package/src/panels/cockpit-panel.ts +183 -0
- package/src/panels/communication-panel.ts +153 -0
- package/src/panels/confirm-state.ts +61 -0
- package/src/panels/context-visualizer-panel.ts +204 -0
- package/src/panels/control-plane-panel.ts +211 -0
- package/src/panels/cost-tracker-panel.ts +444 -0
- package/src/panels/debug-panel.ts +432 -0
- package/src/panels/diff-panel.ts +520 -0
- package/src/panels/docs-panel.ts +283 -0
- package/src/panels/eval-panel.ts +399 -0
- package/src/panels/file-explorer-panel.ts +584 -0
- package/src/panels/file-preview-panel.ts +434 -0
- package/src/panels/forensics-panel.ts +364 -0
- package/src/panels/git-panel.ts +638 -0
- package/src/panels/hooks-panel.ts +239 -0
- package/src/panels/incident-review-panel.ts +197 -0
- package/src/panels/index.ts +46 -0
- package/src/panels/intelligence-panel.ts +176 -0
- package/src/panels/knowledge-panel.ts +345 -0
- package/src/panels/local-auth-panel.ts +130 -0
- package/src/panels/marketplace-panel.ts +212 -0
- package/src/panels/memory-panel.ts +225 -0
- package/src/panels/ops-control-panel.ts +150 -0
- package/src/panels/ops-strategy-panel.ts +235 -0
- package/src/panels/orchestration-panel.ts +273 -0
- package/src/panels/panel-list-panel.ts +509 -0
- package/src/panels/panel-manager.ts +570 -0
- package/src/panels/panel-picker.ts +106 -0
- package/src/panels/plan-dashboard-panel.ts +274 -0
- package/src/panels/plugins-panel.ts +178 -0
- package/src/panels/policy-panel.ts +308 -0
- package/src/panels/polish.ts +717 -0
- package/src/panels/project-planning-panel.ts +711 -0
- package/src/panels/provider-account-snapshot.ts +259 -0
- package/src/panels/provider-accounts-panel.ts +218 -0
- package/src/panels/provider-health-domains.ts +215 -0
- package/src/panels/provider-health-panel.ts +727 -0
- package/src/panels/provider-health-tracker.ts +115 -0
- package/src/panels/provider-stats-panel.ts +366 -0
- package/src/panels/qr-panel.ts +182 -0
- package/src/panels/remote-panel.ts +449 -0
- package/src/panels/routes-panel.ts +178 -0
- package/src/panels/sandbox-panel.ts +283 -0
- package/src/panels/schedule-panel.ts +329 -0
- package/src/panels/scrollable-list-panel.ts +491 -0
- package/src/panels/search-focus.ts +32 -0
- package/src/panels/security-panel.ts +295 -0
- package/src/panels/services-panel.ts +231 -0
- package/src/panels/session-browser-panel.ts +400 -0
- package/src/panels/session-maintenance.ts +125 -0
- package/src/panels/settings-sync-panel.ts +120 -0
- package/src/panels/skills-panel.ts +431 -0
- package/src/panels/subscription-panel.ts +263 -0
- package/src/panels/symbol-outline-panel.ts +486 -0
- package/src/panels/system-messages-panel.ts +230 -0
- package/src/panels/tasks-panel.ts +399 -0
- package/src/panels/thinking-panel.ts +304 -0
- package/src/panels/token-budget-panel.ts +475 -0
- package/src/panels/tool-inspector-panel.ts +429 -0
- package/src/panels/types.ts +54 -0
- package/src/panels/watchers-panel.ts +193 -0
- package/src/panels/work-plan-panel.ts +175 -0
- package/src/panels/worktree-panel.ts +182 -0
- package/src/panels/wrfc-panel.ts +609 -0
- package/src/permissions/prompt.ts +165 -0
- package/src/planning/project-planning-coordinator.ts +543 -0
- package/src/plugins/loader.ts +15 -0
- package/src/renderer/agent-detail-modal.ts +331 -0
- package/src/renderer/agent-workspace.ts +238 -0
- package/src/renderer/ansi-sanitize.ts +76 -0
- package/src/renderer/autocomplete-overlay.ts +154 -0
- package/src/renderer/block-actions.ts +76 -0
- package/src/renderer/bookmark-modal.ts +101 -0
- package/src/renderer/bottom-bar.ts +58 -0
- package/src/renderer/buffer.ts +113 -0
- package/src/renderer/code-block.ts +373 -0
- package/src/renderer/compositor.ts +283 -0
- package/src/renderer/context-inspector.ts +219 -0
- package/src/renderer/conversation-layout.ts +67 -0
- package/src/renderer/conversation-overlays.ts +140 -0
- package/src/renderer/conversation-surface.ts +260 -0
- package/src/renderer/diff-view.ts +132 -0
- package/src/renderer/diff.ts +130 -0
- package/src/renderer/file-picker-overlay.ts +101 -0
- package/src/renderer/file-tree.ts +153 -0
- package/src/renderer/fullscreen-primitives.ts +130 -0
- package/src/renderer/fullscreen-workspace.ts +199 -0
- package/src/renderer/git-status.ts +89 -0
- package/src/renderer/help-overlay.ts +267 -0
- package/src/renderer/history-search-overlay.ts +73 -0
- package/src/renderer/layout-engine.ts +97 -0
- package/src/renderer/layout.ts +32 -0
- package/src/renderer/live-tail-modal.ts +156 -0
- package/src/renderer/markdown.ts +635 -0
- package/src/renderer/mcp-workspace.ts +237 -0
- package/src/renderer/modal-factory.ts +467 -0
- package/src/renderer/modal-utils.ts +24 -0
- package/src/renderer/model-picker-overlay.ts +473 -0
- package/src/renderer/model-workspace.ts +488 -0
- package/src/renderer/onboarding/onboarding-wizard.ts +615 -0
- package/src/renderer/overlay-box.ts +146 -0
- package/src/renderer/overlay-viewport.ts +104 -0
- package/src/renderer/panel-composite.ts +158 -0
- package/src/renderer/panel-picker-overlay.ts +202 -0
- package/src/renderer/panel-tab-bar.ts +69 -0
- package/src/renderer/panel-workspace-bar.ts +42 -0
- package/src/renderer/process-indicator.ts +96 -0
- package/src/renderer/process-modal.ts +656 -0
- package/src/renderer/process-summary.ts +67 -0
- package/src/renderer/profile-picker-modal.ts +129 -0
- package/src/renderer/progress.ts +98 -0
- package/src/renderer/qr-renderer.ts +120 -0
- package/src/renderer/search-overlay.ts +54 -0
- package/src/renderer/selection-modal-overlay.ts +214 -0
- package/src/renderer/semantic-diff.ts +369 -0
- package/src/renderer/session-picker-modal.ts +127 -0
- package/src/renderer/settings-modal-helpers.ts +193 -0
- package/src/renderer/settings-modal.ts +537 -0
- package/src/renderer/shell-surface.ts +88 -0
- package/src/renderer/status-glyphs.ts +21 -0
- package/src/renderer/status-token.ts +67 -0
- package/src/renderer/surface-layout.ts +101 -0
- package/src/renderer/syntax-highlighter.ts +542 -0
- package/src/renderer/system-message.ts +83 -0
- package/src/renderer/tab-strip.ts +108 -0
- package/src/renderer/text-layout.ts +31 -0
- package/src/renderer/thinking.ts +17 -0
- package/src/renderer/tool-call.ts +234 -0
- package/src/renderer/ui-factory.ts +524 -0
- package/src/renderer/ui-primitives.ts +96 -0
- package/src/runtime/bootstrap-command-context.ts +278 -0
- package/src/runtime/bootstrap-command-parts.ts +386 -0
- package/src/runtime/bootstrap-core.ts +540 -0
- package/src/runtime/bootstrap-hook-bridge.ts +112 -0
- package/src/runtime/bootstrap-shell.ts +283 -0
- package/src/runtime/bootstrap.ts +575 -0
- package/src/runtime/cloudflare-control-plane.ts +349 -0
- package/src/runtime/context.ts +142 -0
- package/src/runtime/diagnostics/panels/index.ts +24 -0
- package/src/runtime/diagnostics/panels/ops.ts +156 -0
- package/src/runtime/diagnostics/panels/panel-resources.ts +118 -0
- package/src/runtime/diagnostics/panels/policy.ts +177 -0
- package/src/runtime/index.ts +662 -0
- package/src/runtime/onboarding/apply.ts +642 -0
- package/src/runtime/onboarding/derivation.ts +534 -0
- package/src/runtime/onboarding/index.ts +7 -0
- package/src/runtime/onboarding/markers.ts +148 -0
- package/src/runtime/onboarding/snapshot.ts +406 -0
- package/src/runtime/onboarding/state.ts +141 -0
- package/src/runtime/onboarding/types.ts +404 -0
- package/src/runtime/onboarding/verify.ts +171 -0
- package/src/runtime/operator-token-cleanup.ts +27 -0
- package/src/runtime/perf/panel-contracts.ts +32 -0
- package/src/runtime/perf/panel-health-monitor.ts +18 -0
- package/src/runtime/sandbox-public-gaps.ts +358 -0
- package/src/runtime/services.ts +670 -0
- package/src/runtime/store/domains/domain-read-matrix.ts +15 -0
- package/src/runtime/store/domains/index.ts +222 -0
- package/src/runtime/store/domains/panels.ts +117 -0
- package/src/runtime/store/domains/ui-perf.ts +103 -0
- package/src/runtime/store/index.ts +305 -0
- package/src/runtime/store/selectors/index.ts +359 -0
- package/src/runtime/store/state.ts +145 -0
- package/src/runtime/surface-feature-flags.ts +65 -0
- package/src/runtime/terminal-output-guard.ts +228 -0
- package/src/runtime/ui/index.ts +39 -0
- package/src/runtime/ui/model-picker/data-provider.ts +182 -0
- package/src/runtime/ui/model-picker/health-enrichment.ts +228 -0
- package/src/runtime/ui/model-picker/index.ts +59 -0
- package/src/runtime/ui/model-picker/types.ts +149 -0
- package/src/runtime/ui/provider-health/data-provider.ts +244 -0
- package/src/runtime/ui/provider-health/fallback-visualizer.ts +71 -0
- package/src/runtime/ui/provider-health/index.ts +46 -0
- package/src/runtime/ui/provider-health/types.ts +146 -0
- package/src/runtime/ui-events.ts +1 -0
- package/src/runtime/ui-read-model-helpers.ts +1 -0
- package/src/runtime/ui-read-models-observability-maintenance.ts +1 -0
- package/src/runtime/ui-read-models-observability-options.ts +1 -0
- package/src/runtime/ui-read-models-observability-remote.ts +1 -0
- package/src/runtime/ui-read-models-observability-security.ts +1 -0
- package/src/runtime/ui-read-models-observability-system.ts +1 -0
- package/src/runtime/ui-read-models-observability.ts +1 -0
- package/src/runtime/ui-read-models.ts +61 -0
- package/src/runtime/ui-service-queries.ts +1 -0
- package/src/runtime/ui-services.ts +190 -0
- package/src/scripts/process-messages.ts +42 -0
- package/src/shell/blocking-input.ts +98 -0
- package/src/shell/service-settings-sync.ts +273 -0
- package/src/shell/ui-openers.ts +352 -0
- package/src/tools/index.ts +1 -0
- package/src/tools/wrfc-agent-guard.ts +49 -0
- package/src/types/grid.ts +48 -0
- package/src/types/sql-js.d.ts +15 -0
- package/src/utils/clipboard.ts +22 -0
- package/src/utils/splash-lines.ts +46 -0
- package/src/utils/terminal-width.ts +185 -0
- package/src/verification/live-verifier.ts +430 -0
- package/src/verification/verification-ledger.ts +242 -0
- package/src/version.ts +17 -0
- package/src/widget/index.ts +2 -0
- package/src/widget/types.ts +9 -0
- package/src/widget/widget.ts +8 -0
- package/src/work-plans/work-plan-store.ts +374 -0
- package/tsconfig.json +18 -0
|
@@ -0,0 +1,305 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Runtime store — Zustand vanilla store for goodvibes-agent.
|
|
3
|
+
*
|
|
4
|
+
* Uses `createStore` from `zustand/vanilla` (NOT the React `create` hook)
|
|
5
|
+
* because goodvibes-agent is a terminal app with no React renderer.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
import { createStore } from 'zustand/vanilla';
|
|
9
|
+
import type { StoreApi } from 'zustand';
|
|
10
|
+
import type {
|
|
11
|
+
AgentEvent,
|
|
12
|
+
CommunicationEvent,
|
|
13
|
+
CompactionEvent,
|
|
14
|
+
McpEvent,
|
|
15
|
+
OrchestrationEvent,
|
|
16
|
+
PermissionEvent,
|
|
17
|
+
PluginEvent,
|
|
18
|
+
TaskEvent,
|
|
19
|
+
ToolEvent,
|
|
20
|
+
TransportEvent,
|
|
21
|
+
TurnEvent,
|
|
22
|
+
} from '@pellux/goodvibes-sdk/events';
|
|
23
|
+
import type {
|
|
24
|
+
SessionDomainState,
|
|
25
|
+
ConversationDomainState,
|
|
26
|
+
TaskDomainState,
|
|
27
|
+
TaskLifecycleState,
|
|
28
|
+
RuntimeTask,
|
|
29
|
+
AgentDomainState,
|
|
30
|
+
AgentLifecycleState,
|
|
31
|
+
RuntimeAgent,
|
|
32
|
+
PermissionDomainState,
|
|
33
|
+
PermissionDecision,
|
|
34
|
+
OrchestrationDomainState,
|
|
35
|
+
CommunicationDomainState,
|
|
36
|
+
PluginDomainState,
|
|
37
|
+
McpDomainState,
|
|
38
|
+
AcpDomainState,
|
|
39
|
+
DaemonDomainState,
|
|
40
|
+
IntegrationDomainState,
|
|
41
|
+
IntegrationRecord,
|
|
42
|
+
IntegrationStatus,
|
|
43
|
+
AutomationDomainState,
|
|
44
|
+
RoutesDomainState,
|
|
45
|
+
ControlPlaneDomainState,
|
|
46
|
+
ControlPlaneClientRecord,
|
|
47
|
+
DeliveryDomainState,
|
|
48
|
+
WatcherDomainState,
|
|
49
|
+
WatcherRecord,
|
|
50
|
+
SurfaceDomainState,
|
|
51
|
+
SurfaceRecord,
|
|
52
|
+
} from '@pellux/goodvibes-sdk/platform/runtime/state';
|
|
53
|
+
import type { AutomationJob } from '@pellux/goodvibes-sdk/platform/automation';
|
|
54
|
+
import type { AutomationRun } from '@pellux/goodvibes-sdk/platform/automation';
|
|
55
|
+
import type { AutomationSourceRecord } from '@pellux/goodvibes-sdk/platform/automation';
|
|
56
|
+
import type { AutomationRouteBinding } from '@pellux/goodvibes-sdk/platform/automation';
|
|
57
|
+
import type { AutomationSurfaceKind } from '@pellux/goodvibes-sdk/platform/automation';
|
|
58
|
+
import type { AutomationDeliveryAttempt } from '@pellux/goodvibes-sdk/platform/automation';
|
|
59
|
+
import { createInitialRuntimeState } from './state.ts';
|
|
60
|
+
import type { RuntimeState } from './state.ts';
|
|
61
|
+
import {
|
|
62
|
+
patchControlPlaneDomain,
|
|
63
|
+
syncSessionStatePatch,
|
|
64
|
+
transitionAgentDomainRecord,
|
|
65
|
+
transitionTaskDomainRecord,
|
|
66
|
+
updateAgentState,
|
|
67
|
+
updateAutomationDomainFromJob,
|
|
68
|
+
updateAutomationDomainFromRun,
|
|
69
|
+
updateAutomationDomainFromSource,
|
|
70
|
+
updateCommunicationState,
|
|
71
|
+
updateConversationState,
|
|
72
|
+
updateControlPlaneDomainFromClient,
|
|
73
|
+
updateDeliveryDomainFromAttempt,
|
|
74
|
+
updateIntegrationDomainFromRecord,
|
|
75
|
+
updateMcpState,
|
|
76
|
+
updateOrchestrationState,
|
|
77
|
+
updatePermissionState,
|
|
78
|
+
updatePluginState,
|
|
79
|
+
updateRouteFailureState,
|
|
80
|
+
updateRoutesDomainFromBinding,
|
|
81
|
+
updateSessionState,
|
|
82
|
+
updateSurfaceDomainFromRecord,
|
|
83
|
+
updateTaskDomainFromRecord,
|
|
84
|
+
updateTaskState,
|
|
85
|
+
updateTransportState,
|
|
86
|
+
updateWatcherDomainFromRecord,
|
|
87
|
+
} from '@pellux/goodvibes-sdk/platform/runtime/state';
|
|
88
|
+
|
|
89
|
+
export type RuntimeStore = StoreApi<RuntimeState>;
|
|
90
|
+
|
|
91
|
+
export function createRuntimeStore(): RuntimeStore {
|
|
92
|
+
return createStore<RuntimeState>(() => createInitialRuntimeState());
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
function mutateRuntimeStore(store: RuntimeStore, updater: (state: RuntimeState) => RuntimeState): void {
|
|
96
|
+
store.setState(updater);
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
export interface DomainDispatch {
|
|
100
|
+
dispatchTurnEvent(event: TurnEvent): void;
|
|
101
|
+
dispatchToolEvent(event: ToolEvent): void;
|
|
102
|
+
dispatchPermissionEvent(event: PermissionEvent): void;
|
|
103
|
+
dispatchTaskEvent(event: TaskEvent): void;
|
|
104
|
+
dispatchAgentEvent(event: AgentEvent): void;
|
|
105
|
+
dispatchOrchestrationEvent(event: OrchestrationEvent): void;
|
|
106
|
+
dispatchCommunicationEvent(event: CommunicationEvent): void;
|
|
107
|
+
dispatchPluginEvent(event: PluginEvent): void;
|
|
108
|
+
dispatchMcpEvent(event: McpEvent): void;
|
|
109
|
+
dispatchTransportEvent(event: TransportEvent): void;
|
|
110
|
+
dispatchCompactionEvent(event: CompactionEvent): void;
|
|
111
|
+
syncSessionState(patch: Partial<SessionDomainState>, source?: string): void;
|
|
112
|
+
syncRuntimeTask(task: RuntimeTask, source?: string): void;
|
|
113
|
+
transitionRuntimeTask(
|
|
114
|
+
taskId: string,
|
|
115
|
+
status: TaskLifecycleState,
|
|
116
|
+
patch?: Partial<RuntimeTask>,
|
|
117
|
+
source?: string,
|
|
118
|
+
): void;
|
|
119
|
+
transitionRuntimeAgent(
|
|
120
|
+
agentId: string,
|
|
121
|
+
status: AgentLifecycleState,
|
|
122
|
+
patch?: Partial<RuntimeAgent>,
|
|
123
|
+
source?: string,
|
|
124
|
+
): void;
|
|
125
|
+
syncIntegration(record: IntegrationRecord, source?: string): void;
|
|
126
|
+
syncAutomationSource(record: AutomationSourceRecord, source?: string): void;
|
|
127
|
+
syncAutomationJob(record: AutomationJob, source?: string): void;
|
|
128
|
+
syncAutomationRun(record: AutomationRun, source?: string): void;
|
|
129
|
+
syncRouteBinding(record: AutomationRouteBinding, source?: string): void;
|
|
130
|
+
recordRouteBindingFailure(
|
|
131
|
+
surfaceKind: AutomationSurfaceKind,
|
|
132
|
+
externalId: string,
|
|
133
|
+
source?: string,
|
|
134
|
+
): void;
|
|
135
|
+
syncControlPlaneClient(record: ControlPlaneClientRecord, source?: string): void;
|
|
136
|
+
syncControlPlaneState(patch: Partial<ControlPlaneDomainState>, source?: string): void;
|
|
137
|
+
syncDeliveryAttempt(record: AutomationDeliveryAttempt, source?: string): void;
|
|
138
|
+
syncSurface(record: SurfaceRecord, source?: string): void;
|
|
139
|
+
syncWatcher(record: WatcherRecord, source?: string): void;
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
export function createDomainDispatch(store: RuntimeStore): DomainDispatch {
|
|
143
|
+
return {
|
|
144
|
+
dispatchTurnEvent(event) {
|
|
145
|
+
mutateRuntimeStore(store, (state) => ({
|
|
146
|
+
...state,
|
|
147
|
+
conversation: updateConversationState(state.conversation, event),
|
|
148
|
+
}));
|
|
149
|
+
},
|
|
150
|
+
dispatchToolEvent(event) {
|
|
151
|
+
mutateRuntimeStore(store, (state) => ({
|
|
152
|
+
...state,
|
|
153
|
+
conversation: updateConversationState(state.conversation, event),
|
|
154
|
+
}));
|
|
155
|
+
},
|
|
156
|
+
dispatchPermissionEvent(event) {
|
|
157
|
+
mutateRuntimeStore(store, (state) => ({
|
|
158
|
+
...state,
|
|
159
|
+
permissions: updatePermissionState(state.permissions, event),
|
|
160
|
+
}));
|
|
161
|
+
},
|
|
162
|
+
dispatchTaskEvent(event) {
|
|
163
|
+
mutateRuntimeStore(store, (state) => ({
|
|
164
|
+
...state,
|
|
165
|
+
tasks: updateTaskState(state.tasks, event),
|
|
166
|
+
}));
|
|
167
|
+
},
|
|
168
|
+
dispatchAgentEvent(event) {
|
|
169
|
+
mutateRuntimeStore(store, (state) => ({
|
|
170
|
+
...state,
|
|
171
|
+
agents: updateAgentState(state.agents, event),
|
|
172
|
+
}));
|
|
173
|
+
},
|
|
174
|
+
dispatchOrchestrationEvent(event) {
|
|
175
|
+
mutateRuntimeStore(store, (state) => ({
|
|
176
|
+
...state,
|
|
177
|
+
orchestration: updateOrchestrationState(state.orchestration, event),
|
|
178
|
+
}));
|
|
179
|
+
},
|
|
180
|
+
dispatchCommunicationEvent(event) {
|
|
181
|
+
mutateRuntimeStore(store, (state) => ({
|
|
182
|
+
...state,
|
|
183
|
+
communication: updateCommunicationState(state.communication, event),
|
|
184
|
+
}));
|
|
185
|
+
},
|
|
186
|
+
dispatchPluginEvent(event) {
|
|
187
|
+
mutateRuntimeStore(store, (state) => ({
|
|
188
|
+
...state,
|
|
189
|
+
plugins: updatePluginState(state.plugins, event),
|
|
190
|
+
}));
|
|
191
|
+
},
|
|
192
|
+
dispatchMcpEvent(event) {
|
|
193
|
+
mutateRuntimeStore(store, (state) => ({
|
|
194
|
+
...state,
|
|
195
|
+
mcp: updateMcpState(state.mcp, event),
|
|
196
|
+
}));
|
|
197
|
+
},
|
|
198
|
+
dispatchTransportEvent(event) {
|
|
199
|
+
mutateRuntimeStore(store, (state) => ({
|
|
200
|
+
...state,
|
|
201
|
+
...updateTransportState(state.acp, state.daemon, event),
|
|
202
|
+
}));
|
|
203
|
+
},
|
|
204
|
+
dispatchCompactionEvent(event) {
|
|
205
|
+
mutateRuntimeStore(store, (state) => ({
|
|
206
|
+
...state,
|
|
207
|
+
session: updateSessionState(state.session, event),
|
|
208
|
+
}));
|
|
209
|
+
},
|
|
210
|
+
syncSessionState(patch, source = 'domain-dispatch') {
|
|
211
|
+
mutateRuntimeStore(store, (state) => ({
|
|
212
|
+
...state,
|
|
213
|
+
session: syncSessionStatePatch(state.session, patch, source),
|
|
214
|
+
}));
|
|
215
|
+
},
|
|
216
|
+
syncRuntimeTask(task, source = 'domain-dispatch') {
|
|
217
|
+
mutateRuntimeStore(store, (state) => ({
|
|
218
|
+
...state,
|
|
219
|
+
tasks: updateTaskDomainFromRecord(state.tasks, task, source),
|
|
220
|
+
}));
|
|
221
|
+
},
|
|
222
|
+
transitionRuntimeTask(taskId, status, patch, source = 'domain-dispatch') {
|
|
223
|
+
mutateRuntimeStore(store, (state) => ({
|
|
224
|
+
...state,
|
|
225
|
+
tasks: transitionTaskDomainRecord(state.tasks, taskId, status, patch, source),
|
|
226
|
+
}));
|
|
227
|
+
},
|
|
228
|
+
transitionRuntimeAgent(agentId, status, patch, source = 'domain-dispatch') {
|
|
229
|
+
mutateRuntimeStore(store, (state) => ({
|
|
230
|
+
...state,
|
|
231
|
+
agents: transitionAgentDomainRecord(state.agents, agentId, status, patch, source),
|
|
232
|
+
}));
|
|
233
|
+
},
|
|
234
|
+
syncIntegration(record, source = 'domain-dispatch') {
|
|
235
|
+
mutateRuntimeStore(store, (state) => ({
|
|
236
|
+
...state,
|
|
237
|
+
integrations: updateIntegrationDomainFromRecord(state.integrations, record, source),
|
|
238
|
+
}));
|
|
239
|
+
},
|
|
240
|
+
syncAutomationSource(record, source = 'domain-dispatch') {
|
|
241
|
+
mutateRuntimeStore(store, (state) => ({
|
|
242
|
+
...state,
|
|
243
|
+
automation: updateAutomationDomainFromSource(state.automation, record, source),
|
|
244
|
+
}));
|
|
245
|
+
},
|
|
246
|
+
syncAutomationJob(record, source = 'domain-dispatch') {
|
|
247
|
+
mutateRuntimeStore(store, (state) => ({
|
|
248
|
+
...state,
|
|
249
|
+
automation: updateAutomationDomainFromJob(state.automation, record, source),
|
|
250
|
+
}));
|
|
251
|
+
},
|
|
252
|
+
syncAutomationRun(record, source = 'domain-dispatch') {
|
|
253
|
+
mutateRuntimeStore(store, (state) => ({
|
|
254
|
+
...state,
|
|
255
|
+
automation: updateAutomationDomainFromRun(state.automation, record, source),
|
|
256
|
+
}));
|
|
257
|
+
},
|
|
258
|
+
syncRouteBinding(record, source = 'domain-dispatch') {
|
|
259
|
+
mutateRuntimeStore(store, (state) => ({
|
|
260
|
+
...state,
|
|
261
|
+
routes: updateRoutesDomainFromBinding(state.routes, record, source),
|
|
262
|
+
}));
|
|
263
|
+
},
|
|
264
|
+
recordRouteBindingFailure(surfaceKind, externalId, source = 'domain-dispatch') {
|
|
265
|
+
mutateRuntimeStore(store, (state) => ({
|
|
266
|
+
...state,
|
|
267
|
+
routes: updateRouteFailureState(state.routes, surfaceKind, externalId, source),
|
|
268
|
+
}));
|
|
269
|
+
},
|
|
270
|
+
syncControlPlaneClient(record, source = 'domain-dispatch') {
|
|
271
|
+
mutateRuntimeStore(store, (state) => ({
|
|
272
|
+
...state,
|
|
273
|
+
controlPlane: updateControlPlaneDomainFromClient(state.controlPlane, record, source),
|
|
274
|
+
}));
|
|
275
|
+
},
|
|
276
|
+
syncControlPlaneState(patch, source = 'domain-dispatch') {
|
|
277
|
+
mutateRuntimeStore(store, (state) => ({
|
|
278
|
+
...state,
|
|
279
|
+
controlPlane: patchControlPlaneDomain(state.controlPlane, patch, source),
|
|
280
|
+
}));
|
|
281
|
+
},
|
|
282
|
+
syncDeliveryAttempt(record, source = 'domain-dispatch') {
|
|
283
|
+
mutateRuntimeStore(store, (state) => ({
|
|
284
|
+
...state,
|
|
285
|
+
deliveries: updateDeliveryDomainFromAttempt(state.deliveries, record, source),
|
|
286
|
+
}));
|
|
287
|
+
},
|
|
288
|
+
syncSurface(record, source = 'domain-dispatch') {
|
|
289
|
+
mutateRuntimeStore(store, (state) => ({
|
|
290
|
+
...state,
|
|
291
|
+
surfaces: updateSurfaceDomainFromRecord(state.surfaces, record, source),
|
|
292
|
+
}));
|
|
293
|
+
},
|
|
294
|
+
syncWatcher(record, source = 'domain-dispatch') {
|
|
295
|
+
mutateRuntimeStore(store, (state) => ({
|
|
296
|
+
...state,
|
|
297
|
+
watchers: updateWatcherDomainFromRecord(state.watchers, record, source),
|
|
298
|
+
}));
|
|
299
|
+
},
|
|
300
|
+
};
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
export type { RuntimeState } from './state.ts';
|
|
304
|
+
export { createInitialRuntimeState } from './state.ts';
|
|
305
|
+
export * from './selectors/index.ts';
|
|
@@ -0,0 +1,359 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Typed selectors for the runtime store.
|
|
3
|
+
*
|
|
4
|
+
* Each domain has a primary selector plus derived selectors for
|
|
5
|
+
* common access patterns. All selectors are pure functions of RuntimeState.
|
|
6
|
+
*
|
|
7
|
+
* No ad hoc direct `set` from arbitrary modules.
|
|
8
|
+
* Selectors are the read path; mutations go through DomainDispatch.
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
import type { RuntimeState } from '../state.ts';
|
|
12
|
+
import type { SessionDomainState } from '@/runtime/index.ts';
|
|
13
|
+
import type { ModelDomainState } from '@/runtime/index.ts';
|
|
14
|
+
import type { ConversationDomainState, TurnState } from '@/runtime/index.ts';
|
|
15
|
+
import type { OverlayDomainState, OverlayId } from '@/runtime/index.ts';
|
|
16
|
+
import type { PanelDomainState, PanelState } from '../domains/panels.ts';
|
|
17
|
+
import type { PermissionDomainState, PermissionMode } from '@/runtime/index.ts';
|
|
18
|
+
import type { TaskDomainState, RuntimeTask, TaskKind } from '@/runtime/index.ts';
|
|
19
|
+
import type { AgentDomainState, RuntimeAgent } from '@/runtime/index.ts';
|
|
20
|
+
import type { ProviderHealthDomainState, CompositeHealthStatus } from '@/runtime/index.ts';
|
|
21
|
+
import type { McpDomainState } from '@/runtime/index.ts';
|
|
22
|
+
import type { PluginDomainState } from '@/runtime/index.ts';
|
|
23
|
+
import type { DaemonDomainState } from '@/runtime/index.ts';
|
|
24
|
+
import type { AcpDomainState } from '@/runtime/index.ts';
|
|
25
|
+
import type { IntegrationDomainState } from '@/runtime/index.ts';
|
|
26
|
+
import type { TelemetryDomainState } from '@/runtime/index.ts';
|
|
27
|
+
import type { GitDomainState } from '@/runtime/index.ts';
|
|
28
|
+
import type { DiscoveryDomainState } from '@/runtime/index.ts';
|
|
29
|
+
import type { IntelligenceDomainState } from '@/runtime/index.ts';
|
|
30
|
+
import type { UiPerfDomainState } from '../domains/ui-perf.ts';
|
|
31
|
+
|
|
32
|
+
// ---------------------------------------------------------------------------
|
|
33
|
+
// Primary domain selectors (one per domain)
|
|
34
|
+
// ---------------------------------------------------------------------------
|
|
35
|
+
|
|
36
|
+
/** Select the full session domain slice. */
|
|
37
|
+
export function selectSession(state: RuntimeState): SessionDomainState {
|
|
38
|
+
return state.session;
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
/** Select the full model domain slice. */
|
|
42
|
+
export function selectModel(state: RuntimeState): ModelDomainState {
|
|
43
|
+
return state.model;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
/** Select the full conversation domain slice. */
|
|
47
|
+
export function selectConversation(state: RuntimeState): ConversationDomainState {
|
|
48
|
+
return state.conversation;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
/** Select the full overlays domain slice. */
|
|
52
|
+
export function selectOverlays(state: RuntimeState): OverlayDomainState {
|
|
53
|
+
return state.overlays;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
/** Select the full panels domain slice. Casts from Record<string,unknown> to PanelDomainState. */
|
|
57
|
+
export function selectPanels(state: RuntimeState): PanelDomainState {
|
|
58
|
+
return state.panels as unknown as PanelDomainState;
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
/** Select the full permissions domain slice. */
|
|
62
|
+
export function selectPermissions(state: RuntimeState): PermissionDomainState {
|
|
63
|
+
return state.permissions;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
/** Select the full tasks domain slice. */
|
|
67
|
+
export function selectTasks(state: RuntimeState): TaskDomainState {
|
|
68
|
+
return state.tasks;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
/** Select the full agents domain slice. */
|
|
72
|
+
export function selectAgents(state: RuntimeState): AgentDomainState {
|
|
73
|
+
return state.agents;
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/** Select the full provider health domain slice. */
|
|
77
|
+
export function selectProviderHealth(state: RuntimeState): ProviderHealthDomainState {
|
|
78
|
+
return state.providerHealth;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
/** Select the full MCP domain slice. */
|
|
82
|
+
export function selectMcp(state: RuntimeState): McpDomainState {
|
|
83
|
+
return state.mcp;
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
/** Select the full plugins domain slice. */
|
|
87
|
+
export function selectPlugins(state: RuntimeState): PluginDomainState {
|
|
88
|
+
return state.plugins;
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
/** Select the full daemon domain slice. */
|
|
92
|
+
export function selectDaemon(state: RuntimeState): DaemonDomainState {
|
|
93
|
+
return state.daemon;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
/** Select the full ACP domain slice. */
|
|
97
|
+
export function selectAcp(state: RuntimeState): AcpDomainState {
|
|
98
|
+
return state.acp;
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
/** Select the full integrations domain slice. */
|
|
102
|
+
export function selectIntegrations(state: RuntimeState): IntegrationDomainState {
|
|
103
|
+
return state.integrations;
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
/** Select the full telemetry domain slice. */
|
|
107
|
+
export function selectTelemetry(state: RuntimeState): TelemetryDomainState {
|
|
108
|
+
return state.telemetry;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
/** Select the full git domain slice. */
|
|
112
|
+
export function selectGit(state: RuntimeState): GitDomainState {
|
|
113
|
+
return state.git;
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
/** Select the full discovery domain slice. */
|
|
117
|
+
export function selectDiscovery(state: RuntimeState): DiscoveryDomainState {
|
|
118
|
+
return state.discovery;
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
/** Select the full intelligence domain slice. */
|
|
122
|
+
export function selectIntelligence(state: RuntimeState): IntelligenceDomainState {
|
|
123
|
+
return state.intelligence;
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
/** Select the full surface/UI performance domain slice. */
|
|
127
|
+
export function selectUiPerf(state: RuntimeState): UiPerfDomainState {
|
|
128
|
+
return state.surfacePerf;
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
/** Select the full surface performance domain slice (SDK-compatible alias). */
|
|
132
|
+
export const selectSurfacePerf = selectUiPerf;
|
|
133
|
+
|
|
134
|
+
// ---------------------------------------------------------------------------
|
|
135
|
+
// Derived selectors
|
|
136
|
+
// ---------------------------------------------------------------------------
|
|
137
|
+
|
|
138
|
+
/** Active model summary — the three most-used fields for display and routing. */
|
|
139
|
+
export interface ActiveModelSummary {
|
|
140
|
+
providerId: string;
|
|
141
|
+
modelId: string;
|
|
142
|
+
displayName: string;
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
/**
|
|
146
|
+
* Returns the active model identity fields.
|
|
147
|
+
* Use this in components that need to display or route by model.
|
|
148
|
+
*/
|
|
149
|
+
export function selectActiveModel(state: RuntimeState): ActiveModelSummary {
|
|
150
|
+
const { activeProviderId, activeModelId, displayName } = state.model;
|
|
151
|
+
return { providerId: activeProviderId, modelId: activeModelId, displayName };
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
/**
|
|
155
|
+
* Returns all tasks currently in 'running' state, ordered by startedAt.
|
|
156
|
+
*/
|
|
157
|
+
export function selectRunningTasks(state: RuntimeState): RuntimeTask[] {
|
|
158
|
+
const { tasks, runningIds } = state.tasks;
|
|
159
|
+
return runningIds
|
|
160
|
+
.map((id) => tasks.get(id))
|
|
161
|
+
.filter((t): t is RuntimeTask => t !== undefined)
|
|
162
|
+
.sort((a, b) => (a.startedAt ?? 0) - (b.startedAt ?? 0));
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
/**
|
|
166
|
+
* Returns all agents currently in non-terminal states.
|
|
167
|
+
*/
|
|
168
|
+
export function selectRunningAgents(state: RuntimeState): RuntimeAgent[] {
|
|
169
|
+
const { agents, activeAgentIds } = state.agents;
|
|
170
|
+
return activeAgentIds
|
|
171
|
+
.map((id) => agents.get(id))
|
|
172
|
+
.filter((a): a is RuntimeAgent => a !== undefined);
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
/**
|
|
176
|
+
* Domain names that have a health record in providerHealth.
|
|
177
|
+
* Used to look up health status by a named domain.
|
|
178
|
+
*/
|
|
179
|
+
export type HealthDomain = 'providerHealth' | 'mcp' | 'daemon' | 'acp' | 'integrations';
|
|
180
|
+
|
|
181
|
+
/**
|
|
182
|
+
* Derives a simplified HealthStatus for a named domain.
|
|
183
|
+
* Returns 'healthy', 'degraded', 'critical', or 'unknown'.
|
|
184
|
+
*/
|
|
185
|
+
export function selectDomainHealth(
|
|
186
|
+
state: RuntimeState,
|
|
187
|
+
domain: HealthDomain,
|
|
188
|
+
): CompositeHealthStatus {
|
|
189
|
+
switch (domain) {
|
|
190
|
+
case 'providerHealth':
|
|
191
|
+
return state.providerHealth.compositeStatus;
|
|
192
|
+
case 'mcp': {
|
|
193
|
+
const connected = state.mcp.connectedServerNames.length;
|
|
194
|
+
const total = state.mcp.servers.size;
|
|
195
|
+
if (total === 0) return 'unknown';
|
|
196
|
+
if (connected === total) return 'healthy';
|
|
197
|
+
if (connected === 0) return 'critical';
|
|
198
|
+
return 'degraded';
|
|
199
|
+
}
|
|
200
|
+
case 'daemon': {
|
|
201
|
+
const ts = state.daemon.transportState;
|
|
202
|
+
if (ts === 'connected') return 'healthy';
|
|
203
|
+
if (ts === 'degraded' || ts === 'reconnecting') return 'degraded';
|
|
204
|
+
if (ts === 'terminal_failure') return 'critical';
|
|
205
|
+
return 'unknown';
|
|
206
|
+
}
|
|
207
|
+
case 'acp': {
|
|
208
|
+
const ts = state.acp.managerTransportState;
|
|
209
|
+
if (ts === 'connected') return 'healthy';
|
|
210
|
+
if (ts === 'degraded' || ts === 'reconnecting') return 'degraded';
|
|
211
|
+
if (ts === 'terminal_failure') return 'critical';
|
|
212
|
+
return 'unknown';
|
|
213
|
+
}
|
|
214
|
+
case 'integrations': {
|
|
215
|
+
const { problemIds, integrations } = state.integrations;
|
|
216
|
+
if (integrations.size === 0) return 'unknown';
|
|
217
|
+
if (problemIds.length === 0) return 'healthy';
|
|
218
|
+
if (problemIds.length === integrations.size) return 'critical';
|
|
219
|
+
return 'degraded';
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
/** Composite system health summary across all tracked subsystems. */
|
|
225
|
+
export interface CompositeSystemHealth {
|
|
226
|
+
status: CompositeHealthStatus;
|
|
227
|
+
/** Per-domain breakdown. */
|
|
228
|
+
domains: Record<HealthDomain, CompositeHealthStatus>;
|
|
229
|
+
/** Whether any domain is in critical state. */
|
|
230
|
+
hasCritical: boolean;
|
|
231
|
+
/** Whether any domain is degraded. */
|
|
232
|
+
hasDegraded: boolean;
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
/**
|
|
236
|
+
* Returns a composite system health summary across all tracked subsystems.
|
|
237
|
+
*/
|
|
238
|
+
export function selectSystemHealth(state: RuntimeState): CompositeSystemHealth {
|
|
239
|
+
const domains: Record<HealthDomain, CompositeHealthStatus> = {
|
|
240
|
+
providerHealth: selectDomainHealth(state, 'providerHealth'),
|
|
241
|
+
mcp: selectDomainHealth(state, 'mcp'),
|
|
242
|
+
daemon: selectDomainHealth(state, 'daemon'),
|
|
243
|
+
acp: selectDomainHealth(state, 'acp'),
|
|
244
|
+
integrations: selectDomainHealth(state, 'integrations'),
|
|
245
|
+
};
|
|
246
|
+
|
|
247
|
+
const values = Object.values(domains) as CompositeHealthStatus[];
|
|
248
|
+
const hasCritical = values.includes('critical');
|
|
249
|
+
const hasDegraded = values.includes('degraded');
|
|
250
|
+
|
|
251
|
+
let status: CompositeHealthStatus;
|
|
252
|
+
if (hasCritical) {
|
|
253
|
+
status = 'critical';
|
|
254
|
+
} else if (hasDegraded) {
|
|
255
|
+
status = 'degraded';
|
|
256
|
+
} else if (values.every((v) => v === 'healthy')) {
|
|
257
|
+
status = 'healthy';
|
|
258
|
+
} else {
|
|
259
|
+
status = 'unknown';
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
return { status, domains, hasCritical, hasDegraded };
|
|
263
|
+
}
|
|
264
|
+
|
|
265
|
+
/**
|
|
266
|
+
* Returns the current permission mode.
|
|
267
|
+
*/
|
|
268
|
+
export function selectPermissionMode(state: RuntimeState): PermissionMode {
|
|
269
|
+
return state.permissions.mode;
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
/**
|
|
273
|
+
* Returns all panels that are currently open.
|
|
274
|
+
*/
|
|
275
|
+
export function selectActivePanels(state: RuntimeState): PanelState[] {
|
|
276
|
+
const result: PanelState[] = [];
|
|
277
|
+
const panelDomain = state.panels as unknown as PanelDomainState;
|
|
278
|
+
for (const panel of panelDomain.panels.values()) {
|
|
279
|
+
if (panel.open) {
|
|
280
|
+
result.push(panel);
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
return result;
|
|
284
|
+
}
|
|
285
|
+
|
|
286
|
+
/**
|
|
287
|
+
* Returns the panel currently holding focus.
|
|
288
|
+
*/
|
|
289
|
+
export function selectFocusedPanel(state: RuntimeState): PanelState | undefined {
|
|
290
|
+
const panelDomain = state.panels as unknown as PanelDomainState;
|
|
291
|
+
return panelDomain.panels.get(panelDomain.focusedPanelId);
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
/**
|
|
295
|
+
* Returns whether any overlay is currently visible.
|
|
296
|
+
*/
|
|
297
|
+
export function selectAnyOverlayVisible(state: RuntimeState): boolean {
|
|
298
|
+
return state.overlays.visibleStack.length > 0;
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
/**
|
|
302
|
+
* Returns whether a specific overlay is visible.
|
|
303
|
+
*/
|
|
304
|
+
export function selectOverlayVisible(
|
|
305
|
+
state: RuntimeState,
|
|
306
|
+
overlayId: OverlayId,
|
|
307
|
+
): boolean {
|
|
308
|
+
return state.overlays.visibleStack.includes(overlayId);
|
|
309
|
+
}
|
|
310
|
+
|
|
311
|
+
/**
|
|
312
|
+
* Returns the current turn state from the conversation domain.
|
|
313
|
+
*/
|
|
314
|
+
export function selectTurnState(
|
|
315
|
+
state: RuntimeState,
|
|
316
|
+
): TurnState {
|
|
317
|
+
return state.conversation.turnState;
|
|
318
|
+
}
|
|
319
|
+
|
|
320
|
+
/**
|
|
321
|
+
* Returns the current store-owned partial tool preview for the active stream.
|
|
322
|
+
*/
|
|
323
|
+
export function selectStreamToolPreview(state: RuntimeState): string | undefined {
|
|
324
|
+
return state.conversation.stream.partialToolPreview;
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
/**
|
|
328
|
+
* Returns whether a turn is currently active (not idle or terminal).
|
|
329
|
+
*/
|
|
330
|
+
export function selectIsTurnActive(state: RuntimeState): boolean {
|
|
331
|
+
const ts = state.conversation.turnState;
|
|
332
|
+
return ts !== 'idle' && ts !== 'completed' && ts !== 'failed' && ts !== 'cancelled';
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
/**
|
|
336
|
+
* Returns whether the session is fully initialized and ready.
|
|
337
|
+
*/
|
|
338
|
+
export function selectIsSessionReady(state: RuntimeState): boolean {
|
|
339
|
+
return (
|
|
340
|
+
state.session.status === 'active' &&
|
|
341
|
+
state.session.recoveryState === 'ready'
|
|
342
|
+
);
|
|
343
|
+
}
|
|
344
|
+
|
|
345
|
+
/**
|
|
346
|
+
* Returns the number of currently running tasks, grouped by kind.
|
|
347
|
+
*/
|
|
348
|
+
export function selectRunningTaskCountByKind(
|
|
349
|
+
state: RuntimeState,
|
|
350
|
+
): Partial<Record<TaskKind, number>> {
|
|
351
|
+
const counts: Record<string, number> = {};
|
|
352
|
+
for (const id of state.tasks.runningIds) {
|
|
353
|
+
const task = state.tasks.tasks.get(id);
|
|
354
|
+
if (task) {
|
|
355
|
+
counts[task.kind] = (counts[task.kind] ?? 0) + 1;
|
|
356
|
+
}
|
|
357
|
+
}
|
|
358
|
+
return counts as Partial<Record<TaskKind, number>>;
|
|
359
|
+
}
|