@sudobility/testomniac_ui 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (266) hide show
  1. package/README.md +83 -0
  2. package/dist/components/bundles/AddToBundleButton.d.ts +8 -0
  3. package/dist/components/bundles/AddToBundleButton.d.ts.map +1 -0
  4. package/dist/components/bundles/AddToBundleButton.js +64 -0
  5. package/dist/components/bundles/AddToBundleButton.js.map +1 -0
  6. package/dist/components/cells/BundleCell.d.ts +10 -0
  7. package/dist/components/cells/BundleCell.d.ts.map +1 -0
  8. package/dist/components/cells/BundleCell.js +8 -0
  9. package/dist/components/cells/BundleCell.js.map +1 -0
  10. package/dist/components/cells/InteractionCell.d.ts +17 -0
  11. package/dist/components/cells/InteractionCell.d.ts.map +1 -0
  12. package/dist/components/cells/InteractionCell.js +13 -0
  13. package/dist/components/cells/InteractionCell.js.map +1 -0
  14. package/dist/components/cells/ListCell.d.ts +29 -0
  15. package/dist/components/cells/ListCell.d.ts.map +1 -0
  16. package/dist/components/cells/ListCell.js +19 -0
  17. package/dist/components/cells/ListCell.js.map +1 -0
  18. package/dist/components/cells/PersonaCell.d.ts +10 -0
  19. package/dist/components/cells/PersonaCell.d.ts.map +1 -0
  20. package/dist/components/cells/PersonaCell.js +7 -0
  21. package/dist/components/cells/PersonaCell.js.map +1 -0
  22. package/dist/components/cells/ScaffoldCell.d.ts +12 -0
  23. package/dist/components/cells/ScaffoldCell.d.ts.map +1 -0
  24. package/dist/components/cells/ScaffoldCell.js +10 -0
  25. package/dist/components/cells/ScaffoldCell.js.map +1 -0
  26. package/dist/components/cells/ScenarioCell.d.ts +12 -0
  27. package/dist/components/cells/ScenarioCell.d.ts.map +1 -0
  28. package/dist/components/cells/ScenarioCell.js +8 -0
  29. package/dist/components/cells/ScenarioCell.js.map +1 -0
  30. package/dist/components/cells/SurfaceCell.d.ts +14 -0
  31. package/dist/components/cells/SurfaceCell.d.ts.map +1 -0
  32. package/dist/components/cells/SurfaceCell.js +23 -0
  33. package/dist/components/cells/SurfaceCell.js.map +1 -0
  34. package/dist/components/cells/index.d.ts +9 -0
  35. package/dist/components/cells/index.d.ts.map +1 -0
  36. package/dist/components/cells/index.js +9 -0
  37. package/dist/components/cells/index.js.map +1 -0
  38. package/dist/components/cells/scaffoldMeta.d.ts +6 -0
  39. package/dist/components/cells/scaffoldMeta.d.ts.map +1 -0
  40. package/dist/components/cells/scaffoldMeta.js +47 -0
  41. package/dist/components/cells/scaffoldMeta.js.map +1 -0
  42. package/dist/components/dashboard/DashboardSidebar.d.ts +6 -0
  43. package/dist/components/dashboard/DashboardSidebar.d.ts.map +1 -0
  44. package/dist/components/dashboard/DashboardSidebar.js +163 -0
  45. package/dist/components/dashboard/DashboardSidebar.js.map +1 -0
  46. package/dist/components/data/DataTable.d.ts +16 -0
  47. package/dist/components/data/DataTable.d.ts.map +1 -0
  48. package/dist/components/data/DataTable.js +54 -0
  49. package/dist/components/data/DataTable.js.map +1 -0
  50. package/dist/components/data/JsonViewer.d.ts +6 -0
  51. package/dist/components/data/JsonViewer.d.ts.map +1 -0
  52. package/dist/components/data/JsonViewer.js +5 -0
  53. package/dist/components/data/JsonViewer.js.map +1 -0
  54. package/dist/components/data/index.d.ts +3 -0
  55. package/dist/components/data/index.d.ts.map +1 -0
  56. package/dist/components/data/index.js +3 -0
  57. package/dist/components/data/index.js.map +1 -0
  58. package/dist/components/forms/SelectField.d.ts +22 -0
  59. package/dist/components/forms/SelectField.d.ts.map +1 -0
  60. package/dist/components/forms/SelectField.js +14 -0
  61. package/dist/components/forms/SelectField.js.map +1 -0
  62. package/dist/components/navigation/BackLink.d.ts +7 -0
  63. package/dist/components/navigation/BackLink.d.ts.map +1 -0
  64. package/dist/components/navigation/BackLink.js +6 -0
  65. package/dist/components/navigation/BackLink.js.map +1 -0
  66. package/dist/components/pages/PagesListView.d.ts +12 -0
  67. package/dist/components/pages/PagesListView.d.ts.map +1 -0
  68. package/dist/components/pages/PagesListView.js +19 -0
  69. package/dist/components/pages/PagesListView.js.map +1 -0
  70. package/dist/components/pages/PagesMapView.d.ts +15 -0
  71. package/dist/components/pages/PagesMapView.d.ts.map +1 -0
  72. package/dist/components/pages/PagesMapView.js +232 -0
  73. package/dist/components/pages/PagesMapView.js.map +1 -0
  74. package/dist/components/scanner/EventLog.d.ts +8 -0
  75. package/dist/components/scanner/EventLog.d.ts.map +1 -0
  76. package/dist/components/scanner/EventLog.js +18 -0
  77. package/dist/components/scanner/EventLog.js.map +1 -0
  78. package/dist/components/scanner/LiveCounters.d.ts +9 -0
  79. package/dist/components/scanner/LiveCounters.d.ts.map +1 -0
  80. package/dist/components/scanner/LiveCounters.js +33 -0
  81. package/dist/components/scanner/LiveCounters.js.map +1 -0
  82. package/dist/components/scanner/PhaseIndicator.d.ts +6 -0
  83. package/dist/components/scanner/PhaseIndicator.d.ts.map +1 -0
  84. package/dist/components/scanner/PhaseIndicator.js +31 -0
  85. package/dist/components/scanner/PhaseIndicator.js.map +1 -0
  86. package/dist/components/scanner/RunSummaryCard.d.ts +12 -0
  87. package/dist/components/scanner/RunSummaryCard.d.ts.map +1 -0
  88. package/dist/components/scanner/RunSummaryCard.js +7 -0
  89. package/dist/components/scanner/RunSummaryCard.js.map +1 -0
  90. package/dist/components/scanner/ScanForm.d.ts +9 -0
  91. package/dist/components/scanner/ScanForm.d.ts.map +1 -0
  92. package/dist/components/scanner/ScanForm.js +31 -0
  93. package/dist/components/scanner/ScanForm.js.map +1 -0
  94. package/dist/components/scanner/ScanProgressPanel.d.ts +16 -0
  95. package/dist/components/scanner/ScanProgressPanel.d.ts.map +1 -0
  96. package/dist/components/scanner/ScanProgressPanel.js +8 -0
  97. package/dist/components/scanner/ScanProgressPanel.js.map +1 -0
  98. package/dist/components/scanner/StatusBadge.d.ts +7 -0
  99. package/dist/components/scanner/StatusBadge.d.ts.map +1 -0
  100. package/dist/components/scanner/StatusBadge.js +65 -0
  101. package/dist/components/scanner/StatusBadge.js.map +1 -0
  102. package/dist/components/scanner/index.d.ts +8 -0
  103. package/dist/components/scanner/index.d.ts.map +1 -0
  104. package/dist/components/scanner/index.js +8 -0
  105. package/dist/components/scanner/index.js.map +1 -0
  106. package/dist/components/scenarios/AddScenarioForm.d.ts +14 -0
  107. package/dist/components/scenarios/AddScenarioForm.d.ts.map +1 -0
  108. package/dist/components/scenarios/AddScenarioForm.js +43 -0
  109. package/dist/components/scenarios/AddScenarioForm.js.map +1 -0
  110. package/dist/components/scripts/ScriptPanel.d.ts +17 -0
  111. package/dist/components/scripts/ScriptPanel.d.ts.map +1 -0
  112. package/dist/components/scripts/ScriptPanel.js +32 -0
  113. package/dist/components/scripts/ScriptPanel.js.map +1 -0
  114. package/dist/components/states/index.d.ts +19 -0
  115. package/dist/components/states/index.d.ts.map +1 -0
  116. package/dist/components/states/index.js +16 -0
  117. package/dist/components/states/index.js.map +1 -0
  118. package/dist/config/priorityConfig.d.ts +12 -0
  119. package/dist/config/priorityConfig.d.ts.map +1 -0
  120. package/dist/config/priorityConfig.js +39 -0
  121. package/dist/config/priorityConfig.js.map +1 -0
  122. package/dist/context/config.d.ts +53 -0
  123. package/dist/context/config.d.ts.map +1 -0
  124. package/dist/context/config.js +32 -0
  125. package/dist/context/config.js.map +1 -0
  126. package/dist/context/routing.d.ts +42 -0
  127. package/dist/context/routing.d.ts.map +1 -0
  128. package/dist/context/routing.js +33 -0
  129. package/dist/context/routing.js.map +1 -0
  130. package/dist/hooks/useDashboardEnvironmentContext.d.ts +15 -0
  131. package/dist/hooks/useDashboardEnvironmentContext.d.ts.map +1 -0
  132. package/dist/hooks/useDashboardEnvironmentContext.js +89 -0
  133. package/dist/hooks/useDashboardEnvironmentContext.js.map +1 -0
  134. package/dist/hooks/useEnvBasePath.d.ts +8 -0
  135. package/dist/hooks/useEnvBasePath.d.ts.map +1 -0
  136. package/dist/hooks/useEnvBasePath.js +12 -0
  137. package/dist/hooks/useEnvBasePath.js.map +1 -0
  138. package/dist/hooks/useLocalizedNavigate.d.ts +12 -0
  139. package/dist/hooks/useLocalizedNavigate.d.ts.map +1 -0
  140. package/dist/hooks/useLocalizedNavigate.js +14 -0
  141. package/dist/hooks/useLocalizedNavigate.js.map +1 -0
  142. package/dist/index.d.ts +49 -0
  143. package/dist/index.d.ts.map +1 -0
  144. package/dist/index.js +66 -0
  145. package/dist/index.js.map +1 -0
  146. package/dist/pages/BundleDetailPage.d.ts +2 -0
  147. package/dist/pages/BundleDetailPage.d.ts.map +1 -0
  148. package/dist/pages/BundleDetailPage.js +155 -0
  149. package/dist/pages/BundleDetailPage.js.map +1 -0
  150. package/dist/pages/BundlesPage.d.ts +2 -0
  151. package/dist/pages/BundlesPage.d.ts.map +1 -0
  152. package/dist/pages/BundlesPage.js +61 -0
  153. package/dist/pages/BundlesPage.js.map +1 -0
  154. package/dist/pages/DashboardOverview.d.ts +2 -0
  155. package/dist/pages/DashboardOverview.d.ts.map +1 -0
  156. package/dist/pages/DashboardOverview.js +179 -0
  157. package/dist/pages/DashboardOverview.js.map +1 -0
  158. package/dist/pages/FindingsListPage.d.ts +2 -0
  159. package/dist/pages/FindingsListPage.d.ts.map +1 -0
  160. package/dist/pages/FindingsListPage.js +160 -0
  161. package/dist/pages/FindingsListPage.js.map +1 -0
  162. package/dist/pages/PageDetailPage.d.ts +2 -0
  163. package/dist/pages/PageDetailPage.d.ts.map +1 -0
  164. package/dist/pages/PageDetailPage.js +120 -0
  165. package/dist/pages/PageDetailPage.js.map +1 -0
  166. package/dist/pages/PageGraphPage.d.ts +3 -0
  167. package/dist/pages/PageGraphPage.d.ts.map +1 -0
  168. package/dist/pages/PageGraphPage.js +72 -0
  169. package/dist/pages/PageGraphPage.js.map +1 -0
  170. package/dist/pages/PageStateDetailPage.d.ts +2 -0
  171. package/dist/pages/PageStateDetailPage.d.ts.map +1 -0
  172. package/dist/pages/PageStateDetailPage.js +69 -0
  173. package/dist/pages/PageStateDetailPage.js.map +1 -0
  174. package/dist/pages/PagesPage.d.ts +2 -0
  175. package/dist/pages/PagesPage.d.ts.map +1 -0
  176. package/dist/pages/PagesPage.js +83 -0
  177. package/dist/pages/PagesPage.js.map +1 -0
  178. package/dist/pages/PatternsPage.d.ts +2 -0
  179. package/dist/pages/PatternsPage.d.ts.map +1 -0
  180. package/dist/pages/PatternsPage.js +102 -0
  181. package/dist/pages/PatternsPage.js.map +1 -0
  182. package/dist/pages/PersonasPage.d.ts +2 -0
  183. package/dist/pages/PersonasPage.d.ts.map +1 -0
  184. package/dist/pages/PersonasPage.js +151 -0
  185. package/dist/pages/PersonasPage.js.map +1 -0
  186. package/dist/pages/RunRedirect.d.ts +2 -0
  187. package/dist/pages/RunRedirect.d.ts.map +1 -0
  188. package/dist/pages/RunRedirect.js +25 -0
  189. package/dist/pages/RunRedirect.js.map +1 -0
  190. package/dist/pages/RunSurfaceRunDetailPage.d.ts +2 -0
  191. package/dist/pages/RunSurfaceRunDetailPage.d.ts.map +1 -0
  192. package/dist/pages/RunSurfaceRunDetailPage.js +38 -0
  193. package/dist/pages/RunSurfaceRunDetailPage.js.map +1 -0
  194. package/dist/pages/RunSurfaceRunsPage.d.ts +2 -0
  195. package/dist/pages/RunSurfaceRunsPage.d.ts.map +1 -0
  196. package/dist/pages/RunSurfaceRunsPage.js +35 -0
  197. package/dist/pages/RunSurfaceRunsPage.js.map +1 -0
  198. package/dist/pages/RunTestInteractionRunDetailPage.d.ts +2 -0
  199. package/dist/pages/RunTestInteractionRunDetailPage.d.ts.map +1 -0
  200. package/dist/pages/RunTestInteractionRunDetailPage.js +55 -0
  201. package/dist/pages/RunTestInteractionRunDetailPage.js.map +1 -0
  202. package/dist/pages/RunTestInteractionRunsPage.d.ts +2 -0
  203. package/dist/pages/RunTestInteractionRunsPage.d.ts.map +1 -0
  204. package/dist/pages/RunTestInteractionRunsPage.js +38 -0
  205. package/dist/pages/RunTestInteractionRunsPage.js.map +1 -0
  206. package/dist/pages/RunnerGraphPage.d.ts +3 -0
  207. package/dist/pages/RunnerGraphPage.d.ts.map +1 -0
  208. package/dist/pages/RunnerGraphPage.js +86 -0
  209. package/dist/pages/RunnerGraphPage.js.map +1 -0
  210. package/dist/pages/ScaffoldDetailPage.d.ts +2 -0
  211. package/dist/pages/ScaffoldDetailPage.d.ts.map +1 -0
  212. package/dist/pages/ScaffoldDetailPage.js +56 -0
  213. package/dist/pages/ScaffoldDetailPage.js.map +1 -0
  214. package/dist/pages/ScaffoldsPage.d.ts +2 -0
  215. package/dist/pages/ScaffoldsPage.d.ts.map +1 -0
  216. package/dist/pages/ScaffoldsPage.js +35 -0
  217. package/dist/pages/ScaffoldsPage.js.map +1 -0
  218. package/dist/pages/ScanProgressPage.d.ts +2 -0
  219. package/dist/pages/ScanProgressPage.d.ts.map +1 -0
  220. package/dist/pages/ScanProgressPage.js +30 -0
  221. package/dist/pages/ScanProgressPage.js.map +1 -0
  222. package/dist/pages/SchedulesPage.d.ts +2 -0
  223. package/dist/pages/SchedulesPage.d.ts.map +1 -0
  224. package/dist/pages/SchedulesPage.js +165 -0
  225. package/dist/pages/SchedulesPage.js.map +1 -0
  226. package/dist/pages/StartScanPage.d.ts +2 -0
  227. package/dist/pages/StartScanPage.d.ts.map +1 -0
  228. package/dist/pages/StartScanPage.js +97 -0
  229. package/dist/pages/StartScanPage.js.map +1 -0
  230. package/dist/pages/TestInteractionDetailPage.d.ts +2 -0
  231. package/dist/pages/TestInteractionDetailPage.d.ts.map +1 -0
  232. package/dist/pages/TestInteractionDetailPage.js +60 -0
  233. package/dist/pages/TestInteractionDetailPage.js.map +1 -0
  234. package/dist/pages/TestInteractionsPage.d.ts +2 -0
  235. package/dist/pages/TestInteractionsPage.d.ts.map +1 -0
  236. package/dist/pages/TestInteractionsPage.js +96 -0
  237. package/dist/pages/TestInteractionsPage.js.map +1 -0
  238. package/dist/pages/TestRunDetailPage.d.ts +2 -0
  239. package/dist/pages/TestRunDetailPage.d.ts.map +1 -0
  240. package/dist/pages/TestRunDetailPage.js +81 -0
  241. package/dist/pages/TestRunDetailPage.js.map +1 -0
  242. package/dist/pages/TestRunsListPage.d.ts +2 -0
  243. package/dist/pages/TestRunsListPage.d.ts.map +1 -0
  244. package/dist/pages/TestRunsListPage.js +18 -0
  245. package/dist/pages/TestRunsListPage.js.map +1 -0
  246. package/dist/pages/TestScenarioDetailPage.d.ts +2 -0
  247. package/dist/pages/TestScenarioDetailPage.d.ts.map +1 -0
  248. package/dist/pages/TestScenarioDetailPage.js +101 -0
  249. package/dist/pages/TestScenarioDetailPage.js.map +1 -0
  250. package/dist/pages/TestScenariosPage.d.ts +2 -0
  251. package/dist/pages/TestScenariosPage.d.ts.map +1 -0
  252. package/dist/pages/TestScenariosPage.js +73 -0
  253. package/dist/pages/TestScenariosPage.js.map +1 -0
  254. package/dist/pages/TestSurfaceDetailPage.d.ts +2 -0
  255. package/dist/pages/TestSurfaceDetailPage.d.ts.map +1 -0
  256. package/dist/pages/TestSurfaceDetailPage.js +33 -0
  257. package/dist/pages/TestSurfaceDetailPage.js.map +1 -0
  258. package/dist/pages/TestSurfacesListPage.d.ts +2 -0
  259. package/dist/pages/TestSurfacesListPage.d.ts.map +1 -0
  260. package/dist/pages/TestSurfacesListPage.js +73 -0
  261. package/dist/pages/TestSurfacesListPage.js.map +1 -0
  262. package/dist/utils/formatDateTime.d.ts +13 -0
  263. package/dist/utils/formatDateTime.d.ts.map +1 -0
  264. package/dist/utils/formatDateTime.js +27 -0
  265. package/dist/utils/formatDateTime.js.map +1 -0
  266. package/package.json +72 -0
