@copilotz/admin 0.9.24 → 0.9.27

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.js CHANGED
@@ -256,6 +256,22 @@ async function fetchAdminAgents(search, namespace, options) {
256
256
  limit: "8"
257
257
  }, options);
258
258
  }
259
+ async function fetchAdminUsage(filters, options) {
260
+ return await fetchAdminJson("/v1/admin/usage", {
261
+ from: filters.from,
262
+ to: filters.to,
263
+ interval: filters.interval,
264
+ metric: filters.metric,
265
+ groupBy: filters.groupBy,
266
+ attribution: filters.attribution,
267
+ threadId: filters.threadId,
268
+ participantId: filters.participantId,
269
+ participantType: filters.participantType,
270
+ namespace: filters.namespace,
271
+ provider: filters.provider,
272
+ model: filters.model
273
+ }, options);
274
+ }
259
275
  async function fetchThreadDetail(threadId, options) {
260
276
  return await fetchAdminJson(
261
277
  `/v1/threads/${encodeURIComponent(threadId)}`,
@@ -520,6 +536,16 @@ function CardHeader({ className, ...props }) {
520
536
  }
521
537
  );
522
538
  }
539
+ function CardTitle({ className, ...props }) {
540
+ return /* @__PURE__ */ jsx(
541
+ "div",
542
+ {
543
+ "data-slot": "card-title",
544
+ className: cn("leading-none font-semibold", className),
545
+ ...props
546
+ }
547
+ );
548
+ }
523
549
  function CardContent({ className, ...props }) {
524
550
  return /* @__PURE__ */ jsx(
525
551
  "div",
@@ -1513,7 +1539,26 @@ var AdminHeader = ({
1513
1539
  };
1514
1540
 
1515
1541
  // src/components/views/DashboardView.tsx
1516
- import React5 from "react";
1542
+ import React6 from "react";
1543
+ import {
1544
+ Bar,
1545
+ BarChart,
1546
+ CartesianGrid,
1547
+ Legend,
1548
+ Tooltip as Tooltip2,
1549
+ XAxis,
1550
+ YAxis
1551
+ } from "recharts";
1552
+ import {
1553
+ Activity as Activity2,
1554
+ Database as Database2,
1555
+ Filter,
1556
+ RefreshCw as RefreshCw2,
1557
+ Search,
1558
+ Sparkles,
1559
+ Users as Users2,
1560
+ Wallet
1561
+ } from "lucide-react";
1517
1562
 
1518
1563
  // src/components/ui/badge.tsx
1519
1564
  import { Slot as Slot3 } from "@radix-ui/react-slot";
@@ -1552,8 +1597,124 @@ function Badge({
1552
1597
  );
1553
1598
  }
1554
1599
 
1555
- // src/components/views/DashboardView.tsx
1600
+ // src/components/ui/chart.tsx
1601
+ import * as React5 from "react";
1602
+ import * as RechartsPrimitive from "recharts";
1556
1603
  import { jsx as jsx12, jsxs as jsxs7 } from "react/jsx-runtime";
1604
+ var ChartContext = React5.createContext(null);
1605
+ function useChart() {
1606
+ const context = React5.useContext(ChartContext);
1607
+ if (!context) {
1608
+ throw new Error("useChart must be used within a ChartContainer");
1609
+ }
1610
+ return context;
1611
+ }
1612
+ function ChartContainer({
1613
+ id,
1614
+ className,
1615
+ config,
1616
+ children,
1617
+ ...props
1618
+ }) {
1619
+ const uniqueId = React5.useId();
1620
+ const chartId = `chart-${id ?? uniqueId.replace(/:/g, "")}`;
1621
+ return /* @__PURE__ */ jsx12(ChartContext.Provider, { value: config, children: /* @__PURE__ */ jsxs7(
1622
+ "div",
1623
+ {
1624
+ "data-chart": chartId,
1625
+ className: cn(
1626
+ "flex aspect-auto justify-center text-xs text-muted-foreground [&_.recharts-cartesian-axis-tick_text]:fill-muted-foreground [&_.recharts-cartesian-grid_line[stroke='#ccc']]:stroke-border/70 [&_.recharts-cursor]:fill-muted [&_.recharts-legend-wrapper]:text-muted-foreground [&_.recharts-tooltip-cursor]:fill-muted",
1627
+ className
1628
+ ),
1629
+ ...props,
1630
+ children: [
1631
+ /* @__PURE__ */ jsx12("style", { children: Object.entries(config).map(([key, item]) => {
1632
+ return `[data-chart=${chartId}] { --color-${key}: ${item.color}; }`;
1633
+ }).join("\n") }),
1634
+ /* @__PURE__ */ jsx12(RechartsPrimitive.ResponsiveContainer, { children })
1635
+ ]
1636
+ }
1637
+ ) });
1638
+ }
1639
+ function ChartTooltipContent({
1640
+ active,
1641
+ payload,
1642
+ label,
1643
+ className,
1644
+ formatter,
1645
+ labelFormatter
1646
+ }) {
1647
+ const config = useChart();
1648
+ if (!active || !payload?.length) return null;
1649
+ const total = payload.reduce((sum, item) => {
1650
+ const value = typeof item.value === "number" ? item.value : Number(item.value ?? 0);
1651
+ return sum + (Number.isFinite(value) ? value : 0);
1652
+ }, 0);
1653
+ return /* @__PURE__ */ jsxs7(
1654
+ "div",
1655
+ {
1656
+ className: cn(
1657
+ "min-w-44 rounded-lg border bg-popover px-3 py-2 text-popover-foreground shadow-md",
1658
+ className
1659
+ ),
1660
+ children: [
1661
+ /* @__PURE__ */ jsxs7("div", { className: "mb-2 flex items-center justify-between gap-4 border-b pb-2", children: [
1662
+ /* @__PURE__ */ jsx12("p", { className: "text-xs font-medium text-muted-foreground", children: labelFormatter ? labelFormatter(label) : label }),
1663
+ /* @__PURE__ */ jsx12("p", { className: "text-xs font-semibold text-foreground", children: formatter ? formatter(total) : total })
1664
+ ] }),
1665
+ /* @__PURE__ */ jsx12("div", { className: "space-y-1.5", children: payload.filter((item) => Number(item.value ?? 0) > 0).map((item) => {
1666
+ const key = String(item.dataKey ?? item.name ?? "");
1667
+ const itemConfig = config[key];
1668
+ const color = item.color ?? itemConfig?.color ?? "currentColor";
1669
+ return /* @__PURE__ */ jsxs7(
1670
+ "div",
1671
+ {
1672
+ className: "grid grid-cols-[0.6rem_1fr_auto] items-center gap-2",
1673
+ children: [
1674
+ /* @__PURE__ */ jsx12(
1675
+ "span",
1676
+ {
1677
+ className: "size-2 rounded-[2px]",
1678
+ style: { backgroundColor: color }
1679
+ }
1680
+ ),
1681
+ /* @__PURE__ */ jsx12("span", { className: "max-w-48 truncate text-muted-foreground", children: itemConfig?.label ?? item.name ?? key }),
1682
+ /* @__PURE__ */ jsx12("span", { className: "font-medium text-foreground", children: formatter ? formatter(item.value ?? 0) : item.value })
1683
+ ]
1684
+ },
1685
+ key
1686
+ );
1687
+ }) })
1688
+ ]
1689
+ }
1690
+ );
1691
+ }
1692
+ function ChartLegendContent({
1693
+ payload,
1694
+ className
1695
+ }) {
1696
+ const config = useChart();
1697
+ if (!payload?.length) return null;
1698
+ return /* @__PURE__ */ jsx12("div", { className: cn("flex flex-wrap items-center gap-x-4 gap-y-2", className), children: payload.map((item) => {
1699
+ const key = String(item.dataKey ?? item.value ?? "");
1700
+ const itemConfig = config[key];
1701
+ return /* @__PURE__ */ jsxs7("div", { className: "flex items-center gap-2", children: [
1702
+ /* @__PURE__ */ jsx12(
1703
+ "span",
1704
+ {
1705
+ className: "size-2 rounded-[2px]",
1706
+ style: {
1707
+ backgroundColor: item.color ?? itemConfig?.color ?? "currentColor"
1708
+ }
1709
+ }
1710
+ ),
1711
+ /* @__PURE__ */ jsx12("span", { className: "max-w-52 truncate text-xs text-muted-foreground", children: itemConfig?.label ?? item.value ?? key })
1712
+ ] }, key);
1713
+ }) });
1714
+ }
1715
+
1716
+ // src/components/views/DashboardView.tsx
1717
+ import { Fragment as Fragment3, jsx as jsx13, jsxs as jsxs8 } from "react/jsx-runtime";
1557
1718
  var DashboardView = ({
1558
1719
  config,
1559
1720
  overview,
@@ -1568,423 +1729,650 @@ var DashboardView = ({
1568
1729
  onThreadSearchChange,
1569
1730
  onParticipantSearchChange,
1570
1731
  onAgentSearchChange,
1571
- onThreadClick
1732
+ onThreadClick,
1733
+ namespace
1572
1734
  }) => {
1573
- const [usageMetricKind, setUsageMetricKind] = React5.useState(
1574
- "tokens"
1735
+ void overview;
1736
+ void activity;
1737
+ void threads;
1738
+ void participants;
1739
+ void agents;
1740
+ void interval;
1741
+ void threadSearch;
1742
+ void participantSearch;
1743
+ void agentSearch;
1744
+ void onThreadSearchChange;
1745
+ void onParticipantSearchChange;
1746
+ void onAgentSearchChange;
1747
+ void onThreadClick;
1748
+ if (!config.features.showOverview) {
1749
+ return /* @__PURE__ */ jsx13(
1750
+ EmptyDashboard,
1751
+ {
1752
+ description: config.labels.emptyDescription,
1753
+ title: config.labels.emptyTitle
1754
+ }
1755
+ );
1756
+ }
1757
+ return /* @__PURE__ */ jsx13(
1758
+ UsageDashboard,
1759
+ {
1760
+ config,
1761
+ namespace
1762
+ }
1575
1763
  );
1576
- const [usageDimension, setUsageDimension] = React5.useState(
1577
- "total"
1764
+ };
1765
+ function UsageDashboard({
1766
+ config,
1767
+ namespace
1768
+ }) {
1769
+ const [period, setPeriod] = React6.useState("7d");
1770
+ const [bucket, setBucket] = React6.useState("day");
1771
+ const [metricKind, setMetricKind] = React6.useState(
1772
+ "cost"
1578
1773
  );
1579
- const llmSummaryValue = overview ? getOverviewUsageValue(overview, usageMetricKind, usageDimension) : 0;
1580
- const llmSummaryLabel = getUsageSummaryLabel(
1581
- config.labels,
1582
- usageMetricKind,
1583
- usageDimension
1774
+ const [dimension, setDimension] = React6.useState("total");
1775
+ const [groupBy, setGroupBy] = React6.useState(
1776
+ "participant"
1584
1777
  );
1585
- const usageBreakdownCards = USAGE_DIMENSIONS.map((dimension) => ({
1586
- dimension,
1587
- label: getUsageDimensionLabel(config.labels, dimension),
1588
- value: overview ? getOverviewUsageValue(overview, usageMetricKind, dimension) : 0
1589
- }));
1590
- const cards = [
1591
- {
1592
- label: config.labels.messagesCard,
1593
- value: overview?.messageTotals.total ?? 0,
1594
- detail: `${overview?.messageTotals.toolCallMessages ?? 0} tool-call messages`
1595
- },
1596
- {
1597
- label: config.labels.activeThreadsCard,
1598
- value: overview?.threadTotals.active ?? 0,
1599
- detail: `${overview?.threadTotals.total ?? 0} total threads`
1600
- },
1601
- {
1602
- label: config.labels.participantsCard,
1603
- value: overview?.participantTotals.total ?? 0,
1604
- detail: `${overview?.participantTotals.agents ?? 0} agents`
1605
- },
1606
- {
1607
- label: llmSummaryLabel,
1608
- value: llmSummaryValue,
1609
- detail: `${overview?.llmTotals.totalCalls ?? 0} ${config.labels.usageCallsDetail}`,
1610
- metricKind: usageMetricKind
1611
- },
1612
- {
1613
- label: config.labels.queueCard,
1614
- value: overview?.queueTotals.pending ?? 0,
1615
- detail: `${overview?.queueTotals.failed ?? 0} failed`
1778
+ const [attribution, setAttribution] = React6.useState(
1779
+ "initiatedBy"
1780
+ );
1781
+ const [participantType, setParticipantType] = React6.useState("all");
1782
+ const [threadId, setThreadId] = React6.useState("");
1783
+ const [participantId, setParticipantId] = React6.useState("");
1784
+ const [provider, setProvider] = React6.useState("");
1785
+ const [model, setModel] = React6.useState("");
1786
+ const [customFrom, setCustomFrom] = React6.useState("");
1787
+ const [customTo, setCustomTo] = React6.useState("");
1788
+ const [usage, setUsage] = React6.useState(null);
1789
+ const [isLoading, setIsLoading] = React6.useState(false);
1790
+ const [error, setError] = React6.useState(null);
1791
+ const range = React6.useMemo(() => getUsageRange(period, customFrom, customTo), [
1792
+ customFrom,
1793
+ customTo,
1794
+ period
1795
+ ]);
1796
+ const loadUsage = React6.useCallback(async () => {
1797
+ setIsLoading(true);
1798
+ setError(null);
1799
+ try {
1800
+ const next = await fetchAdminUsage({
1801
+ from: range.from,
1802
+ to: range.to,
1803
+ interval: bucket,
1804
+ metric: metricKind,
1805
+ groupBy,
1806
+ attribution,
1807
+ namespace: namespace || void 0,
1808
+ participantType,
1809
+ threadId: emptyToUndefined(threadId),
1810
+ participantId: emptyToUndefined(participantId),
1811
+ provider: emptyToUndefined(provider),
1812
+ model: emptyToUndefined(model)
1813
+ }, {
1814
+ baseUrl: config.baseUrl,
1815
+ getRequestHeaders: config.getRequestHeaders
1816
+ });
1817
+ setUsage(next);
1818
+ } catch (err) {
1819
+ setError(err instanceof Error ? err.message : "Failed to load usage");
1820
+ setUsage(null);
1821
+ } finally {
1822
+ setIsLoading(false);
1616
1823
  }
1617
- ];
1618
- const isEmpty = cards.every((card) => card.value === 0) && activity.length === 0 && threads.length === 0 && participants.length === 0 && agents.length === 0;
1619
- return /* @__PURE__ */ jsxs7("div", { className: "space-y-6", children: [
1620
- isEmpty && /* @__PURE__ */ jsxs7("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
1621
- /* @__PURE__ */ jsx12("h3", { className: "text-lg font-semibold", children: config.labels.emptyTitle }),
1622
- /* @__PURE__ */ jsx12("p", { className: "mt-2 text-sm text-muted-foreground", children: config.labels.emptyDescription })
1623
- ] }),
1624
- config.features.showOverview && /* @__PURE__ */ jsxs7("section", { className: "space-y-4", children: [
1625
- /* @__PURE__ */ jsx12(SectionHeading, { title: config.labels.overviewTitle }),
1626
- /* @__PURE__ */ jsx12("div", { className: "grid grid-cols-2 gap-4 md:grid-cols-3 lg:grid-cols-5", children: cards.map((card) => /* @__PURE__ */ jsxs7(
1627
- "div",
1824
+ }, [
1825
+ attribution,
1826
+ bucket,
1827
+ config.baseUrl,
1828
+ config.getRequestHeaders,
1829
+ groupBy,
1830
+ metricKind,
1831
+ model,
1832
+ namespace,
1833
+ participantId,
1834
+ participantType,
1835
+ provider,
1836
+ range.from,
1837
+ range.to,
1838
+ threadId
1839
+ ]);
1840
+ React6.useEffect(() => {
1841
+ void loadUsage();
1842
+ }, [loadUsage]);
1843
+ const points = usage?.points ?? [];
1844
+ const totals = usage?.totals ?? EMPTY_TOTALS;
1845
+ const chartState = React6.useMemo(() => buildChartState(points, metricKind, dimension, bucket), [
1846
+ bucket,
1847
+ dimension,
1848
+ metricKind,
1849
+ points
1850
+ ]);
1851
+ const groupedRows = React6.useMemo(() => aggregateUsageRows(points, metricKind, dimension), [
1852
+ dimension,
1853
+ metricKind,
1854
+ points
1855
+ ]);
1856
+ const activeFilterCount = [
1857
+ participantType !== "all" ? participantType : "",
1858
+ threadId,
1859
+ participantId,
1860
+ provider,
1861
+ model,
1862
+ period === "custom" ? customFrom : "",
1863
+ period === "custom" ? customTo : ""
1864
+ ].filter((value) => value.trim().length > 0).length;
1865
+ return /* @__PURE__ */ jsxs8("div", { className: "space-y-4", children: [
1866
+ /* @__PURE__ */ jsxs8("div", { className: "flex flex-col gap-3 lg:flex-row lg:items-start lg:justify-between", children: [
1867
+ /* @__PURE__ */ jsxs8("div", { children: [
1868
+ /* @__PURE__ */ jsx13("h2", { className: "text-2xl font-semibold tracking-tight", children: config.labels.llmUsageTitle }),
1869
+ /* @__PURE__ */ jsxs8("div", { className: "mt-2 flex flex-wrap items-center gap-2", children: [
1870
+ /* @__PURE__ */ jsx13(Badge, { variant: "outline", children: formatUsageRangeLabel(period, range) }),
1871
+ /* @__PURE__ */ jsx13(Badge, { variant: "secondary", children: getGroupByLabel(groupBy) }),
1872
+ groupBy === "participant" && /* @__PURE__ */ jsx13(Badge, { variant: "outline", children: attribution === "initiatedBy" ? "Initiated by sender" : "Generated by caller" })
1873
+ ] })
1874
+ ] }),
1875
+ /* @__PURE__ */ jsxs8(
1876
+ Button,
1628
1877
  {
1629
- className: "rounded-xl border bg-card p-5 shadow-sm",
1878
+ className: "w-full sm:w-auto",
1879
+ disabled: isLoading,
1880
+ onClick: () => void loadUsage(),
1881
+ size: "sm",
1882
+ variant: "outline",
1630
1883
  children: [
1631
- /* @__PURE__ */ jsx12("p", { className: "text-sm font-medium text-muted-foreground", children: card.label }),
1632
- /* @__PURE__ */ jsx12("p", { className: "mt-3 text-3xl font-semibold tracking-tight", children: formatMetricValue(
1633
- card.value,
1634
- card.metricKind ?? "tokens"
1635
- ) }),
1636
- /* @__PURE__ */ jsx12("p", { className: "mt-2 text-xs text-muted-foreground", children: card.detail })
1884
+ /* @__PURE__ */ jsx13(RefreshCw2, { className: cn("size-4", isLoading && "animate-spin") }),
1885
+ config.labels.refresh
1637
1886
  ]
1638
- },
1639
- card.label
1640
- )) })
1887
+ }
1888
+ )
1641
1889
  ] }),
1642
- config.features.showOverview && /* @__PURE__ */ jsxs7("section", { className: "space-y-4", children: [
1643
- /* @__PURE__ */ jsxs7("div", { className: "flex flex-col gap-3 sm:flex-row sm:items-end sm:justify-between", children: [
1644
- /* @__PURE__ */ jsx12(SectionHeading, { title: config.labels.llmUsageTitle }),
1645
- /* @__PURE__ */ jsxs7("div", { className: "grid gap-3 sm:grid-cols-2", children: [
1646
- /* @__PURE__ */ jsxs7("div", { className: "space-y-1", children: [
1647
- /* @__PURE__ */ jsx12("p", { className: "text-xs font-medium uppercase tracking-[0.18em] text-muted-foreground", children: config.labels.usageMetricLabel }),
1648
- /* @__PURE__ */ jsxs7(
1649
- Select,
1890
+ /* @__PURE__ */ jsx13(
1891
+ UsageSummary,
1892
+ {
1893
+ dimension,
1894
+ labels: config.labels,
1895
+ metricKind,
1896
+ totals
1897
+ }
1898
+ ),
1899
+ /* @__PURE__ */ jsx13(Card, { className: "gap-4 overflow-hidden py-4", children: /* @__PURE__ */ jsxs8(CardContent, { className: "space-y-4 px-4 lg:px-5", children: [
1900
+ /* @__PURE__ */ jsxs8("div", { className: "grid gap-2 md:grid-cols-2 xl:grid-cols-6", children: [
1901
+ /* @__PURE__ */ jsx13(
1902
+ UsageSelect,
1903
+ {
1904
+ label: "Period",
1905
+ onValueChange: (value) => setPeriod(value),
1906
+ options: [
1907
+ ["24h", config.labels.range24h],
1908
+ ["7d", config.labels.range7d],
1909
+ ["30d", config.labels.range30d],
1910
+ ["custom", "Custom"]
1911
+ ],
1912
+ value: period
1913
+ }
1914
+ ),
1915
+ /* @__PURE__ */ jsx13(
1916
+ UsageSelect,
1917
+ {
1918
+ label: "Bucket",
1919
+ onValueChange: (value) => setBucket(value),
1920
+ options: [
1921
+ ["minute", "Minute"],
1922
+ ["hour", "Hour"],
1923
+ ["day", "Day"],
1924
+ ["week", "Week"],
1925
+ ["month", "Month"]
1926
+ ],
1927
+ value: bucket
1928
+ }
1929
+ ),
1930
+ /* @__PURE__ */ jsx13(
1931
+ UsageSelect,
1932
+ {
1933
+ label: config.labels.usageMetricLabel,
1934
+ onValueChange: (value) => setMetricKind(value),
1935
+ options: [
1936
+ ["cost", config.labels.usageMetricCost],
1937
+ ["tokens", config.labels.usageMetricTokens],
1938
+ ["calls", "Calls"]
1939
+ ],
1940
+ value: metricKind
1941
+ }
1942
+ ),
1943
+ /* @__PURE__ */ jsx13(
1944
+ UsageSelect,
1945
+ {
1946
+ label: "Group",
1947
+ onValueChange: (value) => setGroupBy(value),
1948
+ options: [
1949
+ ["participant", "Participant"],
1950
+ ["thread", "Thread"],
1951
+ ["namespace", "Namespace"],
1952
+ ["provider", "Provider"],
1953
+ ["model", "Model"]
1954
+ ],
1955
+ value: groupBy
1956
+ }
1957
+ ),
1958
+ /* @__PURE__ */ jsx13(
1959
+ UsageSelect,
1960
+ {
1961
+ label: "Attribution",
1962
+ onValueChange: (value) => setAttribution(value),
1963
+ options: [
1964
+ ["initiatedBy", "Initiated by"],
1965
+ ["generatedBy", "Generated by"]
1966
+ ],
1967
+ value: attribution
1968
+ }
1969
+ ),
1970
+ /* @__PURE__ */ jsx13(
1971
+ UsageSelect,
1972
+ {
1973
+ label: config.labels.usageDimensionLabel,
1974
+ onValueChange: (value) => setDimension(value),
1975
+ options: USAGE_DIMENSIONS.map((nextDimension) => [
1976
+ nextDimension,
1977
+ getUsageDimensionLabel(config.labels, nextDimension)
1978
+ ]),
1979
+ value: dimension
1980
+ }
1981
+ )
1982
+ ] }),
1983
+ /* @__PURE__ */ jsxs8("div", { className: "rounded-lg border bg-muted/30 p-3", children: [
1984
+ /* @__PURE__ */ jsxs8("div", { className: "mb-3 flex items-center justify-between gap-3", children: [
1985
+ /* @__PURE__ */ jsxs8("div", { className: "flex items-center gap-2 text-sm font-medium", children: [
1986
+ /* @__PURE__ */ jsx13(Filter, { className: "size-4" }),
1987
+ /* @__PURE__ */ jsx13("span", { children: "Filters" }),
1988
+ activeFilterCount > 0 && /* @__PURE__ */ jsx13(Badge, { variant: "secondary", children: activeFilterCount })
1989
+ ] }),
1990
+ activeFilterCount > 0 && /* @__PURE__ */ jsx13(
1991
+ Button,
1992
+ {
1993
+ onClick: () => {
1994
+ setParticipantType("all");
1995
+ setThreadId("");
1996
+ setParticipantId("");
1997
+ setProvider("");
1998
+ setModel("");
1999
+ setCustomFrom("");
2000
+ setCustomTo("");
2001
+ },
2002
+ size: "sm",
2003
+ variant: "ghost",
2004
+ children: "Clear"
2005
+ }
2006
+ )
2007
+ ] }),
2008
+ /* @__PURE__ */ jsxs8("div", { className: "grid gap-2 md:grid-cols-2 xl:grid-cols-6", children: [
2009
+ period === "custom" && /* @__PURE__ */ jsxs8(Fragment3, { children: [
2010
+ /* @__PURE__ */ jsx13(
2011
+ FilterInput,
1650
2012
  {
1651
- value: usageMetricKind,
1652
- onValueChange: (value) => setUsageMetricKind(value),
1653
- children: [
1654
- /* @__PURE__ */ jsx12(SelectTrigger, { className: "h-9 w-full min-w-[160px]", children: /* @__PURE__ */ jsx12(SelectValue, {}) }),
1655
- /* @__PURE__ */ jsxs7(SelectContent, { children: [
1656
- /* @__PURE__ */ jsx12(SelectItem, { value: "tokens", children: config.labels.usageMetricTokens }),
1657
- /* @__PURE__ */ jsx12(SelectItem, { value: "cost", children: config.labels.usageMetricCost })
1658
- ] })
1659
- ]
2013
+ label: "From",
2014
+ onChange: setCustomFrom,
2015
+ type: "datetime-local",
2016
+ value: customFrom
1660
2017
  }
1661
- )
1662
- ] }),
1663
- /* @__PURE__ */ jsxs7("div", { className: "space-y-1", children: [
1664
- /* @__PURE__ */ jsx12("p", { className: "text-xs font-medium uppercase tracking-[0.18em] text-muted-foreground", children: config.labels.usageDimensionLabel }),
1665
- /* @__PURE__ */ jsxs7(
1666
- Select,
2018
+ ),
2019
+ /* @__PURE__ */ jsx13(
2020
+ FilterInput,
1667
2021
  {
1668
- value: usageDimension,
1669
- onValueChange: (value) => setUsageDimension(value),
1670
- children: [
1671
- /* @__PURE__ */ jsx12(SelectTrigger, { className: "h-9 w-full min-w-[160px]", children: /* @__PURE__ */ jsx12(SelectValue, {}) }),
1672
- /* @__PURE__ */ jsx12(SelectContent, { children: USAGE_DIMENSIONS.map((dimension) => /* @__PURE__ */ jsx12(SelectItem, { value: dimension, children: getUsageDimensionLabel(config.labels, dimension) }, dimension)) })
1673
- ]
2022
+ label: "To",
2023
+ onChange: setCustomTo,
2024
+ type: "datetime-local",
2025
+ value: customTo
1674
2026
  }
1675
2027
  )
1676
- ] })
1677
- ] })
1678
- ] }),
1679
- /* @__PURE__ */ jsx12("div", { className: "grid gap-4 sm:grid-cols-2 xl:grid-cols-3", children: usageBreakdownCards.map((card) => {
1680
- const isSelected = card.dimension === usageDimension;
1681
- return /* @__PURE__ */ jsxs7(
1682
- "div",
1683
- {
1684
- className: cn(
1685
- "rounded-xl border bg-card p-5 shadow-sm transition-colors",
1686
- isSelected && "border-primary/60 ring-1 ring-primary/15"
1687
- ),
1688
- children: [
1689
- /* @__PURE__ */ jsxs7("div", { className: "flex items-start justify-between gap-3", children: [
1690
- /* @__PURE__ */ jsxs7("div", { children: [
1691
- /* @__PURE__ */ jsx12("p", { className: "text-sm font-medium text-muted-foreground", children: card.label }),
1692
- /* @__PURE__ */ jsx12("p", { className: "mt-3 text-2xl font-semibold tracking-tight", children: formatMetricValue(card.value, usageMetricKind) })
1693
- ] }),
1694
- isSelected && /* @__PURE__ */ jsx12(Badge, { variant: "outline", children: config.labels.usageDimensionLabel })
1695
- ] }),
1696
- /* @__PURE__ */ jsxs7("p", { className: "mt-2 text-xs text-muted-foreground", children: [
1697
- overview?.llmTotals.totalCalls ?? 0,
1698
- " ",
1699
- config.labels.usageCallsDetail
1700
- ] })
1701
- ]
1702
- },
1703
- card.dimension
1704
- );
1705
- }) })
1706
- ] }),
1707
- config.features.showActivity && /* @__PURE__ */ jsxs7("section", { className: "space-y-4", children: [
1708
- /* @__PURE__ */ jsx12(SectionHeading, { title: config.labels.activityTitle }),
1709
- /* @__PURE__ */ jsx12(
1710
- ActivityChart,
1711
- {
1712
- interval,
1713
- labels: config.labels,
1714
- maxBars: config.ui.maxActivityBars,
1715
- points: activity,
1716
- usageDimension,
1717
- usageMetricKind
1718
- }
1719
- )
1720
- ] }),
1721
- /* @__PURE__ */ jsxs7("div", { className: "grid gap-6 lg:grid-cols-3", children: [
1722
- config.features.showThreads && /* @__PURE__ */ jsx12(
1723
- DataTable,
1724
- {
1725
- rows: threads,
1726
- searchPlaceholder: config.labels.threadSearchPlaceholder,
1727
- searchValue: threadSearch,
1728
- setSearchValue: onThreadSearchChange,
1729
- title: config.labels.threadsTitle,
1730
- children: /* @__PURE__ */ jsx12(
1731
- ThreadsTable,
2028
+ ] }),
2029
+ /* @__PURE__ */ jsx13(
2030
+ UsageSelect,
1732
2031
  {
1733
- rows: threads,
1734
- labels: config.labels,
1735
- onThreadClick
2032
+ label: "Type",
2033
+ onValueChange: (value) => setParticipantType(
2034
+ value
2035
+ ),
2036
+ options: [
2037
+ ["all", "All"],
2038
+ ["human", "Human"],
2039
+ ["agent", "Agent"],
2040
+ ["job", "Job"]
2041
+ ],
2042
+ value: participantType
1736
2043
  }
1737
- )
1738
- }
1739
- ),
1740
- config.features.showParticipants && /* @__PURE__ */ jsx12(
1741
- DataTable,
1742
- {
1743
- rows: participants,
1744
- searchPlaceholder: config.labels.participantSearchPlaceholder,
1745
- searchValue: participantSearch,
1746
- setSearchValue: onParticipantSearchChange,
1747
- title: config.labels.participantsTitle,
1748
- children: /* @__PURE__ */ jsx12(ParticipantsTable, { rows: participants, labels: config.labels })
1749
- }
1750
- ),
1751
- config.features.showAgents && /* @__PURE__ */ jsx12(
1752
- DataTable,
1753
- {
1754
- rows: agents,
1755
- searchPlaceholder: config.labels.agentSearchPlaceholder,
1756
- searchValue: agentSearch,
1757
- setSearchValue: onAgentSearchChange,
1758
- title: config.labels.agentsTitle,
1759
- children: /* @__PURE__ */ jsx12(
1760
- AgentsTable,
2044
+ ),
2045
+ /* @__PURE__ */ jsx13(
2046
+ FilterInput,
1761
2047
  {
1762
- rows: agents,
1763
- labels: config.labels,
1764
- usageMetricKind,
1765
- usageDimension
2048
+ icon: /* @__PURE__ */ jsx13(Search, { className: "size-3.5" }),
2049
+ label: "Thread",
2050
+ onChange: setThreadId,
2051
+ value: threadId
1766
2052
  }
1767
- )
1768
- }
1769
- )
1770
- ] })
1771
- ] });
1772
- };
1773
- function SectionHeading({ title }) {
1774
- return /* @__PURE__ */ jsx12("h3", { className: "text-lg font-semibold tracking-tight", children: title });
1775
- }
1776
- function ActivityChart(props) {
1777
- const trimmedPoints = props.points.slice(-props.maxBars);
1778
- const maxUsageValue = Math.max(
1779
- ...trimmedPoints.map(
1780
- (point) => getActivityUsageValue(
1781
- point,
1782
- props.usageMetricKind,
1783
- props.usageDimension
1784
- )
1785
- ),
1786
- 1
1787
- );
1788
- return /* @__PURE__ */ jsx12("div", { className: "rounded-xl border bg-card p-5 shadow-sm", children: trimmedPoints.length === 0 ? /* @__PURE__ */ jsx12("p", { className: "text-sm text-muted-foreground", children: props.labels.noResults }) : /* @__PURE__ */ jsx12("div", { className: "flex min-h-48 items-end gap-2", children: trimmedPoints.map((point) => {
1789
- const usageValue = getActivityUsageValue(
1790
- point,
1791
- props.usageMetricKind,
1792
- props.usageDimension
1793
- );
1794
- return /* @__PURE__ */ jsxs7(
1795
- "div",
1796
- {
1797
- className: "flex min-w-0 flex-1 flex-col items-center gap-2",
1798
- children: [
1799
- /* @__PURE__ */ jsx12("div", { className: "flex h-36 w-full items-end rounded-lg bg-muted px-1 pb-1", children: /* @__PURE__ */ jsx12(
1800
- "div",
2053
+ ),
2054
+ /* @__PURE__ */ jsx13(
2055
+ FilterInput,
1801
2056
  {
1802
- className: "w-full rounded-md bg-primary transition-all",
1803
- style: {
1804
- height: `${Math.max(usageValue / maxUsageValue * 100, 8)}%`
1805
- }
2057
+ icon: /* @__PURE__ */ jsx13(Users2, { className: "size-3.5" }),
2058
+ label: "Participant",
2059
+ onChange: setParticipantId,
2060
+ value: participantId
1806
2061
  }
1807
- ) }),
1808
- /* @__PURE__ */ jsxs7("div", { className: "text-center", children: [
1809
- /* @__PURE__ */ jsx12("p", { className: "text-xs font-medium", children: formatBucket(point.bucket, props.interval) }),
1810
- /* @__PURE__ */ jsx12("p", { className: "text-[11px] text-muted-foreground", children: formatMetricValue(usageValue, props.usageMetricKind) }),
1811
- /* @__PURE__ */ jsxs7("p", { className: "text-[11px] text-muted-foreground", children: [
1812
- formatNumber(point.totalCalls),
1813
- " ",
1814
- props.labels.usageCallsDetail
1815
- ] })
2062
+ ),
2063
+ /* @__PURE__ */ jsx13(
2064
+ FilterInput,
2065
+ {
2066
+ icon: /* @__PURE__ */ jsx13(Database2, { className: "size-3.5" }),
2067
+ label: "Provider",
2068
+ onChange: setProvider,
2069
+ value: provider
2070
+ }
2071
+ ),
2072
+ /* @__PURE__ */ jsx13(
2073
+ FilterInput,
2074
+ {
2075
+ icon: /* @__PURE__ */ jsx13(Sparkles, { className: "size-3.5" }),
2076
+ label: "Model",
2077
+ onChange: setModel,
2078
+ value: model
2079
+ }
2080
+ )
2081
+ ] })
2082
+ ] })
2083
+ ] }) }),
2084
+ /* @__PURE__ */ jsxs8(Card, { className: "gap-3 overflow-hidden py-4", children: [
2085
+ /* @__PURE__ */ jsx13(CardHeader, { className: "px-4 lg:px-5", children: /* @__PURE__ */ jsxs8("div", { className: "flex flex-col gap-2 md:flex-row md:items-start md:justify-between", children: [
2086
+ /* @__PURE__ */ jsxs8("div", { children: [
2087
+ /* @__PURE__ */ jsx13(CardTitle, { className: "text-base", children: getUsageSummaryLabel(config.labels, metricKind, dimension) }),
2088
+ /* @__PURE__ */ jsxs8("p", { className: "mt-1 text-sm text-muted-foreground", children: [
2089
+ formatMetricValue(
2090
+ getUsageTotalValue(totals, metricKind, dimension),
2091
+ metricKind
2092
+ ),
2093
+ " ",
2094
+ "across ",
2095
+ formatNumber(totals.totalCalls),
2096
+ " calls"
1816
2097
  ] })
1817
- ]
1818
- },
1819
- point.bucket
1820
- );
1821
- }) }) });
1822
- }
1823
- function DataTable(props) {
1824
- return /* @__PURE__ */ jsxs7("div", { className: "rounded-xl border bg-card p-5 shadow-sm", children: [
1825
- /* @__PURE__ */ jsxs7("div", { className: "mb-4 flex items-center justify-between gap-3", children: [
1826
- /* @__PURE__ */ jsx12(SectionHeading, { title: props.title }),
1827
- /* @__PURE__ */ jsx12(
1828
- Input,
2098
+ ] }),
2099
+ isLoading && /* @__PURE__ */ jsx13(Badge, { variant: "outline", children: config.labels.loading })
2100
+ ] }) }),
2101
+ /* @__PURE__ */ jsx13(CardContent, { className: "px-2 lg:px-4", children: error ? /* @__PURE__ */ jsx13("div", { className: "rounded-lg border border-destructive/30 bg-destructive/10 p-4 text-sm text-destructive", children: error }) : chartState.data.length === 0 ? /* @__PURE__ */ jsx13(
2102
+ EmptyDashboard,
1829
2103
  {
1830
- className: "h-8 w-full max-w-44",
1831
- onChange: (event) => props.setSearchValue(event.target.value),
1832
- placeholder: props.searchPlaceholder,
1833
- value: props.searchValue
2104
+ description: config.labels.noResults,
2105
+ title: "No usage"
1834
2106
  }
1835
- )
2107
+ ) : /* @__PURE__ */ jsx13(
2108
+ UsageChart,
2109
+ {
2110
+ chartState,
2111
+ metricKind
2112
+ }
2113
+ ) })
1836
2114
  ] }),
1837
- props.rows.length === 0 ? /* @__PURE__ */ jsx12("p", { className: "text-sm text-muted-foreground", children: "No results" }) : props.children
2115
+ /* @__PURE__ */ jsx13(
2116
+ UsageTable,
2117
+ {
2118
+ dimension,
2119
+ groupBy,
2120
+ labels: config.labels,
2121
+ metricKind,
2122
+ onRowFilter: (row) => {
2123
+ if (groupBy === "thread") setThreadId(row.groupKey);
2124
+ if (groupBy === "participant") setParticipantId(row.groupKey);
2125
+ if (groupBy === "provider") setProvider(row.groupKey);
2126
+ if (groupBy === "model") setModel(row.groupKey);
2127
+ },
2128
+ rows: groupedRows,
2129
+ totals
2130
+ }
2131
+ )
1838
2132
  ] });
1839
2133
  }
1840
- function ThreadsTable({
1841
- rows,
2134
+ function UsageSummary({
2135
+ dimension,
1842
2136
  labels,
1843
- onThreadClick
2137
+ metricKind,
2138
+ totals
1844
2139
  }) {
1845
- return /* @__PURE__ */ jsx12("div", { className: "space-y-3", children: rows.map((thread) => /* @__PURE__ */ jsxs7(
1846
- "div",
2140
+ const summary = [
1847
2141
  {
1848
- className: cn(
1849
- "rounded-lg border bg-muted/50 p-4",
1850
- onThreadClick && "cursor-pointer hover:bg-muted transition-colors"
1851
- ),
1852
- onClick: () => onThreadClick?.(thread.threadId),
1853
- children: [
1854
- /* @__PURE__ */ jsxs7("div", { className: "flex items-start justify-between gap-3", children: [
1855
- /* @__PURE__ */ jsxs7("div", { className: "min-w-0", children: [
1856
- /* @__PURE__ */ jsx12("p", { className: "font-medium", children: thread.name }),
1857
- /* @__PURE__ */ jsx12("p", { className: "mt-1 truncate text-xs text-muted-foreground", children: thread.summary ?? thread.lastMessagePreview ?? "No summary yet" })
1858
- ] }),
1859
- /* @__PURE__ */ jsx12(
1860
- Badge,
1861
- {
1862
- variant: thread.status === "archived" ? "secondary" : "default",
1863
- children: thread.status === "archived" ? labels.statusArchived : labels.statusActive
1864
- }
1865
- )
1866
- ] }),
1867
- /* @__PURE__ */ jsxs7("div", { className: "mt-3 flex flex-wrap gap-3 text-xs text-muted-foreground", children: [
1868
- /* @__PURE__ */ jsxs7("span", { children: [
1869
- formatNumber(thread.messageCount),
1870
- " messages"
1871
- ] }),
1872
- /* @__PURE__ */ jsxs7("span", { children: [
1873
- thread.participantIds.length,
1874
- " participants"
1875
- ] }),
1876
- /* @__PURE__ */ jsx12("span", { children: formatDate(thread.lastActivityAt) })
1877
- ] })
1878
- ]
2142
+ label: labels.usageMetricCost,
2143
+ value: formatMetricValue(totals.totalCostUsd, "cost"),
2144
+ detail: `${formatNumber(totals.totalCalls)} ${labels.usageCallsDetail}`,
2145
+ icon: Wallet
1879
2146
  },
1880
- thread.threadId
1881
- )) });
2147
+ {
2148
+ label: labels.usageMetricTokens,
2149
+ value: formatMetricValue(totals.totalTokens, "tokens"),
2150
+ detail: `${formatMetricValue(totals.inputTokens, "tokens")} input`,
2151
+ icon: Activity2
2152
+ },
2153
+ {
2154
+ label: labels.usageCacheRead,
2155
+ value: formatMetricValue(totals.cacheReadInputCostUsd, "cost"),
2156
+ detail: `${formatMetricValue(totals.cacheReadInputTokens, "tokens")} tokens`,
2157
+ icon: Database2
2158
+ },
2159
+ {
2160
+ label: getUsageSummaryLabel(labels, metricKind, dimension),
2161
+ value: formatMetricValue(
2162
+ getUsageTotalValue(totals, metricKind, dimension),
2163
+ metricKind
2164
+ ),
2165
+ detail: labels.usageTotal,
2166
+ icon: Sparkles
2167
+ }
2168
+ ];
2169
+ return /* @__PURE__ */ jsx13("div", { className: "grid gap-3 sm:grid-cols-2 xl:grid-cols-4", children: summary.map((item) => /* @__PURE__ */ jsx13(Card, { className: "gap-3 py-4", children: /* @__PURE__ */ jsx13(CardContent, { className: "px-4", children: /* @__PURE__ */ jsxs8("div", { className: "flex items-start justify-between gap-3", children: [
2170
+ /* @__PURE__ */ jsxs8("div", { className: "min-w-0", children: [
2171
+ /* @__PURE__ */ jsx13("p", { className: "truncate text-sm text-muted-foreground", children: item.label }),
2172
+ /* @__PURE__ */ jsx13("p", { className: "mt-1 truncate text-2xl font-semibold tracking-tight", children: item.value }),
2173
+ /* @__PURE__ */ jsx13("p", { className: "mt-1 truncate text-xs text-muted-foreground", children: item.detail })
2174
+ ] }),
2175
+ /* @__PURE__ */ jsx13("div", { className: "rounded-md border bg-muted/50 p-2 text-muted-foreground", children: /* @__PURE__ */ jsx13(item.icon, { className: "size-4" }) })
2176
+ ] }) }) }, item.label)) });
1882
2177
  }
1883
- function ParticipantsTable({
1884
- rows,
1885
- labels
2178
+ function UsageChart({
2179
+ chartState,
2180
+ metricKind
1886
2181
  }) {
1887
- return /* @__PURE__ */ jsx12("div", { className: "space-y-3", children: rows.map((participant) => /* @__PURE__ */ jsxs7(
1888
- "div",
2182
+ return /* @__PURE__ */ jsx13(
2183
+ ChartContainer,
1889
2184
  {
1890
- className: "rounded-lg border bg-muted/50 p-4",
1891
- children: [
1892
- /* @__PURE__ */ jsxs7("div", { className: "flex items-start justify-between gap-3", children: [
1893
- /* @__PURE__ */ jsxs7("div", { className: "min-w-0", children: [
1894
- /* @__PURE__ */ jsx12("p", { className: "font-medium", children: participant.displayName }),
1895
- /* @__PURE__ */ jsx12("p", { className: "mt-1 text-xs uppercase tracking-[0.18em] text-muted-foreground", children: participant.participantType })
1896
- ] }),
1897
- /* @__PURE__ */ jsx12(Badge, { variant: "outline", children: participant.isGlobal ? labels.scopeGlobal : labels.scopeScoped })
1898
- ] }),
1899
- /* @__PURE__ */ jsxs7("div", { className: "mt-3 flex flex-wrap gap-3 text-xs text-muted-foreground", children: [
1900
- /* @__PURE__ */ jsxs7("span", { children: [
1901
- formatNumber(participant.messageCount),
1902
- " messages"
1903
- ] }),
1904
- /* @__PURE__ */ jsxs7("span", { children: [
1905
- formatNumber(participant.threadCount),
1906
- " threads"
1907
- ] }),
1908
- /* @__PURE__ */ jsx12("span", { children: formatDate(participant.lastActivityAt) })
1909
- ] })
1910
- ]
1911
- },
1912
- `${participant.namespace}:${participant.externalId}`
1913
- )) });
2185
+ className: "h-[320px] w-full",
2186
+ config: chartState.config,
2187
+ children: /* @__PURE__ */ jsxs8(
2188
+ BarChart,
2189
+ {
2190
+ accessibilityLayer: true,
2191
+ data: chartState.data,
2192
+ margin: { left: 8, right: 8, top: 12 },
2193
+ children: [
2194
+ /* @__PURE__ */ jsx13(CartesianGrid, { vertical: false }),
2195
+ /* @__PURE__ */ jsx13(
2196
+ XAxis,
2197
+ {
2198
+ axisLine: false,
2199
+ dataKey: "label",
2200
+ tickLine: false,
2201
+ tickMargin: 10
2202
+ }
2203
+ ),
2204
+ /* @__PURE__ */ jsx13(
2205
+ YAxis,
2206
+ {
2207
+ axisLine: false,
2208
+ tickFormatter: (value) => formatCompactMetric(value, metricKind),
2209
+ tickLine: false,
2210
+ width: 60
2211
+ }
2212
+ ),
2213
+ /* @__PURE__ */ jsx13(
2214
+ Tooltip2,
2215
+ {
2216
+ content: /* @__PURE__ */ jsx13(
2217
+ ChartTooltipContent,
2218
+ {
2219
+ formatter: (value) => formatMetricValue(Number(value), metricKind),
2220
+ labelFormatter: (value) => String(value ?? "")
2221
+ }
2222
+ ),
2223
+ cursor: false
2224
+ }
2225
+ ),
2226
+ /* @__PURE__ */ jsx13(
2227
+ Legend,
2228
+ {
2229
+ content: /* @__PURE__ */ jsx13(ChartLegendContent, { className: "justify-center pt-3" })
2230
+ }
2231
+ ),
2232
+ chartState.series.map((series) => /* @__PURE__ */ jsx13(
2233
+ Bar,
2234
+ {
2235
+ dataKey: series.id,
2236
+ fill: `var(--color-${series.id})`,
2237
+ radius: [4, 4, 0, 0],
2238
+ stackId: "usage"
2239
+ },
2240
+ series.id
2241
+ ))
2242
+ ]
2243
+ }
2244
+ )
2245
+ }
2246
+ );
1914
2247
  }
1915
- function AgentsTable({
1916
- rows,
2248
+ function UsageTable({
2249
+ dimension,
2250
+ groupBy,
1917
2251
  labels,
1918
- usageMetricKind,
1919
- usageDimension
2252
+ metricKind,
2253
+ onRowFilter,
2254
+ rows,
2255
+ totals
1920
2256
  }) {
1921
- return /* @__PURE__ */ jsx12("div", { className: "space-y-3", children: rows.map((agent) => /* @__PURE__ */ jsxs7(
1922
- "div",
1923
- {
1924
- className: "rounded-lg border bg-muted/50 p-4",
1925
- children: [
1926
- /* @__PURE__ */ jsxs7("div", { className: "flex items-start justify-between gap-3", children: [
1927
- /* @__PURE__ */ jsxs7("div", { className: "min-w-0", children: [
1928
- /* @__PURE__ */ jsx12("p", { className: "font-medium", children: agent.displayName }),
1929
- /* @__PURE__ */ jsx12("p", { className: "mt-1 truncate text-xs text-muted-foreground", children: agent.description ?? agent.agentId })
1930
- ] }),
1931
- /* @__PURE__ */ jsx12(Badge, { variant: "outline", children: agent.isConfigured ? labels.configured : labels.unconfigured })
1932
- ] }),
1933
- /* @__PURE__ */ jsx12("div", { className: "mt-3 grid grid-cols-2 gap-2 text-xs", children: [
1934
- {
1935
- label: "Messages",
1936
- value: formatNumber(agent.messageCount)
1937
- },
1938
- {
1939
- label: "LLM calls",
1940
- value: formatNumber(agent.llmCallCount)
1941
- },
2257
+ const totalValue = getUsageTotalValue(totals, metricKind, dimension);
2258
+ const filterable = groupBy !== "namespace";
2259
+ return /* @__PURE__ */ jsxs8(Card, { className: "gap-3 py-4", children: [
2260
+ /* @__PURE__ */ jsx13(CardHeader, { className: "px-4 lg:px-5", children: /* @__PURE__ */ jsxs8("div", { className: "flex flex-col gap-2 sm:flex-row sm:items-center sm:justify-between", children: [
2261
+ /* @__PURE__ */ jsx13(CardTitle, { className: "text-base", children: "Usage detail" }),
2262
+ /* @__PURE__ */ jsxs8(Badge, { variant: "outline", children: [
2263
+ formatNumber(rows.length),
2264
+ " ",
2265
+ getGroupByLabel(groupBy).toLowerCase()
2266
+ ] })
2267
+ ] }) }),
2268
+ /* @__PURE__ */ jsx13(CardContent, { className: "px-0", children: rows.length === 0 ? /* @__PURE__ */ jsx13("p", { className: "px-5 py-4 text-sm text-muted-foreground", children: labels.noResults }) : /* @__PURE__ */ jsx13("div", { className: "overflow-x-auto", children: /* @__PURE__ */ jsxs8("table", { className: "w-full min-w-[940px] text-sm", children: [
2269
+ /* @__PURE__ */ jsx13("thead", { children: /* @__PURE__ */ jsxs8("tr", { className: "border-b text-left text-xs uppercase tracking-[0.12em] text-muted-foreground", children: [
2270
+ /* @__PURE__ */ jsx13("th", { className: "px-5 py-2.5 font-medium", children: getGroupByLabel(groupBy) }),
2271
+ /* @__PURE__ */ jsx13("th", { className: "px-3 py-2.5 text-right font-medium", children: getUsageSummaryLabel(labels, metricKind, dimension) }),
2272
+ /* @__PURE__ */ jsx13("th", { className: "px-3 py-2.5 text-right font-medium", children: "Share" }),
2273
+ /* @__PURE__ */ jsx13("th", { className: "px-3 py-2.5 text-right font-medium", children: "Calls" }),
2274
+ /* @__PURE__ */ jsx13("th", { className: "px-3 py-2.5 text-right font-medium", children: "Input" }),
2275
+ /* @__PURE__ */ jsx13("th", { className: "px-3 py-2.5 text-right font-medium", children: "Output" }),
2276
+ /* @__PURE__ */ jsx13("th", { className: "px-3 py-2.5 text-right font-medium", children: "Reasoning" }),
2277
+ /* @__PURE__ */ jsx13("th", { className: "px-3 py-2.5 text-right font-medium", children: "Cache read" }),
2278
+ /* @__PURE__ */ jsx13("th", { className: "px-5 py-2.5 text-right font-medium", children: "Avg/call" })
2279
+ ] }) }),
2280
+ /* @__PURE__ */ jsx13("tbody", { children: rows.slice(0, 60).map((row) => {
2281
+ const share = totalValue > 0 ? row.value / totalValue : 0;
2282
+ return /* @__PURE__ */ jsxs8(
2283
+ "tr",
1942
2284
  {
1943
- label: "Tool calls",
1944
- value: formatNumber(agent.toolCallMessageCount)
2285
+ className: cn(
2286
+ "border-b last:border-0",
2287
+ filterable && "cursor-pointer transition-colors hover:bg-muted/50"
2288
+ ),
2289
+ onClick: () => filterable && onRowFilter(row),
2290
+ children: [
2291
+ /* @__PURE__ */ jsxs8("td", { className: "px-5 py-3", children: [
2292
+ /* @__PURE__ */ jsx13("div", { className: "max-w-80 truncate font-medium", children: row.groupLabel }),
2293
+ row.groupKey !== row.groupLabel && /* @__PURE__ */ jsx13("div", { className: "mt-0.5 max-w-80 truncate text-xs text-muted-foreground", children: row.groupKey })
2294
+ ] }),
2295
+ /* @__PURE__ */ jsx13("td", { className: "px-3 py-3 text-right font-medium", children: formatMetricValue(row.value, metricKind) }),
2296
+ /* @__PURE__ */ jsx13("td", { className: "px-3 py-3 text-right", children: formatPercent(share) }),
2297
+ /* @__PURE__ */ jsx13("td", { className: "px-3 py-3 text-right", children: formatNumber(row.totalCalls) }),
2298
+ /* @__PURE__ */ jsx13("td", { className: "px-3 py-3 text-right", children: formatMetricValue(
2299
+ getUsageTotalValue(row, metricKind, "input"),
2300
+ metricKind
2301
+ ) }),
2302
+ /* @__PURE__ */ jsx13("td", { className: "px-3 py-3 text-right", children: formatMetricValue(
2303
+ getUsageTotalValue(row, metricKind, "output"),
2304
+ metricKind
2305
+ ) }),
2306
+ /* @__PURE__ */ jsx13("td", { className: "px-3 py-3 text-right", children: formatMetricValue(
2307
+ getUsageTotalValue(row, metricKind, "reasoning"),
2308
+ metricKind
2309
+ ) }),
2310
+ /* @__PURE__ */ jsx13("td", { className: "px-3 py-3 text-right", children: formatMetricValue(
2311
+ getUsageTotalValue(row, metricKind, "cacheRead"),
2312
+ metricKind
2313
+ ) }),
2314
+ /* @__PURE__ */ jsx13("td", { className: "px-5 py-3 text-right", children: formatMetricValue(
2315
+ row.totalCalls > 0 ? row.value / row.totalCalls : 0,
2316
+ metricKind
2317
+ ) })
2318
+ ]
1945
2319
  },
1946
- {
1947
- label: getUsageSummaryLabel(labels, usageMetricKind, usageDimension),
1948
- value: formatMetricValue(
1949
- getAgentUsageValue(agent, usageMetricKind, usageDimension),
1950
- usageMetricKind
1951
- )
1952
- }
1953
- ].map((item) => /* @__PURE__ */ jsxs7("div", { children: [
1954
- /* @__PURE__ */ jsx12("p", { className: "font-medium text-foreground", children: item.value }),
1955
- /* @__PURE__ */ jsx12("p", { className: "text-muted-foreground", children: item.label })
1956
- ] }, item.label)) })
1957
- ]
1958
- },
1959
- `${agent.namespace}:${agent.agentId}`
1960
- )) });
2320
+ row.groupKey
2321
+ );
2322
+ }) })
2323
+ ] }) }) })
2324
+ ] });
1961
2325
  }
1962
- function formatBucket(bucket, interval) {
1963
- const date = new Date(bucket);
1964
- if (Number.isNaN(date.getTime())) return bucket;
1965
- return interval === "hour" ? date.toLocaleString(void 0, {
1966
- hour: "numeric",
1967
- month: "short",
1968
- day: "numeric"
1969
- }) : date.toLocaleDateString(void 0, {
1970
- month: "short",
1971
- day: "numeric"
1972
- });
2326
+ function UsageSelect(props) {
2327
+ return /* @__PURE__ */ jsxs8("label", { className: "space-y-1", children: [
2328
+ /* @__PURE__ */ jsx13("span", { className: "text-[11px] font-medium uppercase tracking-[0.16em] text-muted-foreground", children: props.label }),
2329
+ /* @__PURE__ */ jsxs8(Select, { value: props.value, onValueChange: props.onValueChange, children: [
2330
+ /* @__PURE__ */ jsx13(SelectTrigger, { className: "h-9 w-full min-w-0 bg-background", children: /* @__PURE__ */ jsx13(SelectValue, {}) }),
2331
+ /* @__PURE__ */ jsx13(SelectContent, { children: props.options.map(([value, label]) => /* @__PURE__ */ jsx13(SelectItem, { value, children: label }, value)) })
2332
+ ] })
2333
+ ] });
1973
2334
  }
1974
- function formatDate(value) {
1975
- if (!value) return "No activity";
1976
- const date = new Date(value);
1977
- if (Number.isNaN(date.getTime())) return value;
1978
- return date.toLocaleString(void 0, {
1979
- month: "short",
1980
- day: "numeric",
1981
- hour: "numeric",
1982
- minute: "2-digit"
1983
- });
2335
+ function FilterInput(props) {
2336
+ return /* @__PURE__ */ jsxs8("label", { className: "space-y-1", children: [
2337
+ /* @__PURE__ */ jsx13("span", { className: "text-[11px] font-medium uppercase tracking-[0.16em] text-muted-foreground", children: props.label }),
2338
+ /* @__PURE__ */ jsxs8("div", { className: "relative", children: [
2339
+ props.icon && /* @__PURE__ */ jsx13("span", { className: "pointer-events-none absolute left-3 top-1/2 -translate-y-1/2 text-muted-foreground", children: props.icon }),
2340
+ /* @__PURE__ */ jsx13(
2341
+ Input,
2342
+ {
2343
+ className: cn("h-9 bg-background", props.icon && "pl-8"),
2344
+ onChange: (event) => props.onChange(event.target.value),
2345
+ type: props.type ?? "text",
2346
+ value: props.value
2347
+ }
2348
+ )
2349
+ ] })
2350
+ ] });
1984
2351
  }
1985
- function formatNumber(value) {
1986
- return new Intl.NumberFormat().format(value);
2352
+ function EmptyDashboard({
2353
+ description,
2354
+ title
2355
+ }) {
2356
+ return /* @__PURE__ */ jsxs8("div", { className: "rounded-lg border border-dashed bg-muted/20 p-8 text-center", children: [
2357
+ /* @__PURE__ */ jsx13("h3", { className: "text-base font-semibold", children: title }),
2358
+ /* @__PURE__ */ jsx13("p", { className: "mt-2 text-sm text-muted-foreground", children: description })
2359
+ ] });
1987
2360
  }
2361
+ var EMPTY_TOTALS = {
2362
+ inputTokens: 0,
2363
+ outputTokens: 0,
2364
+ reasoningTokens: 0,
2365
+ cacheReadInputTokens: 0,
2366
+ cacheCreationInputTokens: 0,
2367
+ totalTokens: 0,
2368
+ inputCostUsd: 0,
2369
+ outputCostUsd: 0,
2370
+ reasoningCostUsd: 0,
2371
+ cacheReadInputCostUsd: 0,
2372
+ cacheCreationInputCostUsd: 0,
2373
+ totalCostUsd: 0,
2374
+ totalCalls: 0
2375
+ };
1988
2376
  var USAGE_DIMENSIONS = [
1989
2377
  "total",
1990
2378
  "input",
@@ -1993,6 +2381,128 @@ var USAGE_DIMENSIONS = [
1993
2381
  "cacheRead",
1994
2382
  "cacheWrite"
1995
2383
  ];
2384
+ var USAGE_CHART_COLORS = [
2385
+ "hsl(var(--primary))",
2386
+ "hsl(var(--chart-2, 142 76% 36%))",
2387
+ "hsl(var(--chart-3, 38 92% 50%))",
2388
+ "hsl(var(--chart-4, 199 89% 48%))",
2389
+ "hsl(var(--chart-5, 346 77% 49%))",
2390
+ "hsl(var(--muted-foreground))"
2391
+ ];
2392
+ function buildChartState(points, metricKind, dimension, interval) {
2393
+ const topGroups = topUsageGroups(points, metricKind, dimension);
2394
+ const groupIdByKey = new Map(topGroups.map((group, index) => [
2395
+ group.key,
2396
+ `series${index + 1}`
2397
+ ]));
2398
+ const series = topGroups.map((group, index) => ({
2399
+ color: USAGE_CHART_COLORS[index % USAGE_CHART_COLORS.length],
2400
+ id: groupIdByKey.get(group.key) ?? `series${index + 1}`,
2401
+ key: group.key,
2402
+ label: group.label
2403
+ }));
2404
+ const config = Object.fromEntries(
2405
+ series.map((item) => [item.id, {
2406
+ color: item.color,
2407
+ label: item.label
2408
+ }])
2409
+ );
2410
+ const buckets = buildUsageBuckets(points);
2411
+ const data = buckets.map((bucket) => {
2412
+ const row = {
2413
+ bucket: bucket.bucket,
2414
+ label: formatUsageBucket(bucket.bucket, interval)
2415
+ };
2416
+ for (const item of series) row[item.id] = 0;
2417
+ for (const point of bucket.points) {
2418
+ const seriesId = groupIdByKey.get(point.groupKey);
2419
+ if (!seriesId) continue;
2420
+ row[seriesId] = Number(row[seriesId] ?? 0) + getUsageTotalValue(point, metricKind, dimension);
2421
+ }
2422
+ return row;
2423
+ });
2424
+ return {
2425
+ config,
2426
+ data,
2427
+ series
2428
+ };
2429
+ }
2430
+ function buildUsageBuckets(points) {
2431
+ const byBucket = /* @__PURE__ */ new Map();
2432
+ for (const point of points) {
2433
+ const rows = byBucket.get(point.bucket) ?? [];
2434
+ rows.push(point);
2435
+ byBucket.set(point.bucket, rows);
2436
+ }
2437
+ return Array.from(byBucket.entries()).map(([bucket, bucketPoints]) => ({ bucket, points: bucketPoints })).sort(
2438
+ (a, b) => new Date(a.bucket).getTime() - new Date(b.bucket).getTime()
2439
+ );
2440
+ }
2441
+ function aggregateUsageRows(points, metricKind, dimension) {
2442
+ const totals = /* @__PURE__ */ new Map();
2443
+ for (const point of points) {
2444
+ const existing = totals.get(point.groupKey) ?? {
2445
+ ...EMPTY_TOTALS,
2446
+ groupKey: point.groupKey,
2447
+ groupLabel: point.groupLabel,
2448
+ value: 0
2449
+ };
2450
+ addUsageTotals(existing, point);
2451
+ existing.value = getUsageTotalValue(existing, metricKind, dimension);
2452
+ totals.set(point.groupKey, existing);
2453
+ }
2454
+ return Array.from(totals.values()).sort((a, b) => b.value - a.value);
2455
+ }
2456
+ function addUsageTotals(target, source) {
2457
+ target.inputTokens += source.inputTokens;
2458
+ target.outputTokens += source.outputTokens;
2459
+ target.reasoningTokens += source.reasoningTokens;
2460
+ target.cacheReadInputTokens += source.cacheReadInputTokens;
2461
+ target.cacheCreationInputTokens += source.cacheCreationInputTokens;
2462
+ target.totalTokens += source.totalTokens;
2463
+ target.inputCostUsd += source.inputCostUsd;
2464
+ target.outputCostUsd += source.outputCostUsd;
2465
+ target.reasoningCostUsd += source.reasoningCostUsd;
2466
+ target.cacheReadInputCostUsd += source.cacheReadInputCostUsd;
2467
+ target.cacheCreationInputCostUsd += source.cacheCreationInputCostUsd;
2468
+ target.totalCostUsd += source.totalCostUsd;
2469
+ target.totalCalls += source.totalCalls;
2470
+ }
2471
+ function topUsageGroups(points, metricKind, dimension) {
2472
+ const totals = /* @__PURE__ */ new Map();
2473
+ for (const point of points) {
2474
+ const existing = totals.get(point.groupKey) ?? {
2475
+ key: point.groupKey,
2476
+ label: point.groupLabel,
2477
+ value: 0
2478
+ };
2479
+ existing.value += getUsageTotalValue(point, metricKind, dimension);
2480
+ totals.set(point.groupKey, existing);
2481
+ }
2482
+ return Array.from(totals.values()).sort((a, b) => b.value - a.value).slice(0, 6);
2483
+ }
2484
+ function getUsageRange(period, customFrom, customTo) {
2485
+ if (period === "custom") {
2486
+ return {
2487
+ from: customFrom ? new Date(customFrom).toISOString() : void 0,
2488
+ to: customTo ? new Date(customTo).toISOString() : void 0
2489
+ };
2490
+ }
2491
+ const to = /* @__PURE__ */ new Date();
2492
+ const from = new Date(to);
2493
+ if (period === "24h") {
2494
+ from.setHours(from.getHours() - 24);
2495
+ } else if (period === "30d") {
2496
+ from.setDate(from.getDate() - 30);
2497
+ } else {
2498
+ from.setDate(from.getDate() - 7);
2499
+ }
2500
+ return { from: from.toISOString(), to: to.toISOString() };
2501
+ }
2502
+ function emptyToUndefined(value) {
2503
+ const trimmed = value.trim();
2504
+ return trimmed.length > 0 ? trimmed : void 0;
2505
+ }
1996
2506
  function getUsageDimensionLabel(labels, dimension) {
1997
2507
  switch (dimension) {
1998
2508
  case "input":
@@ -2011,111 +2521,103 @@ function getUsageDimensionLabel(labels, dimension) {
2011
2521
  }
2012
2522
  }
2013
2523
  function getUsageSummaryLabel(labels, metricKind, dimension) {
2014
- const metricLabel = metricKind === "cost" ? labels.usageMetricCost : labels.usageMetricTokens;
2524
+ const metricLabel = metricKind === "cost" ? labels.usageMetricCost : metricKind === "calls" ? "Calls" : labels.usageMetricTokens;
2015
2525
  return `${getUsageDimensionLabel(labels, dimension)} ${metricLabel}`;
2016
2526
  }
2017
- function getOverviewUsageValue(overview, metricKind, dimension) {
2018
- const llmTotals = overview.llmTotals;
2019
- if (metricKind === "cost") {
2020
- switch (dimension) {
2021
- case "input":
2022
- return llmTotals.inputCostUsd;
2023
- case "output":
2024
- return llmTotals.outputCostUsd;
2025
- case "reasoning":
2026
- return llmTotals.reasoningCostUsd;
2027
- case "cacheRead":
2028
- return llmTotals.cacheReadInputCostUsd;
2029
- case "cacheWrite":
2030
- return llmTotals.cacheCreationInputCostUsd;
2031
- case "total":
2032
- default:
2033
- return llmTotals.totalCostUsd;
2034
- }
2035
- }
2036
- switch (dimension) {
2037
- case "input":
2038
- return llmTotals.inputTokens;
2039
- case "output":
2040
- return llmTotals.outputTokens;
2041
- case "reasoning":
2042
- return llmTotals.reasoningTokens;
2043
- case "cacheRead":
2044
- return llmTotals.cacheReadInputTokens;
2045
- case "cacheWrite":
2046
- return llmTotals.cacheCreationInputTokens;
2047
- case "total":
2527
+ function getGroupByLabel(groupBy) {
2528
+ switch (groupBy) {
2529
+ case "thread":
2530
+ return "Thread";
2531
+ case "namespace":
2532
+ return "Namespace";
2533
+ case "provider":
2534
+ return "Provider";
2535
+ case "model":
2536
+ return "Model";
2537
+ case "participant":
2048
2538
  default:
2049
- return llmTotals.totalTokens;
2539
+ return "Participant";
2050
2540
  }
2051
2541
  }
2052
- function getAgentUsageValue(agent, metricKind, dimension) {
2542
+ function getUsageTotalValue(totals, metricKind, dimension) {
2543
+ if (metricKind === "calls") return totals.totalCalls;
2053
2544
  if (metricKind === "cost") {
2054
2545
  switch (dimension) {
2055
2546
  case "input":
2056
- return agent.inputCostUsd;
2547
+ return totals.inputCostUsd;
2057
2548
  case "output":
2058
- return agent.outputCostUsd;
2549
+ return totals.outputCostUsd;
2059
2550
  case "reasoning":
2060
- return agent.reasoningCostUsd;
2551
+ return totals.reasoningCostUsd;
2061
2552
  case "cacheRead":
2062
- return agent.cacheReadInputCostUsd;
2553
+ return totals.cacheReadInputCostUsd;
2063
2554
  case "cacheWrite":
2064
- return agent.cacheCreationInputCostUsd;
2555
+ return totals.cacheCreationInputCostUsd;
2065
2556
  case "total":
2066
2557
  default:
2067
- return agent.totalCostUsd;
2558
+ return totals.totalCostUsd;
2068
2559
  }
2069
2560
  }
2070
2561
  switch (dimension) {
2071
2562
  case "input":
2072
- return agent.inputTokens;
2563
+ return totals.inputTokens;
2073
2564
  case "output":
2074
- return agent.outputTokens;
2565
+ return totals.outputTokens;
2075
2566
  case "reasoning":
2076
- return agent.reasoningTokens;
2567
+ return totals.reasoningTokens;
2077
2568
  case "cacheRead":
2078
- return agent.cacheReadInputTokens;
2569
+ return totals.cacheReadInputTokens;
2079
2570
  case "cacheWrite":
2080
- return agent.cacheCreationInputTokens;
2571
+ return totals.cacheCreationInputTokens;
2081
2572
  case "total":
2082
2573
  default:
2083
- return agent.totalTokens;
2574
+ return totals.totalTokens;
2084
2575
  }
2085
2576
  }
2086
- function getActivityUsageValue(point, metricKind, dimension) {
2087
- if (metricKind === "cost") {
2088
- switch (dimension) {
2089
- case "input":
2090
- return point.inputCostUsd;
2091
- case "output":
2092
- return point.outputCostUsd;
2093
- case "reasoning":
2094
- return point.reasoningCostUsd;
2095
- case "cacheRead":
2096
- return point.cacheReadInputCostUsd;
2097
- case "cacheWrite":
2098
- return point.cacheCreationInputCostUsd;
2099
- case "total":
2100
- default:
2101
- return point.totalCostUsd;
2102
- }
2577
+ function formatUsageBucket(bucket, interval) {
2578
+ const date = new Date(bucket);
2579
+ if (Number.isNaN(date.getTime())) return bucket;
2580
+ if (interval === "minute" || interval === "hour") {
2581
+ return date.toLocaleString(void 0, {
2582
+ month: "short",
2583
+ day: "numeric",
2584
+ hour: "numeric",
2585
+ minute: interval === "minute" ? "2-digit" : void 0
2586
+ });
2103
2587
  }
2104
- switch (dimension) {
2105
- case "input":
2106
- return point.inputTokens;
2107
- case "output":
2108
- return point.outputTokens;
2109
- case "reasoning":
2110
- return point.reasoningTokens;
2111
- case "cacheRead":
2112
- return point.cacheReadInputTokens;
2113
- case "cacheWrite":
2114
- return point.cacheCreationInputTokens;
2115
- case "total":
2116
- default:
2117
- return point.totalTokens;
2588
+ if (interval === "month") {
2589
+ return date.toLocaleDateString(void 0, {
2590
+ month: "short",
2591
+ year: "numeric"
2592
+ });
2118
2593
  }
2594
+ return date.toLocaleDateString(void 0, {
2595
+ month: "short",
2596
+ day: "numeric"
2597
+ });
2598
+ }
2599
+ function formatUsageRangeLabel(period, range) {
2600
+ if (period !== "custom") return period;
2601
+ if (!range.from && !range.to) return "Custom";
2602
+ return `${formatShortDate(range.from)} - ${formatShortDate(range.to)}`;
2603
+ }
2604
+ function formatShortDate(value) {
2605
+ if (!value) return "Open";
2606
+ const date = new Date(value);
2607
+ if (Number.isNaN(date.getTime())) return value;
2608
+ return date.toLocaleDateString(void 0, {
2609
+ month: "short",
2610
+ day: "numeric"
2611
+ });
2612
+ }
2613
+ function formatNumber(value) {
2614
+ return new Intl.NumberFormat().format(value);
2615
+ }
2616
+ function formatPercent(value) {
2617
+ return new Intl.NumberFormat(void 0, {
2618
+ maximumFractionDigits: 1,
2619
+ style: "percent"
2620
+ }).format(value);
2119
2621
  }
2120
2622
  function formatMetricValue(value, metricKind) {
2121
2623
  if (metricKind === "cost") {
@@ -2130,10 +2632,26 @@ function formatMetricValue(value, metricKind) {
2130
2632
  }
2131
2633
  return formatNumber(value);
2132
2634
  }
2635
+ function formatCompactMetric(value, metricKind) {
2636
+ if (metricKind === "cost") {
2637
+ return new Intl.NumberFormat(void 0, {
2638
+ compactDisplay: "short",
2639
+ currency: "USD",
2640
+ maximumFractionDigits: 1,
2641
+ notation: "compact",
2642
+ style: "currency"
2643
+ }).format(value);
2644
+ }
2645
+ return new Intl.NumberFormat(void 0, {
2646
+ compactDisplay: "short",
2647
+ maximumFractionDigits: 1,
2648
+ notation: "compact"
2649
+ }).format(value);
2650
+ }
2133
2651
 
2134
2652
  // src/components/views/ThreadsView.tsx
2135
- import { Search, MessageSquare as MessageSquare2 } from "lucide-react";
2136
- import { jsx as jsx13, jsxs as jsxs8 } from "react/jsx-runtime";
2653
+ import { Search as Search2, MessageSquare as MessageSquare2 } from "lucide-react";
2654
+ import { jsx as jsx14, jsxs as jsxs9 } from "react/jsx-runtime";
2137
2655
  var ThreadsView = ({
2138
2656
  config,
2139
2657
  threads,
@@ -2141,10 +2659,10 @@ var ThreadsView = ({
2141
2659
  onSearchChange,
2142
2660
  onThreadClick
2143
2661
  }) => {
2144
- return /* @__PURE__ */ jsxs8("div", { className: "space-y-4", children: [
2145
- /* @__PURE__ */ jsxs8("div", { className: "relative max-w-sm", children: [
2146
- /* @__PURE__ */ jsx13(Search, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
2147
- /* @__PURE__ */ jsx13(
2662
+ return /* @__PURE__ */ jsxs9("div", { className: "space-y-4", children: [
2663
+ /* @__PURE__ */ jsxs9("div", { className: "relative max-w-sm", children: [
2664
+ /* @__PURE__ */ jsx14(Search2, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
2665
+ /* @__PURE__ */ jsx14(
2148
2666
  Input,
2149
2667
  {
2150
2668
  className: "pl-9",
@@ -2154,19 +2672,19 @@ var ThreadsView = ({
2154
2672
  }
2155
2673
  )
2156
2674
  ] }),
2157
- threads.length === 0 ? /* @__PURE__ */ jsxs8("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
2158
- /* @__PURE__ */ jsx13(MessageSquare2, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
2159
- /* @__PURE__ */ jsx13("p", { className: "mt-3 text-sm text-muted-foreground", children: searchValue ? config.labels.noResults : config.labels.emptyDescription })
2160
- ] }) : /* @__PURE__ */ jsx13("div", { className: "space-y-2", children: threads.map((thread) => /* @__PURE__ */ jsxs8(
2675
+ threads.length === 0 ? /* @__PURE__ */ jsxs9("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
2676
+ /* @__PURE__ */ jsx14(MessageSquare2, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
2677
+ /* @__PURE__ */ jsx14("p", { className: "mt-3 text-sm text-muted-foreground", children: searchValue ? config.labels.noResults : config.labels.emptyDescription })
2678
+ ] }) : /* @__PURE__ */ jsx14("div", { className: "space-y-2", children: threads.map((thread) => /* @__PURE__ */ jsxs9(
2161
2679
  "div",
2162
2680
  {
2163
2681
  className: "flex items-center gap-4 rounded-lg border bg-card p-4 transition-colors hover:bg-muted/50 cursor-pointer",
2164
2682
  onClick: () => onThreadClick?.(thread.threadId),
2165
2683
  children: [
2166
- /* @__PURE__ */ jsxs8("div", { className: "flex-1 min-w-0", children: [
2167
- /* @__PURE__ */ jsxs8("div", { className: "flex items-center gap-2", children: [
2168
- /* @__PURE__ */ jsx13("p", { className: "font-medium truncate", children: thread.name }),
2169
- /* @__PURE__ */ jsx13(
2684
+ /* @__PURE__ */ jsxs9("div", { className: "flex-1 min-w-0", children: [
2685
+ /* @__PURE__ */ jsxs9("div", { className: "flex items-center gap-2", children: [
2686
+ /* @__PURE__ */ jsx14("p", { className: "font-medium truncate", children: thread.name }),
2687
+ /* @__PURE__ */ jsx14(
2170
2688
  Badge,
2171
2689
  {
2172
2690
  variant: thread.status === "archived" ? "secondary" : "default",
@@ -2175,18 +2693,18 @@ var ThreadsView = ({
2175
2693
  }
2176
2694
  )
2177
2695
  ] }),
2178
- /* @__PURE__ */ jsx13("p", { className: "mt-1 text-sm text-muted-foreground truncate", children: thread.summary ?? thread.lastMessagePreview ?? "No summary yet" })
2696
+ /* @__PURE__ */ jsx14("p", { className: "mt-1 text-sm text-muted-foreground truncate", children: thread.summary ?? thread.lastMessagePreview ?? "No summary yet" })
2179
2697
  ] }),
2180
- /* @__PURE__ */ jsxs8("div", { className: "text-right text-xs text-muted-foreground shrink-0 space-y-1", children: [
2181
- /* @__PURE__ */ jsxs8("p", { children: [
2698
+ /* @__PURE__ */ jsxs9("div", { className: "text-right text-xs text-muted-foreground shrink-0 space-y-1", children: [
2699
+ /* @__PURE__ */ jsxs9("p", { children: [
2182
2700
  formatNumber2(thread.messageCount),
2183
2701
  " messages"
2184
2702
  ] }),
2185
- /* @__PURE__ */ jsxs8("p", { children: [
2703
+ /* @__PURE__ */ jsxs9("p", { children: [
2186
2704
  thread.participantIds.length,
2187
2705
  " participants"
2188
2706
  ] }),
2189
- /* @__PURE__ */ jsx13("p", { children: formatDate2(thread.lastActivityAt) })
2707
+ /* @__PURE__ */ jsx14("p", { children: formatDate(thread.lastActivityAt) })
2190
2708
  ] })
2191
2709
  ]
2192
2710
  },
@@ -2194,7 +2712,7 @@ var ThreadsView = ({
2194
2712
  )) })
2195
2713
  ] });
2196
2714
  };
2197
- function formatDate2(value) {
2715
+ function formatDate(value) {
2198
2716
  if (!value) return "No activity";
2199
2717
  const date = new Date(value);
2200
2718
  if (Number.isNaN(date.getTime())) return value;
@@ -2220,7 +2738,7 @@ import {
2220
2738
  Wrench,
2221
2739
  Cpu
2222
2740
  } from "lucide-react";
2223
- import { jsx as jsx14, jsxs as jsxs9 } from "react/jsx-runtime";
2741
+ import { jsx as jsx15, jsxs as jsxs10 } from "react/jsx-runtime";
2224
2742
  var MESSAGES_PAGE_SIZE = 50;
2225
2743
  var ThreadDetailView = ({
2226
2744
  threadId,
@@ -2278,36 +2796,36 @@ var ThreadDetailView = ({
2278
2796
  }
2279
2797
  }, [threadId, pageInfo, isLoadingMore, config.baseUrl, config.getRequestHeaders]);
2280
2798
  if (isLoading) {
2281
- return /* @__PURE__ */ jsx14("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx14(Loader2, { className: "h-6 w-6 animate-spin text-muted-foreground" }) });
2799
+ return /* @__PURE__ */ jsx15("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx15(Loader2, { className: "h-6 w-6 animate-spin text-muted-foreground" }) });
2282
2800
  }
2283
2801
  if (error) {
2284
- return /* @__PURE__ */ jsxs9("div", { className: "space-y-4 py-10 text-center", children: [
2285
- /* @__PURE__ */ jsx14("p", { className: "text-destructive font-medium", children: error.message }),
2286
- /* @__PURE__ */ jsxs9("div", { className: "flex justify-center gap-2", children: [
2287
- /* @__PURE__ */ jsxs9(Button, { variant: "outline", onClick: onBack, children: [
2288
- /* @__PURE__ */ jsx14(ArrowLeft, { className: "mr-2 h-4 w-4" }),
2802
+ return /* @__PURE__ */ jsxs10("div", { className: "space-y-4 py-10 text-center", children: [
2803
+ /* @__PURE__ */ jsx15("p", { className: "text-destructive font-medium", children: error.message }),
2804
+ /* @__PURE__ */ jsxs10("div", { className: "flex justify-center gap-2", children: [
2805
+ /* @__PURE__ */ jsxs10(Button, { variant: "outline", onClick: onBack, children: [
2806
+ /* @__PURE__ */ jsx15(ArrowLeft, { className: "mr-2 h-4 w-4" }),
2289
2807
  "Back"
2290
2808
  ] }),
2291
- /* @__PURE__ */ jsx14(Button, { variant: "destructive", onClick: () => void loadInitial(), children: config.labels.retry })
2809
+ /* @__PURE__ */ jsx15(Button, { variant: "destructive", onClick: () => void loadInitial(), children: config.labels.retry })
2292
2810
  ] })
2293
2811
  ] });
2294
2812
  }
2295
- return /* @__PURE__ */ jsxs9("div", { className: "space-y-6", children: [
2296
- /* @__PURE__ */ jsxs9("div", { className: "flex items-start gap-4", children: [
2297
- /* @__PURE__ */ jsx14(
2813
+ return /* @__PURE__ */ jsxs10("div", { className: "space-y-6", children: [
2814
+ /* @__PURE__ */ jsxs10("div", { className: "flex items-start gap-4", children: [
2815
+ /* @__PURE__ */ jsx15(
2298
2816
  Button,
2299
2817
  {
2300
2818
  variant: "ghost",
2301
2819
  size: "icon",
2302
2820
  className: "mt-1 shrink-0",
2303
2821
  onClick: onBack,
2304
- children: /* @__PURE__ */ jsx14(ArrowLeft, { className: "h-4 w-4" })
2822
+ children: /* @__PURE__ */ jsx15(ArrowLeft, { className: "h-4 w-4" })
2305
2823
  }
2306
2824
  ),
2307
- /* @__PURE__ */ jsxs9("div", { className: "flex-1 min-w-0", children: [
2308
- /* @__PURE__ */ jsxs9("div", { className: "flex items-center gap-2", children: [
2309
- /* @__PURE__ */ jsx14("h2", { className: "text-xl font-semibold truncate", children: thread?.name ?? threadId }),
2310
- /* @__PURE__ */ jsx14(
2825
+ /* @__PURE__ */ jsxs10("div", { className: "flex-1 min-w-0", children: [
2826
+ /* @__PURE__ */ jsxs10("div", { className: "flex items-center gap-2", children: [
2827
+ /* @__PURE__ */ jsx15("h2", { className: "text-xl font-semibold truncate", children: thread?.name ?? threadId }),
2828
+ /* @__PURE__ */ jsx15(
2311
2829
  Badge,
2312
2830
  {
2313
2831
  variant: thread?.status === "archived" ? "secondary" : "default",
@@ -2315,31 +2833,31 @@ var ThreadDetailView = ({
2315
2833
  }
2316
2834
  )
2317
2835
  ] }),
2318
- thread?.summary && /* @__PURE__ */ jsx14("p", { className: "mt-1 text-sm text-muted-foreground", children: thread.summary }),
2319
- /* @__PURE__ */ jsxs9("div", { className: "mt-2 flex flex-wrap gap-4 text-xs text-muted-foreground", children: [
2320
- thread?.createdAt && /* @__PURE__ */ jsxs9("span", { children: [
2836
+ thread?.summary && /* @__PURE__ */ jsx15("p", { className: "mt-1 text-sm text-muted-foreground", children: thread.summary }),
2837
+ /* @__PURE__ */ jsxs10("div", { className: "mt-2 flex flex-wrap gap-4 text-xs text-muted-foreground", children: [
2838
+ thread?.createdAt && /* @__PURE__ */ jsxs10("span", { children: [
2321
2839
  "Created ",
2322
- formatDate3(thread.createdAt)
2840
+ formatDate2(thread.createdAt)
2323
2841
  ] }),
2324
- thread?.updatedAt && /* @__PURE__ */ jsxs9("span", { children: [
2842
+ thread?.updatedAt && /* @__PURE__ */ jsxs10("span", { children: [
2325
2843
  "Updated ",
2326
- formatDate3(thread.updatedAt)
2844
+ formatDate2(thread.updatedAt)
2327
2845
  ] }),
2328
- thread?.participants && /* @__PURE__ */ jsxs9("span", { children: [
2846
+ thread?.participants && /* @__PURE__ */ jsxs10("span", { children: [
2329
2847
  thread.participants.length,
2330
2848
  " participants"
2331
2849
  ] })
2332
2850
  ] })
2333
2851
  ] })
2334
2852
  ] }),
2335
- /* @__PURE__ */ jsxs9("div", { className: "space-y-1", children: [
2336
- /* @__PURE__ */ jsx14("div", { className: "flex items-center justify-between", children: /* @__PURE__ */ jsxs9("h3", { className: "text-sm font-medium text-muted-foreground", children: [
2853
+ /* @__PURE__ */ jsxs10("div", { className: "space-y-1", children: [
2854
+ /* @__PURE__ */ jsx15("div", { className: "flex items-center justify-between", children: /* @__PURE__ */ jsxs10("h3", { className: "text-sm font-medium text-muted-foreground", children: [
2337
2855
  "Messages (",
2338
2856
  messages.length,
2339
2857
  pageInfo?.hasMoreBefore ? "+" : "",
2340
2858
  ")"
2341
2859
  ] }) }),
2342
- pageInfo?.hasMoreBefore && /* @__PURE__ */ jsx14("div", { className: "flex justify-center py-2", children: /* @__PURE__ */ jsxs9(
2860
+ pageInfo?.hasMoreBefore && /* @__PURE__ */ jsx15("div", { className: "flex justify-center py-2", children: /* @__PURE__ */ jsxs10(
2343
2861
  Button,
2344
2862
  {
2345
2863
  variant: "ghost",
@@ -2347,12 +2865,12 @@ var ThreadDetailView = ({
2347
2865
  onClick: () => void loadMore(),
2348
2866
  disabled: isLoadingMore,
2349
2867
  children: [
2350
- isLoadingMore ? /* @__PURE__ */ jsx14(Loader2, { className: "mr-2 h-3 w-3 animate-spin" }) : /* @__PURE__ */ jsx14(ChevronUp2, { className: "mr-2 h-3 w-3" }),
2868
+ isLoadingMore ? /* @__PURE__ */ jsx15(Loader2, { className: "mr-2 h-3 w-3 animate-spin" }) : /* @__PURE__ */ jsx15(ChevronUp2, { className: "mr-2 h-3 w-3" }),
2351
2869
  "Load older messages"
2352
2870
  ]
2353
2871
  }
2354
2872
  ) }),
2355
- /* @__PURE__ */ jsx14("div", { className: "rounded-lg border bg-card", children: messages.length === 0 ? /* @__PURE__ */ jsx14("p", { className: "p-6 text-center text-sm text-muted-foreground", children: "No messages in this thread yet." }) : /* @__PURE__ */ jsx14("div", { className: "divide-y", children: messages.map((message) => /* @__PURE__ */ jsx14(MessageRow, { message }, message.id)) }) })
2873
+ /* @__PURE__ */ jsx15("div", { className: "rounded-lg border bg-card", children: messages.length === 0 ? /* @__PURE__ */ jsx15("p", { className: "p-6 text-center text-sm text-muted-foreground", children: "No messages in this thread yet." }) : /* @__PURE__ */ jsx15("div", { className: "divide-y", children: messages.map((message) => /* @__PURE__ */ jsx15(MessageRow, { message }, message.id)) }) })
2356
2874
  ] })
2357
2875
  ] });
2358
2876
  };
@@ -2360,43 +2878,43 @@ function MessageRow({ message }) {
2360
2878
  const [expanded, setExpanded] = useState4(false);
2361
2879
  const hasToolCalls = Array.isArray(message.toolCalls) && message.toolCalls.length > 0;
2362
2880
  const hasReasoning = !!message.reasoning;
2363
- return /* @__PURE__ */ jsx14("div", { className: "px-4 py-3", children: /* @__PURE__ */ jsxs9("div", { className: "flex items-start gap-3", children: [
2364
- /* @__PURE__ */ jsx14(SenderIcon, { senderType: message.senderType }),
2365
- /* @__PURE__ */ jsxs9("div", { className: "flex-1 min-w-0", children: [
2366
- /* @__PURE__ */ jsxs9("div", { className: "flex items-center gap-2 text-xs", children: [
2367
- /* @__PURE__ */ jsx14("span", { className: "font-medium", children: message.senderId ?? message.senderUserId ?? message.senderType }),
2368
- /* @__PURE__ */ jsx14(Badge, { variant: "outline", className: "text-[10px] px-1.5 py-0", children: message.senderType }),
2369
- message.createdAt && /* @__PURE__ */ jsx14("span", { className: "text-muted-foreground", children: formatTimestamp(message.createdAt) })
2881
+ return /* @__PURE__ */ jsx15("div", { className: "px-4 py-3", children: /* @__PURE__ */ jsxs10("div", { className: "flex items-start gap-3", children: [
2882
+ /* @__PURE__ */ jsx15(SenderIcon, { senderType: message.senderType }),
2883
+ /* @__PURE__ */ jsxs10("div", { className: "flex-1 min-w-0", children: [
2884
+ /* @__PURE__ */ jsxs10("div", { className: "flex items-center gap-2 text-xs", children: [
2885
+ /* @__PURE__ */ jsx15("span", { className: "font-medium", children: message.senderId ?? message.senderUserId ?? message.senderType }),
2886
+ /* @__PURE__ */ jsx15(Badge, { variant: "outline", className: "text-[10px] px-1.5 py-0", children: message.senderType }),
2887
+ message.createdAt && /* @__PURE__ */ jsx15("span", { className: "text-muted-foreground", children: formatTimestamp(message.createdAt) })
2370
2888
  ] }),
2371
- message.content && /* @__PURE__ */ jsx14("p", { className: "mt-1 text-sm whitespace-pre-wrap break-words", children: message.content }),
2372
- (hasToolCalls || hasReasoning) && /* @__PURE__ */ jsxs9("div", { className: "mt-2 space-y-2", children: [
2373
- hasToolCalls && /* @__PURE__ */ jsxs9(
2889
+ message.content && /* @__PURE__ */ jsx15("p", { className: "mt-1 text-sm whitespace-pre-wrap break-words", children: message.content }),
2890
+ (hasToolCalls || hasReasoning) && /* @__PURE__ */ jsxs10("div", { className: "mt-2 space-y-2", children: [
2891
+ hasToolCalls && /* @__PURE__ */ jsxs10(
2374
2892
  "button",
2375
2893
  {
2376
2894
  type: "button",
2377
2895
  onClick: () => setExpanded(!expanded),
2378
2896
  className: "inline-flex items-center gap-1 text-xs text-muted-foreground hover:text-foreground transition-colors",
2379
2897
  children: [
2380
- /* @__PURE__ */ jsx14(Wrench, { className: "h-3 w-3" }),
2898
+ /* @__PURE__ */ jsx15(Wrench, { className: "h-3 w-3" }),
2381
2899
  message.toolCalls.length,
2382
2900
  " tool call",
2383
2901
  message.toolCalls.length > 1 ? "s" : ""
2384
2902
  ]
2385
2903
  }
2386
2904
  ),
2387
- hasReasoning && /* @__PURE__ */ jsxs9(
2905
+ hasReasoning && /* @__PURE__ */ jsxs10(
2388
2906
  "button",
2389
2907
  {
2390
2908
  type: "button",
2391
2909
  onClick: () => setExpanded(!expanded),
2392
2910
  className: "inline-flex items-center gap-1 text-xs text-muted-foreground hover:text-foreground transition-colors",
2393
2911
  children: [
2394
- /* @__PURE__ */ jsx14(Cpu, { className: "h-3 w-3" }),
2912
+ /* @__PURE__ */ jsx15(Cpu, { className: "h-3 w-3" }),
2395
2913
  "Reasoning"
2396
2914
  ]
2397
2915
  }
2398
2916
  ),
2399
- expanded && /* @__PURE__ */ jsx14("pre", { className: "mt-2 rounded-md bg-muted p-3 text-xs overflow-auto max-h-60", children: JSON.stringify(
2917
+ expanded && /* @__PURE__ */ jsx15("pre", { className: "mt-2 rounded-md bg-muted p-3 text-xs overflow-auto max-h-60", children: JSON.stringify(
2400
2918
  {
2401
2919
  ...hasToolCalls ? { toolCalls: message.toolCalls } : {},
2402
2920
  ...hasReasoning ? { reasoning: message.reasoning } : {}
@@ -2412,16 +2930,16 @@ function SenderIcon({ senderType }) {
2412
2930
  const base = "flex h-7 w-7 shrink-0 items-center justify-center rounded-full";
2413
2931
  switch (senderType) {
2414
2932
  case "agent":
2415
- return /* @__PURE__ */ jsx14("div", { className: cn(base, "bg-primary/10 text-primary"), children: /* @__PURE__ */ jsx14(Bot2, { className: "h-3.5 w-3.5" }) });
2933
+ return /* @__PURE__ */ jsx15("div", { className: cn(base, "bg-primary/10 text-primary"), children: /* @__PURE__ */ jsx15(Bot2, { className: "h-3.5 w-3.5" }) });
2416
2934
  case "user":
2417
- return /* @__PURE__ */ jsx14("div", { className: cn(base, "bg-secondary text-secondary-foreground"), children: /* @__PURE__ */ jsx14(User, { className: "h-3.5 w-3.5" }) });
2935
+ return /* @__PURE__ */ jsx15("div", { className: cn(base, "bg-secondary text-secondary-foreground"), children: /* @__PURE__ */ jsx15(User, { className: "h-3.5 w-3.5" }) });
2418
2936
  case "tool":
2419
- return /* @__PURE__ */ jsx14("div", { className: cn(base, "bg-muted text-muted-foreground"), children: /* @__PURE__ */ jsx14(Wrench, { className: "h-3.5 w-3.5" }) });
2937
+ return /* @__PURE__ */ jsx15("div", { className: cn(base, "bg-muted text-muted-foreground"), children: /* @__PURE__ */ jsx15(Wrench, { className: "h-3.5 w-3.5" }) });
2420
2938
  default:
2421
- return /* @__PURE__ */ jsx14("div", { className: cn(base, "bg-muted text-muted-foreground"), children: /* @__PURE__ */ jsx14(Cpu, { className: "h-3.5 w-3.5" }) });
2939
+ return /* @__PURE__ */ jsx15("div", { className: cn(base, "bg-muted text-muted-foreground"), children: /* @__PURE__ */ jsx15(Cpu, { className: "h-3.5 w-3.5" }) });
2422
2940
  }
2423
2941
  }
2424
- function formatDate3(value) {
2942
+ function formatDate2(value) {
2425
2943
  const date = new Date(value);
2426
2944
  if (Number.isNaN(date.getTime())) return value;
2427
2945
  return date.toLocaleDateString(void 0, {
@@ -2443,8 +2961,8 @@ function formatTimestamp(value) {
2443
2961
  }
2444
2962
 
2445
2963
  // src/components/views/ParticipantsView.tsx
2446
- import { Search as Search2, Users as Users2 } from "lucide-react";
2447
- import { jsx as jsx15, jsxs as jsxs10 } from "react/jsx-runtime";
2964
+ import { Search as Search3, Users as Users3 } from "lucide-react";
2965
+ import { jsx as jsx16, jsxs as jsxs11 } from "react/jsx-runtime";
2448
2966
  var ParticipantsView = ({
2449
2967
  config,
2450
2968
  participants,
@@ -2452,10 +2970,10 @@ var ParticipantsView = ({
2452
2970
  onSearchChange,
2453
2971
  onParticipantClick
2454
2972
  }) => {
2455
- return /* @__PURE__ */ jsxs10("div", { className: "space-y-4", children: [
2456
- /* @__PURE__ */ jsxs10("div", { className: "relative max-w-sm", children: [
2457
- /* @__PURE__ */ jsx15(Search2, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
2458
- /* @__PURE__ */ jsx15(
2973
+ return /* @__PURE__ */ jsxs11("div", { className: "space-y-4", children: [
2974
+ /* @__PURE__ */ jsxs11("div", { className: "relative max-w-sm", children: [
2975
+ /* @__PURE__ */ jsx16(Search3, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
2976
+ /* @__PURE__ */ jsx16(
2459
2977
  Input,
2460
2978
  {
2461
2979
  className: "pl-9",
@@ -2465,33 +2983,33 @@ var ParticipantsView = ({
2465
2983
  }
2466
2984
  )
2467
2985
  ] }),
2468
- participants.length === 0 ? /* @__PURE__ */ jsxs10("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
2469
- /* @__PURE__ */ jsx15(Users2, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
2470
- /* @__PURE__ */ jsx15("p", { className: "mt-3 text-sm text-muted-foreground", children: searchValue ? config.labels.noResults : config.labels.emptyDescription })
2471
- ] }) : /* @__PURE__ */ jsx15("div", { className: "space-y-2", children: participants.map((p) => /* @__PURE__ */ jsxs10(
2986
+ participants.length === 0 ? /* @__PURE__ */ jsxs11("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
2987
+ /* @__PURE__ */ jsx16(Users3, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
2988
+ /* @__PURE__ */ jsx16("p", { className: "mt-3 text-sm text-muted-foreground", children: searchValue ? config.labels.noResults : config.labels.emptyDescription })
2989
+ ] }) : /* @__PURE__ */ jsx16("div", { className: "space-y-2", children: participants.map((p) => /* @__PURE__ */ jsxs11(
2472
2990
  "div",
2473
2991
  {
2474
2992
  className: "flex items-center gap-4 rounded-lg border bg-card p-4 transition-colors hover:bg-muted/50 cursor-pointer",
2475
2993
  onClick: () => onParticipantClick?.(p.externalId),
2476
2994
  children: [
2477
- /* @__PURE__ */ jsxs10("div", { className: "flex-1 min-w-0", children: [
2478
- /* @__PURE__ */ jsxs10("div", { className: "flex items-center gap-2", children: [
2479
- /* @__PURE__ */ jsx15("p", { className: "font-medium truncate", children: p.displayName }),
2480
- /* @__PURE__ */ jsx15(Badge, { variant: "outline", className: "shrink-0 text-xs", children: p.participantType }),
2481
- /* @__PURE__ */ jsx15(Badge, { variant: p.isGlobal ? "default" : "secondary", className: "shrink-0 text-xs", children: p.isGlobal ? config.labels.scopeGlobal : config.labels.scopeScoped })
2995
+ /* @__PURE__ */ jsxs11("div", { className: "flex-1 min-w-0", children: [
2996
+ /* @__PURE__ */ jsxs11("div", { className: "flex items-center gap-2", children: [
2997
+ /* @__PURE__ */ jsx16("p", { className: "font-medium truncate", children: p.displayName }),
2998
+ /* @__PURE__ */ jsx16(Badge, { variant: "outline", className: "shrink-0 text-xs", children: p.participantType }),
2999
+ /* @__PURE__ */ jsx16(Badge, { variant: p.isGlobal ? "default" : "secondary", className: "shrink-0 text-xs", children: p.isGlobal ? config.labels.scopeGlobal : config.labels.scopeScoped })
2482
3000
  ] }),
2483
- /* @__PURE__ */ jsx15("p", { className: "mt-1 text-xs text-muted-foreground", children: p.externalId })
3001
+ /* @__PURE__ */ jsx16("p", { className: "mt-1 text-xs text-muted-foreground", children: p.externalId })
2484
3002
  ] }),
2485
- /* @__PURE__ */ jsxs10("div", { className: "text-right text-xs text-muted-foreground shrink-0 space-y-1", children: [
2486
- /* @__PURE__ */ jsxs10("p", { children: [
3003
+ /* @__PURE__ */ jsxs11("div", { className: "text-right text-xs text-muted-foreground shrink-0 space-y-1", children: [
3004
+ /* @__PURE__ */ jsxs11("p", { children: [
2487
3005
  formatNumber3(p.messageCount),
2488
3006
  " messages"
2489
3007
  ] }),
2490
- /* @__PURE__ */ jsxs10("p", { children: [
3008
+ /* @__PURE__ */ jsxs11("p", { children: [
2491
3009
  formatNumber3(p.threadCount),
2492
3010
  " threads"
2493
3011
  ] }),
2494
- /* @__PURE__ */ jsx15("p", { children: formatDate4(p.lastActivityAt) })
3012
+ /* @__PURE__ */ jsx16("p", { children: formatDate3(p.lastActivityAt) })
2495
3013
  ] })
2496
3014
  ]
2497
3015
  },
@@ -2499,7 +3017,7 @@ var ParticipantsView = ({
2499
3017
  )) })
2500
3018
  ] });
2501
3019
  };
2502
- function formatDate4(value) {
3020
+ function formatDate3(value) {
2503
3021
  if (!value) return "No activity";
2504
3022
  const date = new Date(value);
2505
3023
  if (Number.isNaN(date.getTime())) return value;
@@ -2512,7 +3030,7 @@ function formatNumber3(value) {
2512
3030
  // src/components/views/ParticipantDetailView.tsx
2513
3031
  import { useCallback as useCallback4, useEffect as useEffect6, useState as useState5 } from "react";
2514
3032
  import { ArrowLeft as ArrowLeft2, Loader2 as Loader22, Save } from "lucide-react";
2515
- import { jsx as jsx16, jsxs as jsxs11 } from "react/jsx-runtime";
3033
+ import { jsx as jsx17, jsxs as jsxs12 } from "react/jsx-runtime";
2516
3034
  var ParticipantDetailView = ({
2517
3035
  participantId,
2518
3036
  config,
@@ -2562,25 +3080,25 @@ var ParticipantDetailView = ({
2562
3080
  }
2563
3081
  };
2564
3082
  if (isLoading) {
2565
- return /* @__PURE__ */ jsx16("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx16(Loader22, { className: "h-6 w-6 animate-spin text-muted-foreground" }) });
3083
+ return /* @__PURE__ */ jsx17("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx17(Loader22, { className: "h-6 w-6 animate-spin text-muted-foreground" }) });
2566
3084
  }
2567
- return /* @__PURE__ */ jsxs11("div", { className: "space-y-6", children: [
2568
- /* @__PURE__ */ jsxs11("div", { className: "flex items-center gap-4", children: [
2569
- /* @__PURE__ */ jsx16(Button, { variant: "ghost", size: "icon", onClick: onBack, children: /* @__PURE__ */ jsx16(ArrowLeft2, { className: "h-4 w-4" }) }),
2570
- /* @__PURE__ */ jsxs11("div", { className: "flex-1 min-w-0", children: [
2571
- /* @__PURE__ */ jsx16("h2", { className: "text-xl font-semibold truncate", children: participantId }),
2572
- /* @__PURE__ */ jsx16("p", { className: "text-sm text-muted-foreground", children: "Participant Detail" })
3085
+ return /* @__PURE__ */ jsxs12("div", { className: "space-y-6", children: [
3086
+ /* @__PURE__ */ jsxs12("div", { className: "flex items-center gap-4", children: [
3087
+ /* @__PURE__ */ jsx17(Button, { variant: "ghost", size: "icon", onClick: onBack, children: /* @__PURE__ */ jsx17(ArrowLeft2, { className: "h-4 w-4" }) }),
3088
+ /* @__PURE__ */ jsxs12("div", { className: "flex-1 min-w-0", children: [
3089
+ /* @__PURE__ */ jsx17("h2", { className: "text-xl font-semibold truncate", children: participantId }),
3090
+ /* @__PURE__ */ jsx17("p", { className: "text-sm text-muted-foreground", children: "Participant Detail" })
2573
3091
  ] }),
2574
- /* @__PURE__ */ jsxs11("div", { className: "flex items-center gap-2", children: [
2575
- saveMessage && /* @__PURE__ */ jsx16("span", { className: "text-xs text-emerald-600", children: saveMessage }),
2576
- /* @__PURE__ */ jsxs11(Button, { size: "sm", onClick: () => void handleSave(), disabled: isSaving, children: [
2577
- isSaving ? /* @__PURE__ */ jsx16(Loader22, { className: "mr-2 h-3 w-3 animate-spin" }) : /* @__PURE__ */ jsx16(Save, { className: "mr-2 h-3 w-3" }),
3092
+ /* @__PURE__ */ jsxs12("div", { className: "flex items-center gap-2", children: [
3093
+ saveMessage && /* @__PURE__ */ jsx17("span", { className: "text-xs text-emerald-600", children: saveMessage }),
3094
+ /* @__PURE__ */ jsxs12(Button, { size: "sm", onClick: () => void handleSave(), disabled: isSaving, children: [
3095
+ isSaving ? /* @__PURE__ */ jsx17(Loader22, { className: "mr-2 h-3 w-3 animate-spin" }) : /* @__PURE__ */ jsx17(Save, { className: "mr-2 h-3 w-3" }),
2578
3096
  "Save"
2579
3097
  ] })
2580
3098
  ] })
2581
3099
  ] }),
2582
- error && /* @__PURE__ */ jsx16("div", { className: "rounded-lg border border-destructive/50 bg-destructive/10 p-3 text-sm text-destructive", children: error }),
2583
- /* @__PURE__ */ jsx16("div", { className: "rounded-lg border bg-card", children: /* @__PURE__ */ jsx16(
3100
+ error && /* @__PURE__ */ jsx17("div", { className: "rounded-lg border border-destructive/50 bg-destructive/10 p-3 text-sm text-destructive", children: error }),
3101
+ /* @__PURE__ */ jsx17("div", { className: "rounded-lg border bg-card", children: /* @__PURE__ */ jsx17(
2584
3102
  "textarea",
2585
3103
  {
2586
3104
  className: "w-full min-h-[400px] p-4 font-mono text-sm bg-transparent resize-y focus:outline-none",
@@ -2593,8 +3111,8 @@ var ParticipantDetailView = ({
2593
3111
  };
2594
3112
 
2595
3113
  // src/components/views/AgentsView.tsx
2596
- import { Search as Search3, Bot as Bot3 } from "lucide-react";
2597
- import { jsx as jsx17, jsxs as jsxs12 } from "react/jsx-runtime";
3114
+ import { Search as Search4, Bot as Bot3 } from "lucide-react";
3115
+ import { jsx as jsx18, jsxs as jsxs13 } from "react/jsx-runtime";
2598
3116
  var AgentsView = ({
2599
3117
  config,
2600
3118
  agents,
@@ -2602,10 +3120,10 @@ var AgentsView = ({
2602
3120
  onSearchChange,
2603
3121
  onAgentClick
2604
3122
  }) => {
2605
- return /* @__PURE__ */ jsxs12("div", { className: "space-y-4", children: [
2606
- /* @__PURE__ */ jsxs12("div", { className: "relative max-w-sm", children: [
2607
- /* @__PURE__ */ jsx17(Search3, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
2608
- /* @__PURE__ */ jsx17(
3123
+ return /* @__PURE__ */ jsxs13("div", { className: "space-y-4", children: [
3124
+ /* @__PURE__ */ jsxs13("div", { className: "relative max-w-sm", children: [
3125
+ /* @__PURE__ */ jsx18(Search4, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
3126
+ /* @__PURE__ */ jsx18(
2609
3127
  Input,
2610
3128
  {
2611
3129
  className: "pl-9",
@@ -2615,48 +3133,48 @@ var AgentsView = ({
2615
3133
  }
2616
3134
  )
2617
3135
  ] }),
2618
- agents.length === 0 ? /* @__PURE__ */ jsxs12("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
2619
- /* @__PURE__ */ jsx17(Bot3, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
2620
- /* @__PURE__ */ jsx17("p", { className: "mt-3 text-sm text-muted-foreground", children: searchValue ? config.labels.noResults : config.labels.emptyDescription })
2621
- ] }) : /* @__PURE__ */ jsx17("div", { className: "grid gap-4 md:grid-cols-2 lg:grid-cols-3", children: agents.map((agent) => /* @__PURE__ */ jsxs12(
3136
+ agents.length === 0 ? /* @__PURE__ */ jsxs13("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
3137
+ /* @__PURE__ */ jsx18(Bot3, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
3138
+ /* @__PURE__ */ jsx18("p", { className: "mt-3 text-sm text-muted-foreground", children: searchValue ? config.labels.noResults : config.labels.emptyDescription })
3139
+ ] }) : /* @__PURE__ */ jsx18("div", { className: "grid gap-4 md:grid-cols-2 lg:grid-cols-3", children: agents.map((agent) => /* @__PURE__ */ jsxs13(
2622
3140
  "div",
2623
3141
  {
2624
3142
  className: "rounded-lg border bg-card p-5 transition-colors hover:bg-muted/50 cursor-pointer",
2625
3143
  onClick: () => onAgentClick?.(agent.agentId),
2626
3144
  children: [
2627
- /* @__PURE__ */ jsxs12("div", { className: "flex items-start justify-between gap-3", children: [
2628
- /* @__PURE__ */ jsxs12("div", { className: "min-w-0", children: [
2629
- /* @__PURE__ */ jsx17("p", { className: "font-medium truncate", children: agent.displayName }),
2630
- /* @__PURE__ */ jsx17("p", { className: "mt-1 truncate text-xs text-muted-foreground", children: agent.description ?? agent.agentId })
3145
+ /* @__PURE__ */ jsxs13("div", { className: "flex items-start justify-between gap-3", children: [
3146
+ /* @__PURE__ */ jsxs13("div", { className: "min-w-0", children: [
3147
+ /* @__PURE__ */ jsx18("p", { className: "font-medium truncate", children: agent.displayName }),
3148
+ /* @__PURE__ */ jsx18("p", { className: "mt-1 truncate text-xs text-muted-foreground", children: agent.description ?? agent.agentId })
2631
3149
  ] }),
2632
- /* @__PURE__ */ jsx17(Badge, { variant: "outline", className: "shrink-0", children: agent.isConfigured ? config.labels.configured : config.labels.unconfigured })
3150
+ /* @__PURE__ */ jsx18(Badge, { variant: "outline", className: "shrink-0", children: agent.isConfigured ? config.labels.configured : config.labels.unconfigured })
2633
3151
  ] }),
2634
- /* @__PURE__ */ jsxs12("div", { className: "mt-4 grid grid-cols-2 gap-2 text-xs text-muted-foreground", children: [
2635
- /* @__PURE__ */ jsxs12("span", { children: [
3152
+ /* @__PURE__ */ jsxs13("div", { className: "mt-4 grid grid-cols-2 gap-2 text-xs text-muted-foreground", children: [
3153
+ /* @__PURE__ */ jsxs13("span", { children: [
2636
3154
  formatNumber4(agent.messageCount),
2637
3155
  " messages"
2638
3156
  ] }),
2639
- /* @__PURE__ */ jsxs12("span", { children: [
3157
+ /* @__PURE__ */ jsxs13("span", { children: [
2640
3158
  formatNumber4(agent.llmCallCount),
2641
3159
  " LLM calls"
2642
3160
  ] }),
2643
- /* @__PURE__ */ jsxs12("span", { children: [
3161
+ /* @__PURE__ */ jsxs13("span", { children: [
2644
3162
  formatNumber4(agent.toolCallMessageCount),
2645
3163
  " tool calls"
2646
3164
  ] }),
2647
- /* @__PURE__ */ jsxs12("span", { children: [
3165
+ /* @__PURE__ */ jsxs13("span", { children: [
2648
3166
  formatNumber4(agent.totalTokens),
2649
3167
  " tokens"
2650
3168
  ] })
2651
3169
  ] }),
2652
- /* @__PURE__ */ jsx17("p", { className: "mt-3 text-xs text-muted-foreground", children: formatDate5(agent.lastActivityAt) })
3170
+ /* @__PURE__ */ jsx18("p", { className: "mt-3 text-xs text-muted-foreground", children: formatDate4(agent.lastActivityAt) })
2653
3171
  ]
2654
3172
  },
2655
3173
  `${agent.namespace}:${agent.agentId}`
2656
3174
  )) })
2657
3175
  ] });
2658
3176
  };
2659
- function formatDate5(value) {
3177
+ function formatDate4(value) {
2660
3178
  if (!value) return "No activity";
2661
3179
  const date = new Date(value);
2662
3180
  if (Number.isNaN(date.getTime())) return value;
@@ -2668,7 +3186,7 @@ function formatNumber4(value) {
2668
3186
 
2669
3187
  // src/components/views/AgentDetailView.tsx
2670
3188
  import { ArrowLeft as ArrowLeft3, Bot as Bot4 } from "lucide-react";
2671
- import { jsx as jsx18, jsxs as jsxs13 } from "react/jsx-runtime";
3189
+ import { jsx as jsx19, jsxs as jsxs14 } from "react/jsx-runtime";
2672
3190
  var AgentDetailView = ({
2673
3191
  agentId,
2674
3192
  config,
@@ -2677,13 +3195,13 @@ var AgentDetailView = ({
2677
3195
  }) => {
2678
3196
  const agent = agents.find((a) => a.agentId === agentId);
2679
3197
  if (!agent) {
2680
- return /* @__PURE__ */ jsxs13("div", { className: "space-y-4 py-10 text-center", children: [
2681
- /* @__PURE__ */ jsxs13("p", { className: "text-muted-foreground", children: [
3198
+ return /* @__PURE__ */ jsxs14("div", { className: "space-y-4 py-10 text-center", children: [
3199
+ /* @__PURE__ */ jsxs14("p", { className: "text-muted-foreground", children: [
2682
3200
  "Agent not found: ",
2683
3201
  agentId
2684
3202
  ] }),
2685
- /* @__PURE__ */ jsxs13(Button, { variant: "outline", onClick: onBack, children: [
2686
- /* @__PURE__ */ jsx18(ArrowLeft3, { className: "mr-2 h-4 w-4" }),
3203
+ /* @__PURE__ */ jsxs14(Button, { variant: "outline", onClick: onBack, children: [
3204
+ /* @__PURE__ */ jsx19(ArrowLeft3, { className: "mr-2 h-4 w-4" }),
2687
3205
  " Back"
2688
3206
  ] })
2689
3207
  ] });
@@ -2699,43 +3217,43 @@ var AgentDetailView = ({
2699
3217
  { label: "Cache Created", value: agent.cacheCreationInputTokens },
2700
3218
  { label: "Total Tokens", value: agent.totalTokens }
2701
3219
  ];
2702
- return /* @__PURE__ */ jsxs13("div", { className: "space-y-6", children: [
2703
- /* @__PURE__ */ jsxs13("div", { className: "flex items-start gap-4", children: [
2704
- /* @__PURE__ */ jsx18(Button, { variant: "ghost", size: "icon", className: "mt-1 shrink-0", onClick: onBack, children: /* @__PURE__ */ jsx18(ArrowLeft3, { className: "h-4 w-4" }) }),
2705
- /* @__PURE__ */ jsxs13("div", { className: "flex-1 min-w-0", children: [
2706
- /* @__PURE__ */ jsxs13("div", { className: "flex items-center gap-3", children: [
2707
- /* @__PURE__ */ jsx18("div", { className: "flex h-10 w-10 shrink-0 items-center justify-center rounded-lg bg-primary/10 text-primary", children: /* @__PURE__ */ jsx18(Bot4, { className: "h-5 w-5" }) }),
2708
- /* @__PURE__ */ jsxs13("div", { children: [
2709
- /* @__PURE__ */ jsxs13("div", { className: "flex items-center gap-2", children: [
2710
- /* @__PURE__ */ jsx18("h2", { className: "text-xl font-semibold", children: agent.displayName }),
2711
- /* @__PURE__ */ jsx18(Badge, { variant: "outline", children: agent.isConfigured ? config.labels.configured : config.labels.unconfigured })
3220
+ return /* @__PURE__ */ jsxs14("div", { className: "space-y-6", children: [
3221
+ /* @__PURE__ */ jsxs14("div", { className: "flex items-start gap-4", children: [
3222
+ /* @__PURE__ */ jsx19(Button, { variant: "ghost", size: "icon", className: "mt-1 shrink-0", onClick: onBack, children: /* @__PURE__ */ jsx19(ArrowLeft3, { className: "h-4 w-4" }) }),
3223
+ /* @__PURE__ */ jsxs14("div", { className: "flex-1 min-w-0", children: [
3224
+ /* @__PURE__ */ jsxs14("div", { className: "flex items-center gap-3", children: [
3225
+ /* @__PURE__ */ jsx19("div", { className: "flex h-10 w-10 shrink-0 items-center justify-center rounded-lg bg-primary/10 text-primary", children: /* @__PURE__ */ jsx19(Bot4, { className: "h-5 w-5" }) }),
3226
+ /* @__PURE__ */ jsxs14("div", { children: [
3227
+ /* @__PURE__ */ jsxs14("div", { className: "flex items-center gap-2", children: [
3228
+ /* @__PURE__ */ jsx19("h2", { className: "text-xl font-semibold", children: agent.displayName }),
3229
+ /* @__PURE__ */ jsx19(Badge, { variant: "outline", children: agent.isConfigured ? config.labels.configured : config.labels.unconfigured })
2712
3230
  ] }),
2713
- agent.description && /* @__PURE__ */ jsx18("p", { className: "text-sm text-muted-foreground", children: agent.description })
3231
+ agent.description && /* @__PURE__ */ jsx19("p", { className: "text-sm text-muted-foreground", children: agent.description })
2714
3232
  ] })
2715
3233
  ] }),
2716
- /* @__PURE__ */ jsxs13("div", { className: "mt-2 flex flex-wrap gap-4 text-xs text-muted-foreground", children: [
2717
- /* @__PURE__ */ jsxs13("span", { children: [
3234
+ /* @__PURE__ */ jsxs14("div", { className: "mt-2 flex flex-wrap gap-4 text-xs text-muted-foreground", children: [
3235
+ /* @__PURE__ */ jsxs14("span", { children: [
2718
3236
  "ID: ",
2719
3237
  agent.agentId
2720
3238
  ] }),
2721
- /* @__PURE__ */ jsxs13("span", { children: [
3239
+ /* @__PURE__ */ jsxs14("span", { children: [
2722
3240
  "Namespace: ",
2723
3241
  agent.namespace
2724
3242
  ] }),
2725
- agent.lastActivityAt && /* @__PURE__ */ jsxs13("span", { children: [
3243
+ agent.lastActivityAt && /* @__PURE__ */ jsxs14("span", { children: [
2726
3244
  "Last active: ",
2727
- formatDate6(agent.lastActivityAt)
3245
+ formatDate5(agent.lastActivityAt)
2728
3246
  ] })
2729
3247
  ] })
2730
3248
  ] })
2731
3249
  ] }),
2732
- /* @__PURE__ */ jsx18("div", { className: "grid gap-4 sm:grid-cols-3 lg:grid-cols-3", children: stats.map((stat) => /* @__PURE__ */ jsxs13("div", { className: "rounded-xl border bg-card p-5 shadow-sm", children: [
2733
- /* @__PURE__ */ jsx18("p", { className: "text-sm font-medium text-muted-foreground", children: stat.label }),
2734
- /* @__PURE__ */ jsx18("p", { className: "mt-2 text-2xl font-semibold tracking-tight", children: new Intl.NumberFormat().format(stat.value) })
3250
+ /* @__PURE__ */ jsx19("div", { className: "grid gap-4 sm:grid-cols-3 lg:grid-cols-3", children: stats.map((stat) => /* @__PURE__ */ jsxs14("div", { className: "rounded-xl border bg-card p-5 shadow-sm", children: [
3251
+ /* @__PURE__ */ jsx19("p", { className: "text-sm font-medium text-muted-foreground", children: stat.label }),
3252
+ /* @__PURE__ */ jsx19("p", { className: "mt-2 text-2xl font-semibold tracking-tight", children: new Intl.NumberFormat().format(stat.value) })
2735
3253
  ] }, stat.label)) })
2736
3254
  ] });
2737
3255
  };
2738
- function formatDate6(value) {
3256
+ function formatDate5(value) {
2739
3257
  const date = new Date(value);
2740
3258
  if (Number.isNaN(date.getTime())) return value;
2741
3259
  return date.toLocaleString(void 0, { month: "short", day: "numeric", hour: "numeric", minute: "2-digit" });
@@ -2743,8 +3261,8 @@ function formatDate6(value) {
2743
3261
 
2744
3262
  // src/components/views/CollectionItemsView.tsx
2745
3263
  import { useCallback as useCallback5, useEffect as useEffect7, useState as useState6 } from "react";
2746
- import { Loader2 as Loader23, Plus, Search as Search4, Database as Database2 } from "lucide-react";
2747
- import { jsx as jsx19, jsxs as jsxs14 } from "react/jsx-runtime";
3264
+ import { Loader2 as Loader23, Plus, Search as Search5, Database as Database3 } from "lucide-react";
3265
+ import { jsx as jsx20, jsxs as jsxs15 } from "react/jsx-runtime";
2748
3266
  var CollectionItemsView = ({
2749
3267
  collection,
2750
3268
  config,
@@ -2790,17 +3308,17 @@ var CollectionItemsView = ({
2790
3308
  if (keys.length === 0) return "(empty)";
2791
3309
  return keys.slice(0, 3).map((k) => `${k}: ${JSON.stringify(rest[k])?.slice(0, 30)}`).join(", ");
2792
3310
  };
2793
- return /* @__PURE__ */ jsxs14("div", { className: "space-y-4", children: [
2794
- /* @__PURE__ */ jsxs14("div", { className: "flex items-center justify-between gap-4", children: [
2795
- /* @__PURE__ */ jsx19("h2", { className: "text-lg font-semibold capitalize", children: collection }),
2796
- onCreateNew && /* @__PURE__ */ jsxs14(Button, { size: "sm", onClick: onCreateNew, children: [
2797
- /* @__PURE__ */ jsx19(Plus, { className: "mr-2 h-3 w-3" }),
3311
+ return /* @__PURE__ */ jsxs15("div", { className: "space-y-4", children: [
3312
+ /* @__PURE__ */ jsxs15("div", { className: "flex items-center justify-between gap-4", children: [
3313
+ /* @__PURE__ */ jsx20("h2", { className: "text-lg font-semibold capitalize", children: collection }),
3314
+ onCreateNew && /* @__PURE__ */ jsxs15(Button, { size: "sm", onClick: onCreateNew, children: [
3315
+ /* @__PURE__ */ jsx20(Plus, { className: "mr-2 h-3 w-3" }),
2798
3316
  " New"
2799
3317
  ] })
2800
3318
  ] }),
2801
- /* @__PURE__ */ jsxs14("div", { className: "relative max-w-sm", children: [
2802
- /* @__PURE__ */ jsx19(Search4, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
2803
- /* @__PURE__ */ jsx19(
3319
+ /* @__PURE__ */ jsxs15("div", { className: "relative max-w-sm", children: [
3320
+ /* @__PURE__ */ jsx20(Search5, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
3321
+ /* @__PURE__ */ jsx20(
2804
3322
  Input,
2805
3323
  {
2806
3324
  className: "pl-9",
@@ -2810,20 +3328,20 @@ var CollectionItemsView = ({
2810
3328
  }
2811
3329
  )
2812
3330
  ] }),
2813
- error && /* @__PURE__ */ jsx19("div", { className: "rounded-lg border border-destructive/50 bg-destructive/10 p-3 text-sm text-destructive", children: error }),
2814
- isLoading ? /* @__PURE__ */ jsx19("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx19(Loader23, { className: "h-6 w-6 animate-spin text-muted-foreground" }) }) : items.length === 0 ? /* @__PURE__ */ jsxs14("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
2815
- /* @__PURE__ */ jsx19(Database2, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
2816
- /* @__PURE__ */ jsx19("p", { className: "mt-3 text-sm text-muted-foreground", children: search ? config.labels.noResults : `No items in ${collection}` })
2817
- ] }) : /* @__PURE__ */ jsx19("div", { className: "space-y-2", children: items.map((item, idx) => {
3331
+ error && /* @__PURE__ */ jsx20("div", { className: "rounded-lg border border-destructive/50 bg-destructive/10 p-3 text-sm text-destructive", children: error }),
3332
+ isLoading ? /* @__PURE__ */ jsx20("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx20(Loader23, { className: "h-6 w-6 animate-spin text-muted-foreground" }) }) : items.length === 0 ? /* @__PURE__ */ jsxs15("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
3333
+ /* @__PURE__ */ jsx20(Database3, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
3334
+ /* @__PURE__ */ jsx20("p", { className: "mt-3 text-sm text-muted-foreground", children: search ? config.labels.noResults : `No items in ${collection}` })
3335
+ ] }) : /* @__PURE__ */ jsx20("div", { className: "space-y-2", children: items.map((item, idx) => {
2818
3336
  const itemId = getItemId(item);
2819
- return /* @__PURE__ */ jsx19(
3337
+ return /* @__PURE__ */ jsx20(
2820
3338
  "div",
2821
3339
  {
2822
3340
  className: "flex items-center gap-4 rounded-lg border bg-card p-4 transition-colors hover:bg-muted/50 cursor-pointer",
2823
3341
  onClick: () => onItemClick?.(itemId),
2824
- children: /* @__PURE__ */ jsxs14("div", { className: "flex-1 min-w-0", children: [
2825
- /* @__PURE__ */ jsx19("p", { className: "font-medium font-mono text-sm truncate", children: itemId }),
2826
- /* @__PURE__ */ jsx19("p", { className: "mt-1 text-xs text-muted-foreground truncate", children: getItemPreview(item) })
3342
+ children: /* @__PURE__ */ jsxs15("div", { className: "flex-1 min-w-0", children: [
3343
+ /* @__PURE__ */ jsx20("p", { className: "font-medium font-mono text-sm truncate", children: itemId }),
3344
+ /* @__PURE__ */ jsx20("p", { className: "mt-1 text-xs text-muted-foreground truncate", children: getItemPreview(item) })
2827
3345
  ] })
2828
3346
  },
2829
3347
  itemId + idx
@@ -2835,7 +3353,7 @@ var CollectionItemsView = ({
2835
3353
  // src/components/views/CollectionItemDetailView.tsx
2836
3354
  import { useCallback as useCallback6, useEffect as useEffect8, useState as useState7 } from "react";
2837
3355
  import { ArrowLeft as ArrowLeft5, Loader2 as Loader24, Save as Save2, Trash2 } from "lucide-react";
2838
- import { jsx as jsx20, jsxs as jsxs15 } from "react/jsx-runtime";
3356
+ import { jsx as jsx21, jsxs as jsxs16 } from "react/jsx-runtime";
2839
3357
  var CollectionItemDetailView = ({
2840
3358
  collection,
2841
3359
  itemId,
@@ -2909,15 +3427,15 @@ var CollectionItemDetailView = ({
2909
3427
  }
2910
3428
  };
2911
3429
  if (isLoading) {
2912
- return /* @__PURE__ */ jsx20("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx20(Loader24, { className: "h-6 w-6 animate-spin text-muted-foreground" }) });
3430
+ return /* @__PURE__ */ jsx21("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx21(Loader24, { className: "h-6 w-6 animate-spin text-muted-foreground" }) });
2913
3431
  }
2914
- return /* @__PURE__ */ jsxs15("div", { className: "space-y-6", children: [
2915
- /* @__PURE__ */ jsxs15("div", { className: "flex items-center gap-4", children: [
2916
- /* @__PURE__ */ jsx20(Button, { variant: "ghost", size: "icon", onClick: onBack, children: /* @__PURE__ */ jsx20(ArrowLeft5, { className: "h-4 w-4" }) }),
2917
- /* @__PURE__ */ jsx20("div", { className: "flex-1 min-w-0", children: /* @__PURE__ */ jsx20("h2", { className: "text-xl font-semibold truncate capitalize", children: isNew ? `New ${collection} item` : `${collection} / ${itemId}` }) }),
2918
- /* @__PURE__ */ jsxs15("div", { className: "flex items-center gap-2", children: [
2919
- saveMessage && /* @__PURE__ */ jsx20("span", { className: "text-xs text-emerald-600", children: saveMessage }),
2920
- !isNew && /* @__PURE__ */ jsxs15(
3432
+ return /* @__PURE__ */ jsxs16("div", { className: "space-y-6", children: [
3433
+ /* @__PURE__ */ jsxs16("div", { className: "flex items-center gap-4", children: [
3434
+ /* @__PURE__ */ jsx21(Button, { variant: "ghost", size: "icon", onClick: onBack, children: /* @__PURE__ */ jsx21(ArrowLeft5, { className: "h-4 w-4" }) }),
3435
+ /* @__PURE__ */ jsx21("div", { className: "flex-1 min-w-0", children: /* @__PURE__ */ jsx21("h2", { className: "text-xl font-semibold truncate capitalize", children: isNew ? `New ${collection} item` : `${collection} / ${itemId}` }) }),
3436
+ /* @__PURE__ */ jsxs16("div", { className: "flex items-center gap-2", children: [
3437
+ saveMessage && /* @__PURE__ */ jsx21("span", { className: "text-xs text-emerald-600", children: saveMessage }),
3438
+ !isNew && /* @__PURE__ */ jsxs16(
2921
3439
  Button,
2922
3440
  {
2923
3441
  variant: "destructive",
@@ -2925,19 +3443,19 @@ var CollectionItemDetailView = ({
2925
3443
  onClick: () => void handleDelete(),
2926
3444
  disabled: isDeleting,
2927
3445
  children: [
2928
- isDeleting ? /* @__PURE__ */ jsx20(Loader24, { className: "mr-2 h-3 w-3 animate-spin" }) : /* @__PURE__ */ jsx20(Trash2, { className: "mr-2 h-3 w-3" }),
3446
+ isDeleting ? /* @__PURE__ */ jsx21(Loader24, { className: "mr-2 h-3 w-3 animate-spin" }) : /* @__PURE__ */ jsx21(Trash2, { className: "mr-2 h-3 w-3" }),
2929
3447
  "Delete"
2930
3448
  ]
2931
3449
  }
2932
3450
  ),
2933
- /* @__PURE__ */ jsxs15(Button, { size: "sm", onClick: () => void handleSave(), disabled: isSaving, children: [
2934
- isSaving ? /* @__PURE__ */ jsx20(Loader24, { className: "mr-2 h-3 w-3 animate-spin" }) : /* @__PURE__ */ jsx20(Save2, { className: "mr-2 h-3 w-3" }),
3451
+ /* @__PURE__ */ jsxs16(Button, { size: "sm", onClick: () => void handleSave(), disabled: isSaving, children: [
3452
+ isSaving ? /* @__PURE__ */ jsx21(Loader24, { className: "mr-2 h-3 w-3 animate-spin" }) : /* @__PURE__ */ jsx21(Save2, { className: "mr-2 h-3 w-3" }),
2935
3453
  isNew ? "Create" : "Save"
2936
3454
  ] })
2937
3455
  ] })
2938
3456
  ] }),
2939
- error && /* @__PURE__ */ jsx20("div", { className: "rounded-lg border border-destructive/50 bg-destructive/10 p-3 text-sm text-destructive", children: error }),
2940
- /* @__PURE__ */ jsx20("div", { className: "rounded-lg border bg-card", children: /* @__PURE__ */ jsx20(
3457
+ error && /* @__PURE__ */ jsx21("div", { className: "rounded-lg border border-destructive/50 bg-destructive/10 p-3 text-sm text-destructive", children: error }),
3458
+ /* @__PURE__ */ jsx21("div", { className: "rounded-lg border bg-card", children: /* @__PURE__ */ jsx21(
2941
3459
  "textarea",
2942
3460
  {
2943
3461
  className: "w-full min-h-[400px] p-4 font-mono text-sm bg-transparent resize-y focus:outline-none",
@@ -2951,8 +3469,8 @@ var CollectionItemDetailView = ({
2951
3469
 
2952
3470
  // src/components/views/EventsView.tsx
2953
3471
  import { useCallback as useCallback7, useState as useState8 } from "react";
2954
- import { Activity as Activity2, Loader2 as Loader25, Search as Search5 } from "lucide-react";
2955
- import { jsx as jsx21, jsxs as jsxs16 } from "react/jsx-runtime";
3472
+ import { Activity as Activity3, Loader2 as Loader25, Search as Search6 } from "lucide-react";
3473
+ import { jsx as jsx22, jsxs as jsxs17 } from "react/jsx-runtime";
2956
3474
  var STATUS_VARIANTS = {
2957
3475
  pending: "outline",
2958
3476
  processing: "default",
@@ -2985,13 +3503,13 @@ var EventsView = ({ config }) => {
2985
3503
  setIsLoading(false);
2986
3504
  }
2987
3505
  }, [threadId, config.baseUrl, config.getRequestHeaders]);
2988
- return /* @__PURE__ */ jsxs16("div", { className: "space-y-6", children: [
2989
- /* @__PURE__ */ jsxs16("div", { className: "flex items-end gap-3 max-w-lg", children: [
2990
- /* @__PURE__ */ jsxs16("div", { className: "flex-1", children: [
2991
- /* @__PURE__ */ jsx21("label", { className: "text-sm font-medium mb-1 block", children: "Thread ID" }),
2992
- /* @__PURE__ */ jsxs16("div", { className: "relative", children: [
2993
- /* @__PURE__ */ jsx21(Search5, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
2994
- /* @__PURE__ */ jsx21(
3506
+ return /* @__PURE__ */ jsxs17("div", { className: "space-y-6", children: [
3507
+ /* @__PURE__ */ jsxs17("div", { className: "flex items-end gap-3 max-w-lg", children: [
3508
+ /* @__PURE__ */ jsxs17("div", { className: "flex-1", children: [
3509
+ /* @__PURE__ */ jsx22("label", { className: "text-sm font-medium mb-1 block", children: "Thread ID" }),
3510
+ /* @__PURE__ */ jsxs17("div", { className: "relative", children: [
3511
+ /* @__PURE__ */ jsx22(Search6, { className: "pointer-events-none absolute left-3 top-1/2 h-4 w-4 -translate-y-1/2 text-muted-foreground" }),
3512
+ /* @__PURE__ */ jsx22(
2995
3513
  Input,
2996
3514
  {
2997
3515
  className: "pl-9",
@@ -3003,55 +3521,55 @@ var EventsView = ({ config }) => {
3003
3521
  )
3004
3522
  ] })
3005
3523
  ] }),
3006
- /* @__PURE__ */ jsxs16(Button, { onClick: () => void handleSearch(), disabled: isLoading || !threadId.trim(), children: [
3007
- isLoading ? /* @__PURE__ */ jsx21(Loader25, { className: "mr-2 h-4 w-4 animate-spin" }) : null,
3524
+ /* @__PURE__ */ jsxs17(Button, { onClick: () => void handleSearch(), disabled: isLoading || !threadId.trim(), children: [
3525
+ isLoading ? /* @__PURE__ */ jsx22(Loader25, { className: "mr-2 h-4 w-4 animate-spin" }) : null,
3008
3526
  "Inspect"
3009
3527
  ] })
3010
3528
  ] }),
3011
- error && /* @__PURE__ */ jsx21("div", { className: "rounded-lg border border-destructive/50 bg-destructive/10 p-3 text-sm text-destructive", children: error }),
3012
- !hasSearched ? /* @__PURE__ */ jsxs16("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
3013
- /* @__PURE__ */ jsx21(Activity2, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
3014
- /* @__PURE__ */ jsx21("p", { className: "mt-3 text-sm text-muted-foreground", children: "Enter a thread ID to inspect its next pending queue event." })
3015
- ] }) : isLoading ? /* @__PURE__ */ jsx21("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx21(Loader25, { className: "h-6 w-6 animate-spin text-muted-foreground" }) }) : !event ? /* @__PURE__ */ jsxs16("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
3016
- /* @__PURE__ */ jsx21(Activity2, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
3017
- /* @__PURE__ */ jsx21("p", { className: "mt-3 text-sm text-muted-foreground", children: "No pending events found for this thread." })
3018
- ] }) : /* @__PURE__ */ jsxs16("div", { className: "rounded-lg border bg-card p-5 space-y-4", children: [
3019
- /* @__PURE__ */ jsxs16("div", { className: "flex items-start justify-between gap-3", children: [
3020
- /* @__PURE__ */ jsxs16("div", { children: [
3021
- /* @__PURE__ */ jsx21("p", { className: "font-medium", children: event.eventType }),
3022
- /* @__PURE__ */ jsx21("p", { className: "text-xs text-muted-foreground font-mono mt-1", children: event.id })
3529
+ error && /* @__PURE__ */ jsx22("div", { className: "rounded-lg border border-destructive/50 bg-destructive/10 p-3 text-sm text-destructive", children: error }),
3530
+ !hasSearched ? /* @__PURE__ */ jsxs17("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
3531
+ /* @__PURE__ */ jsx22(Activity3, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
3532
+ /* @__PURE__ */ jsx22("p", { className: "mt-3 text-sm text-muted-foreground", children: "Enter a thread ID to inspect its next pending queue event." })
3533
+ ] }) : isLoading ? /* @__PURE__ */ jsx22("div", { className: "flex items-center justify-center py-20", children: /* @__PURE__ */ jsx22(Loader25, { className: "h-6 w-6 animate-spin text-muted-foreground" }) }) : !event ? /* @__PURE__ */ jsxs17("div", { className: "rounded-xl border border-dashed p-10 text-center", children: [
3534
+ /* @__PURE__ */ jsx22(Activity3, { className: "mx-auto h-8 w-8 text-muted-foreground/50" }),
3535
+ /* @__PURE__ */ jsx22("p", { className: "mt-3 text-sm text-muted-foreground", children: "No pending events found for this thread." })
3536
+ ] }) : /* @__PURE__ */ jsxs17("div", { className: "rounded-lg border bg-card p-5 space-y-4", children: [
3537
+ /* @__PURE__ */ jsxs17("div", { className: "flex items-start justify-between gap-3", children: [
3538
+ /* @__PURE__ */ jsxs17("div", { children: [
3539
+ /* @__PURE__ */ jsx22("p", { className: "font-medium", children: event.eventType }),
3540
+ /* @__PURE__ */ jsx22("p", { className: "text-xs text-muted-foreground font-mono mt-1", children: event.id })
3023
3541
  ] }),
3024
- /* @__PURE__ */ jsx21(Badge, { variant: STATUS_VARIANTS[event.status] ?? "outline", children: event.status })
3542
+ /* @__PURE__ */ jsx22(Badge, { variant: STATUS_VARIANTS[event.status] ?? "outline", children: event.status })
3025
3543
  ] }),
3026
- /* @__PURE__ */ jsxs16("div", { className: "grid gap-3 sm:grid-cols-2 text-sm", children: [
3027
- event.traceId && /* @__PURE__ */ jsxs16("div", { children: [
3028
- /* @__PURE__ */ jsx21("span", { className: "text-muted-foreground", children: "Trace:" }),
3544
+ /* @__PURE__ */ jsxs17("div", { className: "grid gap-3 sm:grid-cols-2 text-sm", children: [
3545
+ event.traceId && /* @__PURE__ */ jsxs17("div", { children: [
3546
+ /* @__PURE__ */ jsx22("span", { className: "text-muted-foreground", children: "Trace:" }),
3029
3547
  " ",
3030
- /* @__PURE__ */ jsx21("span", { className: "font-mono text-xs", children: event.traceId })
3548
+ /* @__PURE__ */ jsx22("span", { className: "font-mono text-xs", children: event.traceId })
3031
3549
  ] }),
3032
- event.parentEventId && /* @__PURE__ */ jsxs16("div", { children: [
3033
- /* @__PURE__ */ jsx21("span", { className: "text-muted-foreground", children: "Parent:" }),
3550
+ event.parentEventId && /* @__PURE__ */ jsxs17("div", { children: [
3551
+ /* @__PURE__ */ jsx22("span", { className: "text-muted-foreground", children: "Parent:" }),
3034
3552
  " ",
3035
- /* @__PURE__ */ jsx21("span", { className: "font-mono text-xs", children: event.parentEventId })
3553
+ /* @__PURE__ */ jsx22("span", { className: "font-mono text-xs", children: event.parentEventId })
3036
3554
  ] }),
3037
- event.priority != null && /* @__PURE__ */ jsxs16("div", { children: [
3038
- /* @__PURE__ */ jsx21("span", { className: "text-muted-foreground", children: "Priority:" }),
3555
+ event.priority != null && /* @__PURE__ */ jsxs17("div", { children: [
3556
+ /* @__PURE__ */ jsx22("span", { className: "text-muted-foreground", children: "Priority:" }),
3039
3557
  " ",
3040
3558
  event.priority
3041
3559
  ] }),
3042
- event.createdAt && /* @__PURE__ */ jsxs16("div", { children: [
3043
- /* @__PURE__ */ jsx21("span", { className: "text-muted-foreground", children: "Created:" }),
3560
+ event.createdAt && /* @__PURE__ */ jsxs17("div", { children: [
3561
+ /* @__PURE__ */ jsx22("span", { className: "text-muted-foreground", children: "Created:" }),
3044
3562
  " ",
3045
3563
  formatTimestamp2(event.createdAt)
3046
3564
  ] })
3047
3565
  ] }),
3048
- event.payload != null && /* @__PURE__ */ jsxs16("div", { children: [
3049
- /* @__PURE__ */ jsx21("p", { className: "text-xs font-medium text-muted-foreground mb-1", children: "Payload" }),
3050
- /* @__PURE__ */ jsx21("pre", { className: "rounded-md bg-muted p-3 text-xs overflow-auto max-h-60", children: JSON.stringify(event.payload, null, 2) })
3566
+ event.payload != null && /* @__PURE__ */ jsxs17("div", { children: [
3567
+ /* @__PURE__ */ jsx22("p", { className: "text-xs font-medium text-muted-foreground mb-1", children: "Payload" }),
3568
+ /* @__PURE__ */ jsx22("pre", { className: "rounded-md bg-muted p-3 text-xs overflow-auto max-h-60", children: JSON.stringify(event.payload, null, 2) })
3051
3569
  ] }),
3052
- event.metadata != null && Object.keys(event.metadata).length > 0 && /* @__PURE__ */ jsxs16("div", { children: [
3053
- /* @__PURE__ */ jsx21("p", { className: "text-xs font-medium text-muted-foreground mb-1", children: "Metadata" }),
3054
- /* @__PURE__ */ jsx21("pre", { className: "rounded-md bg-muted p-3 text-xs overflow-auto max-h-40", children: JSON.stringify(event.metadata, null, 2) })
3570
+ event.metadata != null && Object.keys(event.metadata).length > 0 && /* @__PURE__ */ jsxs17("div", { children: [
3571
+ /* @__PURE__ */ jsx22("p", { className: "text-xs font-medium text-muted-foreground mb-1", children: "Metadata" }),
3572
+ /* @__PURE__ */ jsx22("pre", { className: "rounded-md bg-muted p-3 text-xs overflow-auto max-h-40", children: JSON.stringify(event.metadata, null, 2) })
3055
3573
  ] })
3056
3574
  ] })
3057
3575
  ] });
@@ -3069,7 +3587,7 @@ function formatTimestamp2(value) {
3069
3587
  }
3070
3588
 
3071
3589
  // src/CopilotzAdmin.tsx
3072
- import { jsx as jsx22, jsxs as jsxs17 } from "react/jsx-runtime";
3590
+ import { jsx as jsx23, jsxs as jsxs18 } from "react/jsx-runtime";
3073
3591
  var CopilotzAdmin = ({
3074
3592
  config: userConfig,
3075
3593
  className
@@ -3161,18 +3679,18 @@ var CopilotzAdmin = ({
3161
3679
  }
3162
3680
  })();
3163
3681
  if (admin.isLoading && !admin.overview) {
3164
- return /* @__PURE__ */ jsx22(Card, { className: cn("border-border", className), children: /* @__PURE__ */ jsx22(CardContent, { className: "text-muted-foreground flex items-center justify-center min-h-[200px]", children: config.labels.loading }) });
3682
+ return /* @__PURE__ */ jsx23(Card, { className: cn("border-border", className), children: /* @__PURE__ */ jsx23(CardContent, { className: "text-muted-foreground flex items-center justify-center min-h-[200px]", children: config.labels.loading }) });
3165
3683
  }
3166
3684
  if (admin.error && !admin.overview) {
3167
- return /* @__PURE__ */ jsx22(Card, { className: cn("border-destructive/50 bg-destructive/10", className), children: /* @__PURE__ */ jsxs17(CardContent, { className: "space-y-4", children: [
3168
- /* @__PURE__ */ jsx22("p", { className: "text-base font-semibold text-destructive", children: admin.error.message }),
3169
- /* @__PURE__ */ jsx22(Button, { variant: "destructive", onClick: () => void admin.refresh(), children: config.labels.retry })
3685
+ return /* @__PURE__ */ jsx23(Card, { className: cn("border-destructive/50 bg-destructive/10", className), children: /* @__PURE__ */ jsxs18(CardContent, { className: "space-y-4", children: [
3686
+ /* @__PURE__ */ jsx23("p", { className: "text-base font-semibold text-destructive", children: admin.error.message }),
3687
+ /* @__PURE__ */ jsx23(Button, { variant: "destructive", onClick: () => void admin.refresh(), children: config.labels.retry })
3170
3688
  ] }) });
3171
3689
  }
3172
3690
  const renderCurrentView = () => {
3173
3691
  switch (route.page) {
3174
3692
  case "dashboard":
3175
- return /* @__PURE__ */ jsx22(
3693
+ return /* @__PURE__ */ jsx23(
3176
3694
  DashboardView,
3177
3695
  {
3178
3696
  config,
@@ -3182,6 +3700,7 @@ var CopilotzAdmin = ({
3182
3700
  participants: admin.participants,
3183
3701
  agents: admin.agents,
3184
3702
  interval: admin.filters.interval,
3703
+ namespace,
3185
3704
  threadSearch,
3186
3705
  participantSearch,
3187
3706
  agentSearch,
@@ -3192,7 +3711,7 @@ var CopilotzAdmin = ({
3192
3711
  }
3193
3712
  );
3194
3713
  case "threads":
3195
- return /* @__PURE__ */ jsx22(
3714
+ return /* @__PURE__ */ jsx23(
3196
3715
  ThreadsView,
3197
3716
  {
3198
3717
  config,
@@ -3203,9 +3722,9 @@ var CopilotzAdmin = ({
3203
3722
  }
3204
3723
  );
3205
3724
  case "thread-detail":
3206
- return route.resourceId ? /* @__PURE__ */ jsx22(ThreadDetailView, { threadId: route.resourceId, config, onBack: handleBackToThreads }) : null;
3725
+ return route.resourceId ? /* @__PURE__ */ jsx23(ThreadDetailView, { threadId: route.resourceId, config, onBack: handleBackToThreads }) : null;
3207
3726
  case "participants":
3208
- return /* @__PURE__ */ jsx22(
3727
+ return /* @__PURE__ */ jsx23(
3209
3728
  ParticipantsView,
3210
3729
  {
3211
3730
  config,
@@ -3216,9 +3735,9 @@ var CopilotzAdmin = ({
3216
3735
  }
3217
3736
  );
3218
3737
  case "participant-detail":
3219
- return route.resourceId ? /* @__PURE__ */ jsx22(ParticipantDetailView, { participantId: route.resourceId, config, onBack: handleBackToParticipants }) : null;
3738
+ return route.resourceId ? /* @__PURE__ */ jsx23(ParticipantDetailView, { participantId: route.resourceId, config, onBack: handleBackToParticipants }) : null;
3220
3739
  case "agents":
3221
- return /* @__PURE__ */ jsx22(
3740
+ return /* @__PURE__ */ jsx23(
3222
3741
  AgentsView,
3223
3742
  {
3224
3743
  config,
@@ -3229,9 +3748,9 @@ var CopilotzAdmin = ({
3229
3748
  }
3230
3749
  );
3231
3750
  case "agent-detail":
3232
- return route.resourceId ? /* @__PURE__ */ jsx22(AgentDetailView, { agentId: route.resourceId, config, agents: admin.agents, onBack: handleBackToAgents }) : null;
3751
+ return route.resourceId ? /* @__PURE__ */ jsx23(AgentDetailView, { agentId: route.resourceId, config, agents: admin.agents, onBack: handleBackToAgents }) : null;
3233
3752
  case "collection-items":
3234
- return route.collection ? /* @__PURE__ */ jsx22(
3753
+ return route.collection ? /* @__PURE__ */ jsx23(
3235
3754
  CollectionItemsView,
3236
3755
  {
3237
3756
  collection: route.collection,
@@ -3242,7 +3761,7 @@ var CopilotzAdmin = ({
3242
3761
  }
3243
3762
  ) : null;
3244
3763
  case "collection-item-detail":
3245
- return route.collection ? /* @__PURE__ */ jsx22(
3764
+ return route.collection ? /* @__PURE__ */ jsx23(
3246
3765
  CollectionItemDetailView,
3247
3766
  {
3248
3767
  collection: route.collection,
@@ -3253,12 +3772,12 @@ var CopilotzAdmin = ({
3253
3772
  }
3254
3773
  ) : null;
3255
3774
  case "events":
3256
- return /* @__PURE__ */ jsx22(EventsView, { config });
3775
+ return /* @__PURE__ */ jsx23(EventsView, { config });
3257
3776
  default:
3258
3777
  return null;
3259
3778
  }
3260
3779
  };
3261
- return /* @__PURE__ */ jsx22(TooltipProvider, { children: /* @__PURE__ */ jsx22(SidebarProvider, { defaultOpen: config.sidebar.defaultOpen, children: /* @__PURE__ */ jsxs17(
3780
+ return /* @__PURE__ */ jsx23(TooltipProvider, { children: /* @__PURE__ */ jsx23(SidebarProvider, { defaultOpen: config.sidebar.defaultOpen, children: /* @__PURE__ */ jsxs18(
3262
3781
  "div",
3263
3782
  {
3264
3783
  className: cn(
@@ -3266,7 +3785,7 @@ var CopilotzAdmin = ({
3266
3785
  className
3267
3786
  ),
3268
3787
  children: [
3269
- /* @__PURE__ */ jsx22(
3788
+ /* @__PURE__ */ jsx23(
3270
3789
  AdminSidebar,
3271
3790
  {
3272
3791
  config,
@@ -3279,8 +3798,8 @@ var CopilotzAdmin = ({
3279
3798
  onNamespaceChange: setNamespace
3280
3799
  }
3281
3800
  ),
3282
- /* @__PURE__ */ jsx22(SidebarInset, { children: /* @__PURE__ */ jsxs17("div", { className: "flex flex-col h-full min-h-0", children: [
3283
- /* @__PURE__ */ jsx22(
3801
+ /* @__PURE__ */ jsx23(SidebarInset, { children: /* @__PURE__ */ jsxs18("div", { className: "flex flex-col h-full min-h-0", children: [
3802
+ /* @__PURE__ */ jsx23(
3284
3803
  AdminHeader,
3285
3804
  {
3286
3805
  config,
@@ -3293,7 +3812,7 @@ var CopilotzAdmin = ({
3293
3812
  isLoading: admin.isLoading
3294
3813
  }
3295
3814
  ),
3296
- /* @__PURE__ */ jsx22("div", { className: "flex-1 overflow-auto p-6", children: renderCurrentView() })
3815
+ /* @__PURE__ */ jsx23("div", { className: "flex-1 overflow-auto p-6", children: renderCurrentView() })
3297
3816
  ] }) })
3298
3817
  ]
3299
3818
  }
@@ -3309,6 +3828,7 @@ export {
3309
3828
  fetchAdminOverview,
3310
3829
  fetchAdminParticipants,
3311
3830
  fetchAdminThreads,
3831
+ fetchAdminUsage,
3312
3832
  fetchCollectionItem,
3313
3833
  fetchCollectionItems,
3314
3834
  fetchCollectionNames,