@hotmeshio/long-tail 0.10.11 → 0.10.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/build/api/escalations/list.d.ts +1 -0
- package/build/api/escalations/list.js +1 -0
- package/build/api/escalations/metadata.d.ts +11 -0
- package/build/api/escalations/metadata.js +27 -7
- package/build/api/scan-codes/config.d.ts +22 -0
- package/build/api/scan-codes/config.js +136 -0
- package/build/api/scan-codes/execute.d.ts +9 -0
- package/build/api/scan-codes/execute.js +372 -0
- package/build/api/scan-codes/index.d.ts +2 -0
- package/build/api/scan-codes/index.js +14 -0
- package/build/lib/db/schemas/026_scan_codes.sql +51 -0
- package/build/lib/db/schemas/027_scan_codes_reindex.sql +23 -0
- package/build/lib/events/system-events.js +4 -0
- package/build/modules/features.d.ts +8 -0
- package/build/modules/features.js +1 -0
- package/build/routes/escalations/list.js +1 -0
- package/build/routes/index.js +2 -0
- package/build/routes/scan-codes.d.ts +2 -0
- package/build/routes/scan-codes.js +138 -0
- package/build/sdk/index.d.ts +4 -0
- package/build/services/escalation/crud.d.ts +1 -1
- package/build/services/escalation/crud.js +4 -2
- package/build/services/escalation/queries.d.ts +1 -0
- package/build/services/escalation/queries.js +2 -0
- package/build/services/escalation/sql.d.ts +11 -6
- package/build/services/escalation/sql.js +20 -20
- package/build/services/scan-code/index.d.ts +4 -0
- package/build/services/scan-code/index.js +21 -0
- package/build/services/scan-code/parse.d.ts +35 -0
- package/build/services/scan-code/parse.js +108 -0
- package/build/services/scan-code/read.d.ts +5 -0
- package/build/services/scan-code/read.js +50 -0
- package/build/services/scan-code/sql.d.ts +10 -0
- package/build/services/scan-code/sql.js +57 -0
- package/build/services/scan-code/validate.d.ts +12 -0
- package/build/services/scan-code/validate.js +78 -0
- package/build/services/scan-code/write.d.ts +26 -0
- package/build/services/scan-code/write.js +71 -0
- package/build/shared/form-validation/index.d.ts +1 -0
- package/build/shared/form-validation/index.js +1 -0
- package/build/shared/form-validation/x-lt-transition.d.ts +47 -0
- package/build/shared/form-validation/x-lt-transition.js +65 -0
- package/build/system/mcp-servers/admin/index.d.ts +1 -0
- package/build/system/mcp-servers/admin/index.js +5 -2
- package/build/system/mcp-servers/admin/scan-codes.d.ts +10 -0
- package/build/system/mcp-servers/admin/scan-codes.js +111 -0
- package/build/system/mcp-servers/admin/schemas.d.ts +232 -14
- package/build/system/mcp-servers/admin/schemas.js +50 -0
- package/build/system/seed/tool-manifests-admin.d.ts +1380 -0
- package/build/system/seed/tool-manifests-admin.js +6 -0
- package/build/tsconfig.tsbuildinfo +1 -1
- package/build/types/events.d.ts +9 -0
- package/build/types/index.d.ts +2 -0
- package/build/types/index.js +10 -1
- package/build/types/scan-code.d.ts +183 -0
- package/build/types/scan-code.js +80 -0
- package/build/types/startup.d.ts +6 -0
- package/dashboard/dist/assets/{AdminDashboard-CkTbRfY9.js → AdminDashboard-Bv3pHBzn.js} +2 -2
- package/dashboard/dist/assets/{AdminDashboard-CkTbRfY9.js.map → AdminDashboard-Bv3pHBzn.js.map} +1 -1
- package/dashboard/dist/assets/{AgentConfigPage-Cm8FRpXi.js → AgentConfigPage-Dk2zlvDb.js} +6 -6
- package/dashboard/dist/assets/{AgentConfigPage-Cm8FRpXi.js.map → AgentConfigPage-Dk2zlvDb.js.map} +1 -1
- package/dashboard/dist/assets/{AgentDetailPage-sQ1-UT46.js → AgentDetailPage-DUno6EGs.js} +2 -2
- package/dashboard/dist/assets/{AgentDetailPage-sQ1-UT46.js.map → AgentDetailPage-DUno6EGs.js.map} +1 -1
- package/dashboard/dist/assets/{AgentsPage-bSx_mdae.js → AgentsPage-CToVu1qj.js} +2 -2
- package/dashboard/dist/assets/{AgentsPage-bSx_mdae.js.map → AgentsPage-CToVu1qj.js.map} +1 -1
- package/dashboard/dist/assets/{AutoGrowTextarea-y-oNY51_.js → AutoGrowTextarea-DgEQeRQw.js} +2 -2
- package/dashboard/dist/assets/{AutoGrowTextarea-y-oNY51_.js.map → AutoGrowTextarea-DgEQeRQw.js.map} +1 -1
- package/dashboard/dist/assets/{AvailableEscalationsPage-8pMC7Xv6.js → AvailableEscalationsPage-DldboL4W.js} +2 -2
- package/dashboard/dist/assets/{AvailableEscalationsPage-8pMC7Xv6.js.map → AvailableEscalationsPage-DldboL4W.js.map} +1 -1
- package/dashboard/dist/assets/BotPicker-DQOpVB4M.js +2 -0
- package/dashboard/dist/assets/{BotPicker-C4uGH2x9.js.map → BotPicker-DQOpVB4M.js.map} +1 -1
- package/dashboard/dist/assets/{CapabilitiesPage-BRoOeKcc.js → CapabilitiesPage-Dmf46PUJ.js} +2 -2
- package/dashboard/dist/assets/{CapabilitiesPage-BRoOeKcc.js.map → CapabilitiesPage-Dmf46PUJ.js.map} +1 -1
- package/dashboard/dist/assets/{CollapsibleSection-CIj8Adc9.js → CollapsibleSection-CDADefUY.js} +2 -2
- package/dashboard/dist/assets/{CollapsibleSection-CIj8Adc9.js.map → CollapsibleSection-CDADefUY.js.map} +1 -1
- package/dashboard/dist/assets/{ConfirmDeleteModal-Ugi_9Ukq.js → ConfirmDeleteModal-CQsJUzEa.js} +2 -2
- package/dashboard/dist/assets/{ConfirmDeleteModal-Ugi_9Ukq.js.map → ConfirmDeleteModal-CQsJUzEa.js.map} +1 -1
- package/dashboard/dist/assets/{CopyableId-GUEdiiL5.js → CopyableId-4Lqlc5cU.js} +2 -2
- package/dashboard/dist/assets/{CopyableId-GUEdiiL5.js.map → CopyableId-4Lqlc5cU.js.map} +1 -1
- package/dashboard/dist/assets/{CountdownTimer-D3t0XMhE.js → CountdownTimer-DPjIkerB.js} +2 -2
- package/dashboard/dist/assets/{CountdownTimer-D3t0XMhE.js.map → CountdownTimer-DPjIkerB.js.map} +1 -1
- package/dashboard/dist/assets/{CredentialsPage-B73Si6K1.js → CredentialsPage-8LIEvomi.js} +2 -2
- package/dashboard/dist/assets/{CredentialsPage-B73Si6K1.js.map → CredentialsPage-8LIEvomi.js.map} +1 -1
- package/dashboard/dist/assets/{CronLabel-Ca1aHolt.js → CronLabel-CK3WSsM5.js} +2 -2
- package/dashboard/dist/assets/{CronLabel-Ca1aHolt.js.map → CronLabel-CK3WSsM5.js.map} +1 -1
- package/dashboard/dist/assets/{CustomDurationPicker-_9E9x1YN.js → CustomDurationPicker-FPmlA6cE.js} +2 -2
- package/dashboard/dist/assets/{CustomDurationPicker-_9E9x1YN.js.map → CustomDurationPicker-FPmlA6cE.js.map} +1 -1
- package/dashboard/dist/assets/{DataTable-BTu2AaEl.js → DataTable-Bir0Xs1p.js} +2 -2
- package/dashboard/dist/assets/{DataTable-BTu2AaEl.js.map → DataTable-Bir0Xs1p.js.map} +1 -1
- package/dashboard/dist/assets/{DropZone-NYn6TWHz.js → DropZone-CL9gA7pu.js} +2 -2
- package/dashboard/dist/assets/{DropZone-NYn6TWHz.js.map → DropZone-CL9gA7pu.js.map} +1 -1
- package/dashboard/dist/assets/{ElapsedCell-karxia93.js → ElapsedCell-BZVkVxE0.js} +2 -2
- package/dashboard/dist/assets/{ElapsedCell-karxia93.js.map → ElapsedCell-BZVkVxE0.js.map} +1 -1
- package/dashboard/dist/assets/{EmptyState-BcsfPq9T.js → EmptyState-lpUFYfun.js} +2 -2
- package/dashboard/dist/assets/{EmptyState-BcsfPq9T.js.map → EmptyState-lpUFYfun.js.map} +1 -1
- package/dashboard/dist/assets/{EscalationListSchemaPage-CDaNmbUA.js → EscalationListSchemaPage-kYLdUtZX.js} +3 -3
- package/dashboard/dist/assets/{EscalationListSchemaPage-CDaNmbUA.js.map → EscalationListSchemaPage-kYLdUtZX.js.map} +1 -1
- package/dashboard/dist/assets/{EscalationSchemaPage-k-2hFT2t.js → EscalationSchemaPage-kUmCDivo.js} +3 -3
- package/dashboard/dist/assets/{EscalationSchemaPage-k-2hFT2t.js.map → EscalationSchemaPage-kUmCDivo.js.map} +1 -1
- package/dashboard/dist/assets/{EscalationsOverview-C1e7IPn_.js → EscalationsOverview-D17auO-m.js} +2 -2
- package/dashboard/dist/assets/{EscalationsOverview-C1e7IPn_.js.map → EscalationsOverview-D17auO-m.js.map} +1 -1
- package/dashboard/dist/assets/{EventTable-CIrrtL7_.js → EventTable-CwPWl163.js} +2 -2
- package/dashboard/dist/assets/{EventTable-CIrrtL7_.js.map → EventTable-CwPWl163.js.map} +1 -1
- package/dashboard/dist/assets/{FilterBar-CzjtH74v.js → FilterBar-D7GghUsU.js} +2 -2
- package/dashboard/dist/assets/{FilterBar-CzjtH74v.js.map → FilterBar-D7GghUsU.js.map} +1 -1
- package/dashboard/dist/assets/{GraphInvokePage-LMpWw8z1.js → GraphInvokePage-D11uOnZi.js} +2 -2
- package/dashboard/dist/assets/{GraphInvokePage-LMpWw8z1.js.map → GraphInvokePage-D11uOnZi.js.map} +1 -1
- package/dashboard/dist/assets/{HomePage-Kl2DBG6l.js → HomePage-Bcq10Bxx.js} +2 -2
- package/dashboard/dist/assets/{HomePage-Kl2DBG6l.js.map → HomePage-Bcq10Bxx.js.map} +1 -1
- package/dashboard/dist/assets/ListToolbar-IPXsTb3Q.js +2 -0
- package/dashboard/dist/assets/{ListToolbar-B2fub0DY.js.map → ListToolbar-IPXsTb3Q.js.map} +1 -1
- package/dashboard/dist/assets/{McpOverview-odYnCZCC.js → McpOverview-Dx2j0KkF.js} +2 -2
- package/dashboard/dist/assets/{McpOverview-odYnCZCC.js.map → McpOverview-Dx2j0KkF.js.map} +1 -1
- package/dashboard/dist/assets/{McpQueryDetailPage-BtqwHUAg.js → McpQueryDetailPage-CzF_bna8.js} +3 -3
- package/dashboard/dist/assets/{McpQueryDetailPage-BtqwHUAg.js.map → McpQueryDetailPage-CzF_bna8.js.map} +1 -1
- package/dashboard/dist/assets/{McpQueryPage-CPkVwNIK.js → McpQueryPage-CNsuiw_q.js} +2 -2
- package/dashboard/dist/assets/{McpQueryPage-CPkVwNIK.js.map → McpQueryPage-CNsuiw_q.js.map} +1 -1
- package/dashboard/dist/assets/{McpRunDetailPage-D-Rz9MRw.js → McpRunDetailPage-BJguEMS0.js} +2 -2
- package/dashboard/dist/assets/{McpRunDetailPage-D-Rz9MRw.js.map → McpRunDetailPage-BJguEMS0.js.map} +1 -1
- package/dashboard/dist/assets/{McpRunsPage-rdpZ2yMh.js → McpRunsPage-CK96s3Nt.js} +2 -2
- package/dashboard/dist/assets/{McpRunsPage-rdpZ2yMh.js.map → McpRunsPage-CK96s3Nt.js.map} +1 -1
- package/dashboard/dist/assets/{Modal-Dr1Xy0j0.js → Modal-BU7No9NH.js} +2 -2
- package/dashboard/dist/assets/{Modal-Dr1Xy0j0.js.map → Modal-BU7No9NH.js.map} +1 -1
- package/dashboard/dist/assets/{NamespacePill-GwO-WfhX.js → NamespacePill-B9Vc_Pz2.js} +2 -2
- package/dashboard/dist/assets/{NamespacePill-GwO-WfhX.js.map → NamespacePill-B9Vc_Pz2.js.map} +1 -1
- package/dashboard/dist/assets/{OperationsPage-DlyGLPAs.js → OperationsPage-DvWrLuH6.js} +2 -2
- package/dashboard/dist/assets/{OperationsPage-DlyGLPAs.js.map → OperationsPage-DvWrLuH6.js.map} +1 -1
- package/dashboard/dist/assets/{OperatorDashboard-Csei5vj-.js → OperatorDashboard-C-jE0IRA.js} +2 -2
- package/dashboard/dist/assets/{OperatorDashboard-Csei5vj-.js.map → OperatorDashboard-C-jE0IRA.js.map} +1 -1
- package/dashboard/dist/assets/{PageHeader-Bo9BU9pK.js → PageHeader-Ce4GcIYo.js} +2 -2
- package/dashboard/dist/assets/{PageHeader-Bo9BU9pK.js.map → PageHeader-Ce4GcIYo.js.map} +1 -1
- package/dashboard/dist/assets/{PageHeaderWithStats-8_5cOSKL.js → PageHeaderWithStats-Ck0KZvXD.js} +2 -2
- package/dashboard/dist/assets/{PageHeaderWithStats-8_5cOSKL.js.map → PageHeaderWithStats-Ck0KZvXD.js.map} +1 -1
- package/dashboard/dist/assets/{PersonaDetailPage--ZL6Or6v.js → PersonaDetailPage-CJ6jqo7h.js} +2 -2
- package/dashboard/dist/assets/{PersonaDetailPage--ZL6Or6v.js.map → PersonaDetailPage-CJ6jqo7h.js.map} +1 -1
- package/dashboard/dist/assets/{PersonasPage-Bdcoay3P.js → PersonasPage-D8hL3kL5.js} +2 -2
- package/dashboard/dist/assets/{PersonasPage-Bdcoay3P.js.map → PersonasPage-D8hL3kL5.js.map} +1 -1
- package/dashboard/dist/assets/{PriorityBadge-CCERr9vQ.js → PriorityBadge-BETdj4M-.js} +2 -2
- package/dashboard/dist/assets/{PriorityBadge-CCERr9vQ.js.map → PriorityBadge-BETdj4M-.js.map} +1 -1
- package/dashboard/dist/assets/{ProcessDetailPage-HrmVQq7S.js → ProcessDetailPage-Vnx8Z5_y.js} +2 -2
- package/dashboard/dist/assets/{ProcessDetailPage-HrmVQq7S.js.map → ProcessDetailPage-Vnx8Z5_y.js.map} +1 -1
- package/dashboard/dist/assets/{ProcessesListPage-_xmj6Bo-.js → ProcessesListPage-DRYtvS3N.js} +2 -2
- package/dashboard/dist/assets/{ProcessesListPage-_xmj6Bo-.js.map → ProcessesListPage-DRYtvS3N.js.map} +1 -1
- package/dashboard/dist/assets/{RoleDetailPage-C0ju2-4K.js → RoleDetailPage-BKkUvTO-.js} +3 -3
- package/dashboard/dist/assets/{RoleDetailPage-C0ju2-4K.js.map → RoleDetailPage-BKkUvTO-.js.map} +1 -1
- package/dashboard/dist/assets/{RolePill-CQlnEWkK.js → RolePill-CnuBPhPw.js} +2 -2
- package/dashboard/dist/assets/{RolePill-CQlnEWkK.js.map → RolePill-CnuBPhPw.js.map} +1 -1
- package/dashboard/dist/assets/{RolesPage-CKluVSpB.js → RolesPage-BHzWK9n6.js} +2 -2
- package/dashboard/dist/assets/{RolesPage-CKluVSpB.js.map → RolesPage-BHzWK9n6.js.map} +1 -1
- package/dashboard/dist/assets/{RowActions-BA9L9djf.js → RowActions-eYrzgQSj.js} +2 -2
- package/dashboard/dist/assets/{RowActions-BA9L9djf.js.map → RowActions-eYrzgQSj.js.map} +1 -1
- package/dashboard/dist/assets/{RunAsSelector-DdfecQ1U.js → RunAsSelector-CS3KQ-BF.js} +2 -2
- package/dashboard/dist/assets/{RunAsSelector-DdfecQ1U.js.map → RunAsSelector-CS3KQ-BF.js.map} +1 -1
- package/dashboard/dist/assets/ScanCodesPage-BW4P4zWf.js +2 -0
- package/dashboard/dist/assets/ScanCodesPage-BW4P4zWf.js.map +1 -0
- package/dashboard/dist/assets/ScanSchemeDetailPage-BLykA4j-.js +2 -0
- package/dashboard/dist/assets/ScanSchemeDetailPage-BLykA4j-.js.map +1 -0
- package/dashboard/dist/assets/{ScopeBadge-BBYkevuR.js → ScopeBadge-BUpYpS3x.js} +2 -2
- package/dashboard/dist/assets/{ScopeBadge-BBYkevuR.js.map → ScopeBadge-BUpYpS3x.js.map} +1 -1
- package/dashboard/dist/assets/{StatCard-Ca-ngCaD.js → StatCard-BXQ8dD9Y.js} +2 -2
- package/dashboard/dist/assets/{StatCard-Ca-ngCaD.js.map → StatCard-BXQ8dD9Y.js.map} +1 -1
- package/dashboard/dist/assets/{StatusBadge-BwUvykDo.js → StatusBadge-DkgllZHv.js} +2 -2
- package/dashboard/dist/assets/{StatusBadge-BwUvykDo.js.map → StatusBadge-DkgllZHv.js.map} +1 -1
- package/dashboard/dist/assets/{StickyPagination-cLddIdtT.js → StickyPagination-hMrnLXde.js} +2 -2
- package/dashboard/dist/assets/{StickyPagination-cLddIdtT.js.map → StickyPagination-hMrnLXde.js.map} +1 -1
- package/dashboard/dist/assets/{StreamMessageDetail-CZXWDawC.js → StreamMessageDetail-DyJyZwBl.js} +2 -2
- package/dashboard/dist/assets/{StreamMessageDetail-CZXWDawC.js.map → StreamMessageDetail-DyJyZwBl.js.map} +1 -1
- package/dashboard/dist/assets/{SwimlaneTimeline-fWY0gaf3.js → SwimlaneTimeline-BlzV74V5.js} +2 -2
- package/dashboard/dist/assets/{SwimlaneTimeline-fWY0gaf3.js.map → SwimlaneTimeline-BlzV74V5.js.map} +1 -1
- package/dashboard/dist/assets/{TagInput-CDKbslLx.js → TagInput-BbZ25nNe.js} +2 -2
- package/dashboard/dist/assets/{TagInput-CDKbslLx.js.map → TagInput-BbZ25nNe.js.map} +1 -1
- package/dashboard/dist/assets/{TaskDetailPage-BjE4G2yn.js → TaskDetailPage-B0p_Z4J_.js} +2 -2
- package/dashboard/dist/assets/{TaskDetailPage-BjE4G2yn.js.map → TaskDetailPage-B0p_Z4J_.js.map} +1 -1
- package/dashboard/dist/assets/{TaskQueuePill-G3RuYRNZ.js → TaskQueuePill-D0QKBrN3.js} +2 -2
- package/dashboard/dist/assets/{TaskQueuePill-G3RuYRNZ.js.map → TaskQueuePill-D0QKBrN3.js.map} +1 -1
- package/dashboard/dist/assets/{TasksListPage-KAhmCWB2.js → TasksListPage-CiGR2QiQ.js} +2 -2
- package/dashboard/dist/assets/{TasksListPage-KAhmCWB2.js.map → TasksListPage-CiGR2QiQ.js.map} +1 -1
- package/dashboard/dist/assets/TimeAgo-D_DA9ucC.js +2 -0
- package/dashboard/dist/assets/{TimeAgo-C_H2TyZw.js.map → TimeAgo-D_DA9ucC.js.map} +1 -1
- package/dashboard/dist/assets/{TimestampCell-COG_4Flg.js → TimestampCell-C7rkC9nh.js} +2 -2
- package/dashboard/dist/assets/{TimestampCell-COG_4Flg.js.map → TimestampCell-C7rkC9nh.js.map} +1 -1
- package/dashboard/dist/assets/{ToolPill-ChSyRJZC.js → ToolPill-8xY9rkoc.js} +2 -2
- package/dashboard/dist/assets/{ToolPill-ChSyRJZC.js.map → ToolPill-8xY9rkoc.js.map} +1 -1
- package/dashboard/dist/assets/{ToolTestPanel-BPdJECW0.js → ToolTestPanel-E8efYGYs.js} +2 -2
- package/dashboard/dist/assets/{ToolTestPanel-BPdJECW0.js.map → ToolTestPanel-E8efYGYs.js.map} +1 -1
- package/dashboard/dist/assets/{TopicDetailPage-DAqx5JqA.js → TopicDetailPage-B455XrRc.js} +3 -3
- package/dashboard/dist/assets/{TopicDetailPage-DAqx5JqA.js.map → TopicDetailPage-B455XrRc.js.map} +1 -1
- package/dashboard/dist/assets/TopicsPage-1VAc29Qw.js +2 -0
- package/dashboard/dist/assets/{TopicsPage-DoGqAdPm.js.map → TopicsPage-1VAc29Qw.js.map} +1 -1
- package/dashboard/dist/assets/UserName-DikzjQHJ.js +2 -0
- package/dashboard/dist/assets/{UserName-CKO_rk1R.js.map → UserName-DikzjQHJ.js.map} +1 -1
- package/dashboard/dist/assets/{WorkflowExecutionPage-D3VQ9iQV.js → WorkflowExecutionPage-C15GSAoe.js} +2 -2
- package/dashboard/dist/assets/{WorkflowExecutionPage-D3VQ9iQV.js.map → WorkflowExecutionPage-C15GSAoe.js.map} +1 -1
- package/dashboard/dist/assets/{WorkflowPill-CNbwug5p.js → WorkflowPill-Da406nEj.js} +2 -2
- package/dashboard/dist/assets/{WorkflowPill-CNbwug5p.js.map → WorkflowPill-Da406nEj.js.map} +1 -1
- package/dashboard/dist/assets/{WorkflowsDashboard-DdJ86We6.js → WorkflowsDashboard-BMQd_0tW.js} +2 -2
- package/dashboard/dist/assets/{WorkflowsDashboard-DdJ86We6.js.map → WorkflowsDashboard-BMQd_0tW.js.map} +1 -1
- package/dashboard/dist/assets/{WorkflowsOverview-ZfFBzePp.js → WorkflowsOverview-CdxjVifp.js} +2 -2
- package/dashboard/dist/assets/{WorkflowsOverview-ZfFBzePp.js.map → WorkflowsOverview-CdxjVifp.js.map} +1 -1
- package/dashboard/dist/assets/{YamlWorkflowDetailPage-4bd5yXdA.js → YamlWorkflowDetailPage-DNVffIXa.js} +13 -13
- package/dashboard/dist/assets/{YamlWorkflowDetailPage-4bd5yXdA.js.map → YamlWorkflowDetailPage-DNVffIXa.js.map} +1 -1
- package/dashboard/dist/assets/{YamlWorkflowsPage-iHPNXjQj.js → YamlWorkflowsPage-BGP8wuos.js} +2 -2
- package/dashboard/dist/assets/{YamlWorkflowsPage-iHPNXjQj.js.map → YamlWorkflowsPage-BGP8wuos.js.map} +1 -1
- package/dashboard/dist/assets/{agents-DjD5U3Wb.js → agents-BZJLIJ4h.js} +2 -2
- package/dashboard/dist/assets/{agents-DjD5U3Wb.js.map → agents-BZJLIJ4h.js.map} +1 -1
- package/dashboard/dist/assets/{bots-DiljVapH.js → bots-ClLcDGJb.js} +2 -2
- package/dashboard/dist/assets/{bots-DiljVapH.js.map → bots-ClLcDGJb.js.map} +1 -1
- package/dashboard/dist/assets/capabilities-IaCcS7ge.js +2 -0
- package/dashboard/dist/assets/{capabilities-DV_5ghHT.js.map → capabilities-IaCcS7ge.js.map} +1 -1
- package/dashboard/dist/assets/{controlplane-BKMvfWCB.js → controlplane-Zi4m_MSx.js} +2 -2
- package/dashboard/dist/assets/{controlplane-BKMvfWCB.js.map → controlplane-Zi4m_MSx.js.map} +1 -1
- package/dashboard/dist/assets/{escalation-columns-BQpCaJId.js → escalation-columns-BY2mg9DY.js} +2 -2
- package/dashboard/dist/assets/{escalation-columns-BQpCaJId.js.map → escalation-columns-BY2mg9DY.js.map} +1 -1
- package/dashboard/dist/assets/{index-Tx_ETzcH.js → index-BqGnhkh0.js} +2 -2
- package/dashboard/dist/assets/{index-Tx_ETzcH.js.map → index-BqGnhkh0.js.map} +1 -1
- package/dashboard/dist/assets/index-BzkE48xJ.js +6 -0
- package/dashboard/dist/assets/index-BzkE48xJ.js.map +1 -0
- package/dashboard/dist/assets/{index-CI8rrKjx.js → index-C3o4OisO.js} +2 -2
- package/dashboard/dist/assets/{index-CI8rrKjx.js.map → index-C3o4OisO.js.map} +1 -1
- package/dashboard/dist/assets/{index-BO-7S9Xw.js → index-CJu2PBNx.js} +2 -2
- package/dashboard/dist/assets/{index-BO-7S9Xw.js.map → index-CJu2PBNx.js.map} +1 -1
- package/dashboard/dist/assets/{index-CItsikDw.js → index-CLmZaNTK.js} +2 -2
- package/dashboard/dist/assets/{index-CItsikDw.js.map → index-CLmZaNTK.js.map} +1 -1
- package/dashboard/dist/assets/index-CfAi1OsI.js +65 -0
- package/dashboard/dist/assets/index-CfAi1OsI.js.map +1 -0
- package/dashboard/dist/assets/{index-BaV3l0UE.js → index-CmnNqpWg.js} +2 -2
- package/dashboard/dist/assets/{index-BaV3l0UE.js.map → index-CmnNqpWg.js.map} +1 -1
- package/dashboard/dist/assets/{index-nIrYejxe.js → index-CvNBdkB1.js} +3 -3
- package/dashboard/dist/assets/{index-nIrYejxe.js.map → index-CvNBdkB1.js.map} +1 -1
- package/dashboard/dist/assets/{index-xZqQxqu2.js → index-D0zFReGL.js} +2 -2
- package/dashboard/dist/assets/{index-xZqQxqu2.js.map → index-D0zFReGL.js.map} +1 -1
- package/dashboard/dist/assets/{index-CStR4uIU.js → index-Dldi3Q3M.js} +2 -2
- package/dashboard/dist/assets/{index-CStR4uIU.js.map → index-Dldi3Q3M.js.map} +1 -1
- package/dashboard/dist/assets/{index-DhATO1cS.js → index-kiKZresb.js} +2 -2
- package/dashboard/dist/assets/{index-DhATO1cS.js.map → index-kiKZresb.js.map} +1 -1
- package/dashboard/dist/assets/index-mKcQGi2B.js +3 -0
- package/dashboard/dist/assets/index-mKcQGi2B.js.map +1 -0
- package/dashboard/dist/assets/{index-BsOxMMmb.js → index-yGNt29V9.js} +2 -2
- package/dashboard/dist/assets/{index-BsOxMMmb.js.map → index-yGNt29V9.js.map} +1 -1
- package/dashboard/dist/assets/index-zQiUPfxA.css +1 -0
- package/dashboard/dist/assets/{knowledge-BocTnSiA.js → knowledge-DWLxGTib.js} +2 -2
- package/dashboard/dist/assets/{knowledge-BocTnSiA.js.map → knowledge-DWLxGTib.js.map} +1 -1
- package/dashboard/dist/assets/{mcp-C1KBjKQ_.js → mcp-B6AARZ2I.js} +2 -2
- package/dashboard/dist/assets/{mcp-C1KBjKQ_.js.map → mcp-B6AARZ2I.js.map} +1 -1
- package/dashboard/dist/assets/{mcp-query-B3cjukkA.js → mcp-query-DrkvBU3a.js} +2 -2
- package/dashboard/dist/assets/{mcp-query-B3cjukkA.js.map → mcp-query-DrkvBU3a.js.map} +1 -1
- package/dashboard/dist/assets/{personas-DiA2bJaX.js → personas-Cmz2SAEU.js} +2 -2
- package/dashboard/dist/assets/{personas-DiA2bJaX.js.map → personas-Cmz2SAEU.js.map} +1 -1
- package/dashboard/dist/assets/{pipelines-Dt2d2EFR.js → pipelines-CSgfVCMy.js} +2 -2
- package/dashboard/dist/assets/{pipelines-Dt2d2EFR.js.map → pipelines-CSgfVCMy.js.map} +1 -1
- package/dashboard/dist/assets/{tasks-cDh2hNml.js → tasks-UOtUkDk-.js} +2 -2
- package/dashboard/dist/assets/{tasks-cDh2hNml.js.map → tasks-UOtUkDk-.js.map} +1 -1
- package/dashboard/dist/assets/{topics-yFlGF-u1.js → topics-Df5hGh6o.js} +2 -2
- package/dashboard/dist/assets/{topics-yFlGF-u1.js.map → topics-Df5hGh6o.js.map} +1 -1
- package/dashboard/dist/assets/{useDebouncedValue-BA5S7V54.js → useDebouncedValue-C4P2jQuh.js} +2 -2
- package/dashboard/dist/assets/{useDebouncedValue-BA5S7V54.js.map → useDebouncedValue-C4P2jQuh.js.map} +1 -1
- package/dashboard/dist/assets/{useEventHooks-D2R_ckS8.js → useEventHooks-PDbuSJ12.js} +2 -2
- package/dashboard/dist/assets/{useEventHooks-D2R_ckS8.js.map → useEventHooks-PDbuSJ12.js.map} +1 -1
- package/dashboard/dist/assets/{useFilterParams-B7suPsIK.js → useFilterParams-crmlBw_l.js} +2 -2
- package/dashboard/dist/assets/{useFilterParams-B7suPsIK.js.map → useFilterParams-crmlBw_l.js.map} +1 -1
- package/dashboard/dist/assets/{useNamespace-u-V1GVUD.js → useNamespace-tZSOlge3.js} +2 -2
- package/dashboard/dist/assets/{useNamespace-u-V1GVUD.js.map → useNamespace-tZSOlge3.js.map} +1 -1
- package/dashboard/dist/assets/{useYamlActivityEvents-BhOZeqgE.js → useYamlActivityEvents-CINLzE32.js} +2 -2
- package/dashboard/dist/assets/{useYamlActivityEvents-BhOZeqgE.js.map → useYamlActivityEvents-CINLzE32.js.map} +1 -1
- package/dashboard/dist/assets/{users-BoXPwdee.js → users-G8qwyZKS.js} +2 -2
- package/dashboard/dist/assets/{users-BoXPwdee.js.map → users-G8qwyZKS.js.map} +1 -1
- package/dashboard/dist/assets/{vendor-icons-D71XjkNy.js → vendor-icons-BpZiWH2f.js} +135 -130
- package/dashboard/dist/assets/vendor-icons-BpZiWH2f.js.map +1 -0
- package/dashboard/dist/assets/{vendor-query-B2UbickB.js → vendor-query-RUZdMvN6.js} +2 -2
- package/dashboard/dist/assets/{vendor-query-B2UbickB.js.map → vendor-query-RUZdMvN6.js.map} +1 -1
- package/dashboard/dist/assets/{vendor-react-C1YOyCSV.js → vendor-react-CdqEC2zv.js} +2 -2
- package/dashboard/dist/assets/{vendor-react-C1YOyCSV.js.map → vendor-react-CdqEC2zv.js.map} +1 -1
- package/dashboard/dist/assets/{workflows-mCoyKuLZ.js → workflows-DbPqi1TW.js} +2 -2
- package/dashboard/dist/assets/{workflows-mCoyKuLZ.js.map → workflows-DbPqi1TW.js.map} +1 -1
- package/dashboard/dist/assets/{yaml-workflows-CWxXGDpn.js → yaml-workflows-DozD8hpR.js} +2 -2
- package/dashboard/dist/assets/{yaml-workflows-CWxXGDpn.js.map → yaml-workflows-DozD8hpR.js.map} +1 -1
- package/dashboard/dist/index.html +5 -5
- package/docs/hitl/x-lt-transition.md +105 -0
- package/docs/scan-codes.md +243 -0
- package/package.json +2 -2
- package/dashboard/dist/assets/BotPicker-C4uGH2x9.js +0 -2
- package/dashboard/dist/assets/ListToolbar-B2fub0DY.js +0 -2
- package/dashboard/dist/assets/TimeAgo-C_H2TyZw.js +0 -2
- package/dashboard/dist/assets/TopicsPage-DoGqAdPm.js +0 -2
- package/dashboard/dist/assets/UserName-CKO_rk1R.js +0 -2
- package/dashboard/dist/assets/capabilities-DV_5ghHT.js +0 -2
- package/dashboard/dist/assets/index-B-WkiNRN.js +0 -6
- package/dashboard/dist/assets/index-B-WkiNRN.js.map +0 -1
- package/dashboard/dist/assets/index-DbTD-dio.js +0 -63
- package/dashboard/dist/assets/index-DbTD-dio.js.map +0 -1
- package/dashboard/dist/assets/index-DnlsDaAw.css +0 -1
- package/dashboard/dist/assets/index-kzIIeVbx.js +0 -5
- package/dashboard/dist/assets/index-kzIIeVbx.js.map +0 -1
- package/dashboard/dist/assets/vendor-icons-D71XjkNy.js.map +0 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index-CI8rrKjx.js","sources":["../../src/components/common/layout/StepIndicator.tsx","../../src/pages/mcp/servers/detail/server-form-types.ts","../../src/pages/mcp/servers/detail/TransportStep.tsx","../../src/pages/mcp/servers/detail/DiscoveryStep.tsx","../../src/pages/mcp/servers/detail/TestStep.tsx","../../src/pages/mcp/servers/detail/ReviewStep.tsx","../../src/pages/mcp/servers/detail/McpServerDetailPage.tsx"],"sourcesContent":["interface StepIndicatorProps {\n steps: string[];\n currentStep: number;\n onStepClick?: (step: number) => void;\n}\n\nexport function StepIndicator({ steps, currentStep, onStepClick }: StepIndicatorProps) {\n return (\n <div className=\"flex items-center justify-center gap-1 pb-4 border-b border-surface-border mb-4\">\n {steps.map((label, i) => {\n const done = i < currentStep;\n const active = i === currentStep;\n const clickable = !!onStepClick;\n return (\n <div key={label} className=\"flex items-center gap-1\">\n {i > 0 && (\n <div className={`w-4 h-px ${done ? 'bg-accent' : 'bg-surface-border'}`} />\n )}\n <button\n type=\"button\"\n onClick={clickable ? () => onStepClick(i) : undefined}\n className={`flex items-center gap-1 ${clickable ? 'cursor-pointer' : 'cursor-default'}`}\n >\n <span\n className={`w-5 h-5 rounded-full text-2xs font-semibold flex items-center justify-center shrink-0 transition-colors ${\n active\n ? 'bg-accent text-text-inverse'\n : done\n ? 'bg-accent-muted text-accent'\n : 'bg-surface-sunken text-text-tertiary'\n } ${clickable && !active ? 'hover:bg-accent-muted hover:text-accent' : ''}`}\n >\n {i + 1}\n </span>\n <span\n className={`text-2xs font-semibold uppercase tracking-wider whitespace-nowrap transition-colors ${\n active ? 'text-text-primary' : 'text-text-tertiary'\n } ${clickable && !active ? 'hover:text-text-primary' : ''}`}\n >\n {label}\n </span>\n </button>\n </div>\n );\n })}\n </div>\n );\n}\n","import type { McpServerRecord, McpToolManifest } from '../../../../api/types';\n\nexport interface ServerFormState {\n name: string;\n description: string;\n mode: 'in-process' | 'network' | 'local-process';\n transport_type: 'stdio' | 'sse' | 'streamable-http';\n // stdio fields\n command: string;\n args: string;\n env_vars: string;\n // network fields\n url: string;\n // shared\n auto_connect: boolean;\n tags: string[];\n compile_hints: string;\n credential_providers: string[];\n discovered_tools: McpToolManifest[] | null;\n}\n\nexport const EMPTY_FORM: ServerFormState = {\n name: '',\n description: '',\n mode: 'network',\n transport_type: 'sse',\n command: '',\n args: '',\n env_vars: '{}',\n url: '',\n auto_connect: false,\n tags: [],\n compile_hints: '',\n credential_providers: [],\n discovered_tools: null,\n};\n\nexport function serverToForm(s: McpServerRecord): ServerFormState {\n const config = s.transport_config ?? {};\n const isBuiltin = !!(config as any).builtin;\n\n let mode: ServerFormState['mode'] = 'network';\n if (isBuiltin) mode = 'in-process';\n else if (s.transport_type === 'stdio') mode = 'local-process';\n\n return {\n name: s.name,\n description: s.description ?? '',\n mode,\n transport_type: s.transport_type,\n command: (config as any).command ?? '',\n args: ((config as any).args ?? []).join(', '),\n env_vars: (config as any).env ? JSON.stringify((config as any).env, null, 2) : '{}',\n url: (config as any).url ?? '',\n auto_connect: s.auto_connect,\n tags: s.tags ?? [],\n compile_hints: (s as any).compile_hints ?? '',\n credential_providers: s.credential_providers ?? [],\n discovered_tools: s.tool_manifest ?? null,\n };\n}\n\nexport function formToPayload(form: ServerFormState) {\n let transport_config: Record<string, unknown> = {};\n\n if (form.mode === 'local-process') {\n transport_config = {\n command: form.command.trim(),\n args: form.args.split(',').map((a) => a.trim()).filter(Boolean),\n env: form.env_vars.trim() ? JSON.parse(form.env_vars) : undefined,\n };\n } else if (form.mode === 'network') {\n transport_config = { url: form.url.trim() };\n }\n // in-process: transport_config stays empty (server manages it)\n\n return {\n name: form.name.trim(),\n description: form.description.trim() || undefined,\n transport_type: form.mode === 'local-process' ? 'stdio' as const : form.transport_type,\n transport_config,\n auto_connect: form.auto_connect,\n tags: form.tags,\n compile_hints: form.compile_hints.trim() || undefined,\n credential_providers: form.credential_providers.length > 0 ? form.credential_providers : undefined,\n };\n}\n\nexport const STEP_LABELS = ['Transport', 'Discovery', 'Test', 'Review'];\n\nexport function isStepValid(step: number, form: ServerFormState): boolean {\n if (step === 1) {\n if (!form.name.trim()) return false;\n if (form.mode === 'network' && !form.url.trim()) return false;\n if (form.mode === 'local-process' && !form.command.trim()) return false;\n return true;\n }\n return true;\n}\n\nexport const labelCls = 'label';\nexport const hintCls = 'hint';\n","import type { ServerFormState } from './server-form-types';\nimport { labelCls, hintCls } from './server-form-types';\n\ninterface Props {\n form: ServerFormState;\n set: (field: keyof ServerFormState, value: any) => void;\n isBuiltin: boolean;\n}\n\nconst modes = [\n { value: 'in-process', label: 'In-Process', hint: 'Built-in server running inside the app' },\n { value: 'network', label: 'Network Service', hint: 'Remote server via SSE or Streamable HTTP' },\n { value: 'local-process', label: 'Local Process', hint: 'Spawn a local command via stdio' },\n] as const;\n\nexport function TransportStep({ form, set, isBuiltin }: Props) {\n return (\n <div className=\"space-y-5\">\n {/* Mode selector */}\n <div>\n <label className={labelCls}>Connection Mode</label>\n <div className=\"grid grid-cols-3 gap-3 mt-1\">\n {modes.map((m) => {\n const active = form.mode === m.value;\n const disabled = isBuiltin && m.value !== 'in-process';\n return (\n <button\n key={m.value}\n type=\"button\"\n disabled={disabled}\n onClick={() => {\n set('mode', m.value);\n if (m.value === 'local-process') set('transport_type', 'stdio');\n if (m.value === 'network') set('transport_type', 'sse');\n }}\n className={`text-left p-3 rounded-md border transition-colors ${\n active\n ? 'border-accent bg-accent/5'\n : disabled\n ? 'border-surface-border bg-surface-sunken opacity-50 cursor-not-allowed'\n : 'border-surface-border hover:border-text-tertiary cursor-pointer'\n }`}\n >\n <span className={`text-xs font-medium ${active ? 'text-accent' : 'text-text-primary'}`}>\n {m.label}\n </span>\n <span className=\"block text-2xs text-text-tertiary mt-0.5\">{m.hint}</span>\n </button>\n );\n })}\n </div>\n </div>\n\n {/* Name + Description (always shown) */}\n <div className=\"grid grid-cols-2 gap-4\">\n <div>\n <label className={labelCls}>Name</label>\n <input\n type=\"text\"\n value={form.name}\n onChange={(e) => set('name', e.target.value)}\n placeholder=\"e.g., vision-server\"\n className=\"input text-xs w-full\"\n disabled={isBuiltin}\n />\n </div>\n <div>\n <label className={labelCls}>Description</label>\n <input\n type=\"text\"\n value={form.description}\n onChange={(e) => set('description', e.target.value)}\n placeholder=\"Optional description\"\n className=\"input text-xs w-full\"\n />\n </div>\n </div>\n\n {/* In-Process: read-only info */}\n {form.mode === 'in-process' && (\n <div>\n <p className={hintCls}>\n This server runs in-process via InMemoryTransport. Transport is managed automatically — no configuration needed.\n </p>\n </div>\n )}\n\n {/* Network: URL + transport toggle */}\n {form.mode === 'network' && (\n <>\n <div>\n <label className={labelCls}>Server URL</label>\n <input\n type=\"text\"\n value={form.url}\n onChange={(e) => set('url', e.target.value)}\n placeholder=\"https://mcp-server.example.com/sse\"\n className=\"input text-xs w-full font-mono\"\n />\n </div>\n <div>\n <label className={labelCls}>Transport Protocol</label>\n <div className=\"flex gap-2 mt-1\">\n {(['sse', 'streamable-http'] as const).map((t) => (\n <button\n key={t}\n type=\"button\"\n onClick={() => set('transport_type', t)}\n className={`px-3 py-1.5 text-xs rounded-md border transition-colors ${\n form.transport_type === t\n ? 'border-accent bg-accent/5 text-accent font-medium'\n : 'border-surface-border text-text-secondary hover:border-text-tertiary'\n }`}\n >\n {t === 'sse' ? 'SSE' : 'Streamable HTTP'}\n </button>\n ))}\n </div>\n </div>\n </>\n )}\n\n {/* Local Process: command + args + env */}\n {form.mode === 'local-process' && (\n <>\n <div>\n <label className={labelCls}>Command</label>\n <input\n type=\"text\"\n value={form.command}\n onChange={(e) => set('command', e.target.value)}\n placeholder=\"e.g., npx\"\n className=\"input text-xs w-full font-mono\"\n />\n </div>\n <div>\n <label className={labelCls}>Arguments (comma-separated)</label>\n <input\n type=\"text\"\n value={form.args}\n onChange={(e) => set('args', e.target.value)}\n placeholder=\"e.g., -y, @modelcontextprotocol/server-filesystem, /tmp\"\n className=\"input text-xs w-full font-mono\"\n />\n </div>\n <div>\n <label className={labelCls}>Environment Variables (JSON)</label>\n <textarea\n value={form.env_vars}\n onChange={(e) => set('env_vars', e.target.value)}\n className=\"input-json w-full\"\n rows={3}\n spellCheck={false}\n />\n </div>\n </>\n )}\n\n {/* Auto-connect */}\n <label className=\"flex items-center gap-2 cursor-pointer\">\n <input\n type=\"checkbox\"\n checked={form.auto_connect}\n onChange={(e) => set('auto_connect', e.target.checked)}\n className=\"w-4 h-4 rounded border-border accent-accent\"\n />\n <span className=\"text-xs text-text-primary\">Auto-connect on startup</span>\n </label>\n </div>\n );\n}\n","import { useState, type KeyboardEvent } from 'react';\nimport { X } from 'lucide-react';\nimport { TagInput } from '../../../../components/common/form/TagInput';\nimport type { ServerFormState } from './server-form-types';\nimport { labelCls, hintCls } from './server-form-types';\n\ninterface Props {\n form: ServerFormState;\n set: (field: keyof ServerFormState, value: any) => void;\n}\n\nexport function DiscoveryStep({ form, set }: Props) {\n const [cpInput, setCpInput] = useState('');\n\n const addProvider = (raw: string) => {\n const v = raw.trim().toLowerCase();\n if (v && !form.credential_providers.includes(v)) {\n set('credential_providers', [...form.credential_providers, v]);\n }\n setCpInput('');\n };\n\n const removeProvider = (p: string) => {\n set('credential_providers', form.credential_providers.filter((x) => x !== p));\n };\n\n const handleCpKey = (e: KeyboardEvent<HTMLInputElement>) => {\n if (e.key === 'Enter' || e.key === ',') {\n e.preventDefault();\n addProvider(cpInput);\n } else if (e.key === 'Backspace' && !cpInput && form.credential_providers.length > 0) {\n removeProvider(form.credential_providers[form.credential_providers.length - 1]);\n }\n };\n\n return (\n <div className=\"space-y-5\">\n {/* Tags */}\n <div>\n <label className={labelCls}>Tags</label>\n <TagInput\n tags={form.tags}\n onChange={(tags) => set('tags', tags)}\n placeholder=\"Add tag (e.g., database, analytics)...\"\n />\n <p className={hintCls}>\n Tags enable tool discovery. Workflows filter available MCP servers by tags to find relevant tools.\n </p>\n </div>\n\n {/* Compile Hints */}\n <div>\n <label className={labelCls}>Compile Hints</label>\n <textarea\n value={form.compile_hints}\n onChange={(e) => set('compile_hints', e.target.value)}\n placeholder=\"Guidance for the workflow compiler when generating YAML from this server's tools...\"\n className=\"input text-xs w-full leading-relaxed\"\n rows={4}\n spellCheck={false}\n />\n <p className={hintCls}>\n Free-form text that guides the workflow compiler. Describe how tools should be composed, sequenced, or parameterized.\n </p>\n </div>\n\n {/* Credential Providers */}\n <div>\n <label className={labelCls}>Credential Providers</label>\n <div className=\"flex flex-wrap items-center gap-1.5 bg-surface-sunken border border-surface-border rounded-md px-2 py-1.5 focus-within:ring-1 focus-within:ring-accent-primary\">\n {form.credential_providers.map((p) => (\n <span\n key={p}\n className=\"inline-flex items-center gap-1 px-2 py-0.5 rounded-full bg-accent/10 text-accent text-2xs font-medium\"\n >\n {p}\n <button\n type=\"button\"\n onClick={() => removeProvider(p)}\n className=\"hover:text-status-error transition-colors\"\n >\n <X className=\"w-2.5 h-2.5\" />\n </button>\n </span>\n ))}\n <input\n type=\"text\"\n value={cpInput}\n onChange={(e) => setCpInput(e.target.value)}\n onKeyDown={handleCpKey}\n onBlur={() => { if (cpInput.trim()) addProvider(cpInput); }}\n placeholder={form.credential_providers.length === 0 ? 'Add provider (e.g., github, slack)...' : ''}\n className=\"flex-1 min-w-[80px] bg-transparent text-xs text-text-primary outline-none placeholder:text-text-tertiary\"\n />\n </div>\n <p className={hintCls}>\n IAM credential providers required by this server's tools. Users will be prompted to connect these before tool execution.\n </p>\n </div>\n </div>\n );\n}\n","import { CheckCircle2, XCircle, Loader2 } from 'lucide-react';\nimport { useTestConnection } from '../../../../api/mcp';\nimport type { ServerFormState } from './server-form-types';\nimport { formToPayload } from './server-form-types';\nimport { hintCls } from './server-form-types';\n\ninterface Props {\n form: ServerFormState;\n set: (field: keyof ServerFormState, value: any) => void;\n}\n\nexport function TestStep({ form, set }: Props) {\n const test = useTestConnection();\n const isInProcess = form.mode === 'in-process';\n\n const handleTest = () => {\n const payload = formToPayload(form);\n test.mutate(\n { transport_type: payload.transport_type, transport_config: payload.transport_config },\n {\n onSuccess: (result) => {\n if (result.success) {\n set('discovered_tools', result.tools);\n }\n },\n },\n );\n };\n\n const result = test.data;\n const tools = form.discovered_tools ?? result?.tools ?? [];\n\n return (\n <div className=\"space-y-5\">\n {isInProcess ? (\n <div>\n <p className=\"text-sm text-text-secondary\">\n In-process servers connect lazily on first tool call. No connection test needed.\n </p>\n {form.discovered_tools && form.discovered_tools.length > 0 && (\n <div className=\"mt-4\">\n <p className=\"text-xs text-text-tertiary mb-2\">\n {form.discovered_tools.length} tool{form.discovered_tools.length !== 1 ? 's' : ''} cached from last connection\n </p>\n <ToolList tools={form.discovered_tools} />\n </div>\n )}\n </div>\n ) : (\n <>\n <div className=\"flex items-center gap-3\">\n <button\n type=\"button\"\n onClick={handleTest}\n disabled={test.isPending}\n className=\"btn-primary text-xs\"\n >\n {test.isPending ? (\n <span className=\"flex items-center gap-1.5\">\n <Loader2 className=\"w-3 h-3 animate-spin\" />\n Connecting...\n </span>\n ) : (\n 'Test Connection'\n )}\n </button>\n {result?.success && (\n <span className=\"flex items-center gap-1 text-xs text-status-success\">\n <CheckCircle2 className=\"w-3.5 h-3.5\" />\n Connected — {tools.length} tool{tools.length !== 1 ? 's' : ''} discovered\n </span>\n )}\n {result && !result.success && (\n <span className=\"flex items-center gap-1 text-xs text-status-error\">\n <XCircle className=\"w-3.5 h-3.5\" />\n {result.error || 'Connection failed'}\n </span>\n )}\n </div>\n\n {tools.length > 0 && (\n <div>\n <p className=\"text-xs text-text-tertiary mb-2\">Discovered tools</p>\n <ToolList tools={tools} />\n </div>\n )}\n\n <p className={hintCls}>\n Tests connectivity by connecting to the server and listing available tools. The server must be reachable from this machine.\n </p>\n </>\n )}\n </div>\n );\n}\n\nfunction ToolList({ tools }: { tools: { name: string; description?: string }[] }) {\n return (\n <div className=\"max-h-[280px] overflow-y-auto border border-surface-border rounded-md divide-y divide-surface-border\">\n {tools.map((t) => (\n <div key={t.name} className=\"px-3 py-2\">\n <span className=\"text-xs font-medium text-text-primary font-mono\">{t.name}</span>\n {t.description && (\n <span className=\"block text-2xs text-text-tertiary mt-0.5 line-clamp-2\">{t.description}</span>\n )}\n </div>\n ))}\n </div>\n );\n}\n","import type { ServerFormState } from './server-form-types';\nimport { labelCls } from './server-form-types';\n\ninterface Props {\n form: ServerFormState;\n}\n\nconst modeLabels: Record<string, string> = {\n 'in-process': 'In-Process',\n 'network': 'Network Service',\n 'local-process': 'Local Process',\n};\n\nconst transportLabels: Record<string, string> = {\n stdio: 'stdio',\n sse: 'SSE',\n 'streamable-http': 'Streamable HTTP',\n};\n\nexport function ReviewStep({ form }: Props) {\n const tools = form.discovered_tools ?? [];\n\n return (\n <div className=\"space-y-4\">\n <Row label=\"Name\" value={form.name} />\n {form.description && <Row label=\"Description\" value={form.description} />}\n <Row label=\"Mode\" value={modeLabels[form.mode] ?? form.mode} />\n\n {form.mode === 'network' && (\n <>\n <Row label=\"Transport\" value={transportLabels[form.transport_type] ?? form.transport_type} />\n <Row label=\"URL\" value={form.url} mono />\n </>\n )}\n {form.mode === 'local-process' && (\n <>\n <Row label=\"Command\" value={form.command} mono />\n {form.args && <Row label=\"Args\" value={form.args} mono />}\n </>\n )}\n\n <Row label=\"Auto-connect\" value={form.auto_connect ? 'Yes' : 'No'} />\n\n {form.tags.length > 0 && (\n <div>\n <label className={labelCls}>Tags</label>\n <div className=\"flex flex-wrap gap-1.5 mt-1\">\n {form.tags.map((t) => (\n <span key={t} className=\"px-2 py-0.5 rounded-full bg-accent/10 text-accent text-2xs font-medium\">\n {t}\n </span>\n ))}\n </div>\n </div>\n )}\n\n {form.credential_providers.length > 0 && (\n <div>\n <label className={labelCls}>Credential Providers</label>\n <div className=\"flex flex-wrap gap-1.5 mt-1\">\n {form.credential_providers.map((p) => (\n <span key={p} className=\"px-2 py-0.5 rounded-full bg-accent/10 text-accent text-2xs font-medium\">\n {p}\n </span>\n ))}\n </div>\n </div>\n )}\n\n {form.compile_hints && <Row label=\"Compile Hints\" value={form.compile_hints} />}\n\n {tools.length > 0 && (\n <Row label=\"Discovered Tools\" value={`${tools.length} tool${tools.length !== 1 ? 's' : ''}`} />\n )}\n </div>\n );\n}\n\nfunction Row({ label, value, mono }: { label: string; value: string; mono?: boolean }) {\n return (\n <div>\n <label className={labelCls}>{label}</label>\n <p className={`text-xs text-text-primary mt-0.5 ${mono ? 'font-mono' : ''}`}>{value}</p>\n </div>\n );\n}\n","import { useState, useEffect, useCallback } from 'react';\nimport { useParams, useNavigate, useSearchParams } from 'react-router-dom';\nimport { useMcpServer, useCreateMcpServer, useUpdateMcpServer } from '../../../../api/mcp';\nimport { StepIndicator } from '../../../../components/common/layout/StepIndicator';\nimport { PageHeader } from '../../../../components/common/layout/PageHeader';\nimport {\n EMPTY_FORM,\n serverToForm,\n formToPayload,\n STEP_LABELS,\n isStepValid,\n} from './server-form-types';\nimport type { ServerFormState } from './server-form-types';\nimport { TransportStep } from './TransportStep';\nimport { DiscoveryStep } from './DiscoveryStep';\nimport { TestStep } from './TestStep';\nimport { ReviewStep } from './ReviewStep';\n\nexport function McpServerDetailPage() {\n const { serverId } = useParams<{ serverId: string }>();\n const isNew = !serverId;\n const navigate = useNavigate();\n const { data: existing, isLoading } = useMcpServer(serverId ?? '');\n const createServer = useCreateMcpServer();\n const updateServer = useUpdateMcpServer();\n\n const [form, setForm] = useState<ServerFormState>(EMPTY_FORM);\n const [initialized, setInitialized] = useState(false);\n const [saveError, setSaveError] = useState('');\n\n // Step via URL search param\n const [searchParams, setSearchParams] = useSearchParams();\n const step = parseInt(searchParams.get('step') || '1', 10);\n const setStep = useCallback((s: number) => {\n setSearchParams((prev) => {\n const next = new URLSearchParams(prev);\n next.set('step', String(s));\n return next;\n }, { replace: false });\n }, [setSearchParams]);\n\n // Initialize form from existing record\n useEffect(() => {\n if (initialized) return;\n if (isNew) {\n setForm(EMPTY_FORM);\n setInitialized(true);\n return;\n }\n if (existing) {\n setForm(serverToForm(existing));\n setInitialized(true);\n }\n }, [existing, isNew, initialized]);\n\n const set = (field: keyof ServerFormState, value: any) =>\n setForm((f) => ({ ...f, [field]: value }));\n\n const isBuiltin = !!(existing?.transport_config as any)?.builtin;\n\n // Save\n const handleSave = () => {\n setSaveError('');\n const payload = formToPayload(form);\n\n if (existing) {\n updateServer.mutate(\n { id: existing.id, ...payload },\n { onSuccess: () => navigate('/mcp/servers') },\n );\n } else {\n createServer.mutate(payload, {\n onSuccess: () => navigate('/mcp/servers'),\n onError: (err) => setSaveError(err.message),\n });\n }\n };\n\n if (!isNew && isLoading) {\n return (\n <div className=\"animate-pulse space-y-4\">\n <div className=\"h-8 bg-surface-sunken rounded w-48\" />\n <div className=\"h-60 bg-surface-sunken rounded\" />\n </div>\n );\n }\n\n if (!isNew && !existing && !isLoading) {\n return <p className=\"text-sm text-text-secondary\">Server not found.</p>;\n }\n\n const isLast = step === STEP_LABELS.length;\n const isPending = createServer.isPending || updateServer.isPending;\n const error = saveError || (createServer.error as Error | null)?.message || (updateServer.error as Error | null)?.message;\n\n return (\n <div>\n <PageHeader title={isNew ? 'Register MCP Server' : existing?.name ?? ''} />\n\n <div className=\"max-w-3xl\">\n <StepIndicator steps={STEP_LABELS} currentStep={step - 1} onStepClick={(i) => setStep(i + 1)} />\n\n <div className=\"min-h-[360px] py-2\">\n {step === 1 && <TransportStep form={form} set={set} isBuiltin={isBuiltin} />}\n {step === 2 && <DiscoveryStep form={form} set={set} />}\n {step === 3 && <TestStep form={form} set={set} />}\n {step === 4 && <ReviewStep form={form} />}\n </div>\n\n {error && (\n <p className=\"text-xs text-status-error mt-4\">{error}</p>\n )}\n\n {/* Navigation */}\n <div className=\"flex justify-between items-center pt-4 border-t border-surface-border mt-4\">\n <div>\n {step > 1 && (\n <button onClick={() => setStep(step - 1)} className=\"btn-secondary text-xs\">\n Back\n </button>\n )}\n </div>\n <div className=\"flex gap-3\">\n <button onClick={() => navigate('/mcp/servers')} className=\"btn-ghost text-xs\">\n Cancel\n </button>\n {isLast ? (\n <button\n onClick={handleSave}\n disabled={!isStepValid(step, form) || isPending}\n className=\"btn-primary text-xs\"\n >\n {isPending ? 'Saving...' : existing ? 'Save' : 'Register'}\n </button>\n ) : (\n <button\n onClick={() => setStep(step + 1)}\n disabled={!isStepValid(step, form)}\n className=\"btn-primary text-xs\"\n >\n Next\n </button>\n )}\n </div>\n </div>\n </div>\n </div>\n );\n}\n"],"names":["StepIndicator","steps","currentStep","onStepClick","jsx","label","i","done","active","clickable","jsxs","EMPTY_FORM","serverToForm","config","isBuiltin","mode","formToPayload","form","transport_config","a","STEP_LABELS","isStepValid","step","labelCls","hintCls","modes","TransportStep","set","m","disabled","e","Fragment","t","DiscoveryStep","cpInput","setCpInput","useState","addProvider","raw","v","removeProvider","p","x","handleCpKey","TagInput","tags","X","TestStep","test","useTestConnection","isInProcess","handleTest","payload","result","tools","ToolList","Loader2","CheckCircle2","XCircle","modeLabels","transportLabels","ReviewStep","Row","value","mono","McpServerDetailPage","serverId","useParams","isNew","navigate","useNavigate","existing","isLoading","useMcpServer","createServer","useCreateMcpServer","updateServer","useUpdateMcpServer","setForm","initialized","setInitialized","saveError","setSaveError","searchParams","setSearchParams","useSearchParams","setStep","useCallback","s","prev","next","useEffect","field","f","_a","handleSave","err","isLast","isPending","error","_b","_c","PageHeader"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index-C3o4OisO.js","sources":["../../src/components/common/layout/StepIndicator.tsx","../../src/pages/mcp/servers/detail/server-form-types.ts","../../src/pages/mcp/servers/detail/TransportStep.tsx","../../src/pages/mcp/servers/detail/DiscoveryStep.tsx","../../src/pages/mcp/servers/detail/TestStep.tsx","../../src/pages/mcp/servers/detail/ReviewStep.tsx","../../src/pages/mcp/servers/detail/McpServerDetailPage.tsx"],"sourcesContent":["interface StepIndicatorProps {\n steps: string[];\n currentStep: number;\n onStepClick?: (step: number) => void;\n}\n\nexport function StepIndicator({ steps, currentStep, onStepClick }: StepIndicatorProps) {\n return (\n <div className=\"flex items-center justify-center gap-1 pb-4 border-b border-surface-border mb-4\">\n {steps.map((label, i) => {\n const done = i < currentStep;\n const active = i === currentStep;\n const clickable = !!onStepClick;\n return (\n <div key={label} className=\"flex items-center gap-1\">\n {i > 0 && (\n <div className={`w-4 h-px ${done ? 'bg-accent' : 'bg-surface-border'}`} />\n )}\n <button\n type=\"button\"\n onClick={clickable ? () => onStepClick(i) : undefined}\n className={`flex items-center gap-1 ${clickable ? 'cursor-pointer' : 'cursor-default'}`}\n >\n <span\n className={`w-5 h-5 rounded-full text-2xs font-semibold flex items-center justify-center shrink-0 transition-colors ${\n active\n ? 'bg-accent text-text-inverse'\n : done\n ? 'bg-accent-muted text-accent'\n : 'bg-surface-sunken text-text-tertiary'\n } ${clickable && !active ? 'hover:bg-accent-muted hover:text-accent' : ''}`}\n >\n {i + 1}\n </span>\n <span\n className={`text-2xs font-semibold uppercase tracking-wider whitespace-nowrap transition-colors ${\n active ? 'text-text-primary' : 'text-text-tertiary'\n } ${clickable && !active ? 'hover:text-text-primary' : ''}`}\n >\n {label}\n </span>\n </button>\n </div>\n );\n })}\n </div>\n );\n}\n","import type { McpServerRecord, McpToolManifest } from '../../../../api/types';\n\nexport interface ServerFormState {\n name: string;\n description: string;\n mode: 'in-process' | 'network' | 'local-process';\n transport_type: 'stdio' | 'sse' | 'streamable-http';\n // stdio fields\n command: string;\n args: string;\n env_vars: string;\n // network fields\n url: string;\n // shared\n auto_connect: boolean;\n tags: string[];\n compile_hints: string;\n credential_providers: string[];\n discovered_tools: McpToolManifest[] | null;\n}\n\nexport const EMPTY_FORM: ServerFormState = {\n name: '',\n description: '',\n mode: 'network',\n transport_type: 'sse',\n command: '',\n args: '',\n env_vars: '{}',\n url: '',\n auto_connect: false,\n tags: [],\n compile_hints: '',\n credential_providers: [],\n discovered_tools: null,\n};\n\nexport function serverToForm(s: McpServerRecord): ServerFormState {\n const config = s.transport_config ?? {};\n const isBuiltin = !!(config as any).builtin;\n\n let mode: ServerFormState['mode'] = 'network';\n if (isBuiltin) mode = 'in-process';\n else if (s.transport_type === 'stdio') mode = 'local-process';\n\n return {\n name: s.name,\n description: s.description ?? '',\n mode,\n transport_type: s.transport_type,\n command: (config as any).command ?? '',\n args: ((config as any).args ?? []).join(', '),\n env_vars: (config as any).env ? JSON.stringify((config as any).env, null, 2) : '{}',\n url: (config as any).url ?? '',\n auto_connect: s.auto_connect,\n tags: s.tags ?? [],\n compile_hints: (s as any).compile_hints ?? '',\n credential_providers: s.credential_providers ?? [],\n discovered_tools: s.tool_manifest ?? null,\n };\n}\n\nexport function formToPayload(form: ServerFormState) {\n let transport_config: Record<string, unknown> = {};\n\n if (form.mode === 'local-process') {\n transport_config = {\n command: form.command.trim(),\n args: form.args.split(',').map((a) => a.trim()).filter(Boolean),\n env: form.env_vars.trim() ? JSON.parse(form.env_vars) : undefined,\n };\n } else if (form.mode === 'network') {\n transport_config = { url: form.url.trim() };\n }\n // in-process: transport_config stays empty (server manages it)\n\n return {\n name: form.name.trim(),\n description: form.description.trim() || undefined,\n transport_type: form.mode === 'local-process' ? 'stdio' as const : form.transport_type,\n transport_config,\n auto_connect: form.auto_connect,\n tags: form.tags,\n compile_hints: form.compile_hints.trim() || undefined,\n credential_providers: form.credential_providers.length > 0 ? form.credential_providers : undefined,\n };\n}\n\nexport const STEP_LABELS = ['Transport', 'Discovery', 'Test', 'Review'];\n\nexport function isStepValid(step: number, form: ServerFormState): boolean {\n if (step === 1) {\n if (!form.name.trim()) return false;\n if (form.mode === 'network' && !form.url.trim()) return false;\n if (form.mode === 'local-process' && !form.command.trim()) return false;\n return true;\n }\n return true;\n}\n\nexport const labelCls = 'label';\nexport const hintCls = 'hint';\n","import type { ServerFormState } from './server-form-types';\nimport { labelCls, hintCls } from './server-form-types';\n\ninterface Props {\n form: ServerFormState;\n set: (field: keyof ServerFormState, value: any) => void;\n isBuiltin: boolean;\n}\n\nconst modes = [\n { value: 'in-process', label: 'In-Process', hint: 'Built-in server running inside the app' },\n { value: 'network', label: 'Network Service', hint: 'Remote server via SSE or Streamable HTTP' },\n { value: 'local-process', label: 'Local Process', hint: 'Spawn a local command via stdio' },\n] as const;\n\nexport function TransportStep({ form, set, isBuiltin }: Props) {\n return (\n <div className=\"space-y-5\">\n {/* Mode selector */}\n <div>\n <label className={labelCls}>Connection Mode</label>\n <div className=\"grid grid-cols-3 gap-3 mt-1\">\n {modes.map((m) => {\n const active = form.mode === m.value;\n const disabled = isBuiltin && m.value !== 'in-process';\n return (\n <button\n key={m.value}\n type=\"button\"\n disabled={disabled}\n onClick={() => {\n set('mode', m.value);\n if (m.value === 'local-process') set('transport_type', 'stdio');\n if (m.value === 'network') set('transport_type', 'sse');\n }}\n className={`text-left p-3 rounded-md border transition-colors ${\n active\n ? 'border-accent bg-accent/5'\n : disabled\n ? 'border-surface-border bg-surface-sunken opacity-50 cursor-not-allowed'\n : 'border-surface-border hover:border-text-tertiary cursor-pointer'\n }`}\n >\n <span className={`text-xs font-medium ${active ? 'text-accent' : 'text-text-primary'}`}>\n {m.label}\n </span>\n <span className=\"block text-2xs text-text-tertiary mt-0.5\">{m.hint}</span>\n </button>\n );\n })}\n </div>\n </div>\n\n {/* Name + Description (always shown) */}\n <div className=\"grid grid-cols-2 gap-4\">\n <div>\n <label className={labelCls}>Name</label>\n <input\n type=\"text\"\n value={form.name}\n onChange={(e) => set('name', e.target.value)}\n placeholder=\"e.g., vision-server\"\n className=\"input text-xs w-full\"\n disabled={isBuiltin}\n />\n </div>\n <div>\n <label className={labelCls}>Description</label>\n <input\n type=\"text\"\n value={form.description}\n onChange={(e) => set('description', e.target.value)}\n placeholder=\"Optional description\"\n className=\"input text-xs w-full\"\n />\n </div>\n </div>\n\n {/* In-Process: read-only info */}\n {form.mode === 'in-process' && (\n <div>\n <p className={hintCls}>\n This server runs in-process via InMemoryTransport. Transport is managed automatically — no configuration needed.\n </p>\n </div>\n )}\n\n {/* Network: URL + transport toggle */}\n {form.mode === 'network' && (\n <>\n <div>\n <label className={labelCls}>Server URL</label>\n <input\n type=\"text\"\n value={form.url}\n onChange={(e) => set('url', e.target.value)}\n placeholder=\"https://mcp-server.example.com/sse\"\n className=\"input text-xs w-full font-mono\"\n />\n </div>\n <div>\n <label className={labelCls}>Transport Protocol</label>\n <div className=\"flex gap-2 mt-1\">\n {(['sse', 'streamable-http'] as const).map((t) => (\n <button\n key={t}\n type=\"button\"\n onClick={() => set('transport_type', t)}\n className={`px-3 py-1.5 text-xs rounded-md border transition-colors ${\n form.transport_type === t\n ? 'border-accent bg-accent/5 text-accent font-medium'\n : 'border-surface-border text-text-secondary hover:border-text-tertiary'\n }`}\n >\n {t === 'sse' ? 'SSE' : 'Streamable HTTP'}\n </button>\n ))}\n </div>\n </div>\n </>\n )}\n\n {/* Local Process: command + args + env */}\n {form.mode === 'local-process' && (\n <>\n <div>\n <label className={labelCls}>Command</label>\n <input\n type=\"text\"\n value={form.command}\n onChange={(e) => set('command', e.target.value)}\n placeholder=\"e.g., npx\"\n className=\"input text-xs w-full font-mono\"\n />\n </div>\n <div>\n <label className={labelCls}>Arguments (comma-separated)</label>\n <input\n type=\"text\"\n value={form.args}\n onChange={(e) => set('args', e.target.value)}\n placeholder=\"e.g., -y, @modelcontextprotocol/server-filesystem, /tmp\"\n className=\"input text-xs w-full font-mono\"\n />\n </div>\n <div>\n <label className={labelCls}>Environment Variables (JSON)</label>\n <textarea\n value={form.env_vars}\n onChange={(e) => set('env_vars', e.target.value)}\n className=\"input-json w-full\"\n rows={3}\n spellCheck={false}\n />\n </div>\n </>\n )}\n\n {/* Auto-connect */}\n <label className=\"flex items-center gap-2 cursor-pointer\">\n <input\n type=\"checkbox\"\n checked={form.auto_connect}\n onChange={(e) => set('auto_connect', e.target.checked)}\n className=\"w-4 h-4 rounded border-border accent-accent\"\n />\n <span className=\"text-xs text-text-primary\">Auto-connect on startup</span>\n </label>\n </div>\n );\n}\n","import { useState, type KeyboardEvent } from 'react';\nimport { X } from 'lucide-react';\nimport { TagInput } from '../../../../components/common/form/TagInput';\nimport type { ServerFormState } from './server-form-types';\nimport { labelCls, hintCls } from './server-form-types';\n\ninterface Props {\n form: ServerFormState;\n set: (field: keyof ServerFormState, value: any) => void;\n}\n\nexport function DiscoveryStep({ form, set }: Props) {\n const [cpInput, setCpInput] = useState('');\n\n const addProvider = (raw: string) => {\n const v = raw.trim().toLowerCase();\n if (v && !form.credential_providers.includes(v)) {\n set('credential_providers', [...form.credential_providers, v]);\n }\n setCpInput('');\n };\n\n const removeProvider = (p: string) => {\n set('credential_providers', form.credential_providers.filter((x) => x !== p));\n };\n\n const handleCpKey = (e: KeyboardEvent<HTMLInputElement>) => {\n if (e.key === 'Enter' || e.key === ',') {\n e.preventDefault();\n addProvider(cpInput);\n } else if (e.key === 'Backspace' && !cpInput && form.credential_providers.length > 0) {\n removeProvider(form.credential_providers[form.credential_providers.length - 1]);\n }\n };\n\n return (\n <div className=\"space-y-5\">\n {/* Tags */}\n <div>\n <label className={labelCls}>Tags</label>\n <TagInput\n tags={form.tags}\n onChange={(tags) => set('tags', tags)}\n placeholder=\"Add tag (e.g., database, analytics)...\"\n />\n <p className={hintCls}>\n Tags enable tool discovery. Workflows filter available MCP servers by tags to find relevant tools.\n </p>\n </div>\n\n {/* Compile Hints */}\n <div>\n <label className={labelCls}>Compile Hints</label>\n <textarea\n value={form.compile_hints}\n onChange={(e) => set('compile_hints', e.target.value)}\n placeholder=\"Guidance for the workflow compiler when generating YAML from this server's tools...\"\n className=\"input text-xs w-full leading-relaxed\"\n rows={4}\n spellCheck={false}\n />\n <p className={hintCls}>\n Free-form text that guides the workflow compiler. Describe how tools should be composed, sequenced, or parameterized.\n </p>\n </div>\n\n {/* Credential Providers */}\n <div>\n <label className={labelCls}>Credential Providers</label>\n <div className=\"flex flex-wrap items-center gap-1.5 bg-surface-sunken border border-surface-border rounded-md px-2 py-1.5 focus-within:ring-1 focus-within:ring-accent-primary\">\n {form.credential_providers.map((p) => (\n <span\n key={p}\n className=\"inline-flex items-center gap-1 px-2 py-0.5 rounded-full bg-accent/10 text-accent text-2xs font-medium\"\n >\n {p}\n <button\n type=\"button\"\n onClick={() => removeProvider(p)}\n className=\"hover:text-status-error transition-colors\"\n >\n <X className=\"w-2.5 h-2.5\" />\n </button>\n </span>\n ))}\n <input\n type=\"text\"\n value={cpInput}\n onChange={(e) => setCpInput(e.target.value)}\n onKeyDown={handleCpKey}\n onBlur={() => { if (cpInput.trim()) addProvider(cpInput); }}\n placeholder={form.credential_providers.length === 0 ? 'Add provider (e.g., github, slack)...' : ''}\n className=\"flex-1 min-w-[80px] bg-transparent text-xs text-text-primary outline-none placeholder:text-text-tertiary\"\n />\n </div>\n <p className={hintCls}>\n IAM credential providers required by this server's tools. Users will be prompted to connect these before tool execution.\n </p>\n </div>\n </div>\n );\n}\n","import { CheckCircle2, XCircle, Loader2 } from 'lucide-react';\nimport { useTestConnection } from '../../../../api/mcp';\nimport type { ServerFormState } from './server-form-types';\nimport { formToPayload } from './server-form-types';\nimport { hintCls } from './server-form-types';\n\ninterface Props {\n form: ServerFormState;\n set: (field: keyof ServerFormState, value: any) => void;\n}\n\nexport function TestStep({ form, set }: Props) {\n const test = useTestConnection();\n const isInProcess = form.mode === 'in-process';\n\n const handleTest = () => {\n const payload = formToPayload(form);\n test.mutate(\n { transport_type: payload.transport_type, transport_config: payload.transport_config },\n {\n onSuccess: (result) => {\n if (result.success) {\n set('discovered_tools', result.tools);\n }\n },\n },\n );\n };\n\n const result = test.data;\n const tools = form.discovered_tools ?? result?.tools ?? [];\n\n return (\n <div className=\"space-y-5\">\n {isInProcess ? (\n <div>\n <p className=\"text-sm text-text-secondary\">\n In-process servers connect lazily on first tool call. No connection test needed.\n </p>\n {form.discovered_tools && form.discovered_tools.length > 0 && (\n <div className=\"mt-4\">\n <p className=\"text-xs text-text-tertiary mb-2\">\n {form.discovered_tools.length} tool{form.discovered_tools.length !== 1 ? 's' : ''} cached from last connection\n </p>\n <ToolList tools={form.discovered_tools} />\n </div>\n )}\n </div>\n ) : (\n <>\n <div className=\"flex items-center gap-3\">\n <button\n type=\"button\"\n onClick={handleTest}\n disabled={test.isPending}\n className=\"btn-primary text-xs\"\n >\n {test.isPending ? (\n <span className=\"flex items-center gap-1.5\">\n <Loader2 className=\"w-3 h-3 animate-spin\" />\n Connecting...\n </span>\n ) : (\n 'Test Connection'\n )}\n </button>\n {result?.success && (\n <span className=\"flex items-center gap-1 text-xs text-status-success\">\n <CheckCircle2 className=\"w-3.5 h-3.5\" />\n Connected — {tools.length} tool{tools.length !== 1 ? 's' : ''} discovered\n </span>\n )}\n {result && !result.success && (\n <span className=\"flex items-center gap-1 text-xs text-status-error\">\n <XCircle className=\"w-3.5 h-3.5\" />\n {result.error || 'Connection failed'}\n </span>\n )}\n </div>\n\n {tools.length > 0 && (\n <div>\n <p className=\"text-xs text-text-tertiary mb-2\">Discovered tools</p>\n <ToolList tools={tools} />\n </div>\n )}\n\n <p className={hintCls}>\n Tests connectivity by connecting to the server and listing available tools. The server must be reachable from this machine.\n </p>\n </>\n )}\n </div>\n );\n}\n\nfunction ToolList({ tools }: { tools: { name: string; description?: string }[] }) {\n return (\n <div className=\"max-h-[280px] overflow-y-auto border border-surface-border rounded-md divide-y divide-surface-border\">\n {tools.map((t) => (\n <div key={t.name} className=\"px-3 py-2\">\n <span className=\"text-xs font-medium text-text-primary font-mono\">{t.name}</span>\n {t.description && (\n <span className=\"block text-2xs text-text-tertiary mt-0.5 line-clamp-2\">{t.description}</span>\n )}\n </div>\n ))}\n </div>\n );\n}\n","import type { ServerFormState } from './server-form-types';\nimport { labelCls } from './server-form-types';\n\ninterface Props {\n form: ServerFormState;\n}\n\nconst modeLabels: Record<string, string> = {\n 'in-process': 'In-Process',\n 'network': 'Network Service',\n 'local-process': 'Local Process',\n};\n\nconst transportLabels: Record<string, string> = {\n stdio: 'stdio',\n sse: 'SSE',\n 'streamable-http': 'Streamable HTTP',\n};\n\nexport function ReviewStep({ form }: Props) {\n const tools = form.discovered_tools ?? [];\n\n return (\n <div className=\"space-y-4\">\n <Row label=\"Name\" value={form.name} />\n {form.description && <Row label=\"Description\" value={form.description} />}\n <Row label=\"Mode\" value={modeLabels[form.mode] ?? form.mode} />\n\n {form.mode === 'network' && (\n <>\n <Row label=\"Transport\" value={transportLabels[form.transport_type] ?? form.transport_type} />\n <Row label=\"URL\" value={form.url} mono />\n </>\n )}\n {form.mode === 'local-process' && (\n <>\n <Row label=\"Command\" value={form.command} mono />\n {form.args && <Row label=\"Args\" value={form.args} mono />}\n </>\n )}\n\n <Row label=\"Auto-connect\" value={form.auto_connect ? 'Yes' : 'No'} />\n\n {form.tags.length > 0 && (\n <div>\n <label className={labelCls}>Tags</label>\n <div className=\"flex flex-wrap gap-1.5 mt-1\">\n {form.tags.map((t) => (\n <span key={t} className=\"px-2 py-0.5 rounded-full bg-accent/10 text-accent text-2xs font-medium\">\n {t}\n </span>\n ))}\n </div>\n </div>\n )}\n\n {form.credential_providers.length > 0 && (\n <div>\n <label className={labelCls}>Credential Providers</label>\n <div className=\"flex flex-wrap gap-1.5 mt-1\">\n {form.credential_providers.map((p) => (\n <span key={p} className=\"px-2 py-0.5 rounded-full bg-accent/10 text-accent text-2xs font-medium\">\n {p}\n </span>\n ))}\n </div>\n </div>\n )}\n\n {form.compile_hints && <Row label=\"Compile Hints\" value={form.compile_hints} />}\n\n {tools.length > 0 && (\n <Row label=\"Discovered Tools\" value={`${tools.length} tool${tools.length !== 1 ? 's' : ''}`} />\n )}\n </div>\n );\n}\n\nfunction Row({ label, value, mono }: { label: string; value: string; mono?: boolean }) {\n return (\n <div>\n <label className={labelCls}>{label}</label>\n <p className={`text-xs text-text-primary mt-0.5 ${mono ? 'font-mono' : ''}`}>{value}</p>\n </div>\n );\n}\n","import { useState, useEffect, useCallback } from 'react';\nimport { useParams, useNavigate, useSearchParams } from 'react-router-dom';\nimport { useMcpServer, useCreateMcpServer, useUpdateMcpServer } from '../../../../api/mcp';\nimport { StepIndicator } from '../../../../components/common/layout/StepIndicator';\nimport { PageHeader } from '../../../../components/common/layout/PageHeader';\nimport {\n EMPTY_FORM,\n serverToForm,\n formToPayload,\n STEP_LABELS,\n isStepValid,\n} from './server-form-types';\nimport type { ServerFormState } from './server-form-types';\nimport { TransportStep } from './TransportStep';\nimport { DiscoveryStep } from './DiscoveryStep';\nimport { TestStep } from './TestStep';\nimport { ReviewStep } from './ReviewStep';\n\nexport function McpServerDetailPage() {\n const { serverId } = useParams<{ serverId: string }>();\n const isNew = !serverId;\n const navigate = useNavigate();\n const { data: existing, isLoading } = useMcpServer(serverId ?? '');\n const createServer = useCreateMcpServer();\n const updateServer = useUpdateMcpServer();\n\n const [form, setForm] = useState<ServerFormState>(EMPTY_FORM);\n const [initialized, setInitialized] = useState(false);\n const [saveError, setSaveError] = useState('');\n\n // Step via URL search param\n const [searchParams, setSearchParams] = useSearchParams();\n const step = parseInt(searchParams.get('step') || '1', 10);\n const setStep = useCallback((s: number) => {\n setSearchParams((prev) => {\n const next = new URLSearchParams(prev);\n next.set('step', String(s));\n return next;\n }, { replace: false });\n }, [setSearchParams]);\n\n // Initialize form from existing record\n useEffect(() => {\n if (initialized) return;\n if (isNew) {\n setForm(EMPTY_FORM);\n setInitialized(true);\n return;\n }\n if (existing) {\n setForm(serverToForm(existing));\n setInitialized(true);\n }\n }, [existing, isNew, initialized]);\n\n const set = (field: keyof ServerFormState, value: any) =>\n setForm((f) => ({ ...f, [field]: value }));\n\n const isBuiltin = !!(existing?.transport_config as any)?.builtin;\n\n // Save\n const handleSave = () => {\n setSaveError('');\n const payload = formToPayload(form);\n\n if (existing) {\n updateServer.mutate(\n { id: existing.id, ...payload },\n { onSuccess: () => navigate('/mcp/servers') },\n );\n } else {\n createServer.mutate(payload, {\n onSuccess: () => navigate('/mcp/servers'),\n onError: (err) => setSaveError(err.message),\n });\n }\n };\n\n if (!isNew && isLoading) {\n return (\n <div className=\"animate-pulse space-y-4\">\n <div className=\"h-8 bg-surface-sunken rounded w-48\" />\n <div className=\"h-60 bg-surface-sunken rounded\" />\n </div>\n );\n }\n\n if (!isNew && !existing && !isLoading) {\n return <p className=\"text-sm text-text-secondary\">Server not found.</p>;\n }\n\n const isLast = step === STEP_LABELS.length;\n const isPending = createServer.isPending || updateServer.isPending;\n const error = saveError || (createServer.error as Error | null)?.message || (updateServer.error as Error | null)?.message;\n\n return (\n <div>\n <PageHeader title={isNew ? 'Register MCP Server' : existing?.name ?? ''} />\n\n <div className=\"max-w-3xl\">\n <StepIndicator steps={STEP_LABELS} currentStep={step - 1} onStepClick={(i) => setStep(i + 1)} />\n\n <div className=\"min-h-[360px] py-2\">\n {step === 1 && <TransportStep form={form} set={set} isBuiltin={isBuiltin} />}\n {step === 2 && <DiscoveryStep form={form} set={set} />}\n {step === 3 && <TestStep form={form} set={set} />}\n {step === 4 && <ReviewStep form={form} />}\n </div>\n\n {error && (\n <p className=\"text-xs text-status-error mt-4\">{error}</p>\n )}\n\n {/* Navigation */}\n <div className=\"flex justify-between items-center pt-4 border-t border-surface-border mt-4\">\n <div>\n {step > 1 && (\n <button onClick={() => setStep(step - 1)} className=\"btn-secondary text-xs\">\n Back\n </button>\n )}\n </div>\n <div className=\"flex gap-3\">\n <button onClick={() => navigate('/mcp/servers')} className=\"btn-ghost text-xs\">\n Cancel\n </button>\n {isLast ? (\n <button\n onClick={handleSave}\n disabled={!isStepValid(step, form) || isPending}\n className=\"btn-primary text-xs\"\n >\n {isPending ? 'Saving...' : existing ? 'Save' : 'Register'}\n </button>\n ) : (\n <button\n onClick={() => setStep(step + 1)}\n disabled={!isStepValid(step, form)}\n className=\"btn-primary text-xs\"\n >\n Next\n </button>\n )}\n </div>\n </div>\n </div>\n </div>\n );\n}\n"],"names":["StepIndicator","steps","currentStep","onStepClick","jsx","label","i","done","active","clickable","jsxs","EMPTY_FORM","serverToForm","config","isBuiltin","mode","formToPayload","form","transport_config","a","STEP_LABELS","isStepValid","step","labelCls","hintCls","modes","TransportStep","set","m","disabled","e","Fragment","t","DiscoveryStep","cpInput","setCpInput","useState","addProvider","raw","v","removeProvider","p","x","handleCpKey","TagInput","tags","X","TestStep","test","useTestConnection","isInProcess","handleTest","payload","result","tools","ToolList","Loader2","CheckCircle2","XCircle","modeLabels","transportLabels","ReviewStep","Row","value","mono","McpServerDetailPage","serverId","useParams","isNew","navigate","useNavigate","existing","isLoading","useMcpServer","createServer","useCreateMcpServer","updateServer","useUpdateMcpServer","setForm","initialized","setInitialized","saveError","setSaveError","searchParams","setSearchParams","useSearchParams","setStep","useCallback","s","prev","next","useEffect","field","f","_a","handleSave","err","isLast","isPending","error","_b","_c","PageHeader"],"mappings":"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"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{a as i,j as e}from"./vendor-query-B2UbickB.js";import{P as ye}from"./PageHeaderWithStats-8_5cOSKL.js";import{F as we,b as ke}from"./FilterBar-CzjtH74v.js";import{u as Ne}from"./useFilterParams-B7suPsIK.js";import{u as ve}from"./useNamespace-u-V1GVUD.js";import{a as ee,u as Ce,b as $e,c as Se,d as _e}from"./controlplane-BKMvfWCB.js";import{M as Te}from"./Modal-Dr1Xy0j0.js";import{a0 as K,aQ as U,g as Ee,aR as Z,aS as J,a as te,I as Re,ah as Me,ak as Pe,R as Ae,O as Le,aT as We,u as Qe,Z as Fe,aN as Oe}from"./vendor-icons-D71XjkNy.js";import{C as I}from"./CollapsibleSection-CIj8Adc9.js";import{T as Be}from"./TaskQueuePill-G3RuYRNZ.js";import{D as ze}from"./DataTable-BTu2AaEl.js";import{C as W,c as Ie,J as Je}from"./index-DbTD-dio.js";import{R as De,a as Y}from"./RowActions-BA9L9djf.js";import{f as Ue}from"./vendor-react-C1YOyCSV.js";import"./EmptyState-BcsfPq9T.js";const Ve=[{label:"15m",value:"15m"},{label:"30m",value:"30m"},{label:"1h",value:"1h"},{label:"1d",value:"1d"},{label:"7d",value:"7d"}],se={pong:"text-status-success",ping:"text-accent",throttle:"text-status-warning",job:"text-purple-400",work:"text-text-secondary",activate:"text-status-error",cron:"text-text-tertiary",user:"text-text-secondary"},He={pong:"roll call",ping:"ping",throttle:"throttle",job:"job",work:"work",activate:"activate",cron:"cron",user:"user"},qe=250;function M(t){return!!t.worker_topic}function P(t){return typeof t.throttle=="number"&&t.throttle!==0}function V(t){return t===void 0||t===0?"Normal":t===-1?"Paused":t>=864e5?`${(t/864e5).toFixed(0)}d`:t>=36e5?`${(t/36e5).toFixed(1)}h`:t>=6e4?`${(t/6e4).toFixed(1)}m`:t>=1e3?`${(t/1e3).toFixed(1)}s`:`${t}ms`}function Ge(t){if(!t)return null;const s=t.match(/^(\d{4})(\d{2})(\d{2})(\d{2})(\d{2})(\d{2})\.(\d+)$/);if(s){const[,a,n,o,u,l,h,d]=s;return new Date(`${a}-${n}-${o}T${u}:${l}:${h}.${d}Z`)}const r=new Date(t);return isNaN(r.getTime())?null:r}function Ke(t){const s=Ge(t);if(!s)return"--";const r=Date.now()-s.getTime();if(r<0||isNaN(r))return"--";const a=Math.floor(r/1e3);if(a<60)return`${a}s`;const n=Math.floor(a/60);if(n<60)return`${n}m`;const o=Math.floor(n/60);return o<24?`${o}h ${n%60}m`:`${Math.floor(o/24)}d ${o%24}h`}function ne(t){return t.replace(/^hmsh:[^:]+:x:/,"")||"(engine)"}function F(t){const s=t.match(/^([^:]+)::(.+?)-[A-Za-z0-9_]{10,}$/);return s?s[2]:t.length>20?t.slice(0,20)+"...":t}function Ze(t){const s=t.match(/^([^:]+)::/);return(s==null?void 0:s[1])||""}const ae=[{key:"pong",label:"Roll Call",description:"Node health check responses"},{key:"ping",label:"Ping",description:"Health check broadcasts"},{key:"throttle",label:"Throttle",description:"Throttle commands"},{key:"job",label:"Job",description:"Job lifecycle events"},{key:"work",label:"Work",description:"Worker dispatch events"},{key:"activate",label:"Activate",description:"Worker activation"},{key:"cron",label:"Cron",description:"Cron schedule triggers"},{key:"user",label:"User",description:"User-defined messages"}];function B(t){return`${t.engine_id}-${t.worker_topic||"engine"}`}function Ye(t){const s=new Map;for(const r of t){if(!r.worker_topic)continue;const a=r.worker_topic;s.has(a)||s.set(a,[]),s.get(a).push(r)}return s}function T(t){let s=0,r=0,a=0;for(const n of t)if(n.counts)for(const[o,u]of Object.entries(n.counts))s+=u,o==="200"?r+=u:o==="500"&&(a+=u);return{total:s,success:r,errors:a}}function Xe(t){let s=0;for(const r of t)typeof r.stream_depth=="number"&&(s+=r.stream_depth);return s}function et(t){if(t.length===0)return"healthy";if(t.every(a=>a.throttle===-1))return"paused";const{errors:r}=T(t);return r>0||t.some(P)?"degraded":"healthy"}function tt({activeAppId:t,allProfiles:s,profiles:r}){const a=ee(),[n,o]=i.useState(new Set),[u,l]=i.useState(!1),[h,d]=i.useState([]);i.useEffect(()=>{o(new Set)},[t]);const k=i.useCallback(m=>{o(C=>{const f=new Set(C),$=B(m);return f.has($)?f.delete($):f.add($),f})},[]),b=i.useCallback(()=>{n.size===r.length?o(new Set):o(new Set(r.map(B)))},[r,n.size]),j=i.useMemo(()=>{const m=r.filter(N=>n.has(B(N)));if(m.length===0)return[];if(m.length===s.length)return[{label:"Entire Mesh"}];const C=m.filter(N=>!M(N)),f=m.filter(M),$=[];for(const N of C)$.push({label:`Engine ${N.engine_id}`,guid:N.engine_id,scope:"engines"});const A=new Map;for(const N of f){const R=N.worker_topic;A.has(R)||A.set(R,[]),A.get(R).push(N)}for(const[N,R]of A){const O=s.filter(L=>L.worker_topic===N);if(R.length===O.length)$.push({label:N,topic:N});else for(const L of R)$.push({label:`${N} ${L.engine_id}`,guid:L.engine_id})}return $},[r,s,n]);return{selectedIds:n,setSelectedIds:o,toggleCheckbox:k,toggleAll:b,throttleModalOpen:u,throttleTargets:h,selectedThrottleTargets:j,throttleMutation:a,handleBulkThrottle:m=>{const C=h.length>0?h:j;for(const f of C)a.mutate({appId:t,throttle:m,...f.topic?{topic:f.topic}:{},...f.guid?{guid:f.guid}:{},...f.scope?{scope:f.scope}:{}});l(!1),d([])},handleRowClick:(m,C)=>{const f=M(m)?`${m.worker_topic} ${m.engine_id}`:`Engine ${m.engine_id}`;d([{label:f,guid:m.engine_id,scope:C||(M(m)?"workers":"engines")}]),l(!0)},handleBulkThrottleOpen:()=>{d(j),l(!0)},handleResumeThrottle:(m,C)=>{const f=C||(M(m)?"workers":"engines");a.mutate({appId:t,throttle:0,guid:m.engine_id,scope:f})},handleResumeQueue:m=>{a.mutate({appId:t,throttle:0,topic:m})},handleQueueThrottle:m=>{d([{label:m,topic:m}]),l(!0)},closeThrottleModal:()=>{l(!1),d([])}}}const st=[{label:"Resume",ms:0},{label:"0.5s",ms:500},{label:"1s",ms:1e3},{label:"5s",ms:5e3},{label:"30s",ms:3e4},{label:"Pause",ms:-1}];function nt({target:t}){const s=t.label==="Entire Mesh",r=t.label==="All Engines"||t.label.startsWith("Engine "),a=s?"bg-status-error/10 text-status-error":r?"bg-status-active/10 text-status-active":"bg-accent/[0.06] text-text-secondary",n=t.scope==="engines"?"engine only":t.scope==="workers"?"worker only":t.guid?"guid":t.topic?"topic":"mesh";return e.jsxs("span",{className:`inline-flex items-center gap-1.5 px-2 py-0.5 text-2xs font-medium rounded-lg ${a}`,children:[t.label,e.jsx("span",{className:"text-2xs opacity-50",children:n})]})}function at({open:t,onClose:s,targets:r,onApply:a,isPending:n}){const[o,u]=i.useState("");return e.jsx(Te,{open:t,onClose:s,title:"Adjust Throttle",children:e.jsxs("div",{className:"space-y-4",children:[e.jsxs("div",{children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary mb-2",children:"Targets"}),e.jsx("div",{className:"flex flex-wrap gap-1.5",children:r.map((l,h)=>e.jsx(nt,{target:l},l.guid||l.topic||h))})]}),e.jsxs("div",{children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary mb-2",children:"Presets"}),e.jsx("div",{className:"flex flex-wrap gap-2",children:st.map(l=>e.jsx("button",{onClick:()=>a(l.ms),disabled:n,className:`px-3 py-1.5 text-xs rounded transition-colors ${l.ms===-1?"bg-status-error/10 text-status-error hover:bg-status-error/20":l.ms===0?"bg-status-success/10 text-status-success hover:bg-status-success/20":"bg-surface-sunken text-text-secondary hover:bg-surface-hover"} disabled:opacity-50`,children:l.label},l.label))})]}),e.jsxs("div",{children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary mb-2",children:"Custom delay (seconds)"}),e.jsxs("div",{className:"flex items-center gap-3",children:[e.jsx("input",{type:"number",step:"0.1",min:"0",value:o,onChange:l=>u(l.target.value),placeholder:"e.g. 2.5",className:"input text-xs py-1.5 px-3 w-28"}),e.jsx("button",{onClick:()=>{const l=parseFloat(o);isNaN(l)||l<0||a(Math.round(l*1e3))},disabled:n,className:"btn-primary text-xs py-1.5 px-4 disabled:opacity-50",children:"Apply"})]})]})]})})}function rt(){const{data:t}=Ce(),s=ee(),[r,a]=i.useState(null),[n,o]=i.useState(!1),u=(t==null?void 0:t.apps)??[],l=i.useCallback(async(d,k="all")=>{if(u.length===0)return;o(!0);const b=await Promise.allSettled(u.map(v=>s.mutateAsync({appId:v.appId,throttle:d,...k!=="all"?{scope:k}:{}}))),j=b.filter(v=>v.status==="rejected").length;j>0&&console.error(`Emergency throttle: ${j}/${b.length} apps failed`),o(!1),a(null)},[u,s]),h=d=>d==="engines"?"engines":d==="workers"?"workers":"everything";return r?e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsxs("span",{className:"text-xs text-status-error",children:["Pause ",h(r.scope),"?"]}),e.jsx("button",{onClick:()=>l(r.ms,r.scope),disabled:n,className:"px-2.5 py-1 text-xs rounded-md bg-status-error text-text-inverse hover:bg-status-error/90 transition-colors disabled:opacity-50",children:n?e.jsx(K,{className:"w-3.5 h-3.5 animate-spin"}):"Confirm"}),e.jsx("button",{onClick:()=>a(null),disabled:n,className:"px-2.5 py-1 text-xs text-text-tertiary hover:text-text-primary transition-colors disabled:opacity-50",children:"Cancel"})]}):e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsxs("button",{onClick:()=>a({ms:-1,scope:"all"}),disabled:n,className:"flex items-center gap-1.5 px-2.5 py-1 text-xs rounded-md text-status-error/80 hover:text-status-error hover:bg-status-error/10 transition-colors disabled:opacity-50",title:"Pause all engines and workers",children:[e.jsx(U,{className:"w-3.5 h-3.5"}),"Pause All"]}),e.jsxs("button",{onClick:()=>l(0),disabled:n,className:"flex items-center gap-1.5 px-2.5 py-1 text-xs rounded-md text-status-success/80 hover:text-status-success hover:bg-status-success/10 transition-colors disabled:opacity-50",title:"Resume all engines and workers",children:[n?e.jsx(K,{className:"w-3.5 h-3.5 animate-spin"}):e.jsx(Ee,{className:"w-3.5 h-3.5"}),"Resume All"]})]})}function ot({byStream:t,onNodeFilter:s}){const[r,a]=i.useState(!1);if(i.useEffect(()=>{a(!1);const d=requestAnimationFrame(()=>a(!0));return()=>cancelAnimationFrame(d)},[t]),t.length===0)return e.jsx("p",{className:"text-xs text-text-tertiary py-4 text-center",children:"No activity in this period"});const n=t.filter(d=>d.stream_type==="engine"),o=t.filter(d=>d.stream_type==="worker"),u=Math.max(...t.map(d=>d.count)),l=d=>{const k=u>0?d.count/u*100:0,b=d.stream_type==="engine",j=b?"(all engines)":ne(d.stream_name),v=b?"bg-status-active/70":"bg-accent/60",y=b?"text-status-active":"text-text-tertiary";return e.jsxs("div",{className:"flex items-center gap-3",children:[e.jsx("span",{className:`text-2xs font-mono ${y} w-36 truncate text-right shrink-0`,title:d.stream_name,children:j}),e.jsx("div",{className:"flex-1 h-4 bg-surface-sunken rounded overflow-hidden",children:e.jsx("div",{className:`h-full ${v} rounded transition-all duration-500 ease-out`,style:{width:r?`${k}%`:"0%"}})}),e.jsx("span",{className:"text-2xs font-mono tabular-nums text-text-secondary w-12 text-right shrink-0",children:d.count.toLocaleString()})]},`${d.stream_type}-${d.stream_name}`)},h="text-2xs uppercase tracking-widest font-semibold mb-1 cursor-pointer hover:underline";return e.jsxs("div",{className:"space-y-1.5",children:[n.length>0&&e.jsxs(e.Fragment,{children:[e.jsx("p",{className:`${h} text-status-active/70 hover:text-status-active`,onClick:()=>s==null?void 0:s("engines"),children:"Engine Stream"}),n.map(l),o.length>0&&e.jsx("div",{className:"h-2"})]}),o.length>0&&e.jsxs(e.Fragment,{children:[e.jsx("p",{className:`${h} text-accent/70 hover:text-accent`,onClick:()=>s==null?void 0:s("workers"),children:"Worker Streams"}),o.map(l)]})]})}function lt({queue:t,workers:s,expanded:r,onToggle:a,onWorkerClick:n,onResumeThrottle:o,onQueueThrottle:u,onResumeQueue:l,byStream:h,activeDuration:d}){const k=i.useMemo(()=>{const c=h.find(g=>g.stream_type==="worker"&&ne(g.stream_name)===t);return(c==null?void 0:c.count)??0},[h,t]),b=i.useMemo(()=>et(s),[s]),j=i.useMemo(()=>Xe(s),[s]),{errors:v}=i.useMemo(()=>T(s),[s]),y=b==="paused"?"bg-status-error":b==="degraded"?"bg-status-warning":"bg-status-success",x=i.useMemo(()=>[...s].sort((c,g)=>T([g]).total-T([c]).total),[s]),w=i.useMemo(()=>[{key:"engine_id",label:"Router",render:c=>{var m;const g=c.engine_id.replace(/^[^:]+::/,"").replace(/-[A-Za-z0-9_]{10,}$/,"")||c.engine_id,E=((m=c.engine_id.match(/^([^:]+)::/))==null?void 0:m[1])||"";return e.jsxs("div",{className:"flex items-center gap-2",title:c.engine_id,children:[e.jsx("span",{className:"text-xs text-text-secondary truncate max-w-[180px]",children:g}),E&&e.jsx("span",{className:"text-2xs text-text-tertiary/50",children:E})]})}},{key:"processed",label:"Processed",render:c=>{const g=T([c]);return e.jsx("span",{className:"text-xs font-mono tabular-nums text-text-tertiary",children:g.total>0?g.total.toLocaleString():"--"})},className:"w-24"},{key:"throttle",label:"Throttle",render:c=>{const g=c.throttle;return g===-1?e.jsx("span",{className:"text-xs text-status-error font-medium",children:"Paused"}):g&&g>0?e.jsx("span",{className:"text-xs text-status-warning font-medium",children:V(g)}):e.jsx("span",{className:"text-xs text-text-tertiary",children:"0"})},className:"w-24"},{key:"actions",label:"",render:c=>e.jsxs(De,{children:[P(c)&&e.jsx(Y,{icon:Z,title:"Resume (remove throttle)",onClick:()=>o(c),colorClass:"text-text-tertiary hover:text-status-success"}),e.jsx(Y,{icon:J,title:"Adjust throttle",onClick:()=>n(c)})]}),className:"w-16"}],[n,o]);return e.jsxs("div",{children:[e.jsxs("button",{onClick:()=>a(t),className:"group/row relative flex items-center gap-3 w-full py-2 hover:bg-surface-hover transition-colors text-left rounded",children:[e.jsx("span",{className:`w-2.5 h-2.5 rounded-full dot-ring shrink-0 ${y}`,title:b}),e.jsx(te,{className:`w-3.5 h-3.5 text-text-tertiary/50 transition-transform duration-200 ${r?"rotate-90":""}`,strokeWidth:2}),e.jsx(Be,{queue:t,size:"sm"}),e.jsx("span",{className:"flex-1"}),v>0&&e.jsxs("span",{className:"text-2xs text-status-error font-medium mr-2",children:[v," errors"]}),j>0&&e.jsxs("span",{className:"flex items-center gap-1 text-2xs text-status-warning w-20",children:[e.jsx(Re,{className:"w-3 h-3 shrink-0",strokeWidth:1.5}),e.jsx("span",{className:"font-mono tabular-nums",children:j.toLocaleString()})]}),e.jsxs("span",{className:`flex items-center gap-1 text-xs w-24 ${s.some(P)?"text-status-warning":"text-text-tertiary"}`,children:[e.jsx(Me,{className:"w-3 h-3 shrink-0",strokeWidth:1.5}),e.jsx("span",{className:"font-mono tabular-nums",children:s.length}),e.jsx("span",{children:"workers"})]}),e.jsx("span",{className:"flex items-center gap-1 text-xs font-mono text-text-tertiary w-28 justify-end mr-16",children:k>0?e.jsxs(e.Fragment,{children:[e.jsx(Pe,{className:"w-3 h-3 shrink-0",strokeWidth:1.5}),k.toLocaleString()," in ",d]}):e.jsx("span",{className:"text-text-tertiary/40",children:"—"})}),e.jsxs("span",{className:"absolute right-3 top-1/2 -translate-y-1/2 opacity-0 group-hover/row:opacity-100 transition-opacity flex items-center gap-2",children:[s.some(P)&&e.jsx(Z,{className:"w-4 h-4 text-text-tertiary hover:text-status-success",strokeWidth:1.5,onClick:c=>{c.stopPropagation(),l(t)}}),e.jsx(J,{className:"w-4 h-4 text-text-tertiary hover:text-accent",strokeWidth:1.5,onClick:c=>{c.stopPropagation(),u(t)}})]})]}),e.jsx(W,{open:r,children:e.jsx("div",{className:"ml-6",children:e.jsx(ze,{columns:w,data:x,keyFn:B,onRowClick:n,emptyMessage:"No workers",inline:!0})})})]})}let it=0;function ct(t){const s=t.data||{},r=s.topic?String(s.topic):"",a=s.guid?String(s.guid).slice(0,8):"";switch(t.type){case"pong":return r?`Worker ${a}... on "${r}" responded`:`Engine ${a}... responded`;case"ping":return"Roll call broadcast";case"throttle":{const n=s.throttle,o=r?`queue "${r}"`:a?`node ${a}...`:"all nodes";return`${V(n)} applied to ${o}`}case"job":return`Job ${a?a+"...":""} ${s.status||"updated"}`;case"work":return`Dispatched to "${r||"worker"}" ${a?"("+a+"...)":""}`;case"activate":return`Worker "${r||"unknown"}" activated`;case"cron":return`Cron triggered ${r?'"'+r+'"':""}`;default:return r||a||t.type}}function ut(t){const s=[];let r=0;for(;r<t.length;){const a=t[r];if(a.type==="pong"){let n=r+1;for(;n<t.length&&t[n].type==="pong";)n++;const o=t.slice(r,n);if(o.length>=3)s.push({kind:"group",type:"pong",count:o.length,firstTimestamp:o[o.length-1].timestamp,lastTimestamp:o[0].timestamp,events:o});else for(const u of o)s.push({kind:"single",event:u});r=n}else s.push({kind:"single",event:a}),r++}return s}function re({event:t}){const[s,r]=i.useState(!1);return e.jsxs("div",{className:"border-b border-surface-border/50 last:border-b-0",children:[e.jsxs("button",{onClick:()=>r(!s),className:"flex items-center gap-2 py-1.5 w-full text-left hover:bg-surface-hover/50 transition-colors",children:[e.jsx("span",{className:"text-2xs font-mono text-text-tertiary whitespace-nowrap tabular-nums shrink-0",children:new Date(t.timestamp).toLocaleTimeString([],{hour:"2-digit",minute:"2-digit",second:"2-digit"})}),e.jsx("span",{className:`text-2xs font-medium px-1 py-0.5 rounded ${se[t.type]||"text-text-tertiary"} bg-surface-sunken whitespace-nowrap shrink-0`,children:He[t.type]||t.type}),e.jsx("span",{className:"text-2xs text-text-secondary flex-1 min-w-0 truncate",children:ct(t)}),e.jsx("svg",{className:`w-2.5 h-2.5 text-text-tertiary shrink-0 transition-transform duration-150 ${s?"rotate-180":""}`,fill:"none",viewBox:"0 0 24 24",stroke:"currentColor",strokeWidth:2,children:e.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",d:"M19 9l-7 7-7-7"})})]}),e.jsx(W,{open:s,children:e.jsx("div",{className:"pb-2",children:e.jsx(Je,{data:t.data})})})]})}function dt({group:t}){const[s,r]=i.useState(!1),a=t.events.filter(o=>{var u;return!((u=o.data)!=null&&u.topic)}).length,n=t.count-a;return e.jsxs("div",{className:"border-b border-surface-border/50 last:border-b-0",children:[e.jsxs("button",{onClick:()=>r(!s),className:"flex items-center gap-2 py-1.5 w-full text-left hover:bg-surface-hover/50 transition-colors",children:[e.jsx("span",{className:"text-2xs font-mono text-text-tertiary whitespace-nowrap tabular-nums shrink-0",children:new Date(t.lastTimestamp).toLocaleTimeString([],{hour:"2-digit",minute:"2-digit",second:"2-digit"})}),e.jsx("span",{className:`text-2xs font-medium px-1 py-0.5 rounded ${se.pong} bg-surface-sunken whitespace-nowrap shrink-0`,children:"roll call"}),e.jsxs("span",{className:"text-2xs text-text-secondary flex-1 min-w-0 truncate",children:[t.count," nodes responded",a>0&&n>0?` (${a} engine${a!==1?"s":""}, ${n} worker${n!==1?"s":""})`:a>0?` (${a} engine${a!==1?"s":""})`:` (${n} worker${n!==1?"s":""})`]}),e.jsx("svg",{className:`w-2.5 h-2.5 text-text-tertiary shrink-0 transition-transform duration-150 ${s?"rotate-180":""}`,fill:"none",viewBox:"0 0 24 24",stroke:"currentColor",strokeWidth:2,children:e.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",d:"M19 9l-7 7-7-7"})})]}),e.jsx(W,{open:s,children:e.jsx("div",{className:"ml-4",children:t.events.map(o=>e.jsx(re,{event:o},o.id))})})]})}function xt({channels:t,onToggle:s,customFilter:r,onCustomFilterChange:a}){return e.jsxs("div",{className:"space-y-3 pb-3 border-b border-surface-border mb-3",children:[e.jsxs("div",{className:"flex items-center gap-2 mb-1",children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary",children:"Channels"}),e.jsx("p",{className:"text-2xs text-text-tertiary",children:"Unchecked channels are dropped before buffering"})]}),e.jsx("div",{className:"grid grid-cols-2 gap-1",children:ae.map(n=>e.jsxs("label",{className:"flex items-center gap-2 cursor-pointer py-0.5",children:[e.jsx("input",{type:"checkbox",checked:t.has(n.key),onChange:()=>s(n.key),className:"w-3 h-3 rounded border-border accent-accent"}),e.jsx("span",{className:"text-2xs text-text-secondary",title:n.description,children:n.label})]},n.key))}),e.jsxs("div",{children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary mb-1",children:"Text Filter"}),e.jsx("input",{type:"text",value:r,onChange:n=>a(n.target.value),placeholder:"pong",className:"input text-2xs font-mono py-1 px-2 w-full"}),e.jsxs("p",{className:"text-2xs text-text-tertiary mt-1",children:["Filter by event type, e.g. ",e.jsx("span",{className:"font-mono",children:"pong"}),", ",e.jsx("span",{className:"font-mono",children:"throttle"}),", or any text in the event data."]})]})]})}function mt({bridgeActive:t}){const[s,r]=i.useState(!1),[a,n]=i.useState(!1),[o,u]=i.useState([]),[l,h]=i.useState(()=>new Set(ae.map(x=>x.key))),[d,k]=i.useState(""),b=i.useRef(l);i.useEffect(()=>{b.current=l},[l]);const j=i.useRef(d);i.useEffect(()=>{j.current=d},[d]);const v=x=>{h(w=>{const c=new Set(w);return c.has(x)?c.delete(x):c.add(x),c})};Ie("lt.events.mesh.>",i.useCallback(x=>{var g;const w=((g=x.type)==null?void 0:g.replace("mesh.",""))||"unknown";if(!b.current.has(w))return;const c=j.current;c&&!`${w} ${JSON.stringify(x.data||x)}`.toLowerCase().includes(c.toLowerCase())||u(E=>[{id:++it,type:w,timestamp:x.timestamp||new Date().toISOString(),data:x.data||x},...E].slice(0,qe))},[]));const y=()=>u([]);return e.jsxs("div",{className:"border-l border-surface-border pl-6 pt-4 min-h-[300px] sticky top-14 self-start max-h-[calc(100vh-8rem)] flex flex-col",children:[e.jsxs("div",{className:"flex items-center gap-2 mb-3",children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary",children:"Event Stream"}),e.jsx(Ae,{className:`w-3 h-3 ${t?"text-status-success animate-pulse":"text-text-tertiary"}`}),e.jsx("span",{className:"text-2xs text-text-tertiary",children:t?"Live":"..."}),e.jsxs("span",{className:"ml-auto flex items-center gap-1",children:[e.jsx("button",{onClick:()=>{r(x=>!x),n(!1)},className:`p-1 rounded transition-colors ${s?"text-accent bg-accent/10":"text-text-tertiary hover:text-text-primary"}`,title:"Configure channels",children:e.jsx(Le,{className:"w-3.5 h-3.5"})}),e.jsx("button",{onClick:()=>{n(x=>!x),r(!1)},className:`p-1 rounded transition-colors ${a?"text-accent bg-accent/10":"text-text-tertiary hover:text-text-primary"}`,title:"View raw JSON",children:e.jsx(We,{className:"w-3.5 h-3.5"})}),o.length>0&&e.jsx("button",{onClick:y,className:"p-1 rounded text-text-tertiary hover:text-text-primary transition-colors",title:"Clear events",children:e.jsx(Qe,{className:"w-3.5 h-3.5"})})]})]}),e.jsx(W,{open:s,children:e.jsx(xt,{channels:l,onToggle:v,customFilter:d,onCustomFilterChange:k})}),e.jsx(W,{open:a,children:e.jsx("div",{className:"pb-3 border-b border-surface-border mb-3",children:e.jsx("pre",{className:"text-2xs font-mono text-text-tertiary bg-surface-sunken rounded-lg p-3 max-h-[50vh] overflow-auto whitespace-pre-wrap",children:JSON.stringify(o.slice(0,50),null,2)})})}),o.length>0&&e.jsxs("p",{className:"text-2xs text-text-tertiary mb-2",children:[o.length," events"]}),e.jsx("div",{className:"flex-1 overflow-y-auto",children:o.length===0?e.jsx("p",{className:"text-xs text-text-tertiary py-6 text-center",children:t?"Waiting for events...":"Subscribing..."}):ut(o).map((x,w)=>x.kind==="group"?e.jsx(dt,{group:x},`grp-${w}`):e.jsx(re,{event:x.event},x.event.id))})]})}function ht(t){const s=[],r=[],a=[];for(const n of t)P(n)?a.push(n):n.is_scout||T([n]).total>0?s.push(n):r.push(n);return s.sort((n,o)=>n.is_scout&&!o.is_scout?-1:!n.is_scout&&o.is_scout?1:T([o]).total-T([n]).total),r.sort((n,o)=>F(n.engine_id).localeCompare(F(o.engine_id))),a.sort((n,o)=>F(n.engine_id).localeCompare(F(o.engine_id))),{active:s,idle:r,paused:a}}function D({engine:t,isFirst:s,onThrottle:r}){const a=F(t.engine_id),n=Ze(t.engine_id),o=T([t]),u=t.stream_depth??0,l=P(t);return e.jsxs("div",{className:"group/row flex items-center gap-3 py-2 hover:bg-surface-hover/50 transition-colors rounded px-1",children:[l?e.jsx(U,{className:"w-3.5 h-3.5 text-status-warning shrink-0",strokeWidth:1.5}):e.jsx(Fe,{className:`w-3.5 h-3.5 shrink-0 ${o.total>0||t.is_scout?"text-status-success":"text-text-tertiary/30"}`,strokeWidth:1.5}),e.jsx("span",{className:`${s?"text-base font-medium":"text-xs"} text-text-primary truncate max-w-[180px]`,title:t.engine_id,children:a}),n&&e.jsx("span",{className:"text-2xs text-text-tertiary/50",children:n}),t.is_scout&&e.jsx("span",{className:"text-2xs text-status-warning uppercase tracking-widest",children:"scout"}),e.jsx("span",{className:"flex-1"}),l&&e.jsx("span",{className:"text-2xs text-status-warning",children:t.throttle===-1?"Paused":V(t.throttle)}),o.total>0&&e.jsx("span",{className:"text-2xs font-mono tabular-nums text-text-tertiary w-16 text-right",children:o.total.toLocaleString()}),u>0&&e.jsxs("span",{className:`text-2xs font-mono tabular-nums w-14 text-right ${u>100?"text-status-warning":"text-text-tertiary/50"}`,children:[u.toLocaleString()," q"]}),e.jsx("span",{className:"text-2xs font-mono text-text-tertiary/40 w-12 text-right",children:Ke(t.inited)}),e.jsx("span",{className:"opacity-0 group-hover/row:opacity-100 transition-opacity",children:e.jsx("button",{onClick:h=>{h.stopPropagation(),r(t)},className:"text-text-tertiary hover:text-accent transition-colors",title:l?"Resume / adjust throttle":"Pause / throttle",children:e.jsx(J,{className:"w-3.5 h-3.5",strokeWidth:1.5})})})]})}function X({label:t,engines:s,onThrottle:r}){const[a,n]=i.useState(!1);return s.length===0?null:e.jsxs("div",{className:"mt-1",children:[e.jsxs("button",{onClick:()=>n(!a),className:"flex items-center gap-1.5 text-2xs text-text-tertiary hover:text-text-secondary transition-colors py-1",children:[e.jsx(te,{className:`w-3 h-3 transition-transform duration-200 ${a?"rotate-90":""}`,strokeWidth:2}),s.length," ",t]}),e.jsx(W,{open:a,children:e.jsx("div",{className:"ml-1",children:s.map(o=>e.jsx(D,{engine:o,onThrottle:r},o.engine_id))})})]})}function pt({engines:t,onThrottle:s,isLoading:r}){const{active:a,idle:n,paused:o}=i.useMemo(()=>ht(t),[t]);return r?e.jsx("p",{className:"text-xs text-text-tertiary",children:"Discovering engines..."}):t.length===0?e.jsx("p",{className:"text-xs text-text-tertiary",children:"No engines found."}):a.length===0&&n.length===0?e.jsxs("div",{children:[e.jsxs("div",{className:"flex items-center gap-3 py-2",children:[e.jsx(U,{className:"w-4 h-4 text-status-error shrink-0",strokeWidth:1.5}),e.jsxs("span",{className:"text-base text-status-error font-medium",children:["All ",t.length," engines paused"]})]}),e.jsx("p",{className:"text-2xs text-text-tertiary ml-7",children:"Messages are accumulating. Resume at least one engine to restore processing."}),e.jsx("div",{className:"ml-1 mt-2",children:o.map(u=>e.jsx(D,{engine:u,onThrottle:s},u.engine_id))})]}):e.jsxs("div",{children:[a.map((u,l)=>e.jsx(D,{engine:u,isFirst:l===0,onThrottle:s},u.engine_id)),e.jsx(X,{label:"idle",engines:n,onThrottle:s}),e.jsx(X,{label:"paused",engines:o,onThrottle:s})]})}function gt({collapsed:t,toggleSection:s,activeDuration:r,streamStats:a,isLoading:n,queueMap:o,expandedQueues:u,toggleQueue:l,allQueuesExpanded:h,toggleAllQueues:d,handleRowClick:k,handleResumeThrottle:b,handleQueueThrottle:j,handleResumeQueue:v,engines:y,bridgeActive:x}){return e.jsxs("div",{className:"grid grid-cols-1 @split:grid-cols-[1fr_340px] gap-6",children:[e.jsxs("div",{className:"flex flex-col gap-12 mt-10",children:[e.jsx(I,{title:`Message Volume (${r})`,sectionKey:"volume",isCollapsed:!!t.volume,onToggle:s,contentClassName:"mt-4 ml-7",children:e.jsx(ot,{byStream:(a==null?void 0:a.byStream)??[],onNodeFilter:()=>{},onQueueFilter:()=>{}})}),e.jsx(I,{title:`Engine Routers (${y.length})`,sectionKey:"engines",isCollapsed:!!t.engines,onToggle:s,contentClassName:"mt-4 ml-7",children:e.jsx(pt,{engines:y,onThrottle:k,isLoading:n})}),e.jsx(I,{title:"Worker Routers",sectionKey:"queues",isCollapsed:!!t.queues,onToggle:s,contentClassName:"mt-4 ml-7 flex flex-col gap-0",children:n?e.jsx("p",{className:"text-xs text-text-tertiary",children:"Discovering mesh nodes..."}):o.size===0?e.jsx("p",{className:"text-xs text-text-tertiary",children:'No worker routers found. Click "Roll Call" to discover.'}):e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"flex justify-end mb-2",children:e.jsx("button",{onClick:d,className:"text-2xs text-accent hover:underline",children:h?"Collapse all":"Expand all"})}),[...o.entries()].sort(([w],[c])=>w.localeCompare(c)).map(([w,c])=>e.jsx(lt,{queue:w,workers:c,expanded:u.has(w),onToggle:l,onWorkerClick:k,onResumeThrottle:b,onQueueThrottle:j,onResumeQueue:v,byStream:(a==null?void 0:a.byStream)??[],activeDuration:r},w))]})})]}),e.jsx(mt,{bridgeActive:x})]})}function Mt(){const{namespace:t,available:s}=ve(),{filters:r,setFilter:a}=Ne({filters:{app_id:"",duration:"1h"}}),n=r.app_id||t,o=r.duration||"1h",u=$e(),l=6e4,{data:h,isLoading:d,error:k,refetch:b,isFetching:j}=Se(n,l),{data:v}=_e(n,o,void 0,l),y=i.useMemo(()=>[...(h==null?void 0:h.profiles)??[]].sort((S,_)=>{const z=S.worker_topic||S.stream||"",Q=_.worker_topic||_.stream||"";return!S.worker_topic&&_.worker_topic?-1:S.worker_topic&&!_.worker_topic?1:z.localeCompare(Q)}),[h==null?void 0:h.profiles]),x=i.useMemo(()=>y.filter(p=>!M(p)),[y]),w=i.useMemo(()=>y.filter(M),[y]),c=i.useMemo(()=>Ye(y),[y]),g=y.filter(P).length,E=i.useMemo(()=>{const p=new Set(s);return n&&p.add(n),[...p].sort().map(S=>({value:S,label:S}))},[s,n]),[m]=Ue(),C=m.get("queue"),[f,$]=i.useState(()=>C?new Set([C]):new Set),A=i.useCallback(p=>{$(S=>{const _=S.has(p),z=_?new Set:new Set([p]),Q=new URLSearchParams(window.location.search);_?Q.delete("queue"):Q.set("queue",p);const G=Q.toString();return window.history.pushState(null,"",`${window.location.pathname}${G?`?${G}`:""}`),z})},[]),N=c.size>0&&[...c.keys()].every(p=>f.has(p)),R=i.useCallback(()=>{$(N?new Set:new Set(c.keys()))},[N,c]),O="lt:controlplane:collapsed",[L,oe]=i.useState(()=>{try{const p=JSON.parse(localStorage.getItem(O)||"{}");return C&&(p.queues=!1),p}catch{return{}}}),le=i.useCallback(p=>{oe(S=>{const _={...S,[p]:!S[p]};return localStorage.setItem(O,JSON.stringify(_)),_})},[]),{throttleModalOpen:ie,throttleTargets:H,selectedThrottleTargets:ce,throttleMutation:ue,handleBulkThrottle:de,handleRowClick:xe,handleResumeThrottle:me,handleResumeQueue:he,handleQueueThrottle:pe,closeThrottleModal:ge}=tt({activeAppId:n,allProfiles:y,profiles:y}),fe=i.useMemo(()=>{const p=[{label:"Engines",value:x.length,dotClass:"bg-status-active"},{label:"Workers",value:w.length,dotClass:"bg-text-secondary"},{label:"Topics",value:c.size}];return g>0&&p.push({label:"Throttled",value:g,dotClass:"bg-status-warning"}),p},[x.length,w.length,c.size,g]),[q,be]=i.useState(!1),je=i.useCallback(()=>{u.mutate({appId:n},{onSuccess:()=>be(!0)})},[n,u]);return i.useEffect(()=>{!q&&n&&je()},[n]),e.jsxs("div",{children:[e.jsx(ye,{title:"Routers",docsHash:"#docs:dashboard.md:task-queues",stats:fe,actions:e.jsx(rt,{})}),e.jsxs(we,{actions:e.jsx("div",{className:"flex items-center gap-1",children:Ve.map(p=>e.jsx("button",{onClick:()=>a("duration",p.value),className:`px-3 py-1 text-xs rounded-full transition-colors ${o===p.value?"bg-accent text-text-inverse":"text-text-tertiary hover:text-text-primary hover:bg-surface-hover"}`,children:p.label},p.value))}),children:[e.jsx(ke,{label:"Application",value:r.app_id,onChange:p=>a("app_id",p),options:E}),e.jsxs("button",{onClick:()=>b(),disabled:j,className:"flex items-center gap-1.5 px-3 py-1.5 text-xs text-text-tertiary hover:text-text-primary transition-colors disabled:opacity-50",children:[e.jsx(Oe,{className:`w-3.5 h-3.5 ${j?"animate-spin":""}`}),"Roll Call"]})]}),k&&e.jsx("div",{className:"mb-6 px-4 py-3 rounded bg-status-error/10 border border-status-error/20",children:e.jsx("p",{className:"text-xs text-status-error font-medium",children:k.message==="Session expired"?"Session expired — please log in again.":`Failed to load mesh data: ${k.message}`})}),e.jsx(gt,{collapsed:L,toggleSection:le,activeDuration:o,streamStats:v,isLoading:d,queueMap:c,expandedQueues:f,toggleQueue:A,allQueuesExpanded:N,toggleAllQueues:R,handleRowClick:xe,handleResumeThrottle:me,handleQueueThrottle:pe,handleResumeQueue:he,engines:x,bridgeActive:q}),e.jsx(at,{open:ie,onClose:ge,targets:H.length>0?H:ce,onApply:de,isPending:ue.isPending})]})}export{Mt as ControlPlanePage};
|
|
2
|
-
//# sourceMappingURL=index-
|
|
1
|
+
import{a as i,j as e}from"./vendor-query-RUZdMvN6.js";import{P as ye}from"./PageHeaderWithStats-Ck0KZvXD.js";import{F as we,b as ke}from"./FilterBar-D7GghUsU.js";import{u as Ne}from"./useFilterParams-crmlBw_l.js";import{u as ve}from"./useNamespace-tZSOlge3.js";import{a as ee,u as Ce,b as $e,c as Se,d as _e}from"./controlplane-Zi4m_MSx.js";import{M as Te}from"./Modal-BU7No9NH.js";import{a1 as K,aR as U,h as Ee,aS as Z,aT as J,b as te,I as Re,ai as Me,al as Pe,R as Ae,Q as Le,aU as We,v as Qe,Z as Fe,aO as Oe}from"./vendor-icons-BpZiWH2f.js";import{C as I}from"./CollapsibleSection-CDADefUY.js";import{T as Be}from"./TaskQueuePill-D0QKBrN3.js";import{D as ze}from"./DataTable-Bir0Xs1p.js";import{C as W,c as Ie,J as Je}from"./index-CfAi1OsI.js";import{R as De,a as Y}from"./RowActions-eYrzgQSj.js";import{f as Ue}from"./vendor-react-CdqEC2zv.js";import"./EmptyState-lpUFYfun.js";const Ve=[{label:"15m",value:"15m"},{label:"30m",value:"30m"},{label:"1h",value:"1h"},{label:"1d",value:"1d"},{label:"7d",value:"7d"}],se={pong:"text-status-success",ping:"text-accent",throttle:"text-status-warning",job:"text-purple-400",work:"text-text-secondary",activate:"text-status-error",cron:"text-text-tertiary",user:"text-text-secondary"},He={pong:"roll call",ping:"ping",throttle:"throttle",job:"job",work:"work",activate:"activate",cron:"cron",user:"user"},qe=250;function M(t){return!!t.worker_topic}function P(t){return typeof t.throttle=="number"&&t.throttle!==0}function V(t){return t===void 0||t===0?"Normal":t===-1?"Paused":t>=864e5?`${(t/864e5).toFixed(0)}d`:t>=36e5?`${(t/36e5).toFixed(1)}h`:t>=6e4?`${(t/6e4).toFixed(1)}m`:t>=1e3?`${(t/1e3).toFixed(1)}s`:`${t}ms`}function Ge(t){if(!t)return null;const s=t.match(/^(\d{4})(\d{2})(\d{2})(\d{2})(\d{2})(\d{2})\.(\d+)$/);if(s){const[,a,n,o,u,l,h,d]=s;return new Date(`${a}-${n}-${o}T${u}:${l}:${h}.${d}Z`)}const r=new Date(t);return isNaN(r.getTime())?null:r}function Ke(t){const s=Ge(t);if(!s)return"--";const r=Date.now()-s.getTime();if(r<0||isNaN(r))return"--";const a=Math.floor(r/1e3);if(a<60)return`${a}s`;const n=Math.floor(a/60);if(n<60)return`${n}m`;const o=Math.floor(n/60);return o<24?`${o}h ${n%60}m`:`${Math.floor(o/24)}d ${o%24}h`}function ne(t){return t.replace(/^hmsh:[^:]+:x:/,"")||"(engine)"}function F(t){const s=t.match(/^([^:]+)::(.+?)-[A-Za-z0-9_]{10,}$/);return s?s[2]:t.length>20?t.slice(0,20)+"...":t}function Ze(t){const s=t.match(/^([^:]+)::/);return(s==null?void 0:s[1])||""}const ae=[{key:"pong",label:"Roll Call",description:"Node health check responses"},{key:"ping",label:"Ping",description:"Health check broadcasts"},{key:"throttle",label:"Throttle",description:"Throttle commands"},{key:"job",label:"Job",description:"Job lifecycle events"},{key:"work",label:"Work",description:"Worker dispatch events"},{key:"activate",label:"Activate",description:"Worker activation"},{key:"cron",label:"Cron",description:"Cron schedule triggers"},{key:"user",label:"User",description:"User-defined messages"}];function B(t){return`${t.engine_id}-${t.worker_topic||"engine"}`}function Ye(t){const s=new Map;for(const r of t){if(!r.worker_topic)continue;const a=r.worker_topic;s.has(a)||s.set(a,[]),s.get(a).push(r)}return s}function T(t){let s=0,r=0,a=0;for(const n of t)if(n.counts)for(const[o,u]of Object.entries(n.counts))s+=u,o==="200"?r+=u:o==="500"&&(a+=u);return{total:s,success:r,errors:a}}function Xe(t){let s=0;for(const r of t)typeof r.stream_depth=="number"&&(s+=r.stream_depth);return s}function et(t){if(t.length===0)return"healthy";if(t.every(a=>a.throttle===-1))return"paused";const{errors:r}=T(t);return r>0||t.some(P)?"degraded":"healthy"}function tt({activeAppId:t,allProfiles:s,profiles:r}){const a=ee(),[n,o]=i.useState(new Set),[u,l]=i.useState(!1),[h,d]=i.useState([]);i.useEffect(()=>{o(new Set)},[t]);const k=i.useCallback(m=>{o(C=>{const f=new Set(C),$=B(m);return f.has($)?f.delete($):f.add($),f})},[]),b=i.useCallback(()=>{n.size===r.length?o(new Set):o(new Set(r.map(B)))},[r,n.size]),j=i.useMemo(()=>{const m=r.filter(N=>n.has(B(N)));if(m.length===0)return[];if(m.length===s.length)return[{label:"Entire Mesh"}];const C=m.filter(N=>!M(N)),f=m.filter(M),$=[];for(const N of C)$.push({label:`Engine ${N.engine_id}`,guid:N.engine_id,scope:"engines"});const A=new Map;for(const N of f){const R=N.worker_topic;A.has(R)||A.set(R,[]),A.get(R).push(N)}for(const[N,R]of A){const O=s.filter(L=>L.worker_topic===N);if(R.length===O.length)$.push({label:N,topic:N});else for(const L of R)$.push({label:`${N} ${L.engine_id}`,guid:L.engine_id})}return $},[r,s,n]);return{selectedIds:n,setSelectedIds:o,toggleCheckbox:k,toggleAll:b,throttleModalOpen:u,throttleTargets:h,selectedThrottleTargets:j,throttleMutation:a,handleBulkThrottle:m=>{const C=h.length>0?h:j;for(const f of C)a.mutate({appId:t,throttle:m,...f.topic?{topic:f.topic}:{},...f.guid?{guid:f.guid}:{},...f.scope?{scope:f.scope}:{}});l(!1),d([])},handleRowClick:(m,C)=>{const f=M(m)?`${m.worker_topic} ${m.engine_id}`:`Engine ${m.engine_id}`;d([{label:f,guid:m.engine_id,scope:C||(M(m)?"workers":"engines")}]),l(!0)},handleBulkThrottleOpen:()=>{d(j),l(!0)},handleResumeThrottle:(m,C)=>{const f=C||(M(m)?"workers":"engines");a.mutate({appId:t,throttle:0,guid:m.engine_id,scope:f})},handleResumeQueue:m=>{a.mutate({appId:t,throttle:0,topic:m})},handleQueueThrottle:m=>{d([{label:m,topic:m}]),l(!0)},closeThrottleModal:()=>{l(!1),d([])}}}const st=[{label:"Resume",ms:0},{label:"0.5s",ms:500},{label:"1s",ms:1e3},{label:"5s",ms:5e3},{label:"30s",ms:3e4},{label:"Pause",ms:-1}];function nt({target:t}){const s=t.label==="Entire Mesh",r=t.label==="All Engines"||t.label.startsWith("Engine "),a=s?"bg-status-error/10 text-status-error":r?"bg-status-active/10 text-status-active":"bg-accent/[0.06] text-text-secondary",n=t.scope==="engines"?"engine only":t.scope==="workers"?"worker only":t.guid?"guid":t.topic?"topic":"mesh";return e.jsxs("span",{className:`inline-flex items-center gap-1.5 px-2 py-0.5 text-2xs font-medium rounded-lg ${a}`,children:[t.label,e.jsx("span",{className:"text-2xs opacity-50",children:n})]})}function at({open:t,onClose:s,targets:r,onApply:a,isPending:n}){const[o,u]=i.useState("");return e.jsx(Te,{open:t,onClose:s,title:"Adjust Throttle",children:e.jsxs("div",{className:"space-y-4",children:[e.jsxs("div",{children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary mb-2",children:"Targets"}),e.jsx("div",{className:"flex flex-wrap gap-1.5",children:r.map((l,h)=>e.jsx(nt,{target:l},l.guid||l.topic||h))})]}),e.jsxs("div",{children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary mb-2",children:"Presets"}),e.jsx("div",{className:"flex flex-wrap gap-2",children:st.map(l=>e.jsx("button",{onClick:()=>a(l.ms),disabled:n,className:`px-3 py-1.5 text-xs rounded transition-colors ${l.ms===-1?"bg-status-error/10 text-status-error hover:bg-status-error/20":l.ms===0?"bg-status-success/10 text-status-success hover:bg-status-success/20":"bg-surface-sunken text-text-secondary hover:bg-surface-hover"} disabled:opacity-50`,children:l.label},l.label))})]}),e.jsxs("div",{children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary mb-2",children:"Custom delay (seconds)"}),e.jsxs("div",{className:"flex items-center gap-3",children:[e.jsx("input",{type:"number",step:"0.1",min:"0",value:o,onChange:l=>u(l.target.value),placeholder:"e.g. 2.5",className:"input text-xs py-1.5 px-3 w-28"}),e.jsx("button",{onClick:()=>{const l=parseFloat(o);isNaN(l)||l<0||a(Math.round(l*1e3))},disabled:n,className:"btn-primary text-xs py-1.5 px-4 disabled:opacity-50",children:"Apply"})]})]})]})})}function rt(){const{data:t}=Ce(),s=ee(),[r,a]=i.useState(null),[n,o]=i.useState(!1),u=(t==null?void 0:t.apps)??[],l=i.useCallback(async(d,k="all")=>{if(u.length===0)return;o(!0);const b=await Promise.allSettled(u.map(v=>s.mutateAsync({appId:v.appId,throttle:d,...k!=="all"?{scope:k}:{}}))),j=b.filter(v=>v.status==="rejected").length;j>0&&console.error(`Emergency throttle: ${j}/${b.length} apps failed`),o(!1),a(null)},[u,s]),h=d=>d==="engines"?"engines":d==="workers"?"workers":"everything";return r?e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsxs("span",{className:"text-xs text-status-error",children:["Pause ",h(r.scope),"?"]}),e.jsx("button",{onClick:()=>l(r.ms,r.scope),disabled:n,className:"px-2.5 py-1 text-xs rounded-md bg-status-error text-text-inverse hover:bg-status-error/90 transition-colors disabled:opacity-50",children:n?e.jsx(K,{className:"w-3.5 h-3.5 animate-spin"}):"Confirm"}),e.jsx("button",{onClick:()=>a(null),disabled:n,className:"px-2.5 py-1 text-xs text-text-tertiary hover:text-text-primary transition-colors disabled:opacity-50",children:"Cancel"})]}):e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsxs("button",{onClick:()=>a({ms:-1,scope:"all"}),disabled:n,className:"flex items-center gap-1.5 px-2.5 py-1 text-xs rounded-md text-status-error/80 hover:text-status-error hover:bg-status-error/10 transition-colors disabled:opacity-50",title:"Pause all engines and workers",children:[e.jsx(U,{className:"w-3.5 h-3.5"}),"Pause All"]}),e.jsxs("button",{onClick:()=>l(0),disabled:n,className:"flex items-center gap-1.5 px-2.5 py-1 text-xs rounded-md text-status-success/80 hover:text-status-success hover:bg-status-success/10 transition-colors disabled:opacity-50",title:"Resume all engines and workers",children:[n?e.jsx(K,{className:"w-3.5 h-3.5 animate-spin"}):e.jsx(Ee,{className:"w-3.5 h-3.5"}),"Resume All"]})]})}function ot({byStream:t,onNodeFilter:s}){const[r,a]=i.useState(!1);if(i.useEffect(()=>{a(!1);const d=requestAnimationFrame(()=>a(!0));return()=>cancelAnimationFrame(d)},[t]),t.length===0)return e.jsx("p",{className:"text-xs text-text-tertiary py-4 text-center",children:"No activity in this period"});const n=t.filter(d=>d.stream_type==="engine"),o=t.filter(d=>d.stream_type==="worker"),u=Math.max(...t.map(d=>d.count)),l=d=>{const k=u>0?d.count/u*100:0,b=d.stream_type==="engine",j=b?"(all engines)":ne(d.stream_name),v=b?"bg-status-active/70":"bg-accent/60",y=b?"text-status-active":"text-text-tertiary";return e.jsxs("div",{className:"flex items-center gap-3",children:[e.jsx("span",{className:`text-2xs font-mono ${y} w-36 truncate text-right shrink-0`,title:d.stream_name,children:j}),e.jsx("div",{className:"flex-1 h-4 bg-surface-sunken rounded overflow-hidden",children:e.jsx("div",{className:`h-full ${v} rounded transition-all duration-500 ease-out`,style:{width:r?`${k}%`:"0%"}})}),e.jsx("span",{className:"text-2xs font-mono tabular-nums text-text-secondary w-12 text-right shrink-0",children:d.count.toLocaleString()})]},`${d.stream_type}-${d.stream_name}`)},h="text-2xs uppercase tracking-widest font-semibold mb-1 cursor-pointer hover:underline";return e.jsxs("div",{className:"space-y-1.5",children:[n.length>0&&e.jsxs(e.Fragment,{children:[e.jsx("p",{className:`${h} text-status-active/70 hover:text-status-active`,onClick:()=>s==null?void 0:s("engines"),children:"Engine Stream"}),n.map(l),o.length>0&&e.jsx("div",{className:"h-2"})]}),o.length>0&&e.jsxs(e.Fragment,{children:[e.jsx("p",{className:`${h} text-accent/70 hover:text-accent`,onClick:()=>s==null?void 0:s("workers"),children:"Worker Streams"}),o.map(l)]})]})}function lt({queue:t,workers:s,expanded:r,onToggle:a,onWorkerClick:n,onResumeThrottle:o,onQueueThrottle:u,onResumeQueue:l,byStream:h,activeDuration:d}){const k=i.useMemo(()=>{const c=h.find(g=>g.stream_type==="worker"&&ne(g.stream_name)===t);return(c==null?void 0:c.count)??0},[h,t]),b=i.useMemo(()=>et(s),[s]),j=i.useMemo(()=>Xe(s),[s]),{errors:v}=i.useMemo(()=>T(s),[s]),y=b==="paused"?"bg-status-error":b==="degraded"?"bg-status-warning":"bg-status-success",x=i.useMemo(()=>[...s].sort((c,g)=>T([g]).total-T([c]).total),[s]),w=i.useMemo(()=>[{key:"engine_id",label:"Router",render:c=>{var m;const g=c.engine_id.replace(/^[^:]+::/,"").replace(/-[A-Za-z0-9_]{10,}$/,"")||c.engine_id,E=((m=c.engine_id.match(/^([^:]+)::/))==null?void 0:m[1])||"";return e.jsxs("div",{className:"flex items-center gap-2",title:c.engine_id,children:[e.jsx("span",{className:"text-xs text-text-secondary truncate max-w-[180px]",children:g}),E&&e.jsx("span",{className:"text-2xs text-text-tertiary/50",children:E})]})}},{key:"processed",label:"Processed",render:c=>{const g=T([c]);return e.jsx("span",{className:"text-xs font-mono tabular-nums text-text-tertiary",children:g.total>0?g.total.toLocaleString():"--"})},className:"w-24"},{key:"throttle",label:"Throttle",render:c=>{const g=c.throttle;return g===-1?e.jsx("span",{className:"text-xs text-status-error font-medium",children:"Paused"}):g&&g>0?e.jsx("span",{className:"text-xs text-status-warning font-medium",children:V(g)}):e.jsx("span",{className:"text-xs text-text-tertiary",children:"0"})},className:"w-24"},{key:"actions",label:"",render:c=>e.jsxs(De,{children:[P(c)&&e.jsx(Y,{icon:Z,title:"Resume (remove throttle)",onClick:()=>o(c),colorClass:"text-text-tertiary hover:text-status-success"}),e.jsx(Y,{icon:J,title:"Adjust throttle",onClick:()=>n(c)})]}),className:"w-16"}],[n,o]);return e.jsxs("div",{children:[e.jsxs("button",{onClick:()=>a(t),className:"group/row relative flex items-center gap-3 w-full py-2 hover:bg-surface-hover transition-colors text-left rounded",children:[e.jsx("span",{className:`w-2.5 h-2.5 rounded-full dot-ring shrink-0 ${y}`,title:b}),e.jsx(te,{className:`w-3.5 h-3.5 text-text-tertiary/50 transition-transform duration-200 ${r?"rotate-90":""}`,strokeWidth:2}),e.jsx(Be,{queue:t,size:"sm"}),e.jsx("span",{className:"flex-1"}),v>0&&e.jsxs("span",{className:"text-2xs text-status-error font-medium mr-2",children:[v," errors"]}),j>0&&e.jsxs("span",{className:"flex items-center gap-1 text-2xs text-status-warning w-20",children:[e.jsx(Re,{className:"w-3 h-3 shrink-0",strokeWidth:1.5}),e.jsx("span",{className:"font-mono tabular-nums",children:j.toLocaleString()})]}),e.jsxs("span",{className:`flex items-center gap-1 text-xs w-24 ${s.some(P)?"text-status-warning":"text-text-tertiary"}`,children:[e.jsx(Me,{className:"w-3 h-3 shrink-0",strokeWidth:1.5}),e.jsx("span",{className:"font-mono tabular-nums",children:s.length}),e.jsx("span",{children:"workers"})]}),e.jsx("span",{className:"flex items-center gap-1 text-xs font-mono text-text-tertiary w-28 justify-end mr-16",children:k>0?e.jsxs(e.Fragment,{children:[e.jsx(Pe,{className:"w-3 h-3 shrink-0",strokeWidth:1.5}),k.toLocaleString()," in ",d]}):e.jsx("span",{className:"text-text-tertiary/40",children:"—"})}),e.jsxs("span",{className:"absolute right-3 top-1/2 -translate-y-1/2 opacity-0 group-hover/row:opacity-100 transition-opacity flex items-center gap-2",children:[s.some(P)&&e.jsx(Z,{className:"w-4 h-4 text-text-tertiary hover:text-status-success",strokeWidth:1.5,onClick:c=>{c.stopPropagation(),l(t)}}),e.jsx(J,{className:"w-4 h-4 text-text-tertiary hover:text-accent",strokeWidth:1.5,onClick:c=>{c.stopPropagation(),u(t)}})]})]}),e.jsx(W,{open:r,children:e.jsx("div",{className:"ml-6",children:e.jsx(ze,{columns:w,data:x,keyFn:B,onRowClick:n,emptyMessage:"No workers",inline:!0})})})]})}let it=0;function ct(t){const s=t.data||{},r=s.topic?String(s.topic):"",a=s.guid?String(s.guid).slice(0,8):"";switch(t.type){case"pong":return r?`Worker ${a}... on "${r}" responded`:`Engine ${a}... responded`;case"ping":return"Roll call broadcast";case"throttle":{const n=s.throttle,o=r?`queue "${r}"`:a?`node ${a}...`:"all nodes";return`${V(n)} applied to ${o}`}case"job":return`Job ${a?a+"...":""} ${s.status||"updated"}`;case"work":return`Dispatched to "${r||"worker"}" ${a?"("+a+"...)":""}`;case"activate":return`Worker "${r||"unknown"}" activated`;case"cron":return`Cron triggered ${r?'"'+r+'"':""}`;default:return r||a||t.type}}function ut(t){const s=[];let r=0;for(;r<t.length;){const a=t[r];if(a.type==="pong"){let n=r+1;for(;n<t.length&&t[n].type==="pong";)n++;const o=t.slice(r,n);if(o.length>=3)s.push({kind:"group",type:"pong",count:o.length,firstTimestamp:o[o.length-1].timestamp,lastTimestamp:o[0].timestamp,events:o});else for(const u of o)s.push({kind:"single",event:u});r=n}else s.push({kind:"single",event:a}),r++}return s}function re({event:t}){const[s,r]=i.useState(!1);return e.jsxs("div",{className:"border-b border-surface-border/50 last:border-b-0",children:[e.jsxs("button",{onClick:()=>r(!s),className:"flex items-center gap-2 py-1.5 w-full text-left hover:bg-surface-hover/50 transition-colors",children:[e.jsx("span",{className:"text-2xs font-mono text-text-tertiary whitespace-nowrap tabular-nums shrink-0",children:new Date(t.timestamp).toLocaleTimeString([],{hour:"2-digit",minute:"2-digit",second:"2-digit"})}),e.jsx("span",{className:`text-2xs font-medium px-1 py-0.5 rounded ${se[t.type]||"text-text-tertiary"} bg-surface-sunken whitespace-nowrap shrink-0`,children:He[t.type]||t.type}),e.jsx("span",{className:"text-2xs text-text-secondary flex-1 min-w-0 truncate",children:ct(t)}),e.jsx("svg",{className:`w-2.5 h-2.5 text-text-tertiary shrink-0 transition-transform duration-150 ${s?"rotate-180":""}`,fill:"none",viewBox:"0 0 24 24",stroke:"currentColor",strokeWidth:2,children:e.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",d:"M19 9l-7 7-7-7"})})]}),e.jsx(W,{open:s,children:e.jsx("div",{className:"pb-2",children:e.jsx(Je,{data:t.data})})})]})}function dt({group:t}){const[s,r]=i.useState(!1),a=t.events.filter(o=>{var u;return!((u=o.data)!=null&&u.topic)}).length,n=t.count-a;return e.jsxs("div",{className:"border-b border-surface-border/50 last:border-b-0",children:[e.jsxs("button",{onClick:()=>r(!s),className:"flex items-center gap-2 py-1.5 w-full text-left hover:bg-surface-hover/50 transition-colors",children:[e.jsx("span",{className:"text-2xs font-mono text-text-tertiary whitespace-nowrap tabular-nums shrink-0",children:new Date(t.lastTimestamp).toLocaleTimeString([],{hour:"2-digit",minute:"2-digit",second:"2-digit"})}),e.jsx("span",{className:`text-2xs font-medium px-1 py-0.5 rounded ${se.pong} bg-surface-sunken whitespace-nowrap shrink-0`,children:"roll call"}),e.jsxs("span",{className:"text-2xs text-text-secondary flex-1 min-w-0 truncate",children:[t.count," nodes responded",a>0&&n>0?` (${a} engine${a!==1?"s":""}, ${n} worker${n!==1?"s":""})`:a>0?` (${a} engine${a!==1?"s":""})`:` (${n} worker${n!==1?"s":""})`]}),e.jsx("svg",{className:`w-2.5 h-2.5 text-text-tertiary shrink-0 transition-transform duration-150 ${s?"rotate-180":""}`,fill:"none",viewBox:"0 0 24 24",stroke:"currentColor",strokeWidth:2,children:e.jsx("path",{strokeLinecap:"round",strokeLinejoin:"round",d:"M19 9l-7 7-7-7"})})]}),e.jsx(W,{open:s,children:e.jsx("div",{className:"ml-4",children:t.events.map(o=>e.jsx(re,{event:o},o.id))})})]})}function xt({channels:t,onToggle:s,customFilter:r,onCustomFilterChange:a}){return e.jsxs("div",{className:"space-y-3 pb-3 border-b border-surface-border mb-3",children:[e.jsxs("div",{className:"flex items-center gap-2 mb-1",children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary",children:"Channels"}),e.jsx("p",{className:"text-2xs text-text-tertiary",children:"Unchecked channels are dropped before buffering"})]}),e.jsx("div",{className:"grid grid-cols-2 gap-1",children:ae.map(n=>e.jsxs("label",{className:"flex items-center gap-2 cursor-pointer py-0.5",children:[e.jsx("input",{type:"checkbox",checked:t.has(n.key),onChange:()=>s(n.key),className:"w-3 h-3 rounded border-border accent-accent"}),e.jsx("span",{className:"text-2xs text-text-secondary",title:n.description,children:n.label})]},n.key))}),e.jsxs("div",{children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary mb-1",children:"Text Filter"}),e.jsx("input",{type:"text",value:r,onChange:n=>a(n.target.value),placeholder:"pong",className:"input text-2xs font-mono py-1 px-2 w-full"}),e.jsxs("p",{className:"text-2xs text-text-tertiary mt-1",children:["Filter by event type, e.g. ",e.jsx("span",{className:"font-mono",children:"pong"}),", ",e.jsx("span",{className:"font-mono",children:"throttle"}),", or any text in the event data."]})]})]})}function mt({bridgeActive:t}){const[s,r]=i.useState(!1),[a,n]=i.useState(!1),[o,u]=i.useState([]),[l,h]=i.useState(()=>new Set(ae.map(x=>x.key))),[d,k]=i.useState(""),b=i.useRef(l);i.useEffect(()=>{b.current=l},[l]);const j=i.useRef(d);i.useEffect(()=>{j.current=d},[d]);const v=x=>{h(w=>{const c=new Set(w);return c.has(x)?c.delete(x):c.add(x),c})};Ie("lt.events.mesh.>",i.useCallback(x=>{var g;const w=((g=x.type)==null?void 0:g.replace("mesh.",""))||"unknown";if(!b.current.has(w))return;const c=j.current;c&&!`${w} ${JSON.stringify(x.data||x)}`.toLowerCase().includes(c.toLowerCase())||u(E=>[{id:++it,type:w,timestamp:x.timestamp||new Date().toISOString(),data:x.data||x},...E].slice(0,qe))},[]));const y=()=>u([]);return e.jsxs("div",{className:"border-l border-surface-border pl-6 pt-4 min-h-[300px] sticky top-14 self-start max-h-[calc(100vh-8rem)] flex flex-col",children:[e.jsxs("div",{className:"flex items-center gap-2 mb-3",children:[e.jsx("p",{className:"text-2xs font-semibold uppercase tracking-widest text-text-tertiary",children:"Event Stream"}),e.jsx(Ae,{className:`w-3 h-3 ${t?"text-status-success animate-pulse":"text-text-tertiary"}`}),e.jsx("span",{className:"text-2xs text-text-tertiary",children:t?"Live":"..."}),e.jsxs("span",{className:"ml-auto flex items-center gap-1",children:[e.jsx("button",{onClick:()=>{r(x=>!x),n(!1)},className:`p-1 rounded transition-colors ${s?"text-accent bg-accent/10":"text-text-tertiary hover:text-text-primary"}`,title:"Configure channels",children:e.jsx(Le,{className:"w-3.5 h-3.5"})}),e.jsx("button",{onClick:()=>{n(x=>!x),r(!1)},className:`p-1 rounded transition-colors ${a?"text-accent bg-accent/10":"text-text-tertiary hover:text-text-primary"}`,title:"View raw JSON",children:e.jsx(We,{className:"w-3.5 h-3.5"})}),o.length>0&&e.jsx("button",{onClick:y,className:"p-1 rounded text-text-tertiary hover:text-text-primary transition-colors",title:"Clear events",children:e.jsx(Qe,{className:"w-3.5 h-3.5"})})]})]}),e.jsx(W,{open:s,children:e.jsx(xt,{channels:l,onToggle:v,customFilter:d,onCustomFilterChange:k})}),e.jsx(W,{open:a,children:e.jsx("div",{className:"pb-3 border-b border-surface-border mb-3",children:e.jsx("pre",{className:"text-2xs font-mono text-text-tertiary bg-surface-sunken rounded-lg p-3 max-h-[50vh] overflow-auto whitespace-pre-wrap",children:JSON.stringify(o.slice(0,50),null,2)})})}),o.length>0&&e.jsxs("p",{className:"text-2xs text-text-tertiary mb-2",children:[o.length," events"]}),e.jsx("div",{className:"flex-1 overflow-y-auto",children:o.length===0?e.jsx("p",{className:"text-xs text-text-tertiary py-6 text-center",children:t?"Waiting for events...":"Subscribing..."}):ut(o).map((x,w)=>x.kind==="group"?e.jsx(dt,{group:x},`grp-${w}`):e.jsx(re,{event:x.event},x.event.id))})]})}function ht(t){const s=[],r=[],a=[];for(const n of t)P(n)?a.push(n):n.is_scout||T([n]).total>0?s.push(n):r.push(n);return s.sort((n,o)=>n.is_scout&&!o.is_scout?-1:!n.is_scout&&o.is_scout?1:T([o]).total-T([n]).total),r.sort((n,o)=>F(n.engine_id).localeCompare(F(o.engine_id))),a.sort((n,o)=>F(n.engine_id).localeCompare(F(o.engine_id))),{active:s,idle:r,paused:a}}function D({engine:t,isFirst:s,onThrottle:r}){const a=F(t.engine_id),n=Ze(t.engine_id),o=T([t]),u=t.stream_depth??0,l=P(t);return e.jsxs("div",{className:"group/row flex items-center gap-3 py-2 hover:bg-surface-hover/50 transition-colors rounded px-1",children:[l?e.jsx(U,{className:"w-3.5 h-3.5 text-status-warning shrink-0",strokeWidth:1.5}):e.jsx(Fe,{className:`w-3.5 h-3.5 shrink-0 ${o.total>0||t.is_scout?"text-status-success":"text-text-tertiary/30"}`,strokeWidth:1.5}),e.jsx("span",{className:`${s?"text-base font-medium":"text-xs"} text-text-primary truncate max-w-[180px]`,title:t.engine_id,children:a}),n&&e.jsx("span",{className:"text-2xs text-text-tertiary/50",children:n}),t.is_scout&&e.jsx("span",{className:"text-2xs text-status-warning uppercase tracking-widest",children:"scout"}),e.jsx("span",{className:"flex-1"}),l&&e.jsx("span",{className:"text-2xs text-status-warning",children:t.throttle===-1?"Paused":V(t.throttle)}),o.total>0&&e.jsx("span",{className:"text-2xs font-mono tabular-nums text-text-tertiary w-16 text-right",children:o.total.toLocaleString()}),u>0&&e.jsxs("span",{className:`text-2xs font-mono tabular-nums w-14 text-right ${u>100?"text-status-warning":"text-text-tertiary/50"}`,children:[u.toLocaleString()," q"]}),e.jsx("span",{className:"text-2xs font-mono text-text-tertiary/40 w-12 text-right",children:Ke(t.inited)}),e.jsx("span",{className:"opacity-0 group-hover/row:opacity-100 transition-opacity",children:e.jsx("button",{onClick:h=>{h.stopPropagation(),r(t)},className:"text-text-tertiary hover:text-accent transition-colors",title:l?"Resume / adjust throttle":"Pause / throttle",children:e.jsx(J,{className:"w-3.5 h-3.5",strokeWidth:1.5})})})]})}function X({label:t,engines:s,onThrottle:r}){const[a,n]=i.useState(!1);return s.length===0?null:e.jsxs("div",{className:"mt-1",children:[e.jsxs("button",{onClick:()=>n(!a),className:"flex items-center gap-1.5 text-2xs text-text-tertiary hover:text-text-secondary transition-colors py-1",children:[e.jsx(te,{className:`w-3 h-3 transition-transform duration-200 ${a?"rotate-90":""}`,strokeWidth:2}),s.length," ",t]}),e.jsx(W,{open:a,children:e.jsx("div",{className:"ml-1",children:s.map(o=>e.jsx(D,{engine:o,onThrottle:r},o.engine_id))})})]})}function pt({engines:t,onThrottle:s,isLoading:r}){const{active:a,idle:n,paused:o}=i.useMemo(()=>ht(t),[t]);return r?e.jsx("p",{className:"text-xs text-text-tertiary",children:"Discovering engines..."}):t.length===0?e.jsx("p",{className:"text-xs text-text-tertiary",children:"No engines found."}):a.length===0&&n.length===0?e.jsxs("div",{children:[e.jsxs("div",{className:"flex items-center gap-3 py-2",children:[e.jsx(U,{className:"w-4 h-4 text-status-error shrink-0",strokeWidth:1.5}),e.jsxs("span",{className:"text-base text-status-error font-medium",children:["All ",t.length," engines paused"]})]}),e.jsx("p",{className:"text-2xs text-text-tertiary ml-7",children:"Messages are accumulating. Resume at least one engine to restore processing."}),e.jsx("div",{className:"ml-1 mt-2",children:o.map(u=>e.jsx(D,{engine:u,onThrottle:s},u.engine_id))})]}):e.jsxs("div",{children:[a.map((u,l)=>e.jsx(D,{engine:u,isFirst:l===0,onThrottle:s},u.engine_id)),e.jsx(X,{label:"idle",engines:n,onThrottle:s}),e.jsx(X,{label:"paused",engines:o,onThrottle:s})]})}function gt({collapsed:t,toggleSection:s,activeDuration:r,streamStats:a,isLoading:n,queueMap:o,expandedQueues:u,toggleQueue:l,allQueuesExpanded:h,toggleAllQueues:d,handleRowClick:k,handleResumeThrottle:b,handleQueueThrottle:j,handleResumeQueue:v,engines:y,bridgeActive:x}){return e.jsxs("div",{className:"grid grid-cols-1 @split:grid-cols-[1fr_340px] gap-6",children:[e.jsxs("div",{className:"flex flex-col gap-12 mt-10",children:[e.jsx(I,{title:`Message Volume (${r})`,sectionKey:"volume",isCollapsed:!!t.volume,onToggle:s,contentClassName:"mt-4 ml-7",children:e.jsx(ot,{byStream:(a==null?void 0:a.byStream)??[],onNodeFilter:()=>{},onQueueFilter:()=>{}})}),e.jsx(I,{title:`Engine Routers (${y.length})`,sectionKey:"engines",isCollapsed:!!t.engines,onToggle:s,contentClassName:"mt-4 ml-7",children:e.jsx(pt,{engines:y,onThrottle:k,isLoading:n})}),e.jsx(I,{title:"Worker Routers",sectionKey:"queues",isCollapsed:!!t.queues,onToggle:s,contentClassName:"mt-4 ml-7 flex flex-col gap-0",children:n?e.jsx("p",{className:"text-xs text-text-tertiary",children:"Discovering mesh nodes..."}):o.size===0?e.jsx("p",{className:"text-xs text-text-tertiary",children:'No worker routers found. Click "Roll Call" to discover.'}):e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"flex justify-end mb-2",children:e.jsx("button",{onClick:d,className:"text-2xs text-accent hover:underline",children:h?"Collapse all":"Expand all"})}),[...o.entries()].sort(([w],[c])=>w.localeCompare(c)).map(([w,c])=>e.jsx(lt,{queue:w,workers:c,expanded:u.has(w),onToggle:l,onWorkerClick:k,onResumeThrottle:b,onQueueThrottle:j,onResumeQueue:v,byStream:(a==null?void 0:a.byStream)??[],activeDuration:r},w))]})})]}),e.jsx(mt,{bridgeActive:x})]})}function Mt(){const{namespace:t,available:s}=ve(),{filters:r,setFilter:a}=Ne({filters:{app_id:"",duration:"1h"}}),n=r.app_id||t,o=r.duration||"1h",u=$e(),l=6e4,{data:h,isLoading:d,error:k,refetch:b,isFetching:j}=Se(n,l),{data:v}=_e(n,o,void 0,l),y=i.useMemo(()=>[...(h==null?void 0:h.profiles)??[]].sort((S,_)=>{const z=S.worker_topic||S.stream||"",Q=_.worker_topic||_.stream||"";return!S.worker_topic&&_.worker_topic?-1:S.worker_topic&&!_.worker_topic?1:z.localeCompare(Q)}),[h==null?void 0:h.profiles]),x=i.useMemo(()=>y.filter(p=>!M(p)),[y]),w=i.useMemo(()=>y.filter(M),[y]),c=i.useMemo(()=>Ye(y),[y]),g=y.filter(P).length,E=i.useMemo(()=>{const p=new Set(s);return n&&p.add(n),[...p].sort().map(S=>({value:S,label:S}))},[s,n]),[m]=Ue(),C=m.get("queue"),[f,$]=i.useState(()=>C?new Set([C]):new Set),A=i.useCallback(p=>{$(S=>{const _=S.has(p),z=_?new Set:new Set([p]),Q=new URLSearchParams(window.location.search);_?Q.delete("queue"):Q.set("queue",p);const G=Q.toString();return window.history.pushState(null,"",`${window.location.pathname}${G?`?${G}`:""}`),z})},[]),N=c.size>0&&[...c.keys()].every(p=>f.has(p)),R=i.useCallback(()=>{$(N?new Set:new Set(c.keys()))},[N,c]),O="lt:controlplane:collapsed",[L,oe]=i.useState(()=>{try{const p=JSON.parse(localStorage.getItem(O)||"{}");return C&&(p.queues=!1),p}catch{return{}}}),le=i.useCallback(p=>{oe(S=>{const _={...S,[p]:!S[p]};return localStorage.setItem(O,JSON.stringify(_)),_})},[]),{throttleModalOpen:ie,throttleTargets:H,selectedThrottleTargets:ce,throttleMutation:ue,handleBulkThrottle:de,handleRowClick:xe,handleResumeThrottle:me,handleResumeQueue:he,handleQueueThrottle:pe,closeThrottleModal:ge}=tt({activeAppId:n,allProfiles:y,profiles:y}),fe=i.useMemo(()=>{const p=[{label:"Engines",value:x.length,dotClass:"bg-status-active"},{label:"Workers",value:w.length,dotClass:"bg-text-secondary"},{label:"Topics",value:c.size}];return g>0&&p.push({label:"Throttled",value:g,dotClass:"bg-status-warning"}),p},[x.length,w.length,c.size,g]),[q,be]=i.useState(!1),je=i.useCallback(()=>{u.mutate({appId:n},{onSuccess:()=>be(!0)})},[n,u]);return i.useEffect(()=>{!q&&n&&je()},[n]),e.jsxs("div",{children:[e.jsx(ye,{title:"Routers",docsHash:"#docs:dashboard.md:task-queues",stats:fe,actions:e.jsx(rt,{})}),e.jsxs(we,{actions:e.jsx("div",{className:"flex items-center gap-1",children:Ve.map(p=>e.jsx("button",{onClick:()=>a("duration",p.value),className:`px-3 py-1 text-xs rounded-full transition-colors ${o===p.value?"bg-accent text-text-inverse":"text-text-tertiary hover:text-text-primary hover:bg-surface-hover"}`,children:p.label},p.value))}),children:[e.jsx(ke,{label:"Application",value:r.app_id,onChange:p=>a("app_id",p),options:E}),e.jsxs("button",{onClick:()=>b(),disabled:j,className:"flex items-center gap-1.5 px-3 py-1.5 text-xs text-text-tertiary hover:text-text-primary transition-colors disabled:opacity-50",children:[e.jsx(Oe,{className:`w-3.5 h-3.5 ${j?"animate-spin":""}`}),"Roll Call"]})]}),k&&e.jsx("div",{className:"mb-6 px-4 py-3 rounded bg-status-error/10 border border-status-error/20",children:e.jsx("p",{className:"text-xs text-status-error font-medium",children:k.message==="Session expired"?"Session expired — please log in again.":`Failed to load mesh data: ${k.message}`})}),e.jsx(gt,{collapsed:L,toggleSection:le,activeDuration:o,streamStats:v,isLoading:d,queueMap:c,expandedQueues:f,toggleQueue:A,allQueuesExpanded:N,toggleAllQueues:R,handleRowClick:xe,handleResumeThrottle:me,handleQueueThrottle:pe,handleResumeQueue:he,engines:x,bridgeActive:q}),e.jsx(at,{open:ie,onClose:ge,targets:H.length>0?H:ce,onApply:de,isPending:ue.isPending})]})}export{Mt as ControlPlanePage};
|
|
2
|
+
//# sourceMappingURL=index-CJu2PBNx.js.map
|