@@ -0,0 +1,72 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { useMemo, useCallback } from 'react';
3
+ import { ReactFlow, Background, Controls, MiniMap, useNodesState, useEdgesState, } from '@xyflow/react';
4
+ import '@xyflow/react/dist/style.css';
5
+ import { usePageStates, buildArtifactUrl } from '@sudobility/testomniac_client';
6
+ import { layoutDagreGraph } from '@sudobility/testomniac_lib';
7
+ import { SEOHead, useTestomniacApi } from '../context/config';
8
+ import { useRouteParams } from '../context/routing';
9
+ import BackLink from '../components/navigation/BackLink';
10
+ import { useLocalizedNavigate } from '../hooks/useLocalizedNavigate';
11
+ const NODE_WIDTH = 200;
12
+ const NODE_HEIGHT = 160;
13
+ function layoutGraph(nodes, edges) {
14
+ const positions = layoutDagreGraph(nodes, edges, {
15
+ nodeWidth: NODE_WIDTH,
16
+ nodeHeight: NODE_HEIGHT,
17
+ });
18
+ return nodes.map(node => ({
19
+ ...node,
20
+ position: positions.get(node.id) ?? node.position,
21
+ }));
22
+ }
23
+ function PageStateNode({ data }) {
24
+ return (_jsxs("div", { className: "bg-white dark:bg-gray-800 border border-gray-200 dark:border-gray-700 rounded-lg overflow-hidden shadow-sm", style: { width: NODE_WIDTH, height: NODE_HEIGHT }, children: [_jsx("div", { className: "w-full h-[120px] bg-gray-100 dark:bg-gray-900 flex items-center justify-center overflow-hidden", children: data.screenshotUrl ? (_jsx("img", { src: data.screenshotUrl, alt: "", className: "w-full h-full object-cover object-top", loading: "lazy" })) : (_jsxs("svg", { className: "w-8 h-8 text-gray-300 dark:text-gray-600", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "1.5", children: [_jsx("rect", { x: "3", y: "3", width: "18", height: "18", rx: "2" }), _jsx("path", { d: "M3 15l5-5 4 4 3-3 6 6" })] })) }), _jsx("div", { className: "px-2 py-1.5 text-center", children: _jsx("span", { className: "text-xs font-medium text-gray-700 dark:text-gray-300 truncate block", children: data.label }) })] }));
25
+ }
26
+ const nodeTypes = { pageState: PageStateNode };
27
+ export function PageGraphPage() {
28
+ const { pageId, envId, entitySlug } = useRouteParams();
29
+ const { networkClient, token, baseUrl } = useTestomniacApi();
30
+ const { navigate } = useLocalizedNavigate();
31
+ const numericPageId = Number(pageId);
32
+ const { pageStates, isLoading: statesLoading } = usePageStates({
33
+ networkClient,
34
+ baseUrl,
35
+ pageId: numericPageId,
36
+ token: token ?? '',
37
+ enabled: !!pageId && !!token,
38
+ });
39
+ const isLoading = statesLoading;
40
+ const { initialNodes, initialEdges } = useMemo(() => {
41
+ if (pageStates.length === 0)
42
+ return { initialNodes: [], initialEdges: [] };
43
+ const rawNodes = pageStates.map(ps => {
44
+ const screenshotUrl = ps.screenshotPath
45
+ ? buildArtifactUrl(baseUrl, ps.screenshotPath, { thumbnail: true })
46
+ : undefined;
47
+ return {
48
+ id: String(ps.id),
49
+ type: 'pageState',
50
+ data: {
51
+ label: `${ps.sizeClass} (#${ps.id})`,
52
+ screenshotUrl,
53
+ },
54
+ position: { x: 0, y: 0 },
55
+ };
56
+ });
57
+ const rawEdges = [];
58
+ const layoutNodes = layoutGraph(rawNodes, rawEdges);
59
+ return { initialNodes: layoutNodes, initialEdges: rawEdges };
60
+ }, [pageStates, baseUrl]);
61
+ const [nodes, , onNodesChange] = useNodesState(initialNodes);
62
+ const [edges, , onEdgesChange] = useEdgesState(initialEdges);
63
+ const onNodeClick = useCallback((_, node) => {
64
+ navigate(`/dashboard/${entitySlug}/environments/${envId}/pages/${pageId}/states/${node.id}`);
65
+ }, [navigate, entitySlug, envId, pageId]);
66
+ const pagesBasePath = `/dashboard/${entitySlug}/environments/${envId}/pages/${pageId}`;
67
+ if (isLoading) {
68
+ return (_jsx("div", { className: "p-6", children: _jsx("div", { className: "text-center text-gray-500 dark:text-gray-400 py-8", children: "Loading graph..." }) }));
69
+ }
70
+ return (_jsxs("div", { className: "p-6", children: [_jsx(SEOHead, { title: "Page Graph", description: "", noIndex: true }), _jsx(BackLink, { label: "Page Detail", onClick: () => navigate(pagesBasePath) }), _jsx("h1", { className: "text-2xl font-bold text-gray-900 dark:text-gray-100 mb-6", children: "Page Graph" }), pageStates.length === 0 ? (_jsx("p", { className: "text-gray-500 dark:text-gray-400", children: "No page states found." })) : (_jsx("div", { className: "w-full h-[600px] border border-gray-200 dark:border-gray-700 rounded-lg overflow-hidden", children: _jsxs(ReactFlow, { nodes: nodes, edges: edges, onNodesChange: onNodesChange, onEdgesChange: onEdgesChange, onNodeClick: onNodeClick, nodeTypes: nodeTypes, fitView: true, className: "bg-gray-50 dark:bg-gray-900", children: [_jsx(Background, {}), _jsx(Controls, {}), _jsx(MiniMap, {})] }) }))] }));
71
+ }
72
+ //# sourceMappingURL=PageGraphPage.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PageGraphPage.js","sourceRoot":"","sources":["../../src/pages/PageGraphPage.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function PageStateDetailPage(): import("react").JSX.Element;
2
+ //# sourceMappingURL=PageStateDetailPage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PageStateDetailPage.d.ts","sourceRoot":"","sources":["../../src/pages/PageStateDetailPage.tsx"],"names":[],"mappings":"AAeA,wBAAgB,mBAAmB,gCAoQlC"}
@@ -0,0 +1,69 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { useState, useMemo } from 'react';
3
+ import { usePageStates, useHtmlElement, usePageStateScaffolds, buildArtifactUrl, } from '@sudobility/testomniac_client';
4
+ import { Tabs, TabsList, TabsTrigger, Card } from '@sudobility/components';
5
+ import { useTestomniacApi } from '../context/config';
6
+ import { useRouteParams } from '../context/routing';
7
+ import BackLink from '../components/navigation/BackLink';
8
+ import { useLocalizedNavigate } from '../hooks/useLocalizedNavigate';
9
+ export function PageStateDetailPage() {
10
+ const { pageStateId, pageId, envId, entitySlug, runId } = useRouteParams();
11
+ const { networkClient, token, baseUrl } = useTestomniacApi();
12
+ const { navigate } = useLocalizedNavigate();
13
+ const [activeTab, setActiveTab] = useState('body');
14
+ const [bodyView, setBodyView] = useState('rendered');
15
+ const [contentView, setContentView] = useState('rendered');
16
+ const { pageStates, isLoading: statesLoading } = usePageStates({
17
+ networkClient,
18
+ baseUrl,
19
+ pageId: Number(pageId),
20
+ token: token ?? '',
21
+ enabled: !!pageId && !!token,
22
+ });
23
+ const state = useMemo(() => pageStates.find(s => s.id === Number(pageStateId)) ?? null, [pageStates, pageStateId]);
24
+ const { htmlElement: bodyHtmlElement, isLoading: bodyLoading } = useHtmlElement({
25
+ networkClient,
26
+ baseUrl,
27
+ id: state?.bodyHtmlElementId ?? 0,
28
+ token: token ?? '',
29
+ enabled: !!state?.bodyHtmlElementId && !!token,
30
+ });
31
+ const { htmlElement: contentHtmlElement, isLoading: contentLoading } = useHtmlElement({
32
+ networkClient,
33
+ baseUrl,
34
+ id: state?.contentHtmlElementId ?? 0,
35
+ token: token ?? '',
36
+ enabled: !!state?.contentHtmlElementId && !!token,
37
+ });
38
+ const { scaffolds, isLoading: scaffoldsLoading } = usePageStateScaffolds({
39
+ networkClient,
40
+ baseUrl,
41
+ pageStateId: Number(pageStateId),
42
+ token: token ?? '',
43
+ enabled: !!pageStateId && !!token,
44
+ });
45
+ if (statesLoading) {
46
+ return (_jsx("div", { className: "p-6", children: _jsx("div", { className: "text-center text-gray-500 dark:text-gray-400 py-8", children: "Loading..." }) }));
47
+ }
48
+ if (!state) {
49
+ return (_jsx("div", { className: "p-6", children: _jsx("div", { className: "text-center text-gray-500 dark:text-gray-400 py-8", children: "Page state not found." }) }));
50
+ }
51
+ const tabs = [
52
+ { key: 'body', label: 'Body' },
53
+ { key: 'content', label: 'Content' },
54
+ { key: 'scaffolds', label: 'Scaffolds' },
55
+ ];
56
+ const pageBasePath = runId
57
+ ? `/dashboard/${entitySlug}/environments/${envId}/runs/${runId}/pages/${pageId}`
58
+ : `/dashboard/${entitySlug}/environments/${envId}/pages/${pageId}`;
59
+ return (_jsxs("div", { className: "p-6", children: [_jsx(BackLink, { label: `Page #${pageId}`, onClick: () => navigate(pageBasePath) }), _jsxs("div", { className: "mb-6", children: [_jsxs("h1", { className: "text-2xl font-bold text-gray-900 dark:text-gray-100", children: ["Page State #", pageStateId] }), _jsxs("div", { className: "flex items-center gap-3 mt-2", children: [_jsx("span", { className: "px-2 py-0.5 text-xs rounded bg-gray-100 dark:bg-gray-800 text-gray-600 dark:text-gray-400", children: state.sizeClass }), _jsxs("span", { className: "text-xs text-gray-500 dark:text-gray-400", children: ["Environment #", envId, " / Page #", pageId] }), state.capturedAt && (_jsxs("span", { className: "text-xs text-gray-500 dark:text-gray-400", children: ["Captured: ", new Date(state.capturedAt).toLocaleString()] }))] })] }), _jsx(Tabs, { value: activeTab, onValueChange: v => setActiveTab(v), className: "mb-6", children: _jsx(TabsList, { children: tabs.map(tab => (_jsx(TabsTrigger, { value: tab.key, children: tab.label }, tab.key))) }) }), activeTab === 'body' && (_jsxs("div", { children: [_jsxs("div", { className: "flex gap-2 mb-4", children: [_jsx("button", { onClick: () => setBodyView('rendered'), className: `px-3 py-1.5 text-sm rounded-md border ${bodyView === 'rendered'
60
+ ? 'border-blue-500 bg-blue-50 text-blue-700 dark:bg-blue-900/30 dark:text-blue-300'
61
+ : 'border-gray-300 dark:border-gray-600 text-gray-700 dark:text-gray-300'}`, children: "Rendered" }), _jsx("button", { onClick: () => setBodyView('source'), className: `px-3 py-1.5 text-sm rounded-md border ${bodyView === 'source'
62
+ ? 'border-blue-500 bg-blue-50 text-blue-700 dark:bg-blue-900/30 dark:text-blue-300'
63
+ : 'border-gray-300 dark:border-gray-600 text-gray-700 dark:text-gray-300'}`, children: "Source" })] }), bodyView === 'rendered' ? (state.rawHtmlPath ? (_jsx("iframe", { sandbox: "allow-same-origin", src: buildArtifactUrl(baseUrl, state.rawHtmlPath), className: "w-full h-[600px] border border-gray-200 dark:border-gray-700 rounded-lg bg-white", title: "Rendered body HTML" })) : (_jsx("div", { className: "text-gray-500 dark:text-gray-400 py-8 text-center", children: "No raw HTML available." }))) : bodyLoading ? (_jsx("div", { className: "text-gray-500 dark:text-gray-400 py-8 text-center", children: "Loading source..." })) : bodyHtmlElement ? (_jsx("pre", { className: "p-4 bg-gray-50 dark:bg-gray-900 border border-gray-200 dark:border-gray-700 rounded-lg text-xs text-gray-800 dark:text-gray-200 overflow-auto max-h-[600px]", children: bodyHtmlElement.html })) : (_jsx("div", { className: "text-gray-500 dark:text-gray-400 py-8 text-center", children: "No body HTML element available." }))] })), activeTab === 'content' && (_jsxs("div", { children: [_jsxs("div", { className: "flex gap-2 mb-4", children: [_jsx("button", { onClick: () => setContentView('rendered'), className: `px-3 py-1.5 text-sm rounded-md border ${contentView === 'rendered'
64
+ ? 'border-blue-500 bg-blue-50 text-blue-700 dark:bg-blue-900/30 dark:text-blue-300'
65
+ : 'border-gray-300 dark:border-gray-600 text-gray-700 dark:text-gray-300'}`, children: "Rendered" }), _jsx("button", { onClick: () => setContentView('source'), className: `px-3 py-1.5 text-sm rounded-md border ${contentView === 'source'
66
+ ? 'border-blue-500 bg-blue-50 text-blue-700 dark:bg-blue-900/30 dark:text-blue-300'
67
+ : 'border-gray-300 dark:border-gray-600 text-gray-700 dark:text-gray-300'}`, children: "Source" })] }), contentView === 'rendered' ? (_jsxs("div", { className: "space-y-4", children: [state.contentText && (_jsxs("div", { children: [_jsx("h3", { className: "text-sm font-medium text-gray-700 dark:text-gray-300 mb-2", children: "Content Text" }), _jsx("div", { className: "p-4 bg-gray-50 dark:bg-gray-900 border border-gray-200 dark:border-gray-700 rounded-lg text-sm text-gray-800 dark:text-gray-200 whitespace-pre-wrap max-h-[400px] overflow-auto", children: state.contentText })] })), !state.contentText && (_jsx("div", { className: "text-gray-500 dark:text-gray-400 py-8 text-center", children: "No content text available." }))] })) : contentLoading ? (_jsx("div", { className: "text-gray-500 dark:text-gray-400 py-8 text-center", children: "Loading source..." })) : contentHtmlElement ? (_jsx("pre", { className: "p-4 bg-gray-50 dark:bg-gray-900 border border-gray-200 dark:border-gray-700 rounded-lg text-xs text-gray-800 dark:text-gray-200 overflow-auto max-h-[600px]", children: contentHtmlElement.html })) : (_jsx("div", { className: "text-gray-500 dark:text-gray-400 py-8 text-center", children: "No content HTML element available." }))] })), activeTab === 'scaffolds' && (_jsx("div", { children: scaffoldsLoading ? (_jsx("div", { className: "text-gray-500 dark:text-gray-400 py-8 text-center", children: "Loading..." })) : scaffolds.length === 0 ? (_jsx("div", { className: "text-gray-500 dark:text-gray-400 py-8 text-center", children: "No scaffolds found." })) : (_jsx("div", { className: "space-y-3", children: scaffolds.map(element => (_jsxs(Card, { variant: "bordered", padding: "md", children: [_jsxs("div", { className: "flex items-center gap-2", children: [_jsxs("span", { className: "text-sm font-medium text-gray-900 dark:text-gray-100", children: ["Scaffold #", element.scaffoldId] }), _jsx("span", { className: "px-1.5 py-0.5 text-xs rounded bg-blue-100 dark:bg-blue-900/30 text-blue-700 dark:text-blue-300", children: "Scaffold" })] }), _jsxs("div", { className: "text-xs text-gray-500 dark:text-gray-400 mt-1", children: ["Page State #", element.pageStateId] })] }, element.id))) })) }))] }));
68
+ }
69
+ //# sourceMappingURL=PageStateDetailPage.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PageStateDetailPage.js","sourceRoot":"","sources":["../../src/pages/PageStateDetailPage.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function PagesPage(): import("react").JSX.Element;
2
+ //# sourceMappingURL=PagesPage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PagesPage.d.ts","sourceRoot":"","sources":["../../src/pages/PagesPage.tsx"],"names":[],"mappings":"AAaA,wBAAgB,SAAS,gCAoJxB"}
@@ -0,0 +1,83 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { useState, useMemo } from 'react';
3
+ import { useEnvironmentPages, useEnvironmentTestInteractions, useRunPages, useRunTestInteractions, useRunnerPageStates, } from '@sudobility/testomniac_client';
4
+ import { SEOHead, useTestomniacApi } from '../context/config';
5
+ import { useRouteParams } from '../context/routing';
6
+ import { PagesListView } from '../components/pages/PagesListView';
7
+ import { PagesMapView } from '../components/pages/PagesMapView';
8
+ export function PagesPage() {
9
+ const { entitySlug, envId, runId } = useRouteParams();
10
+ const { networkClient, token, baseUrl } = useTestomniacApi();
11
+ const [view, setView] = useState('list');
12
+ const runScoped = Boolean(runId);
13
+ const environmentPagesQuery = useEnvironmentPages({
14
+ networkClient,
15
+ baseUrl,
16
+ envId: Number(envId),
17
+ token: token ?? '',
18
+ enabled: !!envId && !!token && !runScoped,
19
+ });
20
+ const runPagesQuery = useRunPages({
21
+ networkClient,
22
+ baseUrl,
23
+ runId: Number(runId),
24
+ token: token ?? '',
25
+ enabled: !!runId && !!token,
26
+ });
27
+ const environmentElementsQuery = useEnvironmentTestInteractions({
28
+ networkClient,
29
+ baseUrl,
30
+ envId: Number(envId),
31
+ token: token ?? '',
32
+ enabled: !!envId && !!token && !runScoped,
33
+ });
34
+ const runElementsQuery = useRunTestInteractions({
35
+ networkClient,
36
+ baseUrl,
37
+ runId: Number(runId),
38
+ token: token ?? '',
39
+ enabled: !!runId && !!token,
40
+ });
41
+ const pages = runScoped ? runPagesQuery.pages : environmentPagesQuery.pages;
42
+ const testInteractions = runScoped
43
+ ? runElementsQuery.testInteractions
44
+ : environmentElementsQuery.testInteractions;
45
+ const pagesLoading = runScoped ? runPagesQuery.isLoading : environmentPagesQuery.isLoading;
46
+ const elementsLoading = runScoped
47
+ ? runElementsQuery.isLoading
48
+ : environmentElementsQuery.isLoading;
49
+ const pagesError = runScoped ? runPagesQuery.error : environmentPagesQuery.error;
50
+ const elementsError = runScoped ? runElementsQuery.error : environmentElementsQuery.error;
51
+ const isLoading = pagesLoading || elementsLoading;
52
+ const error = pagesError || elementsError;
53
+ // Fetch page states for screenshot paths (used in both list and map views)
54
+ const primaryRunnerId = pages.length > 0 ? pages[0].runnerId : 0;
55
+ const { pageStates } = useRunnerPageStates({
56
+ networkClient,
57
+ baseUrl,
58
+ runnerId: primaryRunnerId,
59
+ token: token ?? '',
60
+ enabled: !!primaryRunnerId && !!token,
61
+ });
62
+ const screenshotsByPageId = useMemo(() => {
63
+ const map = new Map();
64
+ for (const ps of pageStates) {
65
+ if (ps.screenshotPath && !map.has(ps.pageId)) {
66
+ map.set(ps.pageId, ps.screenshotPath);
67
+ }
68
+ }
69
+ return map;
70
+ }, [pageStates]);
71
+ if (isLoading) {
72
+ return (_jsx("div", { className: "p-6", children: _jsx("div", { className: "py-8 text-center text-gray-500 dark:text-gray-400", children: "Loading..." }) }));
73
+ }
74
+ if (error) {
75
+ return (_jsx("div", { className: "p-6", children: _jsxs("div", { className: "py-8 text-center text-red-600 dark:text-red-400", children: ["Error: ", error] }) }));
76
+ }
77
+ return (_jsxs("div", { className: "p-6", children: [_jsx(SEOHead, { title: "Discovered Pages", description: "", noIndex: true }), _jsxs("div", { className: "mb-6 flex items-center justify-between", children: [_jsx("h1", { className: "text-2xl font-bold text-gray-900 dark:text-gray-100", children: runScoped ? `Run #${runId} Pages` : 'Discovered Pages' }), _jsxs("div", { className: "flex rounded-lg border border-gray-200 dark:border-gray-700", children: [_jsx("button", { onClick: () => setView('list'), className: `px-4 py-1.5 text-sm font-medium transition-colors ${view === 'list'
78
+ ? 'bg-gray-900 text-white dark:bg-gray-100 dark:text-gray-900'
79
+ : 'text-gray-600 hover:text-gray-900 dark:text-gray-400 dark:hover:text-gray-100'} rounded-l-md`, children: "List" }), _jsx("button", { onClick: () => setView('map'), className: `px-4 py-1.5 text-sm font-medium transition-colors ${view === 'map'
80
+ ? 'bg-gray-900 text-white dark:bg-gray-100 dark:text-gray-900'
81
+ : 'text-gray-600 hover:text-gray-900 dark:text-gray-400 dark:hover:text-gray-100'} rounded-r-md`, children: "Map" })] })] }), pages.length === 0 ? (_jsx("p", { className: "text-gray-500 dark:text-gray-400", children: "No pages discovered yet." })) : view === 'list' ? (_jsx(PagesListView, { pages: pages, envId: envId, entitySlug: entitySlug, runId: runId, screenshotsByPageId: screenshotsByPageId, apiUrl: baseUrl })) : (_jsx(PagesMapView, { pages: pages, testInteractions: testInteractions, envId: envId, entitySlug: entitySlug, runId: runId, screenshotsByPageId: screenshotsByPageId, apiUrl: baseUrl }))] }));
82
+ }
83
+ //# sourceMappingURL=PagesPage.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PagesPage.js","sourceRoot":"","sources":["../../src/pages/PagesPage.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function PatternsPage(): import("react").JSX.Element;
2
+ //# sourceMappingURL=PatternsPage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PatternsPage.d.ts","sourceRoot":"","sources":["../../src/pages/PatternsPage.tsx"],"names":[],"mappings":"AA2VA,wBAAgB,YAAY,gCA4H3B"}
@@ -0,0 +1,102 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { useMemo, useState } from 'react';
3
+ import { useRunPatterns } from '@sudobility/testomniac_client';
4
+ import { Card } from '@sudobility/components';
5
+ import { SEOHead, useTestomniacApi } from '../context/config';
6
+ import { useRouteParams } from '../context/routing';
7
+ import { SelectField } from '../components/forms/SelectField';
8
+ import { useDashboardEnvironmentContext } from '../hooks/useDashboardEnvironmentContext';
9
+ import { EmptyState } from '../components/states';
10
+ const PATTERN_LABELS = {
11
+ card: 'Card',
12
+ table: 'Table',
13
+ form: 'Form',
14
+ modal: 'Modal',
15
+ toast: 'Toast',
16
+ alert: 'Alert',
17
+ tabs: 'Tabs',
18
+ accordion: 'Accordion',
19
+ carousel: 'Carousel',
20
+ dropdown: 'Dropdown',
21
+ pagination: 'Pagination',
22
+ skeleton: 'Skeleton',
23
+ emptyState: 'Empty State',
24
+ errorMessage: 'Error Message',
25
+ progressBar: 'Progress Bar',
26
+ tooltip: 'Tooltip',
27
+ badge: 'Badge',
28
+ avatar: 'Avatar',
29
+ tag: 'Tag',
30
+ stepper: 'Stepper',
31
+ };
32
+ const PATTERN_ICONS = {
33
+ card: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "1", y: "2", width: "12", height: "10", rx: "1" }), _jsx("line", { x1: "1", y1: "5.5", x2: "13", y2: "5.5" })] })),
34
+ table: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "1", y: "1", width: "12", height: "12", rx: "1" }), _jsx("line", { x1: "1", y1: "5", x2: "13", y2: "5" }), _jsx("line", { x1: "1", y1: "9", x2: "13", y2: "9" }), _jsx("line", { x1: "5", y1: "1", x2: "5", y2: "13" }), _jsx("line", { x1: "9", y1: "1", x2: "9", y2: "13" })] })),
35
+ form: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "2", y: "2", width: "10", height: "3", rx: "0.5" }), _jsx("rect", { x: "2", y: "7", width: "10", height: "3", rx: "0.5" }), _jsx("rect", { x: "4", y: "11.5", width: "6", height: "1.5", rx: "0.5" })] })),
36
+ modal: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "2", y: "3", width: "10", height: "8", rx: "1" }), _jsx("line", { x1: "10", y1: "4.5", x2: "10.5", y2: "4.5", strokeWidth: "2" })] })),
37
+ toast: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "1", y: "9", width: "12", height: "4", rx: "1" }), _jsx("line", { x1: "3", y1: "11", x2: "8", y2: "11" })] })),
38
+ alert: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round", children: [_jsx("path", { d: "M7 1L13 12H1L7 1z" }), _jsx("line", { x1: "7", y1: "5", x2: "7", y2: "8" }), _jsx("circle", { cx: "7", cy: "10", r: "0.5", fill: "currentColor" })] })),
39
+ tabs: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "1", y: "4", width: "12", height: "9", rx: "0.5" }), _jsx("rect", { x: "1", y: "1", width: "4", height: "3", rx: "0.5" }), _jsx("rect", { x: "5.5", y: "1", width: "4", height: "3", rx: "0.5" })] })),
40
+ accordion: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "1", y: "1", width: "12", height: "3", rx: "0.5" }), _jsx("rect", { x: "1", y: "5.5", width: "12", height: "3", rx: "0.5" }), _jsx("rect", { x: "1", y: "10", width: "12", height: "3", rx: "0.5" }), _jsx("polyline", { points: "10,2.5 11,3 10,3.5" })] })),
41
+ carousel: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round", children: [_jsx("rect", { x: "3", y: "2", width: "8", height: "8", rx: "0.5" }), _jsx("polyline", { points: "1,5 2,7 1,9" }), _jsx("polyline", { points: "13,5 12,7 13,9" }), _jsx("circle", { cx: "5.5", cy: "12", r: "0.7", fill: "currentColor" }), _jsx("circle", { cx: "7", cy: "12", r: "0.7", fill: "currentColor" }), _jsx("circle", { cx: "8.5", cy: "12", r: "0.7", fill: "currentColor" })] })),
42
+ dropdown: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "2", y: "2", width: "10", height: "3", rx: "0.5" }), _jsx("polyline", { points: "9,3 10,4 11,3" }), _jsx("rect", { x: "2", y: "6", width: "10", height: "7", rx: "0.5" }), _jsx("line", { x1: "4", y1: "8", x2: "10", y2: "8" }), _jsx("line", { x1: "4", y1: "10.5", x2: "10", y2: "10.5" })] })),
43
+ pagination: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("polyline", { points: "2,7 3.5,5.5 2,4" }), _jsx("rect", { x: "4.5", y: "4.5", width: "2", height: "5", rx: "0.5" }), _jsx("rect", { x: "7.5", y: "4.5", width: "2", height: "5", rx: "0.5" }), _jsx("polyline", { points: "12,4 10.5,5.5 12,7" })] })),
44
+ skeleton: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "1", y: "2", width: "5", height: "3", rx: "0.5", strokeDasharray: "2 1" }), _jsx("rect", { x: "8", y: "2", width: "5", height: "3", rx: "0.5", strokeDasharray: "2 1" }), _jsx("rect", { x: "1", y: "7", width: "12", height: "2", rx: "0.5", strokeDasharray: "2 1" }), _jsx("rect", { x: "1", y: "11", width: "8", height: "2", rx: "0.5", strokeDasharray: "2 1" })] })),
45
+ emptyState: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "2", y: "2", width: "10", height: "10", rx: "1", strokeDasharray: "2 2" }), _jsx("line", { x1: "5", y1: "7", x2: "9", y2: "7" })] })),
46
+ errorMessage: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("circle", { cx: "7", cy: "7", r: "5.5" }), _jsx("line", { x1: "7", y1: "4", x2: "7", y2: "7.5" }), _jsx("circle", { cx: "7", cy: "9.5", r: "0.5", fill: "currentColor" })] })),
47
+ progressBar: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "1", y: "5.5", width: "12", height: "3", rx: "1.5" }), _jsx("rect", { x: "1", y: "5.5", width: "7", height: "3", rx: "1.5", fill: "currentColor", opacity: "0.3" })] })),
48
+ tooltip: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "2", y: "2", width: "10", height: "6", rx: "1" }), _jsx("path", { d: "M6 8L7 10L8 8" })] })),
49
+ badge: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("rect", { x: "2", y: "4.5", width: "10", height: "5", rx: "2.5" }), _jsx("line", { x1: "5", y1: "7", x2: "9", y2: "7" })] })),
50
+ avatar: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("circle", { cx: "7", cy: "5", r: "3" }), _jsx("path", { d: "M2 13c0-2.5 2.2-4.5 5-4.5s5 2 5 4.5" })] })),
51
+ tag: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round", children: [_jsx("path", { d: "M1 7.5V2.5C1 1.9 1.4 1.5 2 1.5H7L13 7.5L7.5 13L1 7.5z" }), _jsx("circle", { cx: "4", cy: "4.5", r: "1", fill: "currentColor" })] })),
52
+ stepper: (_jsxs("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", children: [_jsx("circle", { cx: "3", cy: "7", r: "2" }), _jsx("circle", { cx: "7", cy: "7", r: "2" }), _jsx("circle", { cx: "11", cy: "7", r: "2" }), _jsx("line", { x1: "5", y1: "7", x2: "5", y2: "7" }), _jsx("line", { x1: "9", y1: "7", x2: "9", y2: "7" })] })),
53
+ };
54
+ export function PatternsPage() {
55
+ const { envId } = useRouteParams();
56
+ const { networkClient, token, baseUrl } = useTestomniacApi();
57
+ const [typeFilter, setTypeFilter] = useState('');
58
+ const { latestRun, isLoading: contextLoading, error: contextError, } = useDashboardEnvironmentContext();
59
+ const { patterns, isLoading, error } = useRunPatterns({
60
+ networkClient,
61
+ baseUrl,
62
+ runId: latestRun?.id ?? 0,
63
+ token: token ?? '',
64
+ enabled: !!envId && !!token && !!latestRun,
65
+ });
66
+ const grouped = useMemo(() => {
67
+ const map = new Map();
68
+ for (const p of patterns) {
69
+ const existing = map.get(p.patternType);
70
+ if (existing) {
71
+ existing.totalCount += p.count;
72
+ if (!existing.pageStateIds.includes(p.pageStateId)) {
73
+ existing.pageStateIds.push(p.pageStateId);
74
+ }
75
+ }
76
+ else {
77
+ map.set(p.patternType, {
78
+ patternType: p.patternType,
79
+ totalCount: p.count,
80
+ pageStateIds: [p.pageStateId],
81
+ });
82
+ }
83
+ }
84
+ return Array.from(map.values()).sort((a, b) => a.patternType.localeCompare(b.patternType));
85
+ }, [patterns]);
86
+ const uniqueTypes = useMemo(() => grouped.map(g => g.patternType), [grouped]);
87
+ const filteredPatterns = typeFilter ? grouped.filter(g => g.patternType === typeFilter) : grouped;
88
+ if (contextLoading || isLoading) {
89
+ return (_jsx("div", { className: "p-6", children: _jsx("div", { className: "text-center text-gray-500 dark:text-gray-400 py-8", children: "Loading..." }) }));
90
+ }
91
+ if (contextError || error) {
92
+ return (_jsx("div", { className: "p-6", children: _jsxs("div", { className: "text-center text-red-600 dark:text-red-400 py-8", children: ["Error: ", contextError || error] }) }));
93
+ }
94
+ return (_jsxs("div", { className: "p-6", children: [_jsx(SEOHead, { title: "UI Patterns", description: "", noIndex: true }), _jsx("h1", { className: "text-2xl font-bold text-gray-900 dark:text-gray-100 mb-6", children: "UI Patterns" }), uniqueTypes.length > 1 && (_jsx("div", { className: "mb-4", children: _jsx(SelectField, { value: typeFilter, onChange: setTypeFilter, options: [
95
+ { value: '', label: 'All Types' },
96
+ ...uniqueTypes.map(type => ({
97
+ value: type,
98
+ label: PATTERN_LABELS[type] ?? type,
99
+ })),
100
+ ] }) })), filteredPatterns.length === 0 ? (_jsx(EmptyState, { title: "No UI patterns detected", description: "UI patterns will appear here after a scan detects them." })) : (_jsx("div", { className: "grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-4", children: filteredPatterns.map(pattern => (_jsxs(Card, { variant: "bordered", padding: "md", children: [_jsxs("div", { className: "flex items-center gap-2 mb-3", children: [_jsx("span", { className: "text-gray-500 dark:text-gray-400", children: PATTERN_ICONS[pattern.patternType] ?? (_jsx("svg", { width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", stroke: "currentColor", strokeWidth: "1.5", children: _jsx("rect", { x: "2", y: "2", width: "10", height: "10", rx: "1" }) })) }), _jsx("span", { className: "text-sm font-medium text-gray-900 dark:text-gray-100", children: PATTERN_LABELS[pattern.patternType] ?? pattern.patternType })] }), _jsxs("div", { className: "flex items-center justify-between text-xs text-gray-500 dark:text-gray-400", children: [_jsxs("span", { children: [pattern.totalCount, " instance", pattern.totalCount !== 1 ? 's' : ''] }), _jsxs("span", { children: [pattern.pageStateIds.length, " page state", pattern.pageStateIds.length !== 1 ? 's' : ''] })] })] }, pattern.patternType))) }))] }));
101
+ }
102
+ //# sourceMappingURL=PatternsPage.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PatternsPage.js","sourceRoot":"","sources":["../../src/pages/PatternsPage.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare function PersonasPage(): import("react").JSX.Element;
2
+ //# sourceMappingURL=PersonasPage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"PersonasPage.d.ts","sourceRoot":"","sources":["../../src/pages/PersonasPage.tsx"],"names":[],"mappings":"AAwDA,wBAAgB,YAAY,gCAwR3B"}
@@ -0,0 +1,151 @@
1
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
+ import { useState } from 'react';
3
+ import { Alert, Button, ActionButton, Card, Input, Label, TextArea } from '@sudobility/components';
4
+ import { useProductPersonas, useCreatePersona, useUpdatePersona, useDeletePersona, useDetectPersonas, usePersonaUseCases, } from '@sudobility/testomniac_client';
5
+ import { SEOHead, useTestomniacApi } from '../context/config';
6
+ import { useRouteParams } from '../context/routing';
7
+ import { PersonaCell } from '../components/cells';
8
+ import { useDashboardEnvironmentContext } from '../hooks/useDashboardEnvironmentContext';
9
+ import { ErrorState, LoadingState, EmptyState } from '../components/states';
10
+ // ---------------------------------------------------------------------------
11
+ // Sub-component: Use Cases (expandable per persona)
12
+ // ---------------------------------------------------------------------------
13
+ function PersonaUseCases({ personaId }) {
14
+ const { networkClient, token, baseUrl } = useTestomniacApi();
15
+ const { useCases, isLoading } = usePersonaUseCases({
16
+ networkClient,
17
+ baseUrl,
18
+ personaId,
19
+ token: token ?? '',
20
+ });
21
+ if (isLoading) {
22
+ return _jsx("div", { className: "text-xs text-gray-400 py-2", children: "Loading use cases..." });
23
+ }
24
+ if (useCases.length === 0) {
25
+ return _jsx("div", { className: "text-xs text-gray-400 py-2", children: "No use cases." });
26
+ }
27
+ return (_jsx("div", { className: "space-y-2", children: useCases.map(uc => (_jsxs("div", { className: "text-sm", children: [_jsx("span", { className: "font-medium text-gray-800 dark:text-gray-200", children: uc.title }), uc.description && (_jsxs("span", { className: "text-gray-500 dark:text-gray-400", children: [" \u2014 ", uc.description] }))] }, uc.id))) }));
28
+ }
29
+ // ---------------------------------------------------------------------------
30
+ // Main page
31
+ // ---------------------------------------------------------------------------
32
+ export function PersonasPage() {
33
+ const { envId } = useRouteParams();
34
+ const { baseUrl } = useTestomniacApi();
35
+ const { networkClient, token, productId, isLoading: contextLoading, error: contextError, } = useDashboardEnvironmentContext();
36
+ // Data
37
+ const { personas, isLoading, error, refetch } = useProductPersonas({
38
+ networkClient,
39
+ baseUrl,
40
+ productId: productId ?? 0,
41
+ token,
42
+ enabled: !!envId && !!token && !!productId,
43
+ });
44
+ // Mutations
45
+ const { createPersona, isCreating } = useCreatePersona({
46
+ networkClient,
47
+ baseUrl,
48
+ token,
49
+ });
50
+ const { updatePersona, isUpdating } = useUpdatePersona({
51
+ networkClient,
52
+ baseUrl,
53
+ token,
54
+ });
55
+ const { deletePersona } = useDeletePersona({
56
+ networkClient,
57
+ baseUrl,
58
+ token,
59
+ });
60
+ const { detectPersonas, isDetecting } = useDetectPersonas({
61
+ networkClient,
62
+ baseUrl,
63
+ token,
64
+ });
65
+ // Form state
66
+ const [showForm, setShowForm] = useState(false);
67
+ const [editingPersona, setEditingPersona] = useState(null);
68
+ const [formTitle, setFormTitle] = useState('');
69
+ const [formDescription, setFormDescription] = useState('');
70
+ const [formError, setFormError] = useState(null);
71
+ // Detect state
72
+ const [showDetectWarning, setShowDetectWarning] = useState(false);
73
+ const [detectError, setDetectError] = useState(null);
74
+ // Expand state
75
+ const [expandedId, setExpandedId] = useState(null);
76
+ // Handlers
77
+ const openCreateForm = () => {
78
+ setEditingPersona(null);
79
+ setFormTitle('');
80
+ setFormDescription('');
81
+ setFormError(null);
82
+ setShowForm(true);
83
+ };
84
+ const openEditForm = (persona) => {
85
+ setEditingPersona(persona);
86
+ setFormTitle(persona.title);
87
+ setFormDescription(persona.description ?? '');
88
+ setFormError(null);
89
+ setShowForm(true);
90
+ };
91
+ const closeForm = () => {
92
+ setShowForm(false);
93
+ setEditingPersona(null);
94
+ setFormError(null);
95
+ };
96
+ const handleSave = async () => {
97
+ if (!formTitle.trim()) {
98
+ setFormError('Title is required');
99
+ return;
100
+ }
101
+ setFormError(null);
102
+ try {
103
+ if (editingPersona) {
104
+ await updatePersona({
105
+ personaId: editingPersona.id,
106
+ title: formTitle.trim(),
107
+ description: formDescription.trim() || undefined,
108
+ });
109
+ }
110
+ else {
111
+ await createPersona({
112
+ productId: productId,
113
+ title: formTitle.trim(),
114
+ description: formDescription.trim(),
115
+ });
116
+ }
117
+ closeForm();
118
+ refetch();
119
+ }
120
+ catch (err) {
121
+ setFormError(err instanceof Error ? err.message : 'Save failed');
122
+ }
123
+ };
124
+ const handleDelete = async (personaId) => {
125
+ await deletePersona(personaId);
126
+ refetch();
127
+ };
128
+ const handleDetect = async () => {
129
+ if (personas.length > 0) {
130
+ setShowDetectWarning(true);
131
+ return;
132
+ }
133
+ await runDetect();
134
+ };
135
+ const runDetect = async () => {
136
+ setShowDetectWarning(false);
137
+ setDetectError(null);
138
+ try {
139
+ await detectPersonas({ productId: productId });
140
+ refetch();
141
+ }
142
+ catch (err) {
143
+ setDetectError(err instanceof Error ? err.message : 'Detection failed');
144
+ }
145
+ };
146
+ if (contextError || error) {
147
+ return _jsx(ErrorState, { message: contextError || error || '' });
148
+ }
149
+ return (_jsxs("div", { className: "p-6", children: [_jsx(SEOHead, { title: "Personas", description: "", noIndex: true }), _jsxs("div", { className: "flex items-center justify-between mb-6", children: [_jsx("h1", { className: "text-2xl font-bold text-gray-900 dark:text-gray-100", children: "Personas" }), _jsxs("div", { className: "flex items-center gap-2", children: [_jsx(ActionButton, { variant: "primary", className: "bg-purple-600 hover:bg-purple-700", onClick: handleDetect, disabled: !productId, isLoading: isDetecting, loadingText: "Detecting...", children: "Detect Personas" }), _jsx(Button, { variant: "primary", onClick: showForm ? closeForm : openCreateForm, children: showForm ? 'Cancel' : 'New Persona' })] })] }), detectError && _jsx(Alert, { variant: "error", description: detectError, className: "mb-4" }), showDetectWarning && (_jsxs("div", { className: "mb-4 p-4 rounded-lg border border-amber-300 dark:border-amber-600 bg-amber-50 dark:bg-amber-900/20", children: [_jsxs("p", { className: "text-sm font-medium text-amber-800 dark:text-amber-200", children: ["Detecting personas will replace all ", personas.length, " existing persona", personas.length !== 1 ? 's' : '', ". This cannot be undone."] }), _jsxs("div", { className: "flex items-center gap-2 mt-3", children: [_jsx(ActionButton, { variant: "primary", size: "sm", className: "bg-amber-600 hover:bg-amber-700", onClick: runDetect, isLoading: isDetecting, loadingText: "Detecting...", children: "Continue" }), _jsx(Button, { variant: "secondary", size: "sm", onClick: () => setShowDetectWarning(false), children: "Cancel" })] })] })), showForm && (_jsxs(Card, { variant: "bordered", className: "mb-6", children: [_jsx("h3", { className: "text-sm font-semibold text-gray-900 dark:text-gray-100 mb-3", children: editingPersona ? 'Edit Persona' : 'New Persona' }), _jsxs("div", { className: "space-y-3", children: [_jsxs("div", { children: [_jsx(Label, { className: "mb-1 block", children: "Title" }), _jsx(Input, { type: "text", value: formTitle, onChange: e => setFormTitle(e.target.value), placeholder: "e.g. Power User, First-Time Visitor", className: "w-full" })] }), _jsxs("div", { children: [_jsx(Label, { className: "mb-1 block", children: "Description" }), _jsx(TextArea, { value: formDescription, onChange: setFormDescription, placeholder: "Describe this persona's goals, behavior, and technical proficiency", rows: 3 })] }), formError && _jsx("div", { className: "text-sm text-red-600 dark:text-red-400", children: formError }), _jsxs("div", { className: "flex items-center gap-2", children: [_jsx(ActionButton, { variant: "primary", onClick: handleSave, isLoading: isCreating || isUpdating, loadingText: "Saving...", children: "Save" }), _jsx(Button, { variant: "secondary", onClick: closeForm, children: "Cancel" })] })] })] })), (contextLoading || isLoading) && _jsx(LoadingState, { message: "Loading personas..." }), !isLoading && personas.length === 0 && !showForm && (_jsx(EmptyState, { title: "No personas yet", description: 'Create a persona manually or use "Detect Personas" to generate them from your discovered pages.' })), !isLoading && personas.length > 0 && (_jsx("div", { className: "space-y-2", children: personas.map((persona) => (_jsxs("div", { children: [_jsx(PersonaCell, { persona: persona, onClick: () => setExpandedId(expandedId === persona.id ? null : persona.id), actions: _jsxs(_Fragment, { children: [_jsx(Button, { variant: "link", size: "sm", onClick: () => openEditForm(persona), children: "Edit" }), _jsx(Button, { variant: "link", size: "sm", className: "text-red-600 hover:text-red-700", onClick: () => handleDelete(persona.id), children: "Delete" })] }) }), expandedId === persona.id && (_jsxs(Card, { variant: "bordered", className: "mt-1", children: [_jsx("h4", { className: "text-xs font-medium text-gray-600 dark:text-gray-400 uppercase tracking-wide mb-2", children: "Use Cases" }), _jsx(PersonaUseCases, { personaId: persona.id })] }))] }, persona.id))) }))] }));
150
+ }
151
+ //# sourceMappingURL=PersonasPage.js.map