elseware-ui 2.32.0 → 2.34.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.mjs CHANGED
@@ -1,5 +1,5 @@
1
1
  import { twMerge } from 'tailwind-merge';
2
- import React4, { createContext, forwardRef, useState, useImperativeHandle, useEffect, useMemo, useContext, Fragment as Fragment$1, useRef, useCallback } from 'react';
2
+ import React3, { createContext, forwardRef, useState, useImperativeHandle, useEffect, useMemo, useContext, Fragment as Fragment$1, useCallback, useRef } from 'react';
3
3
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
4
4
  import { BsStarFill, BsStarHalf, BsStar, BsChevronDown, BsFillDiamondFill } from 'react-icons/bs';
5
5
  import { FaSun, FaMoon, FaGripVertical, FaTrash, FaPlus, FaTimes, FaBars, FaCircle, FaEyeSlash, FaEye } from 'react-icons/fa';
@@ -10,7 +10,7 @@ import classNames16 from 'classnames';
10
10
  import { FaCircleChevronDown } from 'react-icons/fa6';
11
11
  import ReactWorldFlags from 'react-world-flags';
12
12
  import emojiFlags from 'emoji-flags';
13
- import * as d3 from 'd3';
13
+ import { ResponsiveContainer, LineChart as LineChart$1, CartesianGrid, XAxis, YAxis, Tooltip as Tooltip$1, Line as Line$1, AreaChart, Area, BarChart as BarChart$1, Bar as Bar$1, PieChart as PieChart$1, Pie as Pie$1, Cell, ScatterChart, Scatter } from 'recharts';
14
14
  import { Image, CloudinaryContext as CloudinaryContext$1 } from 'cloudinary-react';
15
15
  import { useField, ErrorMessage, Formik, Form as Form$1, Field, useFormikContext, FieldArray } from 'formik';
16
16
  import { toast, ToastContainer } from 'react-toastify';
@@ -179,6 +179,326 @@ function resolveAppearanceStyles({
179
179
  return solid[variant];
180
180
  }
181
181
  }
182
+
183
+ // src/utils/configurator/errors.ts
184
+ var ConfiguratorError = class extends Error {
185
+ constructor(message, cause) {
186
+ super(message);
187
+ this.name = "ConfiguratorError";
188
+ this.cause = cause;
189
+ }
190
+ };
191
+ function formatIssue(issue) {
192
+ const path = issue.path?.join(".") || "config";
193
+ return `${path} : ${issue.message ?? "Invalid value"}`;
194
+ }
195
+ function formatConfigError(error) {
196
+ const maybeZodError = error;
197
+ if (Array.isArray(maybeZodError.issues)) {
198
+ return maybeZodError.issues.map(formatIssue).join("\n");
199
+ }
200
+ if (maybeZodError?.message) {
201
+ return maybeZodError.message;
202
+ }
203
+ return "Invalid configuration";
204
+ }
205
+ function toConfiguratorError(error, fallbackMessage) {
206
+ if (error instanceof ConfiguratorError) {
207
+ return error;
208
+ }
209
+ if (error instanceof Error) {
210
+ return new ConfiguratorError(error.message || fallbackMessage, error);
211
+ }
212
+ return new ConfiguratorError(fallbackMessage, error);
213
+ }
214
+
215
+ // src/utils/configurator/Configurator.ts
216
+ var Configurator = class {
217
+ constructor(options) {
218
+ this.initialized = false;
219
+ this.config = null;
220
+ this.configError = null;
221
+ this.name = options.name ?? "config";
222
+ this.source = options.env;
223
+ this.schema = options.schema;
224
+ this.transform = options.transform;
225
+ if (options.validateOnCreate !== false) {
226
+ this.reload();
227
+ }
228
+ }
229
+ get isValid() {
230
+ this.ensureInitialized();
231
+ return !this.configError;
232
+ }
233
+ get error() {
234
+ this.ensureInitialized();
235
+ return this.configError;
236
+ }
237
+ get value() {
238
+ this.ensureInitialized();
239
+ if (this.configError) {
240
+ throw this.configError;
241
+ }
242
+ return this.config;
243
+ }
244
+ get optionalValue() {
245
+ this.ensureInitialized();
246
+ return this.config;
247
+ }
248
+ reload(env = this.source) {
249
+ this.source = env;
250
+ this.initialized = true;
251
+ const result = this.schema.safeParse(env);
252
+ if (!result.success) {
253
+ this.config = null;
254
+ this.configError = toConfiguratorError(
255
+ result.error,
256
+ formatConfigError(result.error)
257
+ );
258
+ return {
259
+ success: false,
260
+ config: null,
261
+ error: this.configError
262
+ };
263
+ }
264
+ try {
265
+ this.config = this.transform ? this.transform(result.data, { name: this.name }) : result.data;
266
+ this.configError = null;
267
+ return {
268
+ success: true,
269
+ config: this.config,
270
+ error: null
271
+ };
272
+ } catch (error) {
273
+ this.config = null;
274
+ this.configError = toConfiguratorError(
275
+ error,
276
+ `Failed to transform ${this.name}`
277
+ );
278
+ return {
279
+ success: false,
280
+ config: null,
281
+ error: this.configError
282
+ };
283
+ }
284
+ }
285
+ get(key) {
286
+ this.ensureInitialized();
287
+ if (!this.config) {
288
+ return void 0;
289
+ }
290
+ return this.config[key];
291
+ }
292
+ getRequired(key) {
293
+ const value = this.get(key);
294
+ if (value === void 0 || value === null) {
295
+ throw new Error(`Missing required config value: ${String(key)}`);
296
+ }
297
+ return value;
298
+ }
299
+ getPath(path, fallback) {
300
+ this.ensureInitialized();
301
+ if (!this.config) {
302
+ return fallback;
303
+ }
304
+ const value = path.split(".").reduce((current, key) => {
305
+ if (!current || typeof current !== "object") {
306
+ return void 0;
307
+ }
308
+ return current[key];
309
+ }, this.config);
310
+ return value === void 0 ? fallback : value;
311
+ }
312
+ getPathRequired(path) {
313
+ const value = this.getPath(path);
314
+ if (value === void 0 || value === null) {
315
+ throw new Error(`Missing required config value: ${path}`);
316
+ }
317
+ return value;
318
+ }
319
+ ensureInitialized() {
320
+ if (!this.initialized) {
321
+ this.reload();
322
+ }
323
+ }
324
+ };
325
+
326
+ // src/utils/configurator/createConfigurator.ts
327
+ function createConfigurator(options) {
328
+ return new Configurator(options);
329
+ }
330
+
331
+ // src/utils/configurator/helpers/browser.ts
332
+ function getBrowserOrigin() {
333
+ if (typeof window === "undefined") {
334
+ return "";
335
+ }
336
+ return window.location.origin;
337
+ }
338
+ function getBrowserHref() {
339
+ if (typeof window === "undefined") {
340
+ return "";
341
+ }
342
+ return window.location.href;
343
+ }
344
+ function getBrowserRedirectURL(options = {}) {
345
+ const {
346
+ queryParam = "redirect_uri",
347
+ fallbackPath = "/",
348
+ currentHref = getBrowserHref(),
349
+ referrerMode = "path"
350
+ } = options;
351
+ try {
352
+ if (currentHref) {
353
+ const currentURL = new URL(currentHref);
354
+ const redirectUri = currentURL.searchParams.get(queryParam);
355
+ if (redirectUri) {
356
+ return redirectUri;
357
+ }
358
+ }
359
+ if (typeof document !== "undefined" && document.referrer) {
360
+ const referrerURL = new URL(document.referrer);
361
+ if (referrerMode === "full") {
362
+ return referrerURL.toString();
363
+ }
364
+ return `${referrerURL.pathname}${referrerURL.search}${referrerURL.hash}`;
365
+ }
366
+ return fallbackPath;
367
+ } catch {
368
+ return fallbackPath;
369
+ }
370
+ }
371
+
372
+ // src/utils/configurator/helpers/json.ts
373
+ function isRecord(value) {
374
+ return Boolean(value) && typeof value === "object" && !Array.isArray(value);
375
+ }
376
+ function parseJson(value, key = "JSON value") {
377
+ if (isRecord(value) || Array.isArray(value)) {
378
+ return value;
379
+ }
380
+ if (typeof value !== "string") {
381
+ throw new ConfiguratorError(`${key} must be a JSON string`);
382
+ }
383
+ try {
384
+ return JSON.parse(value);
385
+ } catch {
386
+ throw new ConfiguratorError(`Invalid ${key} JSON`);
387
+ }
388
+ }
389
+ function parseJsonRecord(value, key = "JSON record", validateValue) {
390
+ const parsed = parseJson(value, key);
391
+ if (!isRecord(parsed)) {
392
+ throw new ConfiguratorError(`${key} must be a JSON object`);
393
+ }
394
+ return Object.entries(parsed).reduce(
395
+ (acc, [name, item]) => {
396
+ acc[name] = validateValue ? validateValue(name, item) : item;
397
+ return acc;
398
+ },
399
+ {}
400
+ );
401
+ }
402
+
403
+ // src/utils/configurator/helpers/url.ts
404
+ function assertAbsoluteURL(value, key = "URL") {
405
+ if (typeof value !== "string") {
406
+ throw new ConfiguratorError(`${key} must be a string URL`);
407
+ }
408
+ try {
409
+ const url = new URL(value);
410
+ if (!["http:", "https:"].includes(url.protocol)) {
411
+ throw new Error();
412
+ }
413
+ return url.toString();
414
+ } catch {
415
+ throw new ConfiguratorError(`${key} must be a valid http/https URL`);
416
+ }
417
+ }
418
+ function parseUrlMap(value, key = "URL map") {
419
+ return parseJsonRecord(
420
+ value,
421
+ key,
422
+ (name, item) => assertAbsoluteURL(item, `${key}.${name}`)
423
+ );
424
+ }
425
+ function buildURL(base, path = "", params = {}) {
426
+ const url = new URL(assertAbsoluteURL(base, "base URL"));
427
+ if (path) {
428
+ const currentPath = url.pathname.replace(/\/$/, "");
429
+ const nextPath = path.replace(/^\/+/, "");
430
+ url.pathname = `${currentPath}/${nextPath}`;
431
+ }
432
+ Object.entries(params).forEach(([key, value]) => {
433
+ if (value !== void 0 && value !== null) {
434
+ url.searchParams.set(key, String(value));
435
+ }
436
+ });
437
+ return url.toString();
438
+ }
439
+ function resolveURLMap(source) {
440
+ return typeof source === "function" ? source() : source;
441
+ }
442
+ function createURLResolver(source, options = {}) {
443
+ const { label = "URL" } = options;
444
+ return (tag, path = "", params = {}) => {
445
+ const map = resolveURLMap(source) ?? {};
446
+ const base = map[tag];
447
+ if (!base) {
448
+ throw new ConfiguratorError(`${label} not configured for tag: ${tag}`);
449
+ }
450
+ return buildURL(base, path, params);
451
+ };
452
+ }
453
+ function getAllowedOrigins(options = {}) {
454
+ const {
455
+ urls = [],
456
+ maps = [],
457
+ includeCurrentOrigin = true,
458
+ currentOrigin = getBrowserOrigin()
459
+ } = options;
460
+ const origins = /* @__PURE__ */ new Set();
461
+ if (includeCurrentOrigin && currentOrigin) {
462
+ origins.add(currentOrigin);
463
+ }
464
+ urls.forEach((url) => {
465
+ origins.add(new URL(assertAbsoluteURL(url)).origin);
466
+ });
467
+ maps.forEach((map) => {
468
+ Object.values(map ?? {}).forEach((url) => {
469
+ origins.add(new URL(assertAbsoluteURL(url)).origin);
470
+ });
471
+ });
472
+ return Array.from(origins);
473
+ }
474
+ function getSafeRedirect(options = {}) {
475
+ const {
476
+ redirectUri,
477
+ fallback = "/",
478
+ allowedOrigins = [],
479
+ currentOrigin = getBrowserOrigin(),
480
+ allowedProtocols = ["http:", "https:"]
481
+ } = options;
482
+ try {
483
+ if (!redirectUri) {
484
+ return fallback;
485
+ }
486
+ const url = new URL(redirectUri, currentOrigin || fallback);
487
+ if (!allowedProtocols.includes(url.protocol)) {
488
+ return fallback;
489
+ }
490
+ const allowed = new Set(allowedOrigins);
491
+ if (currentOrigin) {
492
+ allowed.add(currentOrigin);
493
+ }
494
+ if (!allowed.has(url.origin)) {
495
+ return fallback;
496
+ }
497
+ return url.toString();
498
+ } catch {
499
+ return fallback;
500
+ }
501
+ }
182
502
  var EUIContext = createContext(null);
183
503
  var EUIProvider = ({
184
504
  config,
@@ -1320,257 +1640,2444 @@ var Flag = ({
1320
1640
  );
1321
1641
  };
1322
1642
 
1323
- // src/components/data-display/graphs/layouts/registry.ts
1324
- var registry = /* @__PURE__ */ new Map();
1325
- var registerLayout = (type, executor) => {
1326
- registry.set(type, executor);
1643
+ // src/components/data-display/graphs-v2/constants/graph.constants.ts
1644
+ var GRAPH_DEFAULT_HEIGHT = 320;
1645
+ var GRAPH_DEFAULT_MAX_REALTIME_POINTS = 100;
1646
+ var GRAPH_DEFAULT_POLLING_INTERVAL = 5e3;
1647
+ var GRAPH_DEFAULT_ANIMATION_DURATION = 350;
1648
+ var GRAPH_DEFAULT_MARGIN = {
1649
+ top: 16,
1650
+ right: 24,
1651
+ bottom: 16,
1652
+ left: 8
1327
1653
  };
1328
- var getLayout = (type) => {
1329
- const layout = registry.get(type);
1330
- if (!layout) {
1331
- throw new Error(`Layout "${type}" not registered`);
1332
- }
1333
- return layout;
1654
+ var GRAPH_DEFAULT_STROKE_WIDTH = 2;
1655
+ var GRAPH_DEFAULT_DOT_RADIUS = 3;
1656
+ var GRAPH_DEFAULT_ACTIVE_DOT_RADIUS = 5;
1657
+ var GRAPH_DEFAULT_BAR_RADIUS = [
1658
+ 6,
1659
+ 6,
1660
+ 0,
1661
+ 0
1662
+ ];
1663
+ var GRAPH_STATUSES = {
1664
+ IDLE: "idle",
1665
+ LOADING: "loading",
1666
+ SUCCESS: "success",
1667
+ ERROR: "error",
1668
+ STREAMING: "streaming"
1334
1669
  };
1335
- var createForceLayout = (nodes, edges, width, height) => {
1336
- const nodeMap = new Map(nodes.map((n) => [n.id, n]));
1337
- const d3Links = edges.filter((e) => {
1338
- const fromId = typeof e.from === "string" ? e.from : e.from.id;
1339
- const toId = typeof e.to === "string" ? e.to : e.to.id;
1340
- const valid = nodeMap.has(fromId) && nodeMap.has(toId);
1341
- if (!valid) {
1342
- console.warn("Invalid edge skipped:", e);
1343
- }
1344
- return valid;
1345
- }).map((e) => ({
1346
- source: typeof e.from === "string" ? e.from : e.from.id,
1347
- target: typeof e.to === "string" ? e.to : e.to.id,
1348
- weight: e.weight
1349
- }));
1350
- return d3.forceSimulation(nodes).force(
1351
- "link",
1352
- d3.forceLink(d3Links).id((d) => d.id).distance(120).strength(0.7)
1353
- ).force("charge", d3.forceManyBody().strength(-280)).force("center", d3.forceCenter(width / 2, height / 2)).force("collision", d3.forceCollide().radius(35));
1670
+ var GRAPH_DATA_MODES = {
1671
+ STATIC: "static",
1672
+ POLLING: "polling",
1673
+ REALTIME: "realtime"
1674
+ };
1675
+ var GRAPH_VALUE_FORMATS = {
1676
+ RAW: "raw",
1677
+ NUMBER: "number",
1678
+ INTEGER: "integer",
1679
+ COMPACT: "compact",
1680
+ PERCENT: "percent",
1681
+ CURRENCY: "currency",
1682
+ BYTES: "bytes",
1683
+ DURATION: "duration"
1354
1684
  };
1685
+ var GRAPH_EMPTY_MESSAGE = "No graph data available";
1686
+ var GRAPH_ERROR_MESSAGE = "Unable to load graph data";
1687
+ var GRAPH_LOADING_MESSAGE = "Loading graph data...";
1355
1688
 
1356
- // src/components/data-display/graphs/layouts/gridLayout.ts
1357
- function createGridLayout(nodes, width, height) {
1358
- const cols = Math.ceil(Math.sqrt(nodes.length));
1359
- const spacingX = width / (cols + 1);
1360
- const spacingY = height / (cols + 1);
1361
- return nodes.map((node, i) => ({
1362
- ...node,
1363
- x: spacingX * (i % cols + 1),
1364
- y: spacingY * (Math.floor(i / cols) + 1)
1365
- }));
1366
- }
1689
+ // src/components/data-display/graphs-v2/constants/graph-theme.constants.ts
1690
+ var GRAPH_COLOR_PALETTE = [
1691
+ "#7dd3fc",
1692
+ "#a78bfa",
1693
+ "#34d399",
1694
+ "#fbbf24",
1695
+ "#fb7185",
1696
+ "#60a5fa",
1697
+ "#f472b6",
1698
+ "#22d3ee",
1699
+ "#c084fc",
1700
+ "#a3e635"
1701
+ ];
1702
+ var GRAPH_STATUS_COLORS = {
1703
+ primary: "#7dd3fc",
1704
+ secondary: "#a78bfa",
1705
+ success: "#34d399",
1706
+ warning: "#fbbf24",
1707
+ danger: "#fb7185",
1708
+ info: "#60a5fa",
1709
+ muted: "#6b7280"
1710
+ };
1711
+ var GRAPH_DARK_THEME = {
1712
+ panel: {
1713
+ background: "bg-[#111217]",
1714
+ border: "border border-[#2a2d35]",
1715
+ radius: "rounded-xl",
1716
+ shadow: "shadow-sm"
1717
+ },
1718
+ text: {
1719
+ title: "text-gray-100",
1720
+ description: "text-gray-400",
1721
+ muted: "text-gray-500"
1722
+ },
1723
+ chart: {
1724
+ grid: "#2a2d35",
1725
+ axis: "#8b949e",
1726
+ cursor: "rgba(255, 255, 255, 0.06)"
1727
+ },
1728
+ tooltip: {
1729
+ background: "#181b21",
1730
+ border: "#2a2d35",
1731
+ text: "#f3f4f6",
1732
+ muted: "#9ca3af"
1733
+ },
1734
+ colors: GRAPH_COLOR_PALETTE
1735
+ };
1736
+ var GRAPH_LIGHT_THEME = {
1737
+ panel: {
1738
+ background: "bg-white",
1739
+ border: "border border-gray-200",
1740
+ radius: "rounded-xl",
1741
+ shadow: "shadow-sm"
1742
+ },
1743
+ text: {
1744
+ title: "text-gray-900",
1745
+ description: "text-gray-500",
1746
+ muted: "text-gray-400"
1747
+ },
1748
+ chart: {
1749
+ grid: "#e5e7eb",
1750
+ axis: "#6b7280",
1751
+ cursor: "rgba(0, 0, 0, 0.04)"
1752
+ },
1753
+ tooltip: {
1754
+ background: "#ffffff",
1755
+ border: "#e5e7eb",
1756
+ text: "#111827",
1757
+ muted: "#6b7280"
1758
+ },
1759
+ colors: GRAPH_COLOR_PALETTE
1760
+ };
1761
+ var DEFAULT_GRAPH_THEME = GRAPH_DARK_THEME;
1367
1762
 
1368
- // src/components/data-display/graphs/layouts/treeLayout.ts
1369
- function createTreeLayout(nodes, edges, width, height) {
1370
- const levelMap = {};
1371
- const root = nodes[0];
1372
- if (!root) return nodes;
1373
- levelMap[root.id] = 0;
1374
- edges.forEach((edge) => {
1375
- const fromId = typeof edge.from === "string" ? edge.from : edge.from.id;
1376
- const toId = typeof edge.to === "string" ? edge.to : edge.to.id;
1377
- levelMap[toId] = (levelMap[fromId] ?? 0) + 1;
1378
- });
1379
- const maxLevel = Math.max(...Object.values(levelMap));
1380
- const levelGroups = {};
1381
- nodes.forEach((node) => {
1382
- const level = levelMap[node.id] ?? 0;
1383
- if (!levelGroups[level]) levelGroups[level] = [];
1384
- levelGroups[level].push(node);
1385
- });
1386
- return nodes.map((node) => {
1387
- const level = levelMap[node.id] ?? 0;
1388
- const siblings = levelGroups[level];
1389
- const index = siblings.indexOf(node);
1390
- return {
1391
- ...node,
1392
- x: (index + 1) * width / (siblings.length + 1),
1393
- y: (level + 1) * height / (maxLevel + 2)
1394
- };
1395
- });
1763
+ // src/components/data-display/graphs-v2/utils/normalizeGraphData.ts
1764
+ var DEFAULT_NORMALIZE_OPTIONS = {
1765
+ serializeDates: true,
1766
+ parseNumericStrings: true,
1767
+ sanitizeInvalidNumbers: true,
1768
+ removeUndefined: true
1769
+ };
1770
+ function isNumericString(value) {
1771
+ if (!value.trim()) {
1772
+ return false;
1773
+ }
1774
+ return !Number.isNaN(Number(value));
1396
1775
  }
1397
- var NODE_SIZE = 48;
1398
- var GraphNode = ({ node, renderCustom }) => {
1399
- if (node.x === void 0 || node.y === void 0) return null;
1400
- const x = node.x;
1401
- const y = node.y;
1402
- if (renderCustom) {
1403
- return /* @__PURE__ */ jsx(
1404
- "foreignObject",
1405
- {
1406
- x: x - NODE_SIZE / 2,
1407
- y: y - NODE_SIZE / 2,
1408
- width: NODE_SIZE,
1409
- height: NODE_SIZE,
1410
- style: { overflow: "visible" },
1411
- children: /* @__PURE__ */ jsx(
1412
- "div",
1413
- {
1414
- style: {
1415
- width: NODE_SIZE,
1416
- height: NODE_SIZE,
1417
- display: "flex",
1418
- alignItems: "center",
1419
- justifyContent: "center"
1420
- },
1421
- children: renderCustom(node)
1422
- }
1423
- )
1424
- }
1425
- );
1776
+ function normalizeValue(value, options) {
1777
+ if (value instanceof Date) {
1778
+ return options.serializeDates ? value.toISOString() : value;
1426
1779
  }
1427
- return /* @__PURE__ */ jsxs("g", { transform: `translate(${x}, ${y})`, children: [
1428
- /* @__PURE__ */ jsx("circle", { r: 16, fill: "#4f46e5" }),
1429
- node.label && /* @__PURE__ */ jsx(
1430
- "text",
1431
- {
1432
- y: 4,
1433
- textAnchor: "middle",
1434
- fontSize: "11",
1435
- fill: "white",
1436
- pointerEvents: "none",
1437
- children: node.label
1780
+ if (typeof value === "number") {
1781
+ if (options.sanitizeInvalidNumbers && (Number.isNaN(value) || !Number.isFinite(value))) {
1782
+ return null;
1783
+ }
1784
+ return value;
1785
+ }
1786
+ if (typeof value === "string") {
1787
+ if (options.parseNumericStrings && isNumericString(value)) {
1788
+ return Number(value);
1789
+ }
1790
+ return value;
1791
+ }
1792
+ if (typeof value === "boolean" || value === null || value === void 0) {
1793
+ return value;
1794
+ }
1795
+ return String(value);
1796
+ }
1797
+ function normalizeGraphData(data, options = {}) {
1798
+ if (!Array.isArray(data)) {
1799
+ return [];
1800
+ }
1801
+ const resolvedOptions = {
1802
+ ...DEFAULT_NORMALIZE_OPTIONS,
1803
+ ...options
1804
+ };
1805
+ return data.map((item) => {
1806
+ const normalizedPoint = {};
1807
+ const keys = options.keys ?? Object.keys(item);
1808
+ keys.forEach((key) => {
1809
+ const value = normalizeValue(item[key], resolvedOptions);
1810
+ if (resolvedOptions.removeUndefined && value === void 0) {
1811
+ return;
1438
1812
  }
1439
- )
1440
- ] });
1813
+ normalizedPoint[key] = value;
1814
+ });
1815
+ return normalizedPoint;
1816
+ });
1817
+ }
1818
+ function normalizeGraphDataPoint(dataPoint, options = {}) {
1819
+ return normalizeGraphData([dataPoint], options)[0] ?? {};
1820
+ }
1821
+
1822
+ // src/components/data-display/graphs-v2/utils/formatGraphValue.ts
1823
+ var DEFAULT_FORMAT_OPTIONS = {
1824
+ format: "number",
1825
+ locale: "en-US",
1826
+ fallback: "-"
1441
1827
  };
1442
- function resolveNode(ref, map) {
1443
- return typeof ref === "string" ? map.get(ref) : ref;
1828
+ function isValidNumber(value) {
1829
+ return typeof value === "number" && Number.isFinite(value) && !Number.isNaN(value);
1444
1830
  }
1445
- var GraphEdge = ({ edge, nodeMap }) => {
1446
- const source = resolveNode(edge.from, nodeMap);
1447
- const target = resolveNode(edge.to, nodeMap);
1448
- if (!source || !target) return null;
1449
- if (source.x == null || source.y == null) return null;
1450
- if (target.x == null || target.y == null) return null;
1451
- const labelX = (source.x + target.x) / 2;
1452
- const labelY = (source.y + target.y) / 2;
1453
- return /* @__PURE__ */ jsxs("g", { children: [
1454
- /* @__PURE__ */ jsx(
1455
- "line",
1456
- {
1457
- x1: source.x,
1458
- y1: source.y,
1459
- x2: target.x,
1460
- y2: target.y,
1461
- stroke: "#64748b",
1462
- strokeWidth: 1.5
1463
- }
1464
- ),
1465
- edge.weight && /* @__PURE__ */ jsx(
1466
- "text",
1467
- {
1468
- x: labelX,
1469
- y: labelY - 4,
1470
- textAnchor: "middle",
1471
- fontSize: 10,
1472
- fill: "#e5e7eb",
1473
- children: edge.weight
1474
- }
1475
- )
1476
- ] });
1831
+ function formatBytes(value, locale) {
1832
+ if (value === 0) {
1833
+ return "0 B";
1834
+ }
1835
+ const units = ["B", "KB", "MB", "GB", "TB", "PB"];
1836
+ const unitIndex = Math.min(
1837
+ Math.floor(Math.log(Math.abs(value)) / Math.log(1024)),
1838
+ units.length - 1
1839
+ );
1840
+ const formattedValue = value / 1024 ** unitIndex;
1841
+ return `${new Intl.NumberFormat(locale, {
1842
+ maximumFractionDigits: formattedValue >= 10 ? 1 : 2
1843
+ }).format(formattedValue)} ${units[unitIndex]}`;
1844
+ }
1845
+ function formatDuration(value, locale) {
1846
+ if (value < 1e3) {
1847
+ return `${Math.round(value)} ms`;
1848
+ }
1849
+ const seconds = value / 1e3;
1850
+ if (seconds < 60) {
1851
+ return `${new Intl.NumberFormat(locale, {
1852
+ maximumFractionDigits: 2
1853
+ }).format(seconds)} s`;
1854
+ }
1855
+ const minutes = seconds / 60;
1856
+ if (minutes < 60) {
1857
+ return `${new Intl.NumberFormat(locale, {
1858
+ maximumFractionDigits: 2
1859
+ }).format(minutes)} min`;
1860
+ }
1861
+ const hours = minutes / 60;
1862
+ return `${new Intl.NumberFormat(locale, {
1863
+ maximumFractionDigits: 2
1864
+ }).format(hours)} h`;
1865
+ }
1866
+ function formatGraphValue(value, options = {}) {
1867
+ const {
1868
+ format,
1869
+ locale,
1870
+ fallback,
1871
+ prefix = "",
1872
+ suffix = "",
1873
+ currency = "USD",
1874
+ minimumFractionDigits,
1875
+ maximumFractionDigits
1876
+ } = {
1877
+ ...DEFAULT_FORMAT_OPTIONS,
1878
+ ...options
1879
+ };
1880
+ if (value === null || value === void 0 || value === "") {
1881
+ return fallback;
1882
+ }
1883
+ if (format === "raw") {
1884
+ return `${prefix}${String(value)}${suffix}`;
1885
+ }
1886
+ const numericValue = typeof value === "string" && value.trim() !== "" ? Number(value) : value;
1887
+ if (!isValidNumber(numericValue)) {
1888
+ return `${prefix}${String(value)}${suffix}`;
1889
+ }
1890
+ let formattedValue;
1891
+ switch (format) {
1892
+ case "integer":
1893
+ formattedValue = new Intl.NumberFormat(locale, {
1894
+ maximumFractionDigits: 0
1895
+ }).format(numericValue);
1896
+ break;
1897
+ case "compact":
1898
+ formattedValue = new Intl.NumberFormat(locale, {
1899
+ notation: "compact",
1900
+ maximumFractionDigits: maximumFractionDigits ?? 2
1901
+ }).format(numericValue);
1902
+ break;
1903
+ case "percent":
1904
+ formattedValue = new Intl.NumberFormat(locale, {
1905
+ style: "percent",
1906
+ minimumFractionDigits: minimumFractionDigits ?? 0,
1907
+ maximumFractionDigits: maximumFractionDigits ?? 2
1908
+ }).format(numericValue / 100);
1909
+ break;
1910
+ case "currency":
1911
+ formattedValue = new Intl.NumberFormat(locale, {
1912
+ style: "currency",
1913
+ currency,
1914
+ minimumFractionDigits,
1915
+ maximumFractionDigits
1916
+ }).format(numericValue);
1917
+ break;
1918
+ case "bytes":
1919
+ formattedValue = formatBytes(numericValue, locale);
1920
+ break;
1921
+ case "duration":
1922
+ formattedValue = formatDuration(numericValue, locale);
1923
+ break;
1924
+ case "number":
1925
+ default:
1926
+ formattedValue = new Intl.NumberFormat(locale, {
1927
+ minimumFractionDigits,
1928
+ maximumFractionDigits: maximumFractionDigits ?? 2
1929
+ }).format(numericValue);
1930
+ break;
1931
+ }
1932
+ return `${prefix}${formattedValue}${suffix}`;
1933
+ }
1934
+
1935
+ // src/components/data-display/graphs-v2/utils/resolveGraphColor.ts
1936
+ var NAMED_COLORS = {
1937
+ primary: GRAPH_STATUS_COLORS.primary,
1938
+ secondary: GRAPH_STATUS_COLORS.secondary,
1939
+ success: GRAPH_STATUS_COLORS.success,
1940
+ warning: GRAPH_STATUS_COLORS.warning,
1941
+ danger: GRAPH_STATUS_COLORS.danger,
1942
+ info: GRAPH_STATUS_COLORS.info,
1943
+ muted: GRAPH_STATUS_COLORS.muted
1477
1944
  };
1478
- var GraphRenderer = ({
1945
+ function isCssColor(value) {
1946
+ return value.startsWith("#") || value.startsWith("rgb(") || value.startsWith("rgba(") || value.startsWith("hsl(") || value.startsWith("hsla(") || value.startsWith("var(");
1947
+ }
1948
+ function resolveGraphColor(color, options = {}) {
1949
+ const {
1950
+ index = 0,
1951
+ fallback = GRAPH_COLOR_PALETTE[0],
1952
+ palette = GRAPH_COLOR_PALETTE
1953
+ } = options;
1954
+ if (color) {
1955
+ if (isCssColor(color)) {
1956
+ return color;
1957
+ }
1958
+ if (color in NAMED_COLORS) {
1959
+ return NAMED_COLORS[color];
1960
+ }
1961
+ }
1962
+ if (palette.length > 0) {
1963
+ return palette[index % palette.length];
1964
+ }
1965
+ return fallback;
1966
+ }
1967
+ function resolveGraphColors(count, options = {}) {
1968
+ return Array.from(
1969
+ { length: count },
1970
+ (_, index) => resolveGraphColor(void 0, {
1971
+ ...options,
1972
+ index
1973
+ })
1974
+ );
1975
+ }
1976
+
1977
+ // src/components/data-display/graphs-v2/utils/limitRealtimePoints.ts
1978
+ var DEFAULT_MAX_POINTS = 100;
1979
+ function limitRealtimePoints(currentData = [], nextData, options = {}) {
1980
+ const { maxPoints = DEFAULT_MAX_POINTS, appendDirection = "end" } = options;
1981
+ const incomingData = Array.isArray(nextData) ? nextData : [nextData];
1982
+ const mergedData = appendDirection === "start" ? [...incomingData, ...currentData] : [...currentData, ...incomingData];
1983
+ if (maxPoints <= 0) {
1984
+ return mergedData;
1985
+ }
1986
+ if (mergedData.length <= maxPoints) {
1987
+ return mergedData;
1988
+ }
1989
+ return appendDirection === "start" ? mergedData.slice(0, maxPoints) : mergedData.slice(-maxPoints);
1990
+ }
1991
+ function replaceRealtimePoints(nextData = [], options = {}) {
1992
+ const { maxPoints = DEFAULT_MAX_POINTS } = options;
1993
+ if (maxPoints <= 0) {
1994
+ return nextData;
1995
+ }
1996
+ return nextData.slice(-maxPoints);
1997
+ }
1998
+
1999
+ // src/components/data-display/graphs-v2/hooks/useGraphData.ts
2000
+ function useGraphData({
1479
2001
  data,
1480
- layout = "force",
1481
- nodeRenderer,
1482
- width = 1e3,
1483
- height = 700
1484
- }) => {
1485
- const [nodes, setNodes] = useState([]);
1486
- const edges = data.edges;
1487
- const simulationRef = useRef(null);
1488
- const [offset, setOffset] = useState({ x: 0, y: 0 });
1489
- const isDragging = useRef(false);
1490
- const lastPos = useRef({ x: 0, y: 0 });
1491
- const nodeMap = useMemo(() => {
1492
- return new Map(nodes.map((n) => [n.id, n]));
1493
- }, [nodes]);
1494
- useEffect(() => {
1495
- simulationRef.current?.stop?.();
1496
- const positionedNodes = data.nodes.map((n) => ({
1497
- ...n,
1498
- x: width / 2,
1499
- y: height / 2
1500
- }));
1501
- const executor = getLayout(layout);
1502
- const instance = executor({
1503
- nodes: positionedNodes,
1504
- edges,
1505
- width,
1506
- height,
1507
- onTick: setNodes
2002
+ dataSource,
2003
+ autoLoad = true,
2004
+ maxDataPoints = GRAPH_DEFAULT_MAX_REALTIME_POINTS,
2005
+ normalize: normalize2 = true,
2006
+ onDataChange,
2007
+ onError
2008
+ } = {}) {
2009
+ const [state, setState] = useState({
2010
+ data: data ?? [],
2011
+ loading: false,
2012
+ error: null,
2013
+ status: data?.length ? "success" : "idle",
2014
+ lastUpdatedAt: data?.length ? /* @__PURE__ */ new Date() : void 0
2015
+ });
2016
+ const prepareData = useCallback(
2017
+ (nextData) => {
2018
+ if (!normalize2) {
2019
+ return nextData;
2020
+ }
2021
+ return normalizeGraphData(nextData);
2022
+ },
2023
+ [normalize2]
2024
+ );
2025
+ const replaceData = useCallback(
2026
+ (nextData) => {
2027
+ const normalizedData = prepareData(nextData);
2028
+ setState({
2029
+ data: normalizedData,
2030
+ loading: false,
2031
+ error: null,
2032
+ status: "success",
2033
+ lastUpdatedAt: /* @__PURE__ */ new Date()
2034
+ });
2035
+ onDataChange?.(normalizedData);
2036
+ },
2037
+ [onDataChange, prepareData]
2038
+ );
2039
+ const appendData = useCallback(
2040
+ (nextData) => {
2041
+ setState((currentState) => {
2042
+ const incomingData = Array.isArray(nextData) ? nextData : [nextData];
2043
+ const normalizedIncomingData = prepareData(incomingData);
2044
+ const limitedData = limitRealtimePoints(
2045
+ currentState.data,
2046
+ normalizedIncomingData,
2047
+ {
2048
+ maxPoints: maxDataPoints
2049
+ }
2050
+ );
2051
+ onDataChange?.(limitedData);
2052
+ return {
2053
+ data: limitedData,
2054
+ loading: false,
2055
+ error: null,
2056
+ status: "streaming",
2057
+ lastUpdatedAt: /* @__PURE__ */ new Date()
2058
+ };
2059
+ });
2060
+ },
2061
+ [maxDataPoints, onDataChange, prepareData]
2062
+ );
2063
+ const clearData = useCallback(() => {
2064
+ setState({
2065
+ data: [],
2066
+ loading: false,
2067
+ error: null,
2068
+ status: "idle",
2069
+ lastUpdatedAt: void 0
1508
2070
  });
1509
- simulationRef.current = instance;
1510
- return () => instance.stop?.();
1511
- }, [data, layout, width, height]);
1512
- const onMouseDown = (e) => {
1513
- isDragging.current = true;
1514
- lastPos.current = { x: e.clientX, y: e.clientY };
1515
- };
1516
- const onMouseMove = (e) => {
1517
- if (!isDragging.current) return;
1518
- const dx = e.clientX - lastPos.current.x;
1519
- const dy = e.clientY - lastPos.current.y;
1520
- setOffset((prev) => ({
1521
- x: prev.x + dx,
1522
- y: prev.y + dy
1523
- }));
1524
- lastPos.current = { x: e.clientX, y: e.clientY };
1525
- };
1526
- const stopDrag = () => isDragging.current = false;
1527
- return /* @__PURE__ */ jsx("div", { className: "relative overflow-hidden border border-gray-800 rounded-lg", children: /* @__PURE__ */ jsx(
1528
- "svg",
1529
- {
1530
- width: "100%",
1531
- height,
1532
- viewBox: `0 0 ${width} ${height}`,
1533
- onMouseDown,
1534
- onMouseMove,
1535
- onMouseUp: stopDrag,
1536
- onMouseLeave: stopDrag,
1537
- style: {
1538
- cursor: isDragging.current ? "grabbing" : "grab"
1539
- },
1540
- children: /* @__PURE__ */ jsxs("g", { transform: `translate(${offset.x}, ${offset.y})`, children: [
1541
- edges.map((edge, i) => /* @__PURE__ */ jsx(GraphEdge, { edge, nodeMap }, edge.id || i)),
1542
- nodes.map((node) => /* @__PURE__ */ jsx(GraphNode, { node, renderCustom: nodeRenderer }, node.id))
1543
- ] })
2071
+ onDataChange?.([]);
2072
+ }, [onDataChange]);
2073
+ const handleError = useCallback(
2074
+ (error) => {
2075
+ setState((currentState) => ({
2076
+ ...currentState,
2077
+ loading: false,
2078
+ error,
2079
+ status: "error"
2080
+ }));
2081
+ onError?.(error);
2082
+ },
2083
+ [onError]
2084
+ );
2085
+ const refresh = useCallback(async () => {
2086
+ const resolvedDataSource = dataSource;
2087
+ if (!resolvedDataSource?.refresh && !resolvedDataSource?.getInitialData) {
2088
+ return;
1544
2089
  }
1545
- ) });
1546
- };
1547
- var Graph = ({
1548
- data,
1549
- layout = "force",
1550
- nodeRenderer,
1551
- width = 800,
1552
- height = 500,
1553
- className,
1554
- ...rest
1555
- }) => {
1556
- return /* @__PURE__ */ jsx(
1557
- "div",
1558
- {
1559
- ...rest,
1560
- style: { width, height },
1561
- className: cn("relative bg-gray-900 rounded-lg", className),
1562
- children: /* @__PURE__ */ jsx(
1563
- GraphRenderer,
1564
- {
1565
- data,
1566
- layout,
1567
- nodeRenderer,
1568
- width,
1569
- height
1570
- }
1571
- )
2090
+ try {
2091
+ setState((currentState) => ({
2092
+ ...currentState,
2093
+ loading: true,
2094
+ error: null,
2095
+ status: "loading"
2096
+ }));
2097
+ const loader = resolvedDataSource.refresh ?? resolvedDataSource.getInitialData;
2098
+ const result = await loader?.();
2099
+ replaceData(result ?? []);
2100
+ } catch (error) {
2101
+ handleError(error instanceof Error ? error : new Error(String(error)));
1572
2102
  }
1573
- );
2103
+ }, [dataSource, handleError, replaceData]);
2104
+ useEffect(() => {
2105
+ if (!data) {
2106
+ return;
2107
+ }
2108
+ replaceData(data);
2109
+ }, [data, replaceData]);
2110
+ useEffect(() => {
2111
+ if (!dataSource || !autoLoad) {
2112
+ return;
2113
+ }
2114
+ const resolvedDataSource = dataSource;
2115
+ let unsubscribe;
2116
+ let isMounted = true;
2117
+ async function loadInitialData() {
2118
+ if (!resolvedDataSource.getInitialData) {
2119
+ return;
2120
+ }
2121
+ try {
2122
+ setState((currentState) => ({
2123
+ ...currentState,
2124
+ loading: true,
2125
+ error: null,
2126
+ status: "loading"
2127
+ }));
2128
+ const result = await resolvedDataSource.getInitialData();
2129
+ if (isMounted) {
2130
+ replaceData(result ?? []);
2131
+ }
2132
+ } catch (error) {
2133
+ if (isMounted) {
2134
+ handleError(
2135
+ error instanceof Error ? error : new Error(String(error))
2136
+ );
2137
+ }
2138
+ }
2139
+ }
2140
+ void loadInitialData();
2141
+ if (resolvedDataSource.subscribe) {
2142
+ unsubscribe = resolvedDataSource.subscribe(appendData, handleError);
2143
+ }
2144
+ return () => {
2145
+ isMounted = false;
2146
+ unsubscribe?.();
2147
+ };
2148
+ }, [appendData, autoLoad, dataSource, handleError, replaceData]);
2149
+ return useMemo(
2150
+ () => ({
2151
+ ...state,
2152
+ refresh,
2153
+ replaceData,
2154
+ appendData,
2155
+ clearData
2156
+ }),
2157
+ [appendData, clearData, refresh, replaceData, state]
2158
+ );
2159
+ }
2160
+ function useGraphRealtime({
2161
+ enabled = true,
2162
+ maxDataPoints = GRAPH_DEFAULT_MAX_REALTIME_POINTS,
2163
+ normalize: normalize2 = true,
2164
+ connect,
2165
+ onData,
2166
+ onError
2167
+ }) {
2168
+ const [data, setData] = useState([]);
2169
+ const [error, setError] = useState(null);
2170
+ const [connected, setConnected] = useState(false);
2171
+ const [lastUpdatedAt, setLastUpdatedAt] = useState();
2172
+ useEffect(() => {
2173
+ if (!enabled) {
2174
+ setConnected(false);
2175
+ return;
2176
+ }
2177
+ const handleData = (incomingData) => {
2178
+ const incomingArray = Array.isArray(incomingData) ? incomingData : [incomingData];
2179
+ const normalizedIncomingData = normalize2 ? normalizeGraphData(incomingArray) : incomingArray;
2180
+ setData((currentData) => {
2181
+ const nextData = limitRealtimePoints(
2182
+ currentData,
2183
+ normalizedIncomingData,
2184
+ {
2185
+ maxPoints: maxDataPoints
2186
+ }
2187
+ );
2188
+ onData?.(nextData);
2189
+ return nextData;
2190
+ });
2191
+ setError(null);
2192
+ setConnected(true);
2193
+ setLastUpdatedAt(/* @__PURE__ */ new Date());
2194
+ };
2195
+ const handleError = (nextError) => {
2196
+ setError(nextError);
2197
+ onError?.(nextError);
2198
+ };
2199
+ const unsubscribe = connect(handleData, handleError);
2200
+ setConnected(true);
2201
+ return () => {
2202
+ unsubscribe?.();
2203
+ setConnected(false);
2204
+ };
2205
+ }, [connect, enabled, maxDataPoints, normalize2, onData, onError]);
2206
+ return useMemo(
2207
+ () => ({
2208
+ data,
2209
+ error,
2210
+ connected,
2211
+ loading: enabled && !connected && !error,
2212
+ status: error ? "error" : connected ? "streaming" : "idle",
2213
+ lastUpdatedAt,
2214
+ clearData: () => setData([])
2215
+ }),
2216
+ [connected, data, enabled, error, lastUpdatedAt]
2217
+ );
2218
+ }
2219
+ function useGraphPolling({
2220
+ enabled = true,
2221
+ interval = GRAPH_DEFAULT_POLLING_INTERVAL,
2222
+ immediate = true,
2223
+ normalize: normalize2 = true,
2224
+ fetcher,
2225
+ onData,
2226
+ onError
2227
+ }) {
2228
+ const isMountedRef = useRef(false);
2229
+ const isFetchingRef = useRef(false);
2230
+ const [data, setData] = useState([]);
2231
+ const [error, setError] = useState(null);
2232
+ const [loading, setLoading] = useState(immediate);
2233
+ const [lastUpdatedAt, setLastUpdatedAt] = useState();
2234
+ const refresh = useCallback(async () => {
2235
+ if (isFetchingRef.current) {
2236
+ return;
2237
+ }
2238
+ try {
2239
+ isFetchingRef.current = true;
2240
+ setLoading(true);
2241
+ setError(null);
2242
+ const result = await fetcher();
2243
+ const nextData = normalize2 ? normalizeGraphData(result ?? []) : result ?? [];
2244
+ if (!isMountedRef.current) {
2245
+ return;
2246
+ }
2247
+ setData(nextData);
2248
+ setLastUpdatedAt(/* @__PURE__ */ new Date());
2249
+ onData?.(nextData);
2250
+ } catch (error2) {
2251
+ const nextError = error2 instanceof Error ? error2 : new Error(String(error2));
2252
+ if (isMountedRef.current) {
2253
+ setError(nextError);
2254
+ onError?.(nextError);
2255
+ }
2256
+ } finally {
2257
+ if (isMountedRef.current) {
2258
+ setLoading(false);
2259
+ }
2260
+ isFetchingRef.current = false;
2261
+ }
2262
+ }, [fetcher, normalize2, onData, onError]);
2263
+ useEffect(() => {
2264
+ isMountedRef.current = true;
2265
+ return () => {
2266
+ isMountedRef.current = false;
2267
+ };
2268
+ }, []);
2269
+ useEffect(() => {
2270
+ if (!enabled) {
2271
+ setLoading(false);
2272
+ return;
2273
+ }
2274
+ if (immediate) {
2275
+ void refresh();
2276
+ }
2277
+ const timer = window.setInterval(() => {
2278
+ void refresh();
2279
+ }, interval);
2280
+ return () => {
2281
+ window.clearInterval(timer);
2282
+ };
2283
+ }, [enabled, immediate, interval, refresh]);
2284
+ return useMemo(
2285
+ () => ({
2286
+ data,
2287
+ error,
2288
+ loading,
2289
+ status: error ? "error" : loading ? "loading" : "success",
2290
+ lastUpdatedAt,
2291
+ refresh
2292
+ }),
2293
+ [data, error, lastUpdatedAt, loading, refresh]
2294
+ );
2295
+ }
2296
+ function createLabelFromKey(key) {
2297
+ return key.replace(/[_-]+/g, " ").replace(/([a-z])([A-Z])/g, "$1 $2").replace(/\b\w/g, (character) => character.toUpperCase());
2298
+ }
2299
+ function inferSeriesKeys(data, xKey, excludeKeys = []) {
2300
+ const firstPoint = data[0];
2301
+ if (!firstPoint) {
2302
+ return [];
2303
+ }
2304
+ return Object.keys(firstPoint).filter((key) => {
2305
+ if (key === xKey) {
2306
+ return false;
2307
+ }
2308
+ if (excludeKeys.includes(key)) {
2309
+ return false;
2310
+ }
2311
+ const value = firstPoint[key];
2312
+ return typeof value === "number";
2313
+ });
2314
+ }
2315
+ function useGraphSeries({
2316
+ data = [],
2317
+ series,
2318
+ xKey,
2319
+ excludeKeys = []
2320
+ }) {
2321
+ return useMemo(() => {
2322
+ const normalizedSeries = series && series.length > 0 ? series : inferSeriesKeys(data, xKey, excludeKeys).map((key) => ({
2323
+ key
2324
+ }));
2325
+ return normalizedSeries.map((item, index) => ({
2326
+ key: item.key,
2327
+ label: item.label ?? createLabelFromKey(item.key),
2328
+ type: item.type ?? "line",
2329
+ color: resolveGraphColor(item.color, { index }),
2330
+ unit: item.unit,
2331
+ visible: item.visible ?? true,
2332
+ strokeWidth: item.strokeWidth ?? GRAPH_DEFAULT_STROKE_WIDTH,
2333
+ radius: item.radius ?? GRAPH_DEFAULT_ACTIVE_DOT_RADIUS,
2334
+ format: item.format,
2335
+ prefix: item.prefix,
2336
+ suffix: item.suffix,
2337
+ yAxisId: item.yAxisId
2338
+ }));
2339
+ }, [data, excludeKeys, series, xKey]);
2340
+ }
2341
+ function mergeGraphTheme(baseTheme, customTheme) {
2342
+ if (!customTheme) {
2343
+ return baseTheme;
2344
+ }
2345
+ return {
2346
+ panel: {
2347
+ ...baseTheme.panel,
2348
+ ...customTheme.panel
2349
+ },
2350
+ text: {
2351
+ ...baseTheme.text,
2352
+ ...customTheme.text
2353
+ },
2354
+ chart: {
2355
+ ...baseTheme.chart,
2356
+ ...customTheme.chart
2357
+ },
2358
+ tooltip: {
2359
+ ...baseTheme.tooltip,
2360
+ ...customTheme.tooltip
2361
+ },
2362
+ colors: customTheme.colors ?? baseTheme.colors
2363
+ };
2364
+ }
2365
+ function useGraphTheme({
2366
+ mode = "dark",
2367
+ theme
2368
+ } = {}) {
2369
+ return useMemo(() => {
2370
+ const baseTheme = mode === "light" ? GRAPH_LIGHT_THEME : mode === "dark" ? GRAPH_DARK_THEME : DEFAULT_GRAPH_THEME;
2371
+ return mergeGraphTheme(baseTheme, theme);
2372
+ }, [mode, theme]);
2373
+ }
2374
+ var GraphContext = createContext({
2375
+ data: [],
2376
+ loading: false,
2377
+ error: null,
2378
+ status: "idle",
2379
+ maxDataPoints: GRAPH_DEFAULT_MAX_REALTIME_POINTS,
2380
+ refresh: async () => {
2381
+ },
2382
+ replaceData: () => {
2383
+ },
2384
+ appendData: () => {
2385
+ },
2386
+ clearData: () => {
2387
+ }
2388
+ });
2389
+ function GraphProvider({
2390
+ children,
2391
+ data,
2392
+ dataSource,
2393
+ maxDataPoints = GRAPH_DEFAULT_MAX_REALTIME_POINTS,
2394
+ autoLoad = true,
2395
+ onDataChange,
2396
+ onError
2397
+ }) {
2398
+ const graphData = useGraphData({
2399
+ data,
2400
+ dataSource,
2401
+ autoLoad,
2402
+ maxDataPoints,
2403
+ onDataChange,
2404
+ onError
2405
+ });
2406
+ const value = useMemo(
2407
+ () => ({
2408
+ ...graphData,
2409
+ mode: dataSource?.mode,
2410
+ maxDataPoints
2411
+ }),
2412
+ [dataSource?.mode, graphData, maxDataPoints]
2413
+ );
2414
+ return /* @__PURE__ */ jsx(
2415
+ GraphContext.Provider,
2416
+ {
2417
+ value,
2418
+ children
2419
+ }
2420
+ );
2421
+ }
2422
+ function useGraphContext() {
2423
+ return useContext(GraphContext);
2424
+ }
2425
+
2426
+ // src/components/data-display/graphs-v2/context/graphReducer.ts
2427
+ function createInitialGraphState(data = []) {
2428
+ return {
2429
+ data,
2430
+ loading: false,
2431
+ error: null,
2432
+ status: data.length > 0 ? "success" : "idle",
2433
+ lastUpdatedAt: data.length > 0 ? /* @__PURE__ */ new Date() : void 0
2434
+ };
2435
+ }
2436
+ function graphReducer(state, action) {
2437
+ switch (action.type) {
2438
+ case "SET_LOADING": {
2439
+ const loading = action.payload ?? true;
2440
+ return {
2441
+ ...state,
2442
+ loading,
2443
+ error: loading ? null : state.error,
2444
+ status: loading ? "loading" : state.status
2445
+ };
2446
+ }
2447
+ case "SET_ERROR": {
2448
+ return {
2449
+ ...state,
2450
+ loading: false,
2451
+ error: action.payload,
2452
+ status: action.payload ? "error" : state.data.length > 0 ? "success" : "idle"
2453
+ };
2454
+ }
2455
+ case "SET_DATA": {
2456
+ return {
2457
+ data: action.payload,
2458
+ loading: false,
2459
+ error: null,
2460
+ status: "success",
2461
+ lastUpdatedAt: /* @__PURE__ */ new Date()
2462
+ };
2463
+ }
2464
+ case "APPEND_DATA": {
2465
+ const nextData = limitRealtimePoints(state.data, action.payload.data, {
2466
+ maxPoints: action.payload.maxDataPoints ?? GRAPH_DEFAULT_MAX_REALTIME_POINTS
2467
+ });
2468
+ return {
2469
+ data: nextData,
2470
+ loading: false,
2471
+ error: null,
2472
+ status: "streaming",
2473
+ lastUpdatedAt: /* @__PURE__ */ new Date()
2474
+ };
2475
+ }
2476
+ case "CLEAR_DATA": {
2477
+ return {
2478
+ data: [],
2479
+ loading: false,
2480
+ error: null,
2481
+ status: "idle",
2482
+ lastUpdatedAt: void 0
2483
+ };
2484
+ }
2485
+ case "SET_STREAMING": {
2486
+ const streaming = action.payload ?? true;
2487
+ return {
2488
+ ...state,
2489
+ loading: false,
2490
+ error: null,
2491
+ status: streaming ? "streaming" : state.data.length > 0 ? "success" : "idle",
2492
+ lastUpdatedAt: streaming ? /* @__PURE__ */ new Date() : state.lastUpdatedAt
2493
+ };
2494
+ }
2495
+ default:
2496
+ return state;
2497
+ }
2498
+ }
2499
+ function GraphEmptyState({
2500
+ height = GRAPH_DEFAULT_HEIGHT,
2501
+ message = GRAPH_EMPTY_MESSAGE,
2502
+ description,
2503
+ className = ""
2504
+ }) {
2505
+ return /* @__PURE__ */ jsxs(
2506
+ "div",
2507
+ {
2508
+ className: `eui-graph flex flex-col items-center justify-center rounded-xl border border-dashed border-gray-700/80 bg-[#111217]/40 px-6 text-center ${className}`,
2509
+ style: { height },
2510
+ children: [
2511
+ /* @__PURE__ */ jsx("div", { className: "flex h-10 w-10 items-center justify-center rounded-full border border-gray-700 bg-white/5 text-gray-500", children: "\u2205" }),
2512
+ /* @__PURE__ */ jsx("div", { className: "mt-3 text-sm font-medium text-gray-300", children: message }),
2513
+ description && /* @__PURE__ */ jsx("div", { className: "mt-1 max-w-sm text-xs text-gray-500", children: description })
2514
+ ]
2515
+ }
2516
+ );
2517
+ }
2518
+ function GraphErrorState({
2519
+ error,
2520
+ height = GRAPH_DEFAULT_HEIGHT,
2521
+ title = GRAPH_ERROR_MESSAGE,
2522
+ message,
2523
+ className = "",
2524
+ onRetry,
2525
+ retryLabel = "Retry"
2526
+ }) {
2527
+ const resolvedMessage = message ?? error?.message;
2528
+ return /* @__PURE__ */ jsxs(
2529
+ "div",
2530
+ {
2531
+ className: `eui-graph flex flex-col items-center justify-center rounded-xl border border-red-500/30 bg-red-500/5 px-6 text-center ${className}`,
2532
+ style: { height },
2533
+ role: "alert",
2534
+ children: [
2535
+ /* @__PURE__ */ jsx("div", { className: "flex h-10 w-10 items-center justify-center rounded-full border border-red-500/30 bg-red-500/10 text-red-400", children: "!" }),
2536
+ /* @__PURE__ */ jsx("div", { className: "mt-3 text-sm font-medium text-red-300", children: title }),
2537
+ resolvedMessage && /* @__PURE__ */ jsx("div", { className: "mt-1 max-w-md text-xs text-red-200/70", children: resolvedMessage }),
2538
+ onRetry && /* @__PURE__ */ jsx(
2539
+ "button",
2540
+ {
2541
+ type: "button",
2542
+ onClick: () => void onRetry(),
2543
+ className: "mt-4 rounded-md border border-red-500/30 px-3 py-1.5 text-xs font-medium text-red-200 transition-colors hover:bg-red-500/10",
2544
+ children: retryLabel
2545
+ }
2546
+ )
2547
+ ]
2548
+ }
2549
+ );
2550
+ }
2551
+ function GraphHeader({
2552
+ title,
2553
+ description,
2554
+ actions,
2555
+ className = ""
2556
+ }) {
2557
+ if (!title && !description && !actions) {
2558
+ return null;
2559
+ }
2560
+ return /* @__PURE__ */ jsxs(
2561
+ "div",
2562
+ {
2563
+ className: `flex items-start justify-between gap-4 border-b border-[#2a2d35] px-4 py-3 ${className}`,
2564
+ children: [
2565
+ /* @__PURE__ */ jsxs("div", { className: "min-w-0", children: [
2566
+ title && /* @__PURE__ */ jsx("div", { className: "eui-graph-title truncate text-sm font-semibold text-gray-100", children: title }),
2567
+ description && /* @__PURE__ */ jsx("div", { className: "eui-graph-description mt-1 text-xs text-gray-400", children: description })
2568
+ ] }),
2569
+ actions && /* @__PURE__ */ jsx("div", { className: "shrink-0", children: actions })
2570
+ ]
2571
+ }
2572
+ );
2573
+ }
2574
+ function GraphLoadingState({
2575
+ height = GRAPH_DEFAULT_HEIGHT,
2576
+ message = GRAPH_LOADING_MESSAGE,
2577
+ className = "",
2578
+ showMessage = true
2579
+ }) {
2580
+ return /* @__PURE__ */ jsxs(
2581
+ "div",
2582
+ {
2583
+ className: `eui-graph eui-graph-loading flex flex-col items-center justify-center rounded-xl border border-[#2a2d35] bg-[#111217]/60 px-6 text-center ${className}`,
2584
+ style: { height },
2585
+ role: "status",
2586
+ "aria-live": "polite",
2587
+ "aria-busy": "true",
2588
+ children: [
2589
+ /* @__PURE__ */ jsx("div", { className: "h-7 w-7 animate-spin rounded-full border-2 border-gray-700 border-t-gray-200" }),
2590
+ showMessage && /* @__PURE__ */ jsx("span", { className: "mt-3 text-sm font-medium text-gray-300", children: message })
2591
+ ]
2592
+ }
2593
+ );
2594
+ }
2595
+ function formatLastUpdatedAt(value) {
2596
+ if (!value) {
2597
+ return "Never updated";
2598
+ }
2599
+ return `Updated ${value.toLocaleTimeString([], {
2600
+ hour: "2-digit",
2601
+ minute: "2-digit",
2602
+ second: "2-digit"
2603
+ })}`;
2604
+ }
2605
+ function GraphToolbar({
2606
+ children,
2607
+ className = "",
2608
+ showRefresh = true,
2609
+ showLastUpdated = true,
2610
+ refreshLabel = "Refresh",
2611
+ onRefresh
2612
+ }) {
2613
+ const graph = useGraphContext();
2614
+ async function handleRefresh() {
2615
+ if (onRefresh) {
2616
+ await onRefresh();
2617
+ return;
2618
+ }
2619
+ await graph.refresh();
2620
+ }
2621
+ if (!children && !showRefresh && !showLastUpdated) {
2622
+ return null;
2623
+ }
2624
+ return /* @__PURE__ */ jsxs(
2625
+ "div",
2626
+ {
2627
+ className: `flex flex-wrap items-center justify-between gap-3 border-b border-[#2a2d35] px-4 py-2 ${className}`,
2628
+ children: [
2629
+ /* @__PURE__ */ jsx("div", { className: "flex min-w-0 items-center gap-2", children }),
2630
+ /* @__PURE__ */ jsxs("div", { className: "ml-auto flex items-center gap-3", children: [
2631
+ showLastUpdated && /* @__PURE__ */ jsx("span", { className: "text-xs text-gray-500", children: formatLastUpdatedAt(graph.lastUpdatedAt) }),
2632
+ showRefresh && /* @__PURE__ */ jsx(
2633
+ "button",
2634
+ {
2635
+ type: "button",
2636
+ onClick: () => void handleRefresh(),
2637
+ disabled: graph.loading,
2638
+ className: "rounded-md border border-[#2a2d35] px-2.5 py-1.5 text-xs font-medium text-gray-300 transition-colors hover:bg-white/5 disabled:cursor-not-allowed disabled:opacity-60",
2639
+ children: graph.loading ? "Refreshing..." : refreshLabel
2640
+ }
2641
+ )
2642
+ ] })
2643
+ ]
2644
+ }
2645
+ );
2646
+ }
2647
+ function GraphPanel({
2648
+ title,
2649
+ description,
2650
+ actions,
2651
+ toolbar,
2652
+ children,
2653
+ className = "",
2654
+ contentClassName = "",
2655
+ height = GRAPH_DEFAULT_HEIGHT,
2656
+ loading,
2657
+ error,
2658
+ empty,
2659
+ emptyMessage,
2660
+ emptyDescription,
2661
+ showToolbar = false,
2662
+ showRefresh = true,
2663
+ showLastUpdated = true,
2664
+ onRetry
2665
+ }) {
2666
+ const graph = useGraphContext();
2667
+ const resolvedLoading = loading ?? graph.loading;
2668
+ const resolvedError = error ?? graph.error;
2669
+ const resolvedEmpty = empty ?? graph.data.length === 0;
2670
+ function renderContent() {
2671
+ if (resolvedLoading) {
2672
+ return /* @__PURE__ */ jsx(GraphLoadingState, { height });
2673
+ }
2674
+ if (resolvedError) {
2675
+ return /* @__PURE__ */ jsx(
2676
+ GraphErrorState,
2677
+ {
2678
+ height,
2679
+ error: resolvedError,
2680
+ onRetry: onRetry ?? graph.refresh
2681
+ }
2682
+ );
2683
+ }
2684
+ if (resolvedEmpty) {
2685
+ return /* @__PURE__ */ jsx(
2686
+ GraphEmptyState,
2687
+ {
2688
+ height,
2689
+ message: emptyMessage,
2690
+ description: emptyDescription
2691
+ }
2692
+ );
2693
+ }
2694
+ return children;
2695
+ }
2696
+ return /* @__PURE__ */ jsxs(
2697
+ "section",
2698
+ {
2699
+ className: `eui-graph eui-graph-panel overflow-hidden rounded-xl border border-[#2a2d35] bg-[#111217] ${className}`,
2700
+ children: [
2701
+ /* @__PURE__ */ jsx(GraphHeader, { title, description, actions }),
2702
+ showToolbar && /* @__PURE__ */ jsx(
2703
+ GraphToolbar,
2704
+ {
2705
+ showRefresh,
2706
+ showLastUpdated,
2707
+ children: toolbar
2708
+ }
2709
+ ),
2710
+ /* @__PURE__ */ jsx("div", { className: `p-4 ${contentClassName}`, children: renderContent() })
2711
+ ]
2712
+ }
2713
+ );
2714
+ }
2715
+ function createLabelFromKey2(key) {
2716
+ return key.replace(/[_-]+/g, " ").replace(/([a-z])([A-Z])/g, "$1 $2").replace(/\b\w/g, (character) => character.toUpperCase());
2717
+ }
2718
+ function GraphLegend({
2719
+ items,
2720
+ series,
2721
+ data = [],
2722
+ className = "",
2723
+ showValues = true,
2724
+ valueSource = "latest",
2725
+ onItemClick
2726
+ }) {
2727
+ const legendItems = useMemo(() => {
2728
+ if (items?.length) {
2729
+ return items;
2730
+ }
2731
+ if (!series?.length) {
2732
+ return [];
2733
+ }
2734
+ const latestPoint = data[data.length - 1];
2735
+ return series.map((item, index) => ({
2736
+ key: item.key,
2737
+ label: item.label ?? createLabelFromKey2(item.key),
2738
+ color: resolveGraphColor(item.color, { index }),
2739
+ value: valueSource === "latest" ? latestPoint?.[item.key] : void 0,
2740
+ unit: item.unit,
2741
+ format: item.format,
2742
+ prefix: item.prefix,
2743
+ suffix: item.suffix,
2744
+ active: item.visible ?? true
2745
+ }));
2746
+ }, [data, items, series, valueSource]);
2747
+ if (!legendItems.length) {
2748
+ return null;
2749
+ }
2750
+ return /* @__PURE__ */ jsx(
2751
+ "div",
2752
+ {
2753
+ className: `eui-graph flex flex-wrap items-center gap-x-4 gap-y-2 text-xs ${className}`,
2754
+ children: legendItems.map((item, index) => {
2755
+ const color = resolveGraphColor(item.color, { index });
2756
+ const active = item.active ?? true;
2757
+ return /* @__PURE__ */ jsxs(
2758
+ "button",
2759
+ {
2760
+ type: "button",
2761
+ onClick: () => onItemClick?.(item),
2762
+ disabled: !onItemClick,
2763
+ className: `inline-flex items-center gap-2 rounded-md transition-opacity ${active ? "opacity-100" : "opacity-40"} ${onItemClick ? "cursor-pointer hover:opacity-80" : "cursor-default"}`,
2764
+ children: [
2765
+ /* @__PURE__ */ jsx(
2766
+ "span",
2767
+ {
2768
+ className: "h-2.5 w-2.5 rounded-full",
2769
+ style: { backgroundColor: color }
2770
+ }
2771
+ ),
2772
+ /* @__PURE__ */ jsx("span", { className: "text-gray-400", children: item.label ?? createLabelFromKey2(item.key) }),
2773
+ showValues && item.value !== void 0 && /* @__PURE__ */ jsx("span", { className: "font-medium text-gray-200", children: formatGraphValue(item.value, {
2774
+ format: item.format ?? "number",
2775
+ prefix: item.prefix,
2776
+ suffix: item.suffix ?? item.unit
2777
+ }) })
2778
+ ]
2779
+ },
2780
+ item.key
2781
+ );
2782
+ })
2783
+ }
2784
+ );
2785
+ }
2786
+ function GraphTooltip({
2787
+ active,
2788
+ label,
2789
+ payload,
2790
+ className = "",
2791
+ labelFormatter,
2792
+ valueFormatter,
2793
+ seriesFormatters = {}
2794
+ }) {
2795
+ if (!active || !payload?.length) {
2796
+ return null;
2797
+ }
2798
+ return /* @__PURE__ */ jsxs(
2799
+ "div",
2800
+ {
2801
+ className: `eui-graph rounded-xl border border-[#2a2d35] bg-[#181b21] px-3 py-2 shadow-xl ${className}`,
2802
+ children: [
2803
+ label !== void 0 && /* @__PURE__ */ jsx("div", { className: "mb-2 text-xs font-semibold text-gray-100", children: labelFormatter ? labelFormatter(label) : label }),
2804
+ /* @__PURE__ */ jsx("div", { className: "flex flex-col gap-1.5", children: payload.map((item, index) => {
2805
+ const dataKey = item.dataKey ?? item.name ?? String(index);
2806
+ const formatterOptions = seriesFormatters[dataKey];
2807
+ const formattedValue = valueFormatter ? valueFormatter(item.value, item.name, item) : formatGraphValue(item.value, {
2808
+ format: formatterOptions?.format ?? "number",
2809
+ prefix: formatterOptions?.prefix,
2810
+ suffix: formatterOptions?.suffix ?? formatterOptions?.unit
2811
+ });
2812
+ return /* @__PURE__ */ jsxs(
2813
+ "div",
2814
+ {
2815
+ className: "flex min-w-[140px] items-center justify-between gap-4 text-xs",
2816
+ children: [
2817
+ /* @__PURE__ */ jsxs("div", { className: "flex min-w-0 items-center gap-2", children: [
2818
+ /* @__PURE__ */ jsx(
2819
+ "span",
2820
+ {
2821
+ className: "h-2 w-2 rounded-full",
2822
+ style: { backgroundColor: item.color }
2823
+ }
2824
+ ),
2825
+ /* @__PURE__ */ jsx("span", { className: "truncate text-gray-400", children: item.name ?? dataKey })
2826
+ ] }),
2827
+ /* @__PURE__ */ jsx("span", { className: "font-medium text-gray-100", children: formattedValue })
2828
+ ]
2829
+ },
2830
+ `${dataKey}-${index}`
2831
+ );
2832
+ }) })
2833
+ ]
2834
+ }
2835
+ );
2836
+ }
2837
+ function GraphContainer({
2838
+ children,
2839
+ height = GRAPH_DEFAULT_HEIGHT,
2840
+ className = "",
2841
+ contentClassName = ""
2842
+ }) {
2843
+ return /* @__PURE__ */ jsx(
2844
+ "div",
2845
+ {
2846
+ className: `eui-graph relative w-full min-w-0 overflow-hidden ${className}`,
2847
+ style: { height },
2848
+ children: /* @__PURE__ */ jsx("div", { className: `h-full w-full ${contentClassName}`, children })
2849
+ }
2850
+ );
2851
+ }
2852
+ function LineGraph({
2853
+ data,
2854
+ xKey = "time",
2855
+ series,
2856
+ height = GRAPH_DEFAULT_HEIGHT,
2857
+ loading,
2858
+ error,
2859
+ className = "",
2860
+ showGrid = true,
2861
+ showTooltip = true,
2862
+ showLegend = true,
2863
+ animated = true
2864
+ }) {
2865
+ const context = useGraphContext();
2866
+ const theme = useGraphTheme();
2867
+ const graphData = data ?? context.data;
2868
+ const graphLoading = loading ?? context.loading;
2869
+ const graphError = error ?? context.error;
2870
+ const resolvedSeries = useGraphSeries({
2871
+ data: graphData,
2872
+ series,
2873
+ xKey: String(xKey)
2874
+ }).filter((item) => item.visible);
2875
+ if (graphLoading) {
2876
+ return /* @__PURE__ */ jsx(GraphLoadingState, { height, className });
2877
+ }
2878
+ if (graphError) {
2879
+ return /* @__PURE__ */ jsx(
2880
+ GraphErrorState,
2881
+ {
2882
+ error: graphError,
2883
+ height,
2884
+ className
2885
+ }
2886
+ );
2887
+ }
2888
+ if (!graphData.length || !resolvedSeries.length) {
2889
+ return /* @__PURE__ */ jsx(GraphEmptyState, { height, className });
2890
+ }
2891
+ return /* @__PURE__ */ jsxs("div", { className: `eui-graph flex w-full flex-col gap-3 ${className}`, children: [
2892
+ /* @__PURE__ */ jsx(GraphContainer, { height, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height: "100%", children: /* @__PURE__ */ jsxs(LineChart$1, { data: graphData, margin: GRAPH_DEFAULT_MARGIN, children: [
2893
+ showGrid && /* @__PURE__ */ jsx(
2894
+ CartesianGrid,
2895
+ {
2896
+ stroke: theme.chart.grid,
2897
+ strokeDasharray: "3 3",
2898
+ vertical: false
2899
+ }
2900
+ ),
2901
+ /* @__PURE__ */ jsx(
2902
+ XAxis,
2903
+ {
2904
+ dataKey: String(xKey),
2905
+ stroke: theme.chart.axis,
2906
+ tick: { fill: theme.chart.axis, fontSize: 12 },
2907
+ tickLine: false,
2908
+ axisLine: false
2909
+ }
2910
+ ),
2911
+ /* @__PURE__ */ jsx(
2912
+ YAxis,
2913
+ {
2914
+ stroke: theme.chart.axis,
2915
+ tick: { fill: theme.chart.axis, fontSize: 12 },
2916
+ tickLine: false,
2917
+ axisLine: false,
2918
+ tickFormatter: (value) => formatGraphValue(value, {
2919
+ format: "compact"
2920
+ })
2921
+ }
2922
+ ),
2923
+ showTooltip && /* @__PURE__ */ jsx(
2924
+ Tooltip$1,
2925
+ {
2926
+ content: /* @__PURE__ */ jsx(
2927
+ GraphTooltip,
2928
+ {
2929
+ seriesFormatters: Object.fromEntries(
2930
+ resolvedSeries.map((item) => [
2931
+ item.key,
2932
+ {
2933
+ format: item.format,
2934
+ prefix: item.prefix,
2935
+ suffix: item.suffix,
2936
+ unit: item.unit
2937
+ }
2938
+ ])
2939
+ )
2940
+ }
2941
+ ),
2942
+ cursor: { stroke: theme.chart.cursor }
2943
+ }
2944
+ ),
2945
+ resolvedSeries.map((item) => /* @__PURE__ */ jsx(
2946
+ Line$1,
2947
+ {
2948
+ type: "monotone",
2949
+ dataKey: item.key,
2950
+ name: item.label,
2951
+ stroke: item.color,
2952
+ strokeWidth: item.strokeWidth,
2953
+ dot: false,
2954
+ activeDot: { r: item.radius },
2955
+ isAnimationActive: animated,
2956
+ animationDuration: GRAPH_DEFAULT_ANIMATION_DURATION,
2957
+ yAxisId: item.yAxisId
2958
+ },
2959
+ item.key
2960
+ ))
2961
+ ] }) }) }),
2962
+ showLegend && /* @__PURE__ */ jsx(
2963
+ GraphLegend,
2964
+ {
2965
+ series: resolvedSeries,
2966
+ data: graphData,
2967
+ showValues: true,
2968
+ valueSource: "latest"
2969
+ }
2970
+ )
2971
+ ] });
2972
+ }
2973
+ function AreaGraph({
2974
+ data,
2975
+ xKey = "time",
2976
+ series,
2977
+ height = GRAPH_DEFAULT_HEIGHT,
2978
+ loading,
2979
+ error,
2980
+ className = "",
2981
+ showGrid = true,
2982
+ showTooltip = true,
2983
+ showLegend = true,
2984
+ animated = true
2985
+ }) {
2986
+ const context = useGraphContext();
2987
+ const theme = useGraphTheme();
2988
+ const graphData = data ?? context.data;
2989
+ const graphLoading = loading ?? context.loading;
2990
+ const graphError = error ?? context.error;
2991
+ const resolvedSeries = useGraphSeries({
2992
+ data: graphData,
2993
+ series,
2994
+ xKey: String(xKey)
2995
+ }).filter((item) => item.visible);
2996
+ if (graphLoading) {
2997
+ return /* @__PURE__ */ jsx(GraphLoadingState, { height, className });
2998
+ }
2999
+ if (graphError) {
3000
+ return /* @__PURE__ */ jsx(
3001
+ GraphErrorState,
3002
+ {
3003
+ error: graphError,
3004
+ height,
3005
+ className
3006
+ }
3007
+ );
3008
+ }
3009
+ if (!graphData.length || !resolvedSeries.length) {
3010
+ return /* @__PURE__ */ jsx(GraphEmptyState, { height, className });
3011
+ }
3012
+ return /* @__PURE__ */ jsxs("div", { className: `eui-graph flex w-full flex-col gap-3 ${className}`, children: [
3013
+ /* @__PURE__ */ jsx(GraphContainer, { height, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height: "100%", children: /* @__PURE__ */ jsxs(AreaChart, { data: graphData, margin: GRAPH_DEFAULT_MARGIN, children: [
3014
+ /* @__PURE__ */ jsx("defs", { children: resolvedSeries.map((item) => /* @__PURE__ */ jsxs(
3015
+ "linearGradient",
3016
+ {
3017
+ id: `eui-area-gradient-${item.key}`,
3018
+ x1: "0",
3019
+ y1: "0",
3020
+ x2: "0",
3021
+ y2: "1",
3022
+ children: [
3023
+ /* @__PURE__ */ jsx("stop", { offset: "5%", stopColor: item.color, stopOpacity: 0.35 }),
3024
+ /* @__PURE__ */ jsx(
3025
+ "stop",
3026
+ {
3027
+ offset: "95%",
3028
+ stopColor: item.color,
3029
+ stopOpacity: 0.02
3030
+ }
3031
+ )
3032
+ ]
3033
+ },
3034
+ item.key
3035
+ )) }),
3036
+ showGrid && /* @__PURE__ */ jsx(
3037
+ CartesianGrid,
3038
+ {
3039
+ stroke: theme.chart.grid,
3040
+ strokeDasharray: "3 3",
3041
+ vertical: false
3042
+ }
3043
+ ),
3044
+ /* @__PURE__ */ jsx(
3045
+ XAxis,
3046
+ {
3047
+ dataKey: String(xKey),
3048
+ stroke: theme.chart.axis,
3049
+ tick: { fill: theme.chart.axis, fontSize: 12 },
3050
+ tickLine: false,
3051
+ axisLine: false
3052
+ }
3053
+ ),
3054
+ /* @__PURE__ */ jsx(
3055
+ YAxis,
3056
+ {
3057
+ stroke: theme.chart.axis,
3058
+ tick: { fill: theme.chart.axis, fontSize: 12 },
3059
+ tickLine: false,
3060
+ axisLine: false,
3061
+ tickFormatter: (value) => formatGraphValue(value, {
3062
+ format: "compact"
3063
+ })
3064
+ }
3065
+ ),
3066
+ showTooltip && /* @__PURE__ */ jsx(
3067
+ Tooltip$1,
3068
+ {
3069
+ content: /* @__PURE__ */ jsx(
3070
+ GraphTooltip,
3071
+ {
3072
+ seriesFormatters: Object.fromEntries(
3073
+ resolvedSeries.map((item) => [
3074
+ item.key,
3075
+ {
3076
+ format: item.format,
3077
+ prefix: item.prefix,
3078
+ suffix: item.suffix,
3079
+ unit: item.unit
3080
+ }
3081
+ ])
3082
+ )
3083
+ }
3084
+ ),
3085
+ cursor: { stroke: theme.chart.cursor }
3086
+ }
3087
+ ),
3088
+ resolvedSeries.map((item) => /* @__PURE__ */ jsx(
3089
+ Area,
3090
+ {
3091
+ type: "monotone",
3092
+ dataKey: item.key,
3093
+ name: item.label,
3094
+ stroke: item.color,
3095
+ strokeWidth: item.strokeWidth,
3096
+ fill: `url(#eui-area-gradient-${item.key})`,
3097
+ isAnimationActive: animated,
3098
+ animationDuration: GRAPH_DEFAULT_ANIMATION_DURATION,
3099
+ yAxisId: item.yAxisId
3100
+ },
3101
+ item.key
3102
+ ))
3103
+ ] }) }) }),
3104
+ showLegend && /* @__PURE__ */ jsx(
3105
+ GraphLegend,
3106
+ {
3107
+ series: resolvedSeries,
3108
+ data: graphData,
3109
+ showValues: true,
3110
+ valueSource: "latest"
3111
+ }
3112
+ )
3113
+ ] });
3114
+ }
3115
+ function BarGraph({
3116
+ data,
3117
+ xKey = "name",
3118
+ series,
3119
+ height = GRAPH_DEFAULT_HEIGHT,
3120
+ loading,
3121
+ error,
3122
+ className = "",
3123
+ showGrid = true,
3124
+ showTooltip = true,
3125
+ showLegend = true,
3126
+ animated = true,
3127
+ layout = "horizontal"
3128
+ }) {
3129
+ const context = useGraphContext();
3130
+ const theme = useGraphTheme();
3131
+ const graphData = data ?? context.data;
3132
+ const graphLoading = loading ?? context.loading;
3133
+ const graphError = error ?? context.error;
3134
+ const resolvedSeries = useGraphSeries({
3135
+ data: graphData,
3136
+ series,
3137
+ xKey: String(xKey)
3138
+ }).filter((item) => item.visible);
3139
+ if (graphLoading) {
3140
+ return /* @__PURE__ */ jsx(GraphLoadingState, { height, className });
3141
+ }
3142
+ if (graphError) {
3143
+ return /* @__PURE__ */ jsx(
3144
+ GraphErrorState,
3145
+ {
3146
+ error: graphError,
3147
+ height,
3148
+ className
3149
+ }
3150
+ );
3151
+ }
3152
+ if (!graphData.length || !resolvedSeries.length) {
3153
+ return /* @__PURE__ */ jsx(GraphEmptyState, { height, className });
3154
+ }
3155
+ const isVertical = layout === "vertical";
3156
+ return /* @__PURE__ */ jsxs("div", { className: `eui-graph flex w-full flex-col gap-3 ${className}`, children: [
3157
+ /* @__PURE__ */ jsx(GraphContainer, { height, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height: "100%", children: /* @__PURE__ */ jsxs(
3158
+ BarChart$1,
3159
+ {
3160
+ data: graphData,
3161
+ margin: GRAPH_DEFAULT_MARGIN,
3162
+ layout: isVertical ? "vertical" : "horizontal",
3163
+ children: [
3164
+ showGrid && /* @__PURE__ */ jsx(
3165
+ CartesianGrid,
3166
+ {
3167
+ stroke: theme.chart.grid,
3168
+ strokeDasharray: "3 3",
3169
+ horizontal: !isVertical,
3170
+ vertical: isVertical
3171
+ }
3172
+ ),
3173
+ isVertical ? /* @__PURE__ */ jsxs(Fragment, { children: [
3174
+ /* @__PURE__ */ jsx(
3175
+ XAxis,
3176
+ {
3177
+ type: "number",
3178
+ stroke: theme.chart.axis,
3179
+ tick: { fill: theme.chart.axis, fontSize: 12 },
3180
+ tickLine: false,
3181
+ axisLine: false,
3182
+ tickFormatter: (value) => formatGraphValue(value, {
3183
+ format: "compact"
3184
+ })
3185
+ }
3186
+ ),
3187
+ /* @__PURE__ */ jsx(
3188
+ YAxis,
3189
+ {
3190
+ type: "category",
3191
+ dataKey: String(xKey),
3192
+ stroke: theme.chart.axis,
3193
+ tick: { fill: theme.chart.axis, fontSize: 12 },
3194
+ tickLine: false,
3195
+ axisLine: false,
3196
+ width: 110
3197
+ }
3198
+ )
3199
+ ] }) : /* @__PURE__ */ jsxs(Fragment, { children: [
3200
+ /* @__PURE__ */ jsx(
3201
+ XAxis,
3202
+ {
3203
+ dataKey: String(xKey),
3204
+ stroke: theme.chart.axis,
3205
+ tick: { fill: theme.chart.axis, fontSize: 12 },
3206
+ tickLine: false,
3207
+ axisLine: false
3208
+ }
3209
+ ),
3210
+ /* @__PURE__ */ jsx(
3211
+ YAxis,
3212
+ {
3213
+ stroke: theme.chart.axis,
3214
+ tick: { fill: theme.chart.axis, fontSize: 12 },
3215
+ tickLine: false,
3216
+ axisLine: false,
3217
+ tickFormatter: (value) => formatGraphValue(value, {
3218
+ format: "compact"
3219
+ })
3220
+ }
3221
+ )
3222
+ ] }),
3223
+ showTooltip && /* @__PURE__ */ jsx(
3224
+ Tooltip$1,
3225
+ {
3226
+ content: /* @__PURE__ */ jsx(
3227
+ GraphTooltip,
3228
+ {
3229
+ seriesFormatters: Object.fromEntries(
3230
+ resolvedSeries.map((item) => [
3231
+ item.key,
3232
+ {
3233
+ format: item.format,
3234
+ prefix: item.prefix,
3235
+ suffix: item.suffix,
3236
+ unit: item.unit
3237
+ }
3238
+ ])
3239
+ )
3240
+ }
3241
+ ),
3242
+ cursor: { fill: theme.chart.cursor }
3243
+ }
3244
+ ),
3245
+ resolvedSeries.map((item) => /* @__PURE__ */ jsx(
3246
+ Bar$1,
3247
+ {
3248
+ dataKey: item.key,
3249
+ name: item.label,
3250
+ fill: item.color,
3251
+ radius: GRAPH_DEFAULT_BAR_RADIUS,
3252
+ isAnimationActive: animated,
3253
+ animationDuration: GRAPH_DEFAULT_ANIMATION_DURATION,
3254
+ yAxisId: isVertical ? void 0 : item.yAxisId
3255
+ },
3256
+ item.key
3257
+ ))
3258
+ ]
3259
+ }
3260
+ ) }) }),
3261
+ showLegend && /* @__PURE__ */ jsx(
3262
+ GraphLegend,
3263
+ {
3264
+ series: resolvedSeries,
3265
+ data: graphData,
3266
+ showValues: true,
3267
+ valueSource: "latest"
3268
+ }
3269
+ )
3270
+ ] });
3271
+ }
3272
+ function PieGraph({
3273
+ data,
3274
+ nameKey = "name",
3275
+ valueKey = "value",
3276
+ height = GRAPH_DEFAULT_HEIGHT,
3277
+ loading,
3278
+ error,
3279
+ className = "",
3280
+ showTooltip = true,
3281
+ showLegend = true,
3282
+ animated = true,
3283
+ innerRadius = "45%",
3284
+ outerRadius = "75%",
3285
+ valueFormat = "number",
3286
+ unit
3287
+ }) {
3288
+ const context = useGraphContext();
3289
+ const theme = useGraphTheme();
3290
+ const graphData = data ?? context.data;
3291
+ const graphLoading = loading ?? context.loading;
3292
+ const graphError = error ?? context.error;
3293
+ if (graphLoading) {
3294
+ return /* @__PURE__ */ jsx(GraphLoadingState, { height, className });
3295
+ }
3296
+ if (graphError) {
3297
+ return /* @__PURE__ */ jsx(
3298
+ GraphErrorState,
3299
+ {
3300
+ error: graphError,
3301
+ height,
3302
+ className
3303
+ }
3304
+ );
3305
+ }
3306
+ if (!graphData.length) {
3307
+ return /* @__PURE__ */ jsx(GraphEmptyState, { height, className });
3308
+ }
3309
+ const legendItems = graphData.map((item, index) => {
3310
+ const key = String(item[String(nameKey)] ?? index);
3311
+ return {
3312
+ key,
3313
+ label: key,
3314
+ value: item[String(valueKey)],
3315
+ color: resolveGraphColor(void 0, {
3316
+ index,
3317
+ palette: theme.colors
3318
+ }),
3319
+ format: valueFormat,
3320
+ unit,
3321
+ active: true
3322
+ };
3323
+ });
3324
+ return /* @__PURE__ */ jsxs("div", { className: `eui-graph flex w-full flex-col gap-3 ${className}`, children: [
3325
+ /* @__PURE__ */ jsx(GraphContainer, { height, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height: "100%", children: /* @__PURE__ */ jsxs(PieChart$1, { children: [
3326
+ /* @__PURE__ */ jsx(
3327
+ Pie$1,
3328
+ {
3329
+ data: graphData,
3330
+ dataKey: String(valueKey),
3331
+ nameKey: String(nameKey),
3332
+ innerRadius,
3333
+ outerRadius,
3334
+ paddingAngle: 2,
3335
+ isAnimationActive: animated,
3336
+ animationDuration: GRAPH_DEFAULT_ANIMATION_DURATION,
3337
+ children: graphData.map((_item, index) => /* @__PURE__ */ jsx(
3338
+ Cell,
3339
+ {
3340
+ fill: resolveGraphColor(void 0, {
3341
+ index,
3342
+ palette: theme.colors
3343
+ })
3344
+ },
3345
+ `cell-${index}`
3346
+ ))
3347
+ }
3348
+ ),
3349
+ showTooltip && /* @__PURE__ */ jsx(
3350
+ Tooltip$1,
3351
+ {
3352
+ content: /* @__PURE__ */ jsx(
3353
+ GraphTooltip,
3354
+ {
3355
+ seriesFormatters: {
3356
+ [String(valueKey)]: {
3357
+ format: valueFormat,
3358
+ suffix: unit
3359
+ }
3360
+ }
3361
+ }
3362
+ )
3363
+ }
3364
+ )
3365
+ ] }) }) }),
3366
+ showLegend && /* @__PURE__ */ jsx(GraphLegend, { items: legendItems, showValues: true, valueSource: "latest" })
3367
+ ] });
3368
+ }
3369
+ function ScatterGraph({
3370
+ data,
3371
+ xKey = "x",
3372
+ series,
3373
+ height = GRAPH_DEFAULT_HEIGHT,
3374
+ loading,
3375
+ error,
3376
+ className = "",
3377
+ showGrid = true,
3378
+ showTooltip = true,
3379
+ showLegend = true,
3380
+ animated = true
3381
+ }) {
3382
+ const context = useGraphContext();
3383
+ const theme = useGraphTheme();
3384
+ const graphData = data ?? context.data;
3385
+ const graphLoading = loading ?? context.loading;
3386
+ const graphError = error ?? context.error;
3387
+ const resolvedSeries = useGraphSeries({
3388
+ data: graphData,
3389
+ series,
3390
+ xKey: String(xKey)
3391
+ }).filter((item) => item.visible);
3392
+ if (graphLoading) {
3393
+ return /* @__PURE__ */ jsx(GraphLoadingState, { height, className });
3394
+ }
3395
+ if (graphError) {
3396
+ return /* @__PURE__ */ jsx(
3397
+ GraphErrorState,
3398
+ {
3399
+ error: graphError,
3400
+ height,
3401
+ className
3402
+ }
3403
+ );
3404
+ }
3405
+ if (!graphData.length || !resolvedSeries.length) {
3406
+ return /* @__PURE__ */ jsx(GraphEmptyState, { height, className });
3407
+ }
3408
+ return /* @__PURE__ */ jsxs("div", { className: `eui-graph flex w-full flex-col gap-3 ${className}`, children: [
3409
+ /* @__PURE__ */ jsx(GraphContainer, { height, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height: "100%", children: /* @__PURE__ */ jsxs(ScatterChart, { margin: GRAPH_DEFAULT_MARGIN, children: [
3410
+ showGrid && /* @__PURE__ */ jsx(CartesianGrid, { stroke: theme.chart.grid, strokeDasharray: "3 3" }),
3411
+ /* @__PURE__ */ jsx(
3412
+ XAxis,
3413
+ {
3414
+ type: "number",
3415
+ dataKey: String(xKey),
3416
+ name: String(xKey),
3417
+ stroke: theme.chart.axis,
3418
+ tick: { fill: theme.chart.axis, fontSize: 12 },
3419
+ tickLine: false,
3420
+ axisLine: false,
3421
+ tickFormatter: (value) => formatGraphValue(value, {
3422
+ format: "compact"
3423
+ })
3424
+ }
3425
+ ),
3426
+ /* @__PURE__ */ jsx(
3427
+ YAxis,
3428
+ {
3429
+ type: "number",
3430
+ stroke: theme.chart.axis,
3431
+ tick: { fill: theme.chart.axis, fontSize: 12 },
3432
+ tickLine: false,
3433
+ axisLine: false,
3434
+ tickFormatter: (value) => formatGraphValue(value, {
3435
+ format: "compact"
3436
+ })
3437
+ }
3438
+ ),
3439
+ showTooltip && /* @__PURE__ */ jsx(
3440
+ Tooltip$1,
3441
+ {
3442
+ content: /* @__PURE__ */ jsx(
3443
+ GraphTooltip,
3444
+ {
3445
+ seriesFormatters: Object.fromEntries(
3446
+ resolvedSeries.map((item) => [
3447
+ item.key,
3448
+ {
3449
+ format: item.format,
3450
+ prefix: item.prefix,
3451
+ suffix: item.suffix,
3452
+ unit: item.unit
3453
+ }
3454
+ ])
3455
+ )
3456
+ }
3457
+ ),
3458
+ cursor: { stroke: theme.chart.cursor, strokeDasharray: "3 3" }
3459
+ }
3460
+ ),
3461
+ resolvedSeries.map((item) => /* @__PURE__ */ jsx(
3462
+ Scatter,
3463
+ {
3464
+ data: graphData,
3465
+ dataKey: item.key,
3466
+ name: item.label,
3467
+ fill: item.color,
3468
+ isAnimationActive: animated,
3469
+ animationDuration: GRAPH_DEFAULT_ANIMATION_DURATION
3470
+ },
3471
+ item.key
3472
+ ))
3473
+ ] }) }) }),
3474
+ showLegend && /* @__PURE__ */ jsx(
3475
+ GraphLegend,
3476
+ {
3477
+ series: resolvedSeries,
3478
+ data: graphData,
3479
+ showValues: true,
3480
+ valueSource: "latest"
3481
+ }
3482
+ )
3483
+ ] });
3484
+ }
3485
+ function GaugeGraph({
3486
+ data,
3487
+ valueKey = "value",
3488
+ label,
3489
+ value,
3490
+ min = 0,
3491
+ max = 100,
3492
+ height = GRAPH_DEFAULT_HEIGHT,
3493
+ color,
3494
+ unit,
3495
+ format = "number",
3496
+ loading,
3497
+ error,
3498
+ className = ""
3499
+ }) {
3500
+ const context = useGraphContext();
3501
+ const theme = useGraphTheme();
3502
+ const graphData = data ?? context.data;
3503
+ const graphLoading = loading ?? context.loading;
3504
+ const graphError = error ?? context.error;
3505
+ const resolvedValue = useMemo(() => {
3506
+ if (typeof value === "number") {
3507
+ return value;
3508
+ }
3509
+ const latestPoint = graphData[graphData.length - 1];
3510
+ const latestValue = latestPoint?.[String(valueKey)];
3511
+ return typeof latestValue === "number" ? latestValue : void 0;
3512
+ }, [graphData, value, valueKey]);
3513
+ if (graphLoading) {
3514
+ return /* @__PURE__ */ jsx(GraphLoadingState, { height, className });
3515
+ }
3516
+ if (graphError) {
3517
+ return /* @__PURE__ */ jsx(
3518
+ GraphErrorState,
3519
+ {
3520
+ error: graphError,
3521
+ height,
3522
+ className
3523
+ }
3524
+ );
3525
+ }
3526
+ if (resolvedValue === void 0) {
3527
+ return /* @__PURE__ */ jsx(GraphEmptyState, { height, className });
3528
+ }
3529
+ const range = max - min;
3530
+ const percentage = range === 0 ? 0 : Math.min(100, Math.max(0, (resolvedValue - min) / range * 100));
3531
+ const radius = 72;
3532
+ const strokeWidth = 14;
3533
+ const circumference = Math.PI * radius;
3534
+ const offset = circumference - percentage / 100 * circumference;
3535
+ const resolvedColor = resolveGraphColor(color, {
3536
+ index: 0,
3537
+ palette: theme.colors
3538
+ });
3539
+ return /* @__PURE__ */ jsx(
3540
+ "div",
3541
+ {
3542
+ className: `eui-graph flex items-center justify-center ${className}`,
3543
+ style: { height },
3544
+ children: /* @__PURE__ */ jsxs("div", { className: "flex flex-col items-center gap-3", children: [
3545
+ /* @__PURE__ */ jsxs("svg", { width: "220", height: "130", viewBox: "0 0 220 130", children: [
3546
+ /* @__PURE__ */ jsx(
3547
+ "path",
3548
+ {
3549
+ d: "M 38 104 A 72 72 0 0 1 182 104",
3550
+ fill: "none",
3551
+ stroke: theme.chart.grid,
3552
+ strokeWidth,
3553
+ strokeLinecap: "round"
3554
+ }
3555
+ ),
3556
+ /* @__PURE__ */ jsx(
3557
+ "path",
3558
+ {
3559
+ d: "M 38 104 A 72 72 0 0 1 182 104",
3560
+ fill: "none",
3561
+ stroke: resolvedColor,
3562
+ strokeWidth,
3563
+ strokeLinecap: "round",
3564
+ strokeDasharray: circumference,
3565
+ strokeDashoffset: offset
3566
+ }
3567
+ ),
3568
+ /* @__PURE__ */ jsx(
3569
+ "text",
3570
+ {
3571
+ x: "110",
3572
+ y: "92",
3573
+ textAnchor: "middle",
3574
+ fill: theme.tooltip.text,
3575
+ fontSize: "28",
3576
+ fontWeight: "700",
3577
+ children: formatGraphValue(resolvedValue, {
3578
+ format,
3579
+ suffix: unit,
3580
+ maximumFractionDigits: 2
3581
+ })
3582
+ }
3583
+ ),
3584
+ label && /* @__PURE__ */ jsx(
3585
+ "text",
3586
+ {
3587
+ x: "110",
3588
+ y: "118",
3589
+ textAnchor: "middle",
3590
+ fill: theme.tooltip.muted,
3591
+ fontSize: "12",
3592
+ children: label
3593
+ }
3594
+ )
3595
+ ] }),
3596
+ /* @__PURE__ */ jsxs("div", { className: "flex w-full max-w-[180px] justify-between text-xs text-gray-500", children: [
3597
+ /* @__PURE__ */ jsx("span", { children: formatGraphValue(min, {
3598
+ format,
3599
+ suffix: unit
3600
+ }) }),
3601
+ /* @__PURE__ */ jsx("span", { children: formatGraphValue(max, {
3602
+ format,
3603
+ suffix: unit
3604
+ }) })
3605
+ ] })
3606
+ ] })
3607
+ }
3608
+ );
3609
+ }
3610
+ function StatGraph({
3611
+ data,
3612
+ valueKey = "value",
3613
+ label,
3614
+ value,
3615
+ previousValue,
3616
+ format = "number",
3617
+ prefix,
3618
+ suffix,
3619
+ unit,
3620
+ loading,
3621
+ error,
3622
+ className = "",
3623
+ showTrend = true
3624
+ }) {
3625
+ const context = useGraphContext();
3626
+ const graphData = data ?? context.data;
3627
+ const graphLoading = loading ?? context.loading;
3628
+ const graphError = error ?? context.error;
3629
+ const resolvedValue = useMemo(() => {
3630
+ if (value !== void 0) {
3631
+ return value;
3632
+ }
3633
+ const latestPoint = graphData[graphData.length - 1];
3634
+ return latestPoint?.[String(valueKey)] ?? null;
3635
+ }, [graphData, value, valueKey]);
3636
+ const resolvedPreviousValue = useMemo(() => {
3637
+ if (previousValue !== void 0) {
3638
+ return previousValue;
3639
+ }
3640
+ const previousPoint = graphData[graphData.length - 2];
3641
+ const previous = previousPoint?.[String(valueKey)];
3642
+ return typeof previous === "number" ? previous : void 0;
3643
+ }, [graphData, previousValue, valueKey]);
3644
+ const trend = useMemo(() => {
3645
+ if (typeof resolvedValue !== "number" || typeof resolvedPreviousValue !== "number") {
3646
+ return null;
3647
+ }
3648
+ const difference = resolvedValue - resolvedPreviousValue;
3649
+ const percentage = resolvedPreviousValue === 0 ? 0 : difference / Math.abs(resolvedPreviousValue) * 100;
3650
+ return {
3651
+ difference,
3652
+ percentage,
3653
+ direction: difference > 0 ? "up" : difference < 0 ? "down" : "neutral"
3654
+ };
3655
+ }, [resolvedPreviousValue, resolvedValue]);
3656
+ if (graphLoading) {
3657
+ return /* @__PURE__ */ jsx(GraphLoadingState, { height: 120, className });
3658
+ }
3659
+ if (graphError) {
3660
+ return /* @__PURE__ */ jsx(GraphErrorState, { error: graphError, height: 120, className });
3661
+ }
3662
+ if (resolvedValue === null || resolvedValue === void 0) {
3663
+ return /* @__PURE__ */ jsx(GraphEmptyState, { height: 120, className });
3664
+ }
3665
+ return /* @__PURE__ */ jsxs(
3666
+ "div",
3667
+ {
3668
+ className: `eui-graph rounded-xl border border-[#2a2d35] bg-[#111217] p-5 ${className}`,
3669
+ children: [
3670
+ label && /* @__PURE__ */ jsx("div", { className: "text-sm text-gray-400", children: label }),
3671
+ /* @__PURE__ */ jsx("div", { className: "mt-2 text-3xl font-semibold tracking-tight text-gray-100", children: formatGraphValue(resolvedValue, {
3672
+ format,
3673
+ prefix,
3674
+ suffix: suffix ?? unit
3675
+ }) }),
3676
+ showTrend && trend && /* @__PURE__ */ jsxs(
3677
+ "div",
3678
+ {
3679
+ className: `mt-3 text-sm ${trend.direction === "up" ? "text-emerald-400" : trend.direction === "down" ? "text-red-400" : "text-gray-500"}`,
3680
+ children: [
3681
+ trend.direction === "up" ? "\u2191" : trend.direction === "down" ? "\u2193" : "\u2192",
3682
+ " ",
3683
+ formatGraphValue(Math.abs(trend.percentage), {
3684
+ format: "number",
3685
+ suffix: "%",
3686
+ maximumFractionDigits: 2
3687
+ })
3688
+ ]
3689
+ }
3690
+ )
3691
+ ]
3692
+ }
3693
+ );
3694
+ }
3695
+ function renderGraphChart(props) {
3696
+ const {
3697
+ type = "line",
3698
+ data,
3699
+ xKey,
3700
+ series,
3701
+ height,
3702
+ loading,
3703
+ error,
3704
+ chartClassName = "",
3705
+ showGrid = true,
3706
+ showTooltip = true,
3707
+ showLegend = true,
3708
+ animated = true,
3709
+ layout,
3710
+ nameKey,
3711
+ valueKey,
3712
+ innerRadius,
3713
+ outerRadius,
3714
+ valueFormat,
3715
+ value,
3716
+ previousValue,
3717
+ label,
3718
+ min,
3719
+ max,
3720
+ color,
3721
+ unit,
3722
+ format,
3723
+ prefix,
3724
+ suffix,
3725
+ showTrend
3726
+ } = props;
3727
+ switch (type) {
3728
+ case "area":
3729
+ return /* @__PURE__ */ jsx(
3730
+ AreaGraph,
3731
+ {
3732
+ data,
3733
+ xKey,
3734
+ series,
3735
+ height,
3736
+ loading,
3737
+ error,
3738
+ className: chartClassName,
3739
+ showGrid,
3740
+ showTooltip,
3741
+ showLegend,
3742
+ animated
3743
+ }
3744
+ );
3745
+ case "bar":
3746
+ return /* @__PURE__ */ jsx(
3747
+ BarGraph,
3748
+ {
3749
+ data,
3750
+ xKey,
3751
+ series,
3752
+ height,
3753
+ loading,
3754
+ error,
3755
+ className: chartClassName,
3756
+ showGrid,
3757
+ showTooltip,
3758
+ showLegend,
3759
+ animated,
3760
+ layout
3761
+ }
3762
+ );
3763
+ case "pie":
3764
+ return /* @__PURE__ */ jsx(
3765
+ PieGraph,
3766
+ {
3767
+ data,
3768
+ nameKey,
3769
+ valueKey,
3770
+ height,
3771
+ loading,
3772
+ error,
3773
+ className: chartClassName,
3774
+ showTooltip,
3775
+ showLegend,
3776
+ animated,
3777
+ innerRadius,
3778
+ outerRadius,
3779
+ valueFormat,
3780
+ unit
3781
+ }
3782
+ );
3783
+ case "scatter":
3784
+ return /* @__PURE__ */ jsx(
3785
+ ScatterGraph,
3786
+ {
3787
+ data,
3788
+ xKey,
3789
+ series,
3790
+ height,
3791
+ loading,
3792
+ error,
3793
+ className: chartClassName,
3794
+ showGrid,
3795
+ showTooltip,
3796
+ showLegend,
3797
+ animated
3798
+ }
3799
+ );
3800
+ case "gauge":
3801
+ return /* @__PURE__ */ jsx(
3802
+ GaugeGraph,
3803
+ {
3804
+ data,
3805
+ valueKey,
3806
+ value: typeof value === "number" ? value : void 0,
3807
+ label,
3808
+ min,
3809
+ max,
3810
+ height,
3811
+ color,
3812
+ unit,
3813
+ format,
3814
+ loading,
3815
+ error,
3816
+ className: chartClassName
3817
+ }
3818
+ );
3819
+ case "stat":
3820
+ return /* @__PURE__ */ jsx(
3821
+ StatGraph,
3822
+ {
3823
+ data,
3824
+ valueKey,
3825
+ value,
3826
+ previousValue,
3827
+ label,
3828
+ format,
3829
+ prefix,
3830
+ suffix,
3831
+ unit,
3832
+ loading,
3833
+ error,
3834
+ className: chartClassName,
3835
+ showTrend
3836
+ }
3837
+ );
3838
+ case "line":
3839
+ default:
3840
+ return /* @__PURE__ */ jsx(
3841
+ LineGraph,
3842
+ {
3843
+ data,
3844
+ xKey,
3845
+ series,
3846
+ height,
3847
+ loading,
3848
+ error,
3849
+ className: chartClassName,
3850
+ showGrid,
3851
+ showTooltip,
3852
+ showLegend,
3853
+ animated
3854
+ }
3855
+ );
3856
+ }
3857
+ }
3858
+ function GraphContent(props) {
3859
+ const {
3860
+ children,
3861
+ withPanel = true,
3862
+ title,
3863
+ description,
3864
+ actions,
3865
+ toolbar,
3866
+ className = "",
3867
+ contentClassName = "",
3868
+ height,
3869
+ loading,
3870
+ error,
3871
+ showToolbar = false,
3872
+ showRefresh = true,
3873
+ showLastUpdated = true,
3874
+ emptyMessage,
3875
+ emptyDescription,
3876
+ onRetry
3877
+ } = props;
3878
+ const chart = children ?? renderGraphChart(props);
3879
+ if (!withPanel) {
3880
+ return /* @__PURE__ */ jsx(Fragment, { children: chart });
3881
+ }
3882
+ return /* @__PURE__ */ jsx(
3883
+ GraphPanel,
3884
+ {
3885
+ title,
3886
+ description,
3887
+ actions,
3888
+ toolbar,
3889
+ className,
3890
+ contentClassName,
3891
+ height,
3892
+ loading,
3893
+ error,
3894
+ empty: children ? false : void 0,
3895
+ showToolbar,
3896
+ showRefresh,
3897
+ showLastUpdated,
3898
+ emptyMessage,
3899
+ emptyDescription,
3900
+ onRetry,
3901
+ children: chart
3902
+ }
3903
+ );
3904
+ }
3905
+ function Graph(props) {
3906
+ const {
3907
+ data,
3908
+ dataSource,
3909
+ autoLoad = true,
3910
+ maxDataPoints,
3911
+ theme,
3912
+ onDataChange,
3913
+ onError
3914
+ } = props;
3915
+ const shouldUseProvider = Boolean(data || dataSource);
3916
+ const content = /* @__PURE__ */ jsx(GraphContent, { ...props });
3917
+ if (!shouldUseProvider) {
3918
+ return content;
3919
+ }
3920
+ return /* @__PURE__ */ jsx(
3921
+ GraphProvider,
3922
+ {
3923
+ data,
3924
+ dataSource,
3925
+ autoLoad,
3926
+ maxDataPoints,
3927
+ theme,
3928
+ onDataChange,
3929
+ onError,
3930
+ children: content
3931
+ }
3932
+ );
3933
+ }
3934
+
3935
+ // src/components/data-display/graphs-v2/datasource/GraphDataSource.ts
3936
+ var BaseGraphDataSource = class {
3937
+ normalizeError(error) {
3938
+ if (error instanceof Error) {
3939
+ return error;
3940
+ }
3941
+ return new Error(String(error));
3942
+ }
3943
+ ensureArray(data) {
3944
+ if (!data) {
3945
+ return [];
3946
+ }
3947
+ return Array.isArray(data) ? data : [data];
3948
+ }
3949
+ safeExecute(executor) {
3950
+ try {
3951
+ return Promise.resolve(executor());
3952
+ } catch (error) {
3953
+ return Promise.reject(this.normalizeError(error));
3954
+ }
3955
+ }
3956
+ };
3957
+
3958
+ // src/components/data-display/graphs-v2/datasource/StaticGraphDataSource.ts
3959
+ var StaticGraphDataSource = class extends BaseGraphDataSource {
3960
+ constructor(config = {}) {
3961
+ super();
3962
+ this.mode = GRAPH_DATA_MODES.STATIC;
3963
+ this.data = Array.isArray(config) ? config : config.data ?? [];
3964
+ }
3965
+ getInitialData() {
3966
+ return this.data;
3967
+ }
3968
+ refresh() {
3969
+ return this.data;
3970
+ }
3971
+ setData(data) {
3972
+ this.data = data;
3973
+ }
3974
+ appendData(data) {
3975
+ const nextData = this.ensureArray(data);
3976
+ this.data = [...this.data, ...nextData];
3977
+ }
3978
+ clearData() {
3979
+ this.data = [];
3980
+ }
3981
+ };
3982
+
3983
+ // src/components/data-display/graphs-v2/datasource/PollingGraphDataSource.ts
3984
+ var PollingGraphDataSource = class extends BaseGraphDataSource {
3985
+ constructor(config) {
3986
+ super();
3987
+ this.mode = GRAPH_DATA_MODES.POLLING;
3988
+ this.fetcher = config.fetcher;
3989
+ this.interval = config.interval ?? GRAPH_DEFAULT_POLLING_INTERVAL;
3990
+ this.immediate = config.immediate ?? true;
3991
+ }
3992
+ getInitialData() {
3993
+ return this.refresh();
3994
+ }
3995
+ refresh() {
3996
+ return this.safeExecute(async () => {
3997
+ const data = await this.fetcher();
3998
+ return this.ensureArray(data);
3999
+ });
4000
+ }
4001
+ subscribe(onData, onError) {
4002
+ let disposed = false;
4003
+ let fetching = false;
4004
+ let timer;
4005
+ const execute = async () => {
4006
+ if (disposed || fetching) {
4007
+ return;
4008
+ }
4009
+ try {
4010
+ fetching = true;
4011
+ const data = await this.refresh();
4012
+ if (!disposed) {
4013
+ onData(data);
4014
+ }
4015
+ } catch (error) {
4016
+ if (!disposed) {
4017
+ onError?.(this.normalizeError(error));
4018
+ }
4019
+ } finally {
4020
+ fetching = false;
4021
+ }
4022
+ };
4023
+ if (this.immediate) {
4024
+ void execute();
4025
+ }
4026
+ timer = globalThis.setInterval(() => {
4027
+ void execute();
4028
+ }, this.interval);
4029
+ return () => {
4030
+ disposed = true;
4031
+ if (timer) {
4032
+ globalThis.clearInterval(timer);
4033
+ }
4034
+ };
4035
+ }
4036
+ };
4037
+
4038
+ // src/components/data-display/graphs-v2/datasource/RealtimeGraphDataSource.ts
4039
+ var RealtimeGraphDataSource = class extends BaseGraphDataSource {
4040
+ constructor(config) {
4041
+ super();
4042
+ this.mode = GRAPH_DATA_MODES.REALTIME;
4043
+ this.connect = config.connect;
4044
+ this.initialDataLoader = config.getInitialData;
4045
+ this.refreshHandler = config.refresh;
4046
+ }
4047
+ getInitialData() {
4048
+ if (!this.initialDataLoader) {
4049
+ return [];
4050
+ }
4051
+ return this.safeExecute(async () => {
4052
+ const data = await this.initialDataLoader?.();
4053
+ return this.ensureArray(data);
4054
+ });
4055
+ }
4056
+ refresh() {
4057
+ if (!this.refreshHandler) {
4058
+ return this.getInitialData();
4059
+ }
4060
+ return this.safeExecute(async () => {
4061
+ const data = await this.refreshHandler?.();
4062
+ return this.ensureArray(data);
4063
+ });
4064
+ }
4065
+ subscribe(onData, onError) {
4066
+ try {
4067
+ return this.connect(
4068
+ (data) => {
4069
+ onData(this.ensureArray(data));
4070
+ },
4071
+ (error) => {
4072
+ onError?.(this.normalizeError(error));
4073
+ }
4074
+ );
4075
+ } catch (error) {
4076
+ onError?.(this.normalizeError(error));
4077
+ return () => {
4078
+ };
4079
+ }
4080
+ }
1574
4081
  };
1575
4082
  var CloudinaryContext = createContext(null);
1576
4083
  var CloudinaryProvider = ({
@@ -2033,7 +4540,7 @@ var ListItem = ({
2033
4540
  children: bullet
2034
4541
  }
2035
4542
  ),
2036
- /* @__PURE__ */ jsx("div", { className: "flex-1 min-w-0", children: TypographyComponent ? React4.cloneElement(
4543
+ /* @__PURE__ */ jsx("div", { className: "flex-1 min-w-0", children: TypographyComponent ? React3.cloneElement(
2037
4544
  TypographyComponent,
2038
4545
  {
2039
4546
  className: cn(
@@ -2067,7 +4574,7 @@ function normalizeItem(item, defaultBulletType) {
2067
4574
  bulletType: defaultBulletType
2068
4575
  };
2069
4576
  }
2070
- if (React4.isValidElement(item)) {
4577
+ if (React3.isValidElement(item)) {
2071
4578
  return {
2072
4579
  content: item,
2073
4580
  bulletType: defaultBulletType
@@ -2624,7 +5131,7 @@ function Tag({ text, className, ...rest }) {
2624
5131
  );
2625
5132
  }
2626
5133
  var Tag_default = Tag;
2627
- function Tooltip4({
5134
+ function Tooltip9({
2628
5135
  children,
2629
5136
  show,
2630
5137
  offsetX = 20,
@@ -14526,7 +17033,7 @@ function WorldMap({
14526
17033
  ]
14527
17034
  }
14528
17035
  ) }),
14529
- /* @__PURE__ */ jsx(Tooltip4, { show: showTooltip, children: tooltipContent })
17036
+ /* @__PURE__ */ jsx(Tooltip9, { show: showTooltip, children: tooltipContent })
14530
17037
  ] });
14531
17038
  }
14532
17039
  var sizes4 = {
@@ -16326,7 +18833,7 @@ var Breadcrumb = ({
16326
18833
  navigate(item.href);
16327
18834
  }
16328
18835
  };
16329
- return /* @__PURE__ */ jsxs(React4.Fragment, { children: [
18836
+ return /* @__PURE__ */ jsxs(React3.Fragment, { children: [
16330
18837
  /* @__PURE__ */ jsx(
16331
18838
  BreadcrumbItem_default,
16332
18839
  {
@@ -19100,6 +21607,6 @@ function ScrollToTop({
19100
21607
  }
19101
21608
  var ScrollToTop_default = ScrollToTop;
19102
21609
 
19103
- export { Accordion_default as Accordion, AsyncComponentWrapper_default as AsyncComponentWrapper, Avatar, Backdrop_default as Backdrop, Badge, BarChart_default as BarChart, Block_default as Block, BlockGroup_default as BlockGroup, BoxNav_default as BoxNav, BoxNavItem_default as BoxNavItem, Brand_default as Brand, Breadcrumb, BreadcrumbItem_default as BreadcrumbItem, Button_default as Button, Caption, Card_default as Card, CardContent_default as CardContent, CardFooter_default as CardFooter, CardHeader_default as CardHeader, Chapter, Checkbox_default as Checkbox, Chip, CloudinaryImage_default as CloudinaryImage, CloudinaryProvider, CloudinaryVideo_default as CloudinaryVideo, Code, CommentThread_default as CommentThread, Content, ContentArea_default as ContentArea, DataView, DataViewTable_default as DataViewTable, DateSelector_default as DateSelector, DefaultLayout_default as DefaultLayout, Display, DocumentationPanel_default as DocumentationPanel, Drawer, DrawerToggler_default as DrawerToggler, EUIDevLayout_default as EUIDevLayout, EUIProvider, Flag, Flex, FlexCol_default as FlexCol, FlexRow_default as FlexRow, Footer, FooterNav_default as FooterNav, FooterNavGroup_default as FooterNavGroup, FooterNavItem, FooterNavItemContext, FooterNavItemTitle, Form, FormResponse_default as FormResponse, GenericLayout_default as GenericLayout, GlowWrapper_default as GlowWrapper, Graph, GraphEdge, GraphNode, GraphRenderer, Grid_default as Grid, Header, HeaderNav_default as HeaderNav, HeaderNavGroup_default as HeaderNavGroup, HeaderNavItem, HeaderNavItemContext, HeaderNavItemTitle, HomeLayout_default as HomeLayout, Image2 as Image, ImageInput_default as ImageInput, InfiniteScrollTrigger_default as InfiniteScrollTrigger, Info_default as Info, Input, InputFile, InputLabel_default as InputLabel, InputList, InputListGroup, InputResponse_default as InputResponse, Label, Layout, Lead, LineChart_default as LineChart, Link, List_default as List, ListItem_default as ListItem, MarkdownEditor_default as MarkdownEditor, MarkdownProvider_default as MarkdownProvider, MarkdownTOC_default as MarkdownTOC, MarkdownViewer_default as MarkdownViewer, Menu, MenuGroup, MenuItem, MenuItemTitle, Modal_default as Modal, MotionSurface_default as MotionSurface, MultiImageInput_default as MultiImageInput, NumericRating_default as NumericRating, Overline, Paragraph, PieChart_default as PieChart, PriceTag, ProgressBar, ProgressBarRating_default as ProgressBarRating, Quote, Radio_default as Radio, RouteTab_default as RouteTab, RouteTabs_default as RouteTabs, ScrollToTop_default as ScrollToTop, Section, Select_default as Select, ShapeSwitch, ShowMore_default as ShowMore, Sidebar_default as Sidebar, SidebarLayout_default as SidebarLayout, SidemenuLayout_default as SidemenuLayout, Skeleton, Slider_default as Slider, StarRating_default as StarRating, StarRatingDistribution_default as StarRatingDistribution, StarRatingInput_default as StarRatingInput, Switch_default as Switch, TNDropdown, TNDropdownItem, TNDropdownTitle, TNGroup, Table_default as Table, Tag_default as Tag, Tags_default as Tags, TextArea_default as TextArea, ThemeContext, ThemeProvider, ThemeSwitch, TitleBanner, Toast, Tooltip4 as Tooltip, TopNav, Transition4 as Transition, TransitionDropdown_default as TransitionDropdown, TransitionFadeIn_default as TransitionFadeIn, Typography, UnderConstructionBanner, ValueBadge_default as ValueBadge, WorldMap, WorldMapCountryTable, YoutubeVideo_default as YoutubeVideoPlayer, addReplyToCache, applyReactionState, cn, createForceLayout, createGridLayout, createTreeLayout, decrementReplyCount, enumValues, formatCommentDate, getCurrencySymbol, getLayout, getOptimisticDislikeState, getOptimisticLikeState, incrementReplyCount, isMatch, isRenderFn, normalize, registerLayout, removeComment, removeCommentTreeFromCache, resolveAppearanceStyles, resolveWithGlobal, sendToast, updateComment, updateReplyCacheComment, useClickOutside, useCloudinaryConfig, useCurrentTheme_default as useCurrentTheme, useDrawer_default as useDrawer, useEUIConfig, useIsMobile_default as useIsMobile, useModal_default as useModal, useTheme_default as useTheme };
21610
+ export { Accordion_default as Accordion, AreaGraph, AsyncComponentWrapper_default as AsyncComponentWrapper, Avatar, Backdrop_default as Backdrop, Badge, BarChart_default as BarChart, BarGraph, BaseGraphDataSource, Block_default as Block, BlockGroup_default as BlockGroup, BoxNav_default as BoxNav, BoxNavItem_default as BoxNavItem, Brand_default as Brand, Breadcrumb, BreadcrumbItem_default as BreadcrumbItem, Button_default as Button, Caption, Card_default as Card, CardContent_default as CardContent, CardFooter_default as CardFooter, CardHeader_default as CardHeader, Chapter, Checkbox_default as Checkbox, Chip, CloudinaryImage_default as CloudinaryImage, CloudinaryProvider, CloudinaryVideo_default as CloudinaryVideo, Code, CommentThread_default as CommentThread, Configurator, ConfiguratorError, Content, ContentArea_default as ContentArea, DEFAULT_GRAPH_THEME, DataView, DataViewTable_default as DataViewTable, DateSelector_default as DateSelector, DefaultLayout_default as DefaultLayout, Display, DocumentationPanel_default as DocumentationPanel, Drawer, DrawerToggler_default as DrawerToggler, EUIDevLayout_default as EUIDevLayout, EUIProvider, Flag, Flex, FlexCol_default as FlexCol, FlexRow_default as FlexRow, Footer, FooterNav_default as FooterNav, FooterNavGroup_default as FooterNavGroup, FooterNavItem, FooterNavItemContext, FooterNavItemTitle, Form, FormResponse_default as FormResponse, GRAPH_COLOR_PALETTE, GRAPH_DARK_THEME, GRAPH_DATA_MODES, GRAPH_DEFAULT_ACTIVE_DOT_RADIUS, GRAPH_DEFAULT_ANIMATION_DURATION, GRAPH_DEFAULT_BAR_RADIUS, GRAPH_DEFAULT_DOT_RADIUS, GRAPH_DEFAULT_HEIGHT, GRAPH_DEFAULT_MARGIN, GRAPH_DEFAULT_MAX_REALTIME_POINTS, GRAPH_DEFAULT_POLLING_INTERVAL, GRAPH_DEFAULT_STROKE_WIDTH, GRAPH_EMPTY_MESSAGE, GRAPH_ERROR_MESSAGE, GRAPH_LIGHT_THEME, GRAPH_LOADING_MESSAGE, GRAPH_STATUSES, GRAPH_STATUS_COLORS, GRAPH_VALUE_FORMATS, GaugeGraph, GenericLayout_default as GenericLayout, GlowWrapper_default as GlowWrapper, Graph, GraphContainer, GraphContext, GraphEmptyState, GraphErrorState, GraphHeader, GraphLegend, GraphLoadingState, GraphPanel, GraphProvider, GraphToolbar, GraphTooltip, Grid_default as Grid, Header, HeaderNav_default as HeaderNav, HeaderNavGroup_default as HeaderNavGroup, HeaderNavItem, HeaderNavItemContext, HeaderNavItemTitle, HomeLayout_default as HomeLayout, Image2 as Image, ImageInput_default as ImageInput, InfiniteScrollTrigger_default as InfiniteScrollTrigger, Info_default as Info, Input, InputFile, InputLabel_default as InputLabel, InputList, InputListGroup, InputResponse_default as InputResponse, Label, Layout, Lead, LineChart_default as LineChart, LineGraph, Link, List_default as List, ListItem_default as ListItem, MarkdownEditor_default as MarkdownEditor, MarkdownProvider_default as MarkdownProvider, MarkdownTOC_default as MarkdownTOC, MarkdownViewer_default as MarkdownViewer, Menu, MenuGroup, MenuItem, MenuItemTitle, Modal_default as Modal, MotionSurface_default as MotionSurface, MultiImageInput_default as MultiImageInput, NumericRating_default as NumericRating, Overline, Paragraph, PieChart_default as PieChart, PieGraph, PollingGraphDataSource, PriceTag, ProgressBar, ProgressBarRating_default as ProgressBarRating, Quote, Radio_default as Radio, RealtimeGraphDataSource, RouteTab_default as RouteTab, RouteTabs_default as RouteTabs, ScatterGraph, ScrollToTop_default as ScrollToTop, Section, Select_default as Select, ShapeSwitch, ShowMore_default as ShowMore, Sidebar_default as Sidebar, SidebarLayout_default as SidebarLayout, SidemenuLayout_default as SidemenuLayout, Skeleton, Slider_default as Slider, StarRating_default as StarRating, StarRatingDistribution_default as StarRatingDistribution, StarRatingInput_default as StarRatingInput, StatGraph, StaticGraphDataSource, Switch_default as Switch, TNDropdown, TNDropdownItem, TNDropdownTitle, TNGroup, Table_default as Table, Tag_default as Tag, Tags_default as Tags, TextArea_default as TextArea, ThemeContext, ThemeProvider, ThemeSwitch, TitleBanner, Toast, Tooltip9 as Tooltip, TopNav, Transition4 as Transition, TransitionDropdown_default as TransitionDropdown, TransitionFadeIn_default as TransitionFadeIn, Typography, UnderConstructionBanner, ValueBadge_default as ValueBadge, WorldMap, WorldMapCountryTable, YoutubeVideo_default as YoutubeVideoPlayer, addReplyToCache, applyReactionState, assertAbsoluteURL, buildURL, cn, createConfigurator, createInitialGraphState, createURLResolver, decrementReplyCount, enumValues, formatCommentDate, formatConfigError, formatGraphValue, getAllowedOrigins, getBrowserHref, getBrowserOrigin, getBrowserRedirectURL, getCurrencySymbol, getOptimisticDislikeState, getOptimisticLikeState, getSafeRedirect, graphReducer, incrementReplyCount, isMatch, isRenderFn, limitRealtimePoints, normalize, normalizeGraphData, normalizeGraphDataPoint, parseJson, parseJsonRecord, parseUrlMap, removeComment, removeCommentTreeFromCache, replaceRealtimePoints, resolveAppearanceStyles, resolveGraphColor, resolveGraphColors, resolveWithGlobal, sendToast, toConfiguratorError, updateComment, updateReplyCacheComment, useClickOutside, useCloudinaryConfig, useCurrentTheme_default as useCurrentTheme, useDrawer_default as useDrawer, useEUIConfig, useGraphContext, useGraphData, useGraphPolling, useGraphRealtime, useGraphSeries, useGraphTheme, useIsMobile_default as useIsMobile, useModal_default as useModal, useTheme_default as useTheme };
19104
21611
  //# sourceMappingURL=index.mjs.map
19105
21612
  //# sourceMappingURL=index.mjs.map