@object-ui/plugin-report 17.6.0 → 17.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1,56 +1,56 @@
1
- import { ComponentRegistry as e, buildCategoryOrder as t, buildChartSeries as n, buildDatasetDrillFilter as r, buildDatasetFieldHelpers as i, buildOptionColorMap as a, chartConfigPresentation as o, deriveDimensionLabelMaps as s, dimensionOptionTranslator as c, formatDimensionValue as l, formatMeasure as u, localizeFieldOptions as d, mergeAuthoredSeries as f, mergeFilters as p, pivotBucketId as m, pivotCellKey as h, pivotDimensionValue as g, relabelDimensions as _ } from "@object-ui/core";
2
- import * as v from "react";
3
- import y from "react";
4
- import { isSpecReport as b, specReportToPresentation as x } from "@object-ui/types";
5
- import { SchemaRenderer as S, SchemaRendererContext as C, toRenderableSchema as w, useDatasetDimensionLabels as T, useDatasetDimensionMeta as E } from "@object-ui/react";
6
- import { Badge as D, Button as O, Card as k, CardContent as A, CardDescription as j, CardHeader as M, CardTitle as N, Skeleton as P } from "@object-ui/components";
7
- import { jsx as F, jsxs as I } from "react/jsx-runtime";
8
- import { AlertTriangle as ee, Download as L, Loader2 as te, Printer as R, RefreshCw as ne, Table2 as re } from "lucide-react";
9
- import { getCellRenderer as ie, resolveCellRendererType as ae } from "@object-ui/fields";
10
- import { pickLocalized as oe, useDisplayLocale as z, useObjectTranslation as se, useSafeFieldLabel as B, useSafeTranslate as V } from "@object-ui/i18n";
1
+ import { ComponentRegistry as e, FilterOperatorError as t, buildCategoryOrder as n, buildChartSeries as r, buildDatasetDrillFilter as i, buildDatasetFieldHelpers as a, buildOptionColorMap as o, chartConfigPresentation as s, deriveDimensionLabelMaps as c, dimensionOptionTranslator as l, formatDimensionValue as u, formatMeasure as d, localizeFieldOptions as f, mergeAuthoredSeries as p, mergeFilters as m, pivotBucketId as h, pivotCellKey as g, pivotDimensionValue as _, relabelDimensions as v, toDisplayDate as y } from "@object-ui/core";
2
+ import * as b from "react";
3
+ import x from "react";
4
+ import { isSpecReport as S, specReportToPresentation as C } from "@object-ui/types";
5
+ import { SchemaRenderer as w, SchemaRendererContext as T, toRenderableSchema as E, useDataInvalidation as D, useDatasetDimensionLabels as O, useDatasetDimensionMeta as k } from "@object-ui/react";
6
+ import { Badge as A, Button as j, Card as M, CardContent as N, CardDescription as P, CardHeader as F, CardTitle as I, Skeleton as L, renderNodeSlot as ee } from "@object-ui/components";
7
+ import { jsx as R, jsxs as z } from "react/jsx-runtime";
8
+ import { AlertTriangle as te, Download as B, Loader2 as ne, Printer as re, RefreshCw as ie, Table2 as ae } from "lucide-react";
9
+ import { getCellRenderer as oe, resolveCellRendererType as se } from "@object-ui/fields";
10
+ import { builtinAggregateLabels as V, pickLocalized as ce, useDisplayLocale as H, useObjectTranslation as le, useSafeFieldLabel as U, useSafeTranslate as W } from "@object-ui/i18n";
11
11
  //#region src/LegacyReportRenderer.tsx
12
- var H = ({ schema: t }) => {
12
+ var ue = ({ schema: t }) => {
13
13
  let { title: n, description: r, data: i, columns: a } = t;
14
14
  t.chart?.type;
15
15
  let o = !!t.chart;
16
- return /* @__PURE__ */ I(k, {
16
+ return /* @__PURE__ */ z(M, {
17
17
  className: `h-full flex flex-col ${t.className || ""}`,
18
- children: [/* @__PURE__ */ I(M, { children: [n && /* @__PURE__ */ F(N, { children: n }), r && /* @__PURE__ */ F(j, { children: r })] }), /* @__PURE__ */ I(A, {
18
+ children: [/* @__PURE__ */ z(F, { children: [n && /* @__PURE__ */ R(I, { children: n }), r && /* @__PURE__ */ R(P, { children: r })] }), /* @__PURE__ */ z(N, {
19
19
  className: "flex-1 overflow-auto space-y-4",
20
20
  children: [o && (() => {
21
21
  let n = t.chart?.type, r = n ? e.get(n) : null;
22
- return r ||= e.get("chart"), r ? /* @__PURE__ */ F("div", {
22
+ return r ||= e.get("chart"), r ? /* @__PURE__ */ R("div", {
23
23
  className: "min-h-[300px] border rounded-lg p-4 bg-background/50",
24
- children: /* @__PURE__ */ F(r, { schema: {
24
+ children: /* @__PURE__ */ R(r, { schema: {
25
25
  ...t.chart,
26
26
  data: t.chart.data || i
27
27
  } })
28
- }) : /* @__PURE__ */ I("div", {
28
+ }) : /* @__PURE__ */ z("div", {
29
29
  className: "min-h-[100px] border rounded-md p-4 bg-muted/20 text-muted-foreground flex items-center justify-center",
30
30
  children: ["Unknown component type: ", n || "chart"]
31
31
  });
32
- })(), i && i.length > 0 && /* @__PURE__ */ F("div", {
32
+ })(), i && i.length > 0 && /* @__PURE__ */ R("div", {
33
33
  className: "border rounded-lg",
34
34
  children: (() => {
35
35
  let t = e.get("grid") || e.get("table");
36
- return t ? /* @__PURE__ */ F(t, { schema: {
36
+ return t ? /* @__PURE__ */ R(t, { schema: {
37
37
  type: "grid",
38
38
  rowData: i,
39
39
  columnDefs: a,
40
40
  domLayout: "autoHeight"
41
- } }) : /* @__PURE__ */ F("div", {
41
+ } }) : /* @__PURE__ */ R("div", {
42
42
  className: "overflow-x-auto",
43
- children: /* @__PURE__ */ I("table", {
43
+ children: /* @__PURE__ */ z("table", {
44
44
  className: "w-full text-sm text-left",
45
- children: [/* @__PURE__ */ F("thead", {
45
+ children: [/* @__PURE__ */ R("thead", {
46
46
  className: "text-xs uppercase bg-muted",
47
- children: /* @__PURE__ */ F("tr", { children: a?.map((e) => /* @__PURE__ */ F("th", {
47
+ children: /* @__PURE__ */ R("tr", { children: a?.map((e) => /* @__PURE__ */ R("th", {
48
48
  className: "px-6 py-3",
49
49
  children: e.headerName || e.label || e.field
50
50
  }, e.field)) })
51
- }), /* @__PURE__ */ F("tbody", { children: i.map((e, t) => /* @__PURE__ */ F("tr", {
51
+ }), /* @__PURE__ */ R("tbody", { children: i.map((e, t) => /* @__PURE__ */ R("tr", {
52
52
  className: "bg-background border-b",
53
- children: a?.map((t) => /* @__PURE__ */ F("td", {
53
+ children: a?.map((t) => /* @__PURE__ */ R("td", {
54
54
  className: "px-6 py-4",
55
55
  children: e[t.field]
56
56
  }, t.field))
@@ -62,33 +62,40 @@ var H = ({ schema: t }) => {
62
62
  })]
63
63
  });
64
64
  };
65
+ function G(e, t, n) {
66
+ try {
67
+ return e.toLocaleString(t, n);
68
+ } catch {
69
+ return e.toLocaleString("en", n);
70
+ }
71
+ }
65
72
  //#endregion
66
73
  //#region src/ReportExportEngine.ts
67
- function ce(e, t, n) {
74
+ function de(e, t, n) {
68
75
  let r = e.fields || [], i = r.map((e) => e.label || e.name), a = t.map((e) => r.map((t) => {
69
76
  let n = e[t.name];
70
- return n = fe(n), typeof n == "string" && (n.includes(",") || n.includes("\"") || n.includes("\n")) ? `"${n.replace(/"/g, "\"\"")}"` : n ?? "";
77
+ return n = ge(n), typeof n == "string" && (n.includes(",") || n.includes("\"") || n.includes("\n")) ? `"${n.replace(/"/g, "\"\"")}"` : n ?? "";
71
78
  }));
72
- K([...n?.includeHeaders === !1 ? [] : [i.join(",")], ...a.map((e) => e.join(","))].join("\n"), n?.filename || `${e.title || "report"}.csv`, "text/csv");
79
+ J([...n?.includeHeaders === !1 ? [] : [i.join(",")], ...a.map((e) => e.join(","))].join("\n"), n?.filename || `${e.title || "report"}.csv`, "text/csv");
73
80
  }
74
- function le(e, t, n) {
81
+ function fe(e, t, n) {
75
82
  let r = {
76
83
  title: e.title,
77
84
  description: e.description,
78
85
  generatedAt: (/* @__PURE__ */ new Date()).toISOString(),
79
86
  data: t
80
87
  };
81
- K(JSON.stringify(r, null, 2), n?.filename || `${e.title || "report"}.json`, "application/json");
88
+ J(JSON.stringify(r, null, 2), n?.filename || `${e.title || "report"}.json`, "application/json");
82
89
  }
83
- function U(e, t, n) {
84
- let r = e.fields || [], i = me(n?.orientation), a = pe(n?.pageSize);
85
- K(`<!DOCTYPE html>
90
+ function K(e, t, n, r = "en") {
91
+ let i = e.fields || [], a = ve(n?.orientation), o = _e(n?.pageSize);
92
+ J(`<!DOCTYPE html>
86
93
  <html>
87
94
  <head>
88
95
  <meta charset="utf-8">
89
- <title>${G(e.title || "Report")}</title>
96
+ <title>${q(e.title || "Report")}</title>
90
97
  <style>
91
- @page { size: ${a} ${i}; margin: 20mm; }
98
+ @page { size: ${o} ${a}; margin: 20mm; }
92
99
  body { font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif; color: #333; }
93
100
  h1 { font-size: 24px; margin-bottom: 8px; }
94
101
  .description { color: #666; margin-bottom: 24px; }
@@ -100,33 +107,33 @@ function U(e, t, n) {
100
107
  </style>
101
108
  </head>
102
109
  <body>
103
- <h1>${G(e.title || "Report")}</h1>
104
- ${e.description ? `<p class="description">${G(e.description)}</p>` : ""}
105
- <p class="meta">Generated: ${(/* @__PURE__ */ new Date()).toLocaleString()}</p>
110
+ <h1>${q(e.title || "Report")}</h1>
111
+ ${e.description ? `<p class="description">${q(e.description)}</p>` : ""}
112
+ <p class="meta">Generated: ${(/* @__PURE__ */ new Date()).toLocaleString(r)}</p>
106
113
  <table>
107
- <thead><tr>${r.map((e) => `<th>${G(e.label || e.name)}</th>`).join("")}</tr></thead>
108
- <tbody>${t.map((e) => `<tr>${r.map((t) => `<td>${G(String(e[t.name] ?? ""))}</td>`).join("")}</tr>`).join("")}</tbody>
114
+ <thead><tr>${i.map((e) => `<th>${q(e.label || e.name)}</th>`).join("")}</tr></thead>
115
+ <tbody>${t.map((e) => `<tr>${i.map((t) => `<td>${q(String(e[t.name] ?? ""))}</td>`).join("")}</tr>`).join("")}</tbody>
109
116
  </table>
110
117
  </body>
111
118
  </html>`, n?.filename || `${e.title || "report"}.html`, "text/html");
112
119
  }
113
- function ue(e, t, n) {
114
- let r = e.fields || [], i = me(n?.orientation), a = pe(n?.pageSize), o = window.open("", "_blank");
115
- if (!o) {
116
- U(e, t, {
120
+ function pe(e, t, n, r = "en") {
121
+ let i = e.fields || [], a = ve(n?.orientation), o = _e(n?.pageSize), s = window.open("", "_blank");
122
+ if (!s) {
123
+ K(e, t, {
117
124
  ...n,
118
125
  format: "html",
119
126
  filename: n?.filename?.replace(/\.pdf$/, ".html") || `${e.title || "report"}.html`
120
- });
127
+ }, r);
121
128
  return;
122
129
  }
123
- o.document.write(`<!DOCTYPE html>
130
+ s.document.write(`<!DOCTYPE html>
124
131
  <html>
125
132
  <head>
126
133
  <meta charset="utf-8">
127
- <title>${G(e.title || "Report")}</title>
134
+ <title>${q(e.title || "Report")}</title>
128
135
  <style>
129
- @page { size: ${a} ${i}; margin: 20mm; }
136
+ @page { size: ${o} ${a}; margin: 20mm; }
130
137
  @media print { .no-print { display: none; } }
131
138
  body { font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif; color: #333; }
132
139
  h1 { font-size: 24px; margin-bottom: 8px; }
@@ -139,56 +146,56 @@ function ue(e, t, n) {
139
146
  </style>
140
147
  </head>
141
148
  <body>
142
- <h1>${G(e.title || "Report")}</h1>
143
- ${e.description ? `<p class="description">${G(e.description)}</p>` : ""}
144
- <p class="meta">Generated: ${(/* @__PURE__ */ new Date()).toLocaleString()}</p>
149
+ <h1>${q(e.title || "Report")}</h1>
150
+ ${e.description ? `<p class="description">${q(e.description)}</p>` : ""}
151
+ <p class="meta">Generated: ${(/* @__PURE__ */ new Date()).toLocaleString(r)}</p>
145
152
  <table>
146
- <thead><tr>${r.map((e) => `<th>${G(e.label || e.name)}</th>`).join("")}</tr></thead>
147
- <tbody>${t.map((e) => `<tr>${r.map((t) => `<td>${G(String(e[t.name] ?? ""))}</td>`).join("")}</tr>`).join("")}</tbody>
153
+ <thead><tr>${i.map((e) => `<th>${q(e.label || e.name)}</th>`).join("")}</tr></thead>
154
+ <tbody>${t.map((e) => `<tr>${i.map((t) => `<td>${q(String(e[t.name] ?? ""))}</td>`).join("")}</tr>`).join("")}</tbody>
148
155
  </table>
149
156
  </body>
150
- </html>`), o.document.close(), o.onload = () => {
151
- o.print();
157
+ </html>`), s.document.close(), s.onload = () => {
158
+ s.print();
152
159
  };
153
160
  }
154
- function de(e, t, n) {
161
+ function me(e, t, n) {
155
162
  let r = e.fields || [], i = r.map((e) => e.label || e.name), a = t.map((e) => r.map((t) => {
156
163
  let n = e[t.name];
157
- return n = fe(n), typeof n == "string" && (n.includes(",") || n.includes("\"") || n.includes("\n") || n.includes(" ")) ? `"${n.replace(/"/g, "\"\"")}"` : n ?? "";
164
+ return n = ge(n), typeof n == "string" && (n.includes(",") || n.includes("\"") || n.includes("\n") || n.includes(" ")) ? `"${n.replace(/"/g, "\"\"")}"` : n ?? "";
158
165
  }));
159
- K("" + [...n?.includeHeaders === !1 ? [] : [i.join(" ")], ...a.map((e) => e.join(" "))].join("\n"), n?.filename || `${e.title || "report"}.tsv`, "text/tab-separated-values");
166
+ J("" + [...n?.includeHeaders === !1 ? [] : [i.join(" ")], ...a.map((e) => e.join(" "))].join("\n"), n?.filename || `${e.title || "report"}.tsv`, "text/tab-separated-values");
160
167
  }
161
- function W(e, t, n, r) {
168
+ function he(e, t, n, r, i = "en") {
162
169
  switch (e) {
163
170
  case "csv":
164
- ce(t, n, r);
171
+ de(t, n, r);
165
172
  break;
166
173
  case "json":
167
- le(t, n, r);
174
+ fe(t, n, r);
168
175
  break;
169
176
  case "html":
170
- U(t, n, r);
177
+ K(t, n, r, i);
171
178
  break;
172
179
  case "pdf":
173
- ue(t, n, r);
180
+ pe(t, n, r, i);
174
181
  break;
175
182
  case "excel":
176
- de(t, n, r);
183
+ me(t, n, r);
177
184
  break;
178
185
  default: console.warn(`Unsupported export format: ${e}`);
179
186
  }
180
187
  }
181
- function G(e) {
188
+ function q(e) {
182
189
  return e.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;").replace(/"/g, "&quot;").replace(/'/g, "&#039;");
183
190
  }
184
- function fe(e) {
191
+ function ge(e) {
185
192
  if (typeof e == "string" && e.length > 0) {
186
193
  let t = e.charAt(0);
187
194
  if (t === "=" || t === "+" || t === "-" || t === "@" || t === "|") return `\t${e}`;
188
195
  }
189
196
  return e;
190
197
  }
191
- function pe(e) {
198
+ function _e(e) {
192
199
  return [
193
200
  "A4",
194
201
  "A3",
@@ -196,40 +203,40 @@ function pe(e) {
196
203
  "Legal"
197
204
  ].includes(e || "") ? e : "A4";
198
205
  }
199
- function me(e) {
206
+ function ve(e) {
200
207
  return e === "landscape" ? "landscape" : "portrait";
201
208
  }
202
- function K(e, t, n) {
209
+ function J(e, t, n) {
203
210
  let r = new Blob([e], { type: `${n};charset=utf-8` }), i = URL.createObjectURL(r), a = document.createElement("a");
204
211
  a.href = i, a.download = t, document.body.appendChild(a), a.click(), document.body.removeChild(a), URL.revokeObjectURL(i);
205
212
  }
206
213
  //#endregion
207
214
  //#region src/formatValue.ts
208
- function q(e, t) {
215
+ function Y(e, t, n = "en") {
209
216
  if (e == null || e === "") return "";
210
- let n = t?.type, r = t?.format;
211
- if (n === "date" || r === "date" || he(e)) return ge(e);
212
- if (n === "number" || typeof e == "number") {
217
+ let r = t?.type, i = t?.format;
218
+ if (r === "date" || i === "date" || ye(e)) return be(e);
219
+ if (r === "number" || typeof e == "number") {
213
220
  let t = typeof e == "number" ? e : Number(e);
214
- return isNaN(t) ? String(e) : r === "currency" || r === "currency_cny" ? `¥${t.toLocaleString("en-US", {
221
+ return isNaN(t) ? String(e) : i === "currency" || i === "currency_cny" ? `¥${G(t, n, {
215
222
  minimumFractionDigits: 0,
216
223
  maximumFractionDigits: 0
217
- })}` : r === "currency_usd" ? `$${t.toLocaleString("en-US", {
224
+ })}` : i === "currency_usd" ? `$${G(t, n, {
218
225
  minimumFractionDigits: 0,
219
226
  maximumFractionDigits: 0
220
- })}` : r === "percent" ? `${t.toLocaleString("en-US", {
227
+ })}` : i === "percent" ? `${G(t, n, {
221
228
  minimumFractionDigits: 1,
222
229
  maximumFractionDigits: 1
223
- })}%` : t.toLocaleString("en-US");
230
+ })}%` : G(t, n);
224
231
  }
225
232
  return String(e);
226
233
  }
227
- function he(e) {
234
+ function ye(e) {
228
235
  return typeof e == "string" && /^\d{4}-\d{2}-\d{2}(T\d{2}:\d{2}:\d{2})?/.test(e);
229
236
  }
230
- function ge(e) {
237
+ function be(e) {
231
238
  try {
232
- let t = new Date(e);
239
+ let t = y(e);
233
240
  return isNaN(t.getTime()) ? String(e) : `${t.getFullYear()}-${String(t.getMonth() + 1).padStart(2, "0")}-${String(t.getDate()).padStart(2, "0")}`;
234
241
  } catch {
235
242
  return String(e);
@@ -237,7 +244,7 @@ function ge(e) {
237
244
  }
238
245
  //#endregion
239
246
  //#region src/ReportViewer.tsx
240
- function _e(e, t) {
247
+ function xe(e, t) {
241
248
  if (!t || t.length === 0 || !e || e.length === 0) return null;
242
249
  let n = t[0], r = n.field, i = /* @__PURE__ */ new Map();
243
250
  for (let t of e) {
@@ -253,7 +260,7 @@ function _e(e, t) {
253
260
  let o = n.sort === "desc" ? -1 : 1;
254
261
  return a.sort((e, t) => e.key.localeCompare(t.key) * o), a;
255
262
  }
256
- function ve(e, t, n) {
263
+ function Se(e, t, n) {
257
264
  if (!e) return 0;
258
265
  let r = e.map((e) => Number(e[t]) || 0);
259
266
  switch (n) {
@@ -266,20 +273,20 @@ function ve(e, t, n) {
266
273
  default: return "";
267
274
  }
268
275
  }
269
- var J = ({ schema: e, onRefresh: t }) => {
270
- let { report: n, data: r, showToolbar: i = !0, allowExport: a = !0, allowPrint: o = !0, loading: s = !1 } = e, c = V(), l = (e) => {
276
+ var Ce = ({ schema: e, onRefresh: t }) => {
277
+ let { report: n, data: r, showToolbar: i = !0, allowExport: a = !0, allowPrint: o = !0, loading: s = !1 } = e, c = W(), l = H(), u = (e) => {
271
278
  if (!n) {
272
279
  console.warn("ReportViewer: Cannot export, no report defined");
273
280
  return;
274
281
  }
275
- W(e, n, r || [], n.exportConfigs?.[e]);
276
- }, u = c("common.printDialogHint", "Opens your browser’s print dialog (not a PDF export)"), d = () => {
282
+ he(e, n, r || [], n.exportConfigs?.[e], l);
283
+ }, d = c("common.printDialogHint", "Opens your browser’s print dialog (not a PDF export)"), f = () => {
277
284
  window.print();
278
- }, f = () => {
285
+ }, p = () => {
279
286
  t?.();
280
- }, p = (e, t) => ve(r, e, t), m = (e, t) => {
287
+ }, m = (e, t) => Se(r, e, t), h = (e, t) => {
281
288
  let r = n?.conditionalFormatting;
282
- if (!(!r || !Array.isArray(r))) for (let n of r) {
289
+ if (r && Array.isArray(r)) for (let n of r) {
283
290
  if (n.field !== e) continue;
284
291
  let r = String(t ?? ""), i = String(n.value ?? ""), a = !1;
285
292
  switch (n.operator) {
@@ -302,16 +309,16 @@ var J = ({ schema: e, onRefresh: t }) => {
302
309
  return n.backgroundColor && (e.backgroundColor = n.backgroundColor), n.textColor && (e.color = n.textColor), e;
303
310
  }
304
311
  }
305
- }, h = (e, t) => {
312
+ }, g = (e, t) => {
306
313
  if (e == null || e === "") return "";
307
314
  if (t.renderAs === "badge" && (!t.type || t.type === "string" || t.type === "text")) {
308
315
  let n = t.colorMap?.[String(e)] || "";
309
- return /* @__PURE__ */ F(D, {
316
+ return /* @__PURE__ */ R(A, {
310
317
  className: n,
311
318
  children: String(e)
312
319
  });
313
320
  }
314
- if (t.aggregation) return q(e, t);
321
+ if (t.aggregation) return Y(e, t, l);
315
322
  if (t.type) {
316
323
  let n = { ...t };
317
324
  t.colorMap && !n.options && (n.options = Object.entries(t.colorMap).map(([e, t]) => ({
@@ -319,132 +326,132 @@ var J = ({ schema: e, onRefresh: t }) => {
319
326
  label: e,
320
327
  color: t
321
328
  })));
322
- let r = ie(ae(n));
323
- return /* @__PURE__ */ F(r, {
329
+ let r = oe(se(n));
330
+ return /* @__PURE__ */ R(r, {
324
331
  value: e,
325
332
  field: n
326
333
  });
327
334
  }
328
- return q(e, t);
335
+ return Y(e, t, l);
329
336
  };
330
- return n ? /* @__PURE__ */ I("div", {
337
+ return n ? /* @__PURE__ */ z("div", {
331
338
  className: "space-y-4",
332
- children: [i && /* @__PURE__ */ I("div", {
339
+ children: [i && /* @__PURE__ */ z("div", {
333
340
  className: "flex items-center justify-between gap-2 p-4 bg-card rounded-lg border",
334
- children: [/* @__PURE__ */ I("div", { children: [/* @__PURE__ */ F("h2", {
341
+ children: [/* @__PURE__ */ z("div", { children: [/* @__PURE__ */ R("h2", {
335
342
  className: "text-lg font-semibold",
336
343
  children: n.title
337
- }), n.description && /* @__PURE__ */ F("p", {
344
+ }), n.description && /* @__PURE__ */ R("p", {
338
345
  className: "text-sm text-muted-foreground",
339
346
  children: n.description
340
- })] }), /* @__PURE__ */ I("div", {
347
+ })] }), /* @__PURE__ */ z("div", {
341
348
  className: "flex items-center gap-2",
342
349
  "data-print-hide": !0,
343
350
  children: [
344
- n.refreshInterval && /* @__PURE__ */ I(O, {
351
+ n.refreshInterval && /* @__PURE__ */ z(j, {
345
352
  variant: "outline",
346
353
  size: "sm",
347
- onClick: f,
348
- children: [/* @__PURE__ */ F(ne, { className: "h-4 w-4 mr-2" }), "Refresh"]
354
+ onClick: p,
355
+ children: [/* @__PURE__ */ R(ie, { className: "h-4 w-4 mr-2" }), "Refresh"]
349
356
  }),
350
- o && /* @__PURE__ */ I(O, {
357
+ o && /* @__PURE__ */ z(j, {
351
358
  variant: "outline",
352
359
  size: "sm",
353
- onClick: d,
354
- "aria-label": `Print: ${u}`,
355
- title: u,
356
- children: [/* @__PURE__ */ F(R, { className: "h-4 w-4 mr-2" }), "Print"]
360
+ onClick: f,
361
+ "aria-label": `Print: ${d}`,
362
+ title: d,
363
+ children: [/* @__PURE__ */ R(re, { className: "h-4 w-4 mr-2" }), "Print"]
357
364
  }),
358
- a && n.showExportButtons && /* @__PURE__ */ I("div", {
365
+ a && n.showExportButtons && /* @__PURE__ */ z("div", {
359
366
  className: "flex items-center gap-1",
360
367
  children: [
361
- /* @__PURE__ */ I(O, {
368
+ /* @__PURE__ */ z(j, {
362
369
  variant: "outline",
363
370
  size: "sm",
364
- onClick: () => l("pdf"),
365
- children: [/* @__PURE__ */ F(L, { className: "h-4 w-4 mr-2" }), "PDF"]
371
+ onClick: () => u("pdf"),
372
+ children: [/* @__PURE__ */ R(B, { className: "h-4 w-4 mr-2" }), "PDF"]
366
373
  }),
367
- /* @__PURE__ */ I(O, {
374
+ /* @__PURE__ */ z(j, {
368
375
  variant: "outline",
369
376
  size: "sm",
370
- onClick: () => l("excel"),
371
- children: [/* @__PURE__ */ F(L, { className: "h-4 w-4 mr-2" }), "Excel"]
377
+ onClick: () => u("excel"),
378
+ children: [/* @__PURE__ */ R(B, { className: "h-4 w-4 mr-2" }), "Excel"]
372
379
  }),
373
- /* @__PURE__ */ I(O, {
380
+ /* @__PURE__ */ z(j, {
374
381
  variant: "outline",
375
382
  size: "sm",
376
- onClick: () => l("csv"),
377
- children: [/* @__PURE__ */ F(L, { className: "h-4 w-4 mr-2" }), "CSV"]
383
+ onClick: () => u("csv"),
384
+ children: [/* @__PURE__ */ R(B, { className: "h-4 w-4 mr-2" }), "CSV"]
378
385
  })
379
386
  ]
380
387
  })
381
388
  ]
382
389
  })]
383
- }), /* @__PURE__ */ I(k, { children: [/* @__PURE__ */ I(M, { children: [!i && n.title && /* @__PURE__ */ F(N, { children: n.title }), !i && n.description && /* @__PURE__ */ F(j, { children: n.description })] }), /* @__PURE__ */ I(A, {
390
+ }), /* @__PURE__ */ z(M, { children: [/* @__PURE__ */ z(F, { children: [!i && n.title && /* @__PURE__ */ R(I, { children: n.title }), !i && n.description && /* @__PURE__ */ R(P, { children: n.description })] }), /* @__PURE__ */ z(N, {
384
391
  className: "space-y-6",
385
392
  children: [
386
- s && /* @__PURE__ */ I("div", {
393
+ s && /* @__PURE__ */ z("div", {
387
394
  className: "space-y-6",
388
- children: [/* @__PURE__ */ F("div", {
395
+ children: [/* @__PURE__ */ R("div", {
389
396
  className: "grid grid-cols-1 md:grid-cols-3 gap-4",
390
397
  children: [
391
398
  1,
392
399
  2,
393
400
  3
394
- ].map((e) => /* @__PURE__ */ F(k, { children: /* @__PURE__ */ I(A, {
401
+ ].map((e) => /* @__PURE__ */ R(M, { children: /* @__PURE__ */ z(N, {
395
402
  className: "p-4 space-y-2",
396
- children: [/* @__PURE__ */ F(P, { className: "h-4 w-20" }), /* @__PURE__ */ F(P, { className: "h-8 w-28" })]
403
+ children: [/* @__PURE__ */ R(L, { className: "h-4 w-20" }), /* @__PURE__ */ R(L, { className: "h-8 w-28" })]
397
404
  }) }, e))
398
- }), /* @__PURE__ */ I("div", {
405
+ }), /* @__PURE__ */ z("div", {
399
406
  className: "space-y-2",
400
- children: [/* @__PURE__ */ F(P, { className: "h-10 w-full" }), [
407
+ children: [/* @__PURE__ */ R(L, { className: "h-10 w-full" }), [
401
408
  1,
402
409
  2,
403
410
  3,
404
411
  4,
405
412
  5
406
- ].map((e) => /* @__PURE__ */ F(P, { className: "h-8 w-full" }, e))]
413
+ ].map((e) => /* @__PURE__ */ R(L, { className: "h-8 w-full" }, e))]
407
414
  })]
408
415
  }),
409
- !s && n.sections?.map((e, t) => e.visible === !1 ? null : /* @__PURE__ */ I("div", {
416
+ !s && n.sections?.map((e, t) => e.visible === !1 ? null : /* @__PURE__ */ z("div", {
410
417
  className: "space-y-2",
411
418
  children: [
412
- e.title && e.type !== "header" && /* @__PURE__ */ F("h3", {
419
+ e.title && e.type !== "header" && /* @__PURE__ */ R("h3", {
413
420
  className: "text-lg font-semibold border-b pb-2",
414
421
  children: e.title
415
422
  }),
416
- e.type === "header" && e.title && /* @__PURE__ */ F("div", {
423
+ e.type === "header" && e.title && /* @__PURE__ */ R("div", {
417
424
  className: "text-2xl font-bold py-4",
418
425
  children: e.title
419
426
  }),
420
- e.type === "summary" && /* @__PURE__ */ F("div", {
427
+ e.type === "summary" && /* @__PURE__ */ R("div", {
421
428
  className: "grid grid-cols-1 md:grid-cols-3 gap-4",
422
- children: n.fields?.filter((e) => e.showInSummary).map((e, t) => /* @__PURE__ */ F(k, { children: /* @__PURE__ */ I(A, {
429
+ children: n.fields?.filter((e) => e.showInSummary).map((e, t) => /* @__PURE__ */ R(M, { children: /* @__PURE__ */ z(N, {
423
430
  className: "p-4",
424
- children: [/* @__PURE__ */ F("div", {
431
+ children: [/* @__PURE__ */ R("div", {
425
432
  className: "text-sm text-muted-foreground",
426
433
  children: e.label || e.name
427
- }), /* @__PURE__ */ F("div", {
434
+ }), /* @__PURE__ */ R("div", {
428
435
  className: "text-2xl font-bold",
429
- children: q(p(e.name, e.aggregation), e)
436
+ children: Y(m(e.name, e.aggregation), e, l)
430
437
  })]
431
438
  }) }, t))
432
439
  }),
433
- e.type === "table" && /* @__PURE__ */ F("div", {
440
+ e.type === "table" && /* @__PURE__ */ R("div", {
434
441
  className: "border rounded-lg overflow-x-auto",
435
- children: /* @__PURE__ */ I("table", {
442
+ children: /* @__PURE__ */ z("table", {
436
443
  className: "w-full text-sm min-w-[600px]",
437
- children: [/* @__PURE__ */ F("thead", {
444
+ children: [/* @__PURE__ */ R("thead", {
438
445
  className: "bg-muted",
439
- children: /* @__PURE__ */ F("tr", { children: e.columns?.map((e, t) => /* @__PURE__ */ F("th", {
446
+ children: /* @__PURE__ */ R("tr", { children: e.columns?.map((e, t) => /* @__PURE__ */ R("th", {
440
447
  className: `px-4 py-2 font-medium ${e.type === "number" ? "text-right" : "text-left"}`,
441
448
  children: e.label || e.name
442
449
  }, t)) })
443
- }), /* @__PURE__ */ F("tbody", { children: (() => {
444
- let t = _e(r || [], n.groupBy || []);
445
- return t ? t.map((t) => /* @__PURE__ */ I(y.Fragment, { children: [/* @__PURE__ */ F("tr", {
450
+ }), /* @__PURE__ */ R("tbody", { children: (() => {
451
+ let t = xe(r || [], n.groupBy || []);
452
+ return t ? t.map((t) => /* @__PURE__ */ z(x.Fragment, { children: [/* @__PURE__ */ R("tr", {
446
453
  className: "bg-muted/60",
447
- children: /* @__PURE__ */ I("td", {
454
+ children: /* @__PURE__ */ z("td", {
448
455
  colSpan: e.columns?.length || 1,
449
456
  className: "px-4 py-2 font-semibold text-sm",
450
457
  children: [
@@ -454,107 +461,107 @@ var J = ({ schema: e, onRefresh: t }) => {
454
461
  ")"
455
462
  ]
456
463
  })
457
- }), t.rows.map((t, n) => /* @__PURE__ */ F("tr", {
464
+ }), t.rows.map((t, n) => /* @__PURE__ */ R("tr", {
458
465
  className: "border-t hover:bg-muted/50 even:bg-muted/20",
459
- children: e.columns?.map((e, n) => /* @__PURE__ */ F("td", {
466
+ children: e.columns?.map((e, n) => /* @__PURE__ */ R("td", {
460
467
  className: `px-4 py-2 ${e.type === "number" ? "text-right tabular-nums" : ""}`,
461
- style: m(e.name, t[e.name]),
462
- children: h(t[e.name], e)
468
+ style: h(e.name, t[e.name]),
469
+ children: g(t[e.name], e)
463
470
  }, n))
464
- }, n))] }, t.key)) : r?.map((t, n) => /* @__PURE__ */ F("tr", {
471
+ }, n))] }, t.key)) : r?.map((t, n) => /* @__PURE__ */ R("tr", {
465
472
  className: "border-t hover:bg-muted/50 even:bg-muted/20",
466
- children: e.columns?.map((e, n) => /* @__PURE__ */ F("td", {
473
+ children: e.columns?.map((e, n) => /* @__PURE__ */ R("td", {
467
474
  className: `px-4 py-2 ${e.type === "number" ? "text-right tabular-nums" : ""}`,
468
- style: m(e.name, t[e.name]),
469
- children: h(t[e.name], e)
475
+ style: h(e.name, t[e.name]),
476
+ children: g(t[e.name], e)
470
477
  }, n))
471
478
  }, n));
472
479
  })() })]
473
480
  })
474
481
  }),
475
- e.type === "text" && e.text && /* @__PURE__ */ F("div", {
482
+ e.type === "text" && e.text && /* @__PURE__ */ R("div", {
476
483
  className: "prose max-w-none",
477
- children: /* @__PURE__ */ F("p", { children: e.text })
484
+ children: /* @__PURE__ */ R("p", { children: e.text })
478
485
  }),
479
- e.type === "page-break" && /* @__PURE__ */ F("div", { className: "border-t-2 border-dashed my-8 print:page-break-after-always" }),
480
- Array.isArray(e.content) ? e.content.map((e, t) => /* @__PURE__ */ F(S, { schema: w(e) }, t)) : e.content && /* @__PURE__ */ F(S, { schema: w(e.content) })
486
+ e.type === "page-break" && /* @__PURE__ */ R("div", { className: "border-t-2 border-dashed my-8 print:page-break-after-always" }),
487
+ Array.isArray(e.content) ? e.content.map((e, t) => /* @__PURE__ */ R(w, { schema: E(e) }, t)) : ee(e.content, (e) => /* @__PURE__ */ R(w, { schema: E(e) }))
481
488
  ]
482
489
  }, t)),
483
- !n.sections && r && r.length > 0 && /* @__PURE__ */ F("div", {
490
+ !n.sections && r && r.length > 0 && /* @__PURE__ */ R("div", {
484
491
  className: "border rounded-lg overflow-x-auto",
485
- children: /* @__PURE__ */ I("table", {
492
+ children: /* @__PURE__ */ z("table", {
486
493
  className: "w-full text-sm min-w-[600px]",
487
- children: [/* @__PURE__ */ F("thead", {
494
+ children: [/* @__PURE__ */ R("thead", {
488
495
  className: "bg-muted",
489
- children: /* @__PURE__ */ F("tr", { children: n.fields?.map((e, t) => /* @__PURE__ */ F("th", {
496
+ children: /* @__PURE__ */ R("tr", { children: n.fields?.map((e, t) => /* @__PURE__ */ R("th", {
490
497
  className: `px-4 py-2 font-medium ${e.type === "number" ? "text-right" : "text-left"}`,
491
498
  children: e.label || e.name
492
499
  }, t)) })
493
- }), /* @__PURE__ */ F("tbody", { children: r.map((e, t) => /* @__PURE__ */ F("tr", {
500
+ }), /* @__PURE__ */ R("tbody", { children: r.map((e, t) => /* @__PURE__ */ R("tr", {
494
501
  className: "border-t hover:bg-muted/50 even:bg-muted/20",
495
- children: n.fields?.map((t, n) => /* @__PURE__ */ F("td", {
502
+ children: n.fields?.map((t, n) => /* @__PURE__ */ R("td", {
496
503
  className: `px-4 py-2 ${t.type === "number" ? "text-right tabular-nums" : ""}`,
497
- style: m(t.name, e[t.name]),
498
- children: h(e[t.name], t)
504
+ style: h(t.name, e[t.name]),
505
+ children: g(e[t.name], t)
499
506
  }, n))
500
507
  }, t)) })]
501
508
  })
502
509
  })
503
510
  ]
504
511
  })] })]
505
- }) : /* @__PURE__ */ F(k, { children: /* @__PURE__ */ F(A, {
512
+ }) : /* @__PURE__ */ R(M, { children: /* @__PURE__ */ R(N, {
506
513
  className: "p-8 text-center text-muted-foreground",
507
514
  children: "No report to display"
508
515
  }) });
509
516
  };
510
517
  //#endregion
511
518
  //#region src/DatasetReportRenderer.tsx
512
- function ye(e) {
519
+ function we(e) {
513
520
  if (!e || typeof e != "object") return !1;
514
521
  let t = e;
515
522
  return typeof t.dataset == "string" && t.dataset.length > 0 || t.type === "joined" && Array.isArray(t.blocks) && t.blocks.some((e) => typeof e?.dataset == "string");
516
523
  }
517
- var be = /* @__PURE__ */ new Set(), xe = () => globalThis.process?.env?.NODE_ENV !== "production";
518
- function Se(e, t) {
519
- if (!xe()) return;
524
+ var Te = /* @__PURE__ */ new Set(), Ee = () => globalThis.process?.env?.NODE_ENV !== "production";
525
+ function De(e, t) {
526
+ if (!Ee()) return;
520
527
  let n = e.filter;
521
528
  if (n === void 0) return;
522
529
  let r = `${t}:${n && typeof n == "object" ? Object.keys(n).sort().join(",") : String(n)}`;
523
- be.has(r) || (be.add(r), console.warn(`[ObjectUI] ${t} carries \`filter\`, which is not an authorable key. Did you mean \`filter\` → \`runtimeFilter\`? NO filter was applied — it renders UNFILTERED, showing rows the report was scoped to exclude. \`ReportSchema\` (\`@objectstack/spec\`) is strict and rejects \`filter\`, so this document did not come through the validated path; the renderer no longer reads it either. Fix the producer: rename \`filter\` to \`runtimeFilter\`. (objectui#5137)`));
530
+ Te.has(r) || (Te.add(r), console.warn(`[ObjectUI] ${t} carries \`filter\`, which is not an authorable key. Did you mean \`filter\` → \`runtimeFilter\`? NO filter was applied — it renders UNFILTERED, showing rows the report was scoped to exclude. \`ReportSchema\` (\`@objectstack/spec\`) is strict and rejects \`filter\`, so this document did not come through the validated path; the renderer no longer reads it either. Fix the producer: rename \`filter\` to \`runtimeFilter\`. (objectui#5137)`));
524
531
  }
525
- function Ce(e) {
532
+ function Oe(e) {
526
533
  return `Report \`${e.name ?? "(unnamed)"}\``;
527
534
  }
528
- function we(e, t) {
535
+ function ke(e, t) {
529
536
  return e ? typeof e == "string" ? e : typeof e == "object" && typeof e.default == "string" ? e.default : t : t;
530
537
  }
531
- function Y(e) {
538
+ function X(e) {
532
539
  return Array.isArray(e) ? e.filter((e) => typeof e == "string" && !!e) : [];
533
540
  }
534
- function Te(e) {
541
+ function Ae(e) {
535
542
  if (!Array.isArray(e)) return;
536
543
  let t = {};
537
544
  for (let n of e) {
538
545
  let e = n && typeof n == "object" ? n.by : void 0;
539
- typeof e != "string" || !e || (t[e] = n.direction === "desc" ? "desc" : "asc");
546
+ typeof e == "string" && e && (t[e] = n.direction === "desc" ? "desc" : "asc");
540
547
  }
541
548
  return Object.keys(t).length > 0 ? t : void 0;
542
549
  }
543
- function Ee(e, t, n) {
550
+ function je(e, t, n) {
544
551
  if (!e) return;
545
552
  let r = /* @__PURE__ */ new Set([...t, ...n]), i = {};
546
553
  for (let [t, n] of Object.entries(e)) r.has(t) && (i[t] = n);
547
554
  return Object.keys(i).length > 0 ? i : void 0;
548
555
  }
549
- function X(e, t, n, r, i, a, o) {
550
- let [s, c] = v.useState({
556
+ function Z(e, t, n, r, i, a, o) {
557
+ let [s, c] = b.useState({
551
558
  status: "idle",
552
559
  rows: []
553
- }), l = Ee(o, t, n), u = JSON.stringify(r ?? null), d = JSON.stringify(a ?? null), f = JSON.stringify(l ?? null), p = `${e}|${t.join(",")}|${n.join(",")}|${u}|${d}|${f}`;
554
- return v.useEffect(() => {
560
+ }), l = je(o, t, n), u = JSON.stringify(r ?? null), d = JSON.stringify(a ?? null), f = JSON.stringify(l ?? null), p = `${e}|${t.join(",")}|${n.join(",")}|${u}|${d}|${f}`, [m, h] = b.useState(void 0), g = D(m), _ = b.useRef(null);
561
+ return b.useEffect(() => {
555
562
  let o = i;
556
563
  if (!o || typeof o.queryDataset != "function") {
557
- c({
564
+ _.current = null, h(void 0), c({
558
565
  status: "error",
559
566
  rows: [],
560
567
  error: "This data source does not support dataset queries."
@@ -562,24 +569,24 @@ function X(e, t, n, r, i, a, o) {
562
569
  return;
563
570
  }
564
571
  if (!e || n.length === 0) {
565
- c({
572
+ _.current = null, h(void 0), c({
566
573
  status: "idle",
567
574
  rows: []
568
575
  });
569
576
  return;
570
577
  }
571
- let s = !1;
572
- return c({
578
+ let s = !1, u = _.current === p;
579
+ return _.current = p, u || (h(void 0), c({
573
580
  status: "loading",
574
581
  rows: []
575
- }), o.queryDataset(e, {
582
+ })), o.queryDataset(e, {
576
583
  dimensions: t,
577
584
  measures: n,
578
585
  ...r && Object.keys(r).length > 0 ? { runtimeFilter: r } : {},
579
586
  ...a ? { totals: { groupings: a } } : {},
580
587
  ...l ? { order: l } : {}
581
588
  }).then((e) => {
582
- s || c({
589
+ s || (h(typeof e?.object == "string" && e.object ? e.object : void 0), c({
583
590
  status: "ok",
584
591
  rows: Array.isArray(e?.rows) ? e.rows : [],
585
592
  fields: Array.isArray(e?.fields) ? e.fields : [],
@@ -588,7 +595,7 @@ function X(e, t, n, r, i, a, o) {
588
595
  drillRawRows: Array.isArray(e?.drillRawRows) ? e.drillRawRows : void 0,
589
596
  drillRanges: Array.isArray(e?.drillRanges) ? e.drillRanges : void 0,
590
597
  totals: Array.isArray(e?.totals) ? e.totals : void 0
591
- });
598
+ }));
592
599
  }).catch((e) => {
593
600
  s || c({
594
601
  status: "error",
@@ -598,10 +605,18 @@ function X(e, t, n, r, i, a, o) {
598
605
  }), () => {
599
606
  s = !0;
600
607
  };
601
- }, [p]), s;
608
+ }, [p, g]), s;
602
609
  }
603
- function De({ dataset: e }) {
604
- return /* @__PURE__ */ I("div", {
610
+ function Me(...e) {
611
+ try {
612
+ return i(...e);
613
+ } catch (e) {
614
+ if (!(e instanceof t)) throw e;
615
+ return console.warn(`[DatasetReportRenderer] drill-down refused — the drilled list cannot be scoped: ${e.message}`), null;
616
+ }
617
+ }
618
+ function Ne({ dataset: e }) {
619
+ return /* @__PURE__ */ z("div", {
605
620
  className: "flex items-center justify-center rounded-md border border-dashed bg-muted/20 p-4 text-xs text-muted-foreground",
606
621
  children: [
607
622
  "This report binds the “",
@@ -610,81 +625,86 @@ function De({ dataset: e }) {
610
625
  ]
611
626
  });
612
627
  }
613
- function Z({ status: e, error: t }) {
614
- return e === "error" ? /* @__PURE__ */ I("div", {
628
+ function Q({ status: e, error: t }) {
629
+ return e === "error" ? /* @__PURE__ */ z("div", {
615
630
  role: "alert",
616
631
  className: "flex items-start gap-2 rounded-md border border-destructive/40 bg-destructive/5 px-3 py-2 text-xs text-destructive",
617
- children: [/* @__PURE__ */ F(ee, { className: "h-3.5 w-3.5 mt-0.5 shrink-0" }), /* @__PURE__ */ F("span", {
632
+ children: [/* @__PURE__ */ R(te, { className: "h-3.5 w-3.5 mt-0.5 shrink-0" }), /* @__PURE__ */ R("span", {
618
633
  className: "break-words",
619
634
  children: t
620
635
  })]
621
- }) : /* @__PURE__ */ I("div", {
636
+ }) : /* @__PURE__ */ z("div", {
622
637
  className: "flex items-center gap-2 p-4 text-xs text-muted-foreground",
623
- children: [/* @__PURE__ */ F(te, { className: "h-4 w-4 animate-spin" }), " Running report…"]
638
+ children: [/* @__PURE__ */ R(ne, { className: "h-4 w-4 animate-spin" }), " Running report…"]
624
639
  });
625
640
  }
626
- function Oe() {
627
- return /* @__PURE__ */ I("div", {
641
+ function Pe() {
642
+ return /* @__PURE__ */ z("div", {
628
643
  className: "flex flex-col items-center justify-center gap-2 rounded-md border border-dashed bg-muted/20 p-6 text-xs text-muted-foreground",
629
- children: [/* @__PURE__ */ F(re, { className: "h-6 w-6" }), " The dataset returned no rows for this report’s scope."]
644
+ children: [/* @__PURE__ */ R(ae, { className: "h-6 w-6" }), " The dataset returned no rows for this report’s scope."]
630
645
  });
631
646
  }
632
- var ke = "cursor-pointer hover:bg-accent/40";
633
- function Ae({ dataset: e, rows: t, values: n, runtimeFilter: a, dataSource: o, onDrill: s, order: c, withTotals: d }) {
634
- let f = X(e, t, n, a, o, d && t.length > 0 ? [[]] : void 0, c), { fieldLabel: p } = B(), m = V(), h = z(), g = T(f.object, f.dimensionFields, t);
635
- if (n.length === 0) return /* @__PURE__ */ F(De, { dataset: e });
636
- if (f.status === "loading" || f.status === "idle") return /* @__PURE__ */ F(Z, { status: f.status });
637
- if (f.status === "error") return /* @__PURE__ */ F(Z, {
647
+ var Fe = "cursor-pointer hover:bg-accent/40";
648
+ function Ie({ dataset: e, rows: t, values: n, runtimeFilter: r, dataSource: i, onDrill: o, order: s, withTotals: c }) {
649
+ let l = Z(e, t, n, r, i, c && t.length > 0 ? [[]] : void 0, s), { fieldLabel: f } = U(), p = W(), m = H(), h = O(l.object, l.dimensionFields, t);
650
+ if (n.length === 0) return /* @__PURE__ */ R(Ne, { dataset: e });
651
+ if (l.status === "loading" || l.status === "idle") return /* @__PURE__ */ R(Q, { status: l.status });
652
+ if (l.status === "error") return /* @__PURE__ */ R(Q, {
638
653
  status: "error",
639
- error: f.error
654
+ error: l.error
640
655
  });
641
- if (f.rows.length === 0) return /* @__PURE__ */ F(Oe, {});
642
- let v = !!s && t.length > 0, y = f.dimensionFields ? t.filter((e) => e in f.dimensionFields) : [], b = (n, i) => {
643
- let o = {};
644
- for (let e of t) o[e] = n[e];
645
- let c = f.drillRanges?.[i], l = !!c && Object.keys(c).length > 0, u = f.object && (y.length > 0 || l) ? r(f.drillRawRows?.[i], y, f.dimensionFields ?? {}, a, c) : void 0;
646
- s({
656
+ if (l.rows.length === 0) return /* @__PURE__ */ R(Pe, {});
657
+ let g = !!o && t.length > 0, _ = l.dimensionFields ? t.filter((e) => e in l.dimensionFields) : [], y = (n, i) => {
658
+ let a = {};
659
+ for (let e of t) a[e] = n[e];
660
+ let s = l.drillRanges?.[i], c = !!s && Object.keys(s).length > 0, u;
661
+ if (l.object && (_.length > 0 || c)) {
662
+ let e = Me(l.drillRawRows?.[i], _, l.dimensionFields ?? {}, r, s);
663
+ if (e === null) return;
664
+ u = e;
665
+ }
666
+ o({
647
667
  dataset: e,
648
- groupKey: o,
649
- runtimeFilter: a,
650
- object: f.object,
668
+ groupKey: a,
669
+ runtimeFilter: r,
670
+ object: l.object,
651
671
  objectFilter: u
652
672
  });
653
- }, { measureField: x, headerLabel: S } = i(f.fields, f.object, p), C = [...t, ...n], w = _(f.rows, g), E = d ? f.totals?.find((e) => Array.isArray(e.dimensions) && e.dimensions.length === 0)?.rows?.[0] : void 0, D = m("report.total", "Total");
654
- return /* @__PURE__ */ F("div", {
673
+ }, { measureField: b, headerLabel: x } = a(l.fields, l.object, f, V(p)), S = [...t, ...n], C = v(l.rows, h), w = c ? l.totals?.find((e) => Array.isArray(e.dimensions) && e.dimensions.length === 0)?.rows?.[0] : void 0, T = p("report.total", "Total");
674
+ return /* @__PURE__ */ R("div", {
655
675
  className: "overflow-auto max-h-[70vh] rounded-md border",
656
- children: /* @__PURE__ */ I("table", {
676
+ children: /* @__PURE__ */ z("table", {
657
677
  className: "w-full text-xs",
658
- children: [/* @__PURE__ */ F("thead", {
678
+ children: [/* @__PURE__ */ R("thead", {
659
679
  className: "bg-muted/40",
660
- children: /* @__PURE__ */ F("tr", { children: C.map((e) => /* @__PURE__ */ F("th", {
680
+ children: /* @__PURE__ */ R("tr", { children: S.map((e) => /* @__PURE__ */ R("th", {
661
681
  className: "px-2 py-1.5 text-left font-medium whitespace-nowrap",
662
- children: S(e)
682
+ children: x(e)
663
683
  }, e)) })
664
- }), /* @__PURE__ */ I("tbody", { children: [w.map((e, t) => /* @__PURE__ */ F("tr", {
665
- className: `border-t${v ? ` ${ke}` : ""}`,
666
- "data-testid": v ? "dataset-drill-row" : void 0,
667
- onClick: v ? () => b(f.rows[t], t) : void 0,
668
- children: C.map((t) => /* @__PURE__ */ F("td", {
684
+ }), /* @__PURE__ */ z("tbody", { children: [C.map((e, t) => /* @__PURE__ */ R("tr", {
685
+ className: `border-t${g ? ` ${Fe}` : ""}`,
686
+ "data-testid": g ? "dataset-drill-row" : void 0,
687
+ onClick: g ? () => y(l.rows[t], t) : void 0,
688
+ children: S.map((t) => /* @__PURE__ */ R("td", {
669
689
  className: "px-2 py-1 tabular-nums whitespace-nowrap",
670
- children: n.includes(t) ? u(e[t], x(t)?.format, x(t)?.currency, x(t)?.percentScale, h) : l(e[t], h)
690
+ children: n.includes(t) ? d(e[t], b(t)?.format, b(t)?.currency, b(t)?.percentScale, m) : u(e[t], m)
671
691
  }, t))
672
- }, t)), E && /* @__PURE__ */ I("tr", {
692
+ }, t)), w && /* @__PURE__ */ z("tr", {
673
693
  className: "border-t bg-muted/30 font-medium",
674
694
  "data-testid": "dataset-report-total-row",
675
- children: [t.length > 0 && /* @__PURE__ */ F("td", {
695
+ children: [t.length > 0 && /* @__PURE__ */ R("td", {
676
696
  colSpan: t.length,
677
697
  className: "px-2 py-1 whitespace-nowrap",
678
- children: D
679
- }), n.map((e) => /* @__PURE__ */ F("td", {
698
+ children: T
699
+ }), n.map((e) => /* @__PURE__ */ R("td", {
680
700
  className: "px-2 py-1 tabular-nums whitespace-nowrap",
681
- children: u(E[e], x(e)?.format, x(e)?.currency, x(e)?.percentScale, h)
701
+ children: d(w[e], b(e)?.format, b(e)?.currency, b(e)?.percentScale, m)
682
702
  }, e))]
683
703
  })] })]
684
704
  })
685
705
  });
686
706
  }
687
- function je(e) {
707
+ function Le(e) {
688
708
  switch (e) {
689
709
  case "summary": return "summary";
690
710
  case "matrix": return "matrix";
@@ -692,7 +712,7 @@ function je(e) {
692
712
  default: return "tabular";
693
713
  }
694
714
  }
695
- function Me(e) {
715
+ function Re(e) {
696
716
  switch (e) {
697
717
  case "bar":
698
718
  case "column":
@@ -723,9 +743,9 @@ function Me(e) {
723
743
  };
724
744
  }
725
745
  }
726
- function Ne(t) {
727
- let [, n] = v.useReducer((e) => e + 1, 0);
728
- return v.useEffect(() => {
746
+ function ze(t) {
747
+ let [, n] = b.useReducer((e) => e + 1, 0);
748
+ return b.useEffect(() => {
729
749
  if (e.get(t)) return;
730
750
  let r = typeof e.subscribe == "function" ? e.subscribe(() => {
731
751
  e.get(t) && n();
@@ -733,127 +753,130 @@ function Ne(t) {
733
753
  return i && typeof i.then == "function" && i.then(() => n()).catch(() => {}), r;
734
754
  }, [t]), e.get(t);
735
755
  }
736
- function Pe(e, t, n) {
737
- if (!(!Array.isArray(e) || !t)) for (let r of e) {
756
+ function Be(e, t, n) {
757
+ if (Array.isArray(e) && t) for (let r of e) {
738
758
  if (!r || typeof r != "object") continue;
739
759
  let { name: e, label: i } = r;
740
- if (e === t) return oe(i, n) || void 0;
760
+ if (e === t) return ce(i, n) || void 0;
741
761
  }
742
762
  }
743
- function Fe({ dataset: e, chart: r, runtimeFilter: l, dataSource: p, order: m }) {
744
- let h = typeof r.xAxis == "string" ? r.xAxis : "", g = typeof r.yAxis == "string" ? r.yAxis : "", y = Me(r.type), b = y.kind === "series" || y.kind === "single_value", x = X(e, y.kind === "series" && h ? [h] : [], b && g ? [g] : [], l, p, void 0, m), S = Ne("chart"), { fieldLabel: C, fieldOptionLabel: w } = B(), T = V(), D = z(), { language: O } = se(), k = v.useMemo(() => h ? [h] : [], [h]), A = E(x.object, x.dimensionFields, k), { categoryColors: j, dimensionLabels: M, categoryOrder: N } = v.useMemo(() => {
763
+ function Ve({ dataset: e, chart: t, runtimeFilter: i, dataSource: u, order: m }) {
764
+ let h = typeof t.xAxis == "string" ? t.xAxis : "", g = typeof t.yAxis == "string" ? t.yAxis : "", _ = Re(t.type), y = _.kind === "series" || _.kind === "single_value", x = Z(e, _.kind === "series" && h ? [h] : [], y && g ? [g] : [], i, u, void 0, m), S = ze("chart"), { fieldLabel: C, fieldOptionLabel: w } = U(), T = W(), E = H(), { language: D } = le(), O = b.useMemo(() => h ? [h] : [], [h]), A = k(x.object, x.dimensionFields, O), { categoryColors: j, dimensionLabels: M, categoryOrder: N } = b.useMemo(() => {
745
765
  if (!A) return {
746
766
  categoryColors: null,
747
767
  dimensionLabels: null,
748
768
  categoryOrder: null
749
769
  };
750
- let { metaByPath: e, relabel: n } = A, r = n[0]?.path, i = r ? e[r] : void 0, o = r ? d(i?.options, c(i, w)) : void 0;
770
+ let { metaByPath: e, relabel: t } = A, r = t[0]?.path, i = r ? e[r] : void 0, a = r ? f(i?.options, l(i, w)) : void 0;
751
771
  return {
752
- categoryColors: a(o),
753
- dimensionLabels: s(e, n, w),
754
- categoryOrder: t(o)
772
+ categoryColors: o(a),
773
+ dimensionLabels: c(e, t, w),
774
+ categoryOrder: n(a)
755
775
  };
756
- }, [A, w]), P = typeof r.title == "string" ? r.title : void 0;
757
- if (y.kind === "tabular") return null;
758
- if (y.kind === "unsupported") return /* @__PURE__ */ I("div", {
776
+ }, [A, w]), P = ce(t.title, D) || void 0;
777
+ if (_.kind === "tabular") return null;
778
+ if (_.kind === "unsupported") return /* @__PURE__ */ z("div", {
759
779
  className: "rounded-md border border-dashed bg-muted/20 px-3 py-2 text-xs text-muted-foreground",
760
780
  "data-testid": "dataset-report-chart-unsupported",
761
781
  children: [
762
782
  "Chart type “",
763
- y.type,
764
- "” is not a spec chart type — the grouped table below carries this report’s numbers."
783
+ _.type,
784
+ "” is not a spec chart type — the report’s table carries its numbers."
765
785
  ]
766
786
  });
767
- if (y.kind === "series" && !h || !g) return null;
768
- if (x.status === "loading" || x.status === "idle") return /* @__PURE__ */ I("div", {
787
+ if (_.kind === "series" && !h || !g) return null;
788
+ if (x.status === "loading" || x.status === "idle") return /* @__PURE__ */ z("div", {
769
789
  className: "flex items-center gap-2 p-4 text-xs text-muted-foreground",
770
- children: [/* @__PURE__ */ F(te, { className: "h-4 w-4 animate-spin" }), " Loading chart…"]
790
+ children: [/* @__PURE__ */ R(ne, { className: "h-4 w-4 animate-spin" }), " Loading chart…"]
771
791
  });
772
792
  if (x.status === "error" || x.rows.length === 0) return null;
773
- let { measureField: ee, headerLabel: L } = i(x.fields, x.object, C), R = Pe(r.series, g, O) ?? L(g);
774
- if (y.kind === "single_value") {
775
- let e = ee(g);
776
- return /* @__PURE__ */ I("div", {
793
+ let { measureField: F, headerLabel: I } = a(x.fields, x.object, C, V(T)), L = Be(t.series, g, D) ?? I(g);
794
+ if (_.kind === "single_value") {
795
+ let e = F(g);
796
+ return /* @__PURE__ */ z("div", {
777
797
  className: "rounded-md border bg-card p-3",
778
798
  "data-testid": "dataset-report-metric",
779
- children: [P ? /* @__PURE__ */ F("h3", {
799
+ children: [P ? /* @__PURE__ */ R("h3", {
780
800
  className: "mb-2 text-sm font-semibold",
781
801
  children: P
782
- }) : null, /* @__PURE__ */ I("div", {
802
+ }) : null, /* @__PURE__ */ z("div", {
783
803
  className: "flex flex-col gap-0.5 py-2",
784
- children: [/* @__PURE__ */ F("span", {
804
+ children: [/* @__PURE__ */ R("span", {
785
805
  className: "text-2xl font-semibold tabular-nums",
786
- children: u(x.rows[0]?.[g], e?.format, e?.currency, e?.percentScale, D)
787
- }), /* @__PURE__ */ F("span", {
806
+ children: d(x.rows[0]?.[g], e?.format, e?.currency, e?.percentScale, E)
807
+ }), /* @__PURE__ */ R("span", {
788
808
  className: "text-xs text-muted-foreground",
789
- children: R
809
+ children: L
790
810
  })]
791
811
  })]
792
812
  });
793
813
  }
794
814
  if (!S) return null;
795
- let { data: ne, xAxisKey: re, series: ie } = n(_(x.rows, M), [h], [g], x.fields, { nullCategoryLabel: T("chart.nullCategory", "(None)") }), ae = f(ie, r.series).map((e) => e.dataKey === g ? {
815
+ let { data: ee, xAxisKey: te, series: B } = r(v(x.rows, M), [h], [g], x.fields, {
816
+ nullCategoryLabel: T("chart.nullCategory", "(None)"),
817
+ builtinAggregateLabels: V(T)
818
+ }), re = p(B, t.series).map((e) => e.dataKey === g ? {
796
819
  ...e,
797
- label: R
798
- } : e), { title: oe, ...H } = o(r, j);
799
- return /* @__PURE__ */ I("div", {
820
+ label: L
821
+ } : e), { title: ie, ...ae } = s(t, j);
822
+ return /* @__PURE__ */ z("div", {
800
823
  className: "rounded-md border bg-card p-3",
801
824
  "data-testid": "dataset-report-chart",
802
- children: [P ? /* @__PURE__ */ F("h3", {
825
+ children: [P ? /* @__PURE__ */ R("h3", {
803
826
  className: "mb-2 text-sm font-semibold",
804
827
  children: P
805
- }) : null, /* @__PURE__ */ F(S, { schema: {
806
- chartType: y.chartType,
807
- data: ne,
808
- xAxisKey: re,
809
- series: ae,
828
+ }) : null, /* @__PURE__ */ R(S, { schema: {
829
+ chartType: _.chartType,
830
+ data: ee,
831
+ xAxisKey: te,
832
+ series: re,
810
833
  height: 280,
811
834
  isAnimationActive: !1,
812
- ...H,
835
+ ...ae,
813
836
  ...N ? { categoryOrder: N } : {}
814
837
  } })]
815
838
  });
816
839
  }
817
- function Q(e, t) {
818
- return m(e.map((e) => g(t[e])));
840
+ function $(e, t) {
841
+ return h(e.map((e) => _(t[e])));
819
842
  }
820
- function Ie(e, t, n) {
821
- return e.map((e) => l(t[e], n)).join(" / ");
843
+ function He(e, t, n) {
844
+ return e.map((e) => u(t[e], n)).join(" / ");
822
845
  }
823
- function Le({ dataset: e, rows: t, columnsAcross: n, values: a, runtimeFilter: o, dataSource: s, onDrill: c, order: d }) {
824
- let f = X(e, [...t, ...n], a, o, s, [
846
+ function Ue({ dataset: e, rows: t, columnsAcross: n, values: r, runtimeFilter: i, dataSource: o, onDrill: s, order: c }) {
847
+ let l = Z(e, [...t, ...n], r, i, o, [
825
848
  t,
826
849
  n,
827
850
  []
828
- ], d), p = V(), { fieldLabel: m } = B(), g = z(), y = T(f.object, f.dimensionFields, [...t, ...n]), b = v.useMemo(() => {
829
- if (f.status !== "ok") return null;
851
+ ], c), f = W(), { fieldLabel: p } = U(), m = H(), h = O(l.object, l.dimensionFields, [...t, ...n]), _ = b.useMemo(() => {
852
+ if (l.status !== "ok") return null;
830
853
  let e = [], r = [], i = /* @__PURE__ */ new Set(), a = /* @__PURE__ */ new Set(), o = /* @__PURE__ */ new Map();
831
- return _(f.rows, y).forEach((s, c) => {
832
- let l = f.rows[c], u = Q(t, s), d = Q(n, s);
833
- if (!i.has(u)) {
834
- i.add(u);
854
+ return v(l.rows, h).forEach((s, c) => {
855
+ let u = l.rows[c], d = $(t, s), f = $(n, s);
856
+ if (!i.has(d)) {
857
+ i.add(d);
835
858
  let n = {}, r = {};
836
- for (let e of t) n[e] = l[e], r[e] = s[e];
859
+ for (let e of t) n[e] = u[e], r[e] = s[e];
837
860
  e.push({
838
- id: u,
839
- label: Ie(t, s, g),
861
+ id: d,
862
+ label: He(t, s, m),
840
863
  key: n,
841
864
  display: r
842
865
  });
843
866
  }
844
- if (!a.has(d)) {
845
- a.add(d);
867
+ if (!a.has(f)) {
868
+ a.add(f);
846
869
  let e = {}, t = {};
847
- for (let r of n) e[r] = l[r], t[r] = s[r];
870
+ for (let r of n) e[r] = u[r], t[r] = s[r];
848
871
  r.push({
849
- id: d,
850
- label: Ie(n, s, g),
872
+ id: f,
873
+ label: He(n, s, m),
851
874
  key: e,
852
875
  display: t
853
876
  });
854
877
  }
855
- o.set(h(u, d), {
856
- row: l,
878
+ o.set(g(d, f), {
879
+ row: u,
857
880
  index: c
858
881
  });
859
882
  }), {
@@ -862,115 +885,120 @@ function Le({ dataset: e, rows: t, columnsAcross: n, values: a, runtimeFilter: o
862
885
  cells: o
863
886
  };
864
887
  }, [
865
- f,
888
+ l,
866
889
  t,
867
890
  n,
868
- y,
869
- g
891
+ h,
892
+ m
870
893
  ]);
871
- if (a.length === 0) return /* @__PURE__ */ F(De, { dataset: e });
872
- if (f.status === "loading" || f.status === "idle") return /* @__PURE__ */ F(Z, { status: f.status });
873
- if (f.status === "error") return /* @__PURE__ */ F(Z, {
894
+ if (r.length === 0) return /* @__PURE__ */ R(Ne, { dataset: e });
895
+ if (l.status === "loading" || l.status === "idle") return /* @__PURE__ */ R(Q, { status: l.status });
896
+ if (l.status === "error") return /* @__PURE__ */ R(Q, {
874
897
  status: "error",
875
- error: f.error
898
+ error: l.error
876
899
  });
877
- if (!b || b.rowHeaders.length === 0) return /* @__PURE__ */ F(Oe, {});
878
- let { measureField: x, headerLabel: S } = i(f.fields, f.object, m), C = p("report.total", "Total"), w = !!c, E = f.dimensionFields ? [...t, ...n].filter((e) => e in f.dimensionFields) : [], D = (t, n, i) => {
879
- let a = f.drillRanges?.[i], s = !!a && Object.keys(a).length > 0, l = f.object && (E.length > 0 || s) ? r(f.drillRawRows?.[i], E, f.dimensionFields ?? {}, o, a) : void 0;
880
- c({
900
+ if (!_ || _.rowHeaders.length === 0) return /* @__PURE__ */ R(Pe, {});
901
+ let { measureField: y, headerLabel: x } = a(l.fields, l.object, p, V(f)), S = f("report.total", "Total"), C = !!s, w = l.dimensionFields ? [...t, ...n].filter((e) => e in l.dimensionFields) : [], T = (t, n, r) => {
902
+ let a = l.drillRanges?.[r], o = !!a && Object.keys(a).length > 0, c;
903
+ if (l.object && (w.length > 0 || o)) {
904
+ let e = Me(l.drillRawRows?.[r], w, l.dimensionFields ?? {}, i, a);
905
+ if (e === null) return;
906
+ c = e;
907
+ }
908
+ s({
881
909
  dataset: e,
882
910
  groupKey: {
883
911
  ...t,
884
912
  ...n
885
913
  },
886
- runtimeFilter: o,
887
- object: f.object,
888
- objectFilter: l
914
+ runtimeFilter: i,
915
+ object: l.object,
916
+ objectFilter: c
889
917
  });
890
- }, O = b.colHeaders.flatMap((e) => a.map((t) => ({
918
+ }, E = _.colHeaders.flatMap((e) => r.map((t) => ({
891
919
  col: e,
892
920
  measure: t,
893
- header: a.length === 1 ? e.label : `${e.label} · ${S(t)}`
894
- }))), k = (e) => {
895
- let t = f.totals?.find((t) => Array.isArray(t.dimensions) && t.dimensions.join(",") === e.join(","))?.rows;
896
- return t && _(t, y);
897
- }, A = /* @__PURE__ */ new Map();
898
- for (let e of k(t) ?? []) A.set(Q(t, e), e);
899
- let j = /* @__PURE__ */ new Map();
900
- for (let e of k(n) ?? []) j.set(Q(n, e), e);
901
- let M = k([])?.[0], N = A.size > 0, P = j.size > 0;
902
- return /* @__PURE__ */ F("div", {
921
+ header: r.length === 1 ? e.label : `${e.label} · ${x(t)}`
922
+ }))), D = (e) => {
923
+ let t = l.totals?.find((t) => Array.isArray(t.dimensions) && t.dimensions.join(",") === e.join(","))?.rows;
924
+ return t && v(t, h);
925
+ }, k = /* @__PURE__ */ new Map();
926
+ for (let e of D(t) ?? []) k.set($(t, e), e);
927
+ let A = /* @__PURE__ */ new Map();
928
+ for (let e of D(n) ?? []) A.set($(n, e), e);
929
+ let j = D([])?.[0], M = k.size > 0, N = A.size > 0;
930
+ return /* @__PURE__ */ R("div", {
903
931
  className: "overflow-auto max-h-[70vh] rounded-md border",
904
932
  "data-testid": "dataset-matrix",
905
- children: /* @__PURE__ */ I("table", {
933
+ children: /* @__PURE__ */ z("table", {
906
934
  className: "w-full text-xs",
907
- children: [/* @__PURE__ */ F("thead", {
935
+ children: [/* @__PURE__ */ R("thead", {
908
936
  className: "bg-muted/40",
909
- children: /* @__PURE__ */ I("tr", { children: [
910
- t.map((e) => /* @__PURE__ */ F("th", {
937
+ children: /* @__PURE__ */ z("tr", { children: [
938
+ t.map((e) => /* @__PURE__ */ R("th", {
911
939
  className: "px-2 py-1.5 text-left font-medium whitespace-nowrap",
912
- children: S(e)
940
+ children: x(e)
913
941
  }, e)),
914
- O.map((e) => /* @__PURE__ */ F("th", {
942
+ E.map((e) => /* @__PURE__ */ R("th", {
915
943
  className: "px-2 py-1.5 text-right font-medium whitespace-nowrap",
916
944
  children: e.header
917
945
  }, `${e.col.id}-${e.measure}`)),
918
- N && a.map((e) => /* @__PURE__ */ F("th", {
946
+ M && r.map((e) => /* @__PURE__ */ R("th", {
919
947
  className: "px-2 py-1.5 text-right font-medium whitespace-nowrap",
920
948
  "data-testid": "matrix-total-col-header",
921
- children: a.length === 1 ? C : `${C} · ${S(e)}`
949
+ children: r.length === 1 ? S : `${S} · ${x(e)}`
922
950
  }, `total-${e}`))
923
951
  ] })
924
- }), /* @__PURE__ */ I("tbody", { children: [b.rowHeaders.map((e) => /* @__PURE__ */ I("tr", {
952
+ }), /* @__PURE__ */ z("tbody", { children: [_.rowHeaders.map((e) => /* @__PURE__ */ z("tr", {
925
953
  className: "border-t",
926
954
  children: [
927
- t.map((t) => /* @__PURE__ */ F("td", {
955
+ t.map((t) => /* @__PURE__ */ R("td", {
928
956
  className: "px-2 py-1 whitespace-nowrap font-medium",
929
- children: l(e.display[t], g)
957
+ children: u(e.display[t], m)
930
958
  }, t)),
931
- O.map((t) => {
932
- let n = b.cells.get(h(e.id, t.col.id)), r = n?.row[t.measure], i = w && n != null;
933
- return /* @__PURE__ */ F("td", {
934
- className: `px-2 py-1 text-right tabular-nums whitespace-nowrap${i ? ` ${ke}` : ""}`,
959
+ E.map((t) => {
960
+ let n = _.cells.get(g(e.id, t.col.id)), r = n?.row[t.measure], i = C && n != null;
961
+ return /* @__PURE__ */ R("td", {
962
+ className: `px-2 py-1 text-right tabular-nums whitespace-nowrap${i ? ` ${Fe}` : ""}`,
935
963
  "data-testid": i ? "dataset-drill-cell" : void 0,
936
- onClick: i ? () => D(e.key, t.col.key, n.index) : void 0,
937
- children: u(r, x(t.measure)?.format, x(t.measure)?.currency, x(t.measure)?.percentScale, g)
964
+ onClick: i ? () => T(e.key, t.col.key, n.index) : void 0,
965
+ children: d(r, y(t.measure)?.format, y(t.measure)?.currency, y(t.measure)?.percentScale, m)
938
966
  }, `${t.col.id}-${t.measure}`);
939
967
  }),
940
- N && a.map((t) => /* @__PURE__ */ F("td", {
968
+ M && r.map((t) => /* @__PURE__ */ R("td", {
941
969
  className: "px-2 py-1 text-right tabular-nums whitespace-nowrap font-medium",
942
970
  "data-testid": "matrix-row-total",
943
- children: u(A.get(e.id)?.[t], x(t)?.format, x(t)?.currency, x(t)?.percentScale, g)
971
+ children: d(k.get(e.id)?.[t], y(t)?.format, y(t)?.currency, y(t)?.percentScale, m)
944
972
  }, `total-${t}`))
945
973
  ]
946
- }, e.id)), P && /* @__PURE__ */ I("tr", {
974
+ }, e.id)), N && /* @__PURE__ */ z("tr", {
947
975
  className: "border-t bg-muted/30 font-medium",
948
976
  "data-testid": "matrix-total-row",
949
977
  children: [
950
- t.length > 0 && /* @__PURE__ */ F("td", {
978
+ t.length > 0 && /* @__PURE__ */ R("td", {
951
979
  colSpan: t.length,
952
980
  className: "px-2 py-1 whitespace-nowrap",
953
- children: C
981
+ children: S
954
982
  }),
955
- O.map((e) => /* @__PURE__ */ F("td", {
983
+ E.map((e) => /* @__PURE__ */ R("td", {
956
984
  className: "px-2 py-1 text-right tabular-nums whitespace-nowrap",
957
- children: u(j.get(e.col.id)?.[e.measure], x(e.measure)?.format, x(e.measure)?.currency, x(e.measure)?.percentScale, g)
985
+ children: d(A.get(e.col.id)?.[e.measure], y(e.measure)?.format, y(e.measure)?.currency, y(e.measure)?.percentScale, m)
958
986
  }, `${e.col.id}-${e.measure}`)),
959
- N && a.map((e) => /* @__PURE__ */ F("td", {
987
+ M && r.map((e) => /* @__PURE__ */ R("td", {
960
988
  className: "px-2 py-1 text-right tabular-nums whitespace-nowrap",
961
989
  "data-testid": "matrix-grand-total",
962
- children: u(M?.[e], x(e)?.format, x(e)?.currency, x(e)?.percentScale, g)
990
+ children: d(j?.[e], y(e)?.format, y(e)?.currency, y(e)?.percentScale, m)
963
991
  }, `grand-${e}`))
964
992
  ]
965
993
  })] })]
966
994
  })
967
995
  });
968
996
  }
969
- var Re = ({ report: e, dataSource: t, runtimeFilter: n, onDrill: r, className: i }) => {
970
- let a = Ce(e);
971
- Se(e, a);
972
- let o = p(e.runtimeFilter, n), s = e.drilldown === !1 ? void 0 : r, c = je(e.type);
973
- if (c === "joined" && Array.isArray(e.blocks)) return /* @__PURE__ */ F("div", {
997
+ var We = ({ report: e, dataSource: t, runtimeFilter: n, onDrill: r, className: i }) => {
998
+ let a = Oe(e);
999
+ De(e, a);
1000
+ let o = m(e.runtimeFilter, n), s = e.drilldown === !1 ? void 0 : r, c = Le(e.type);
1001
+ if (c === "joined" && Array.isArray(e.blocks)) return /* @__PURE__ */ R("div", {
974
1002
  className: i,
975
1003
  "data-testid": "dataset-joined-report",
976
1004
  "data-report-name": e.name,
@@ -980,141 +1008,134 @@ var Re = ({ report: e, dataSource: t, runtimeFilter: n, onDrill: r, className: i
980
1008
  gap: 24
981
1009
  },
982
1010
  children: e.blocks.map((e, n) => {
983
- Se(e, `${a} block \`${e.name ?? n}\``);
984
- let r = p(o, e.runtimeFilter), i = Y(e.columns), c = Te(e.order), l = je(e.type), u = l === "matrix" && i.length > 0 ? /* @__PURE__ */ F(Le, {
1011
+ De(e, `${a} block \`${e.name ?? n}\``);
1012
+ let r = m(o, e.runtimeFilter), i = X(e.columns), c = Ae(e.order), l = Le(e.type), u = l === "matrix" && i.length > 0 ? /* @__PURE__ */ R(Ue, {
985
1013
  dataset: String(e.dataset ?? ""),
986
- rows: Y(e.rows),
1014
+ rows: X(e.rows),
987
1015
  columnsAcross: i,
988
- values: Y(e.values),
1016
+ values: X(e.values),
989
1017
  runtimeFilter: r,
990
1018
  dataSource: t,
991
1019
  onDrill: s,
992
1020
  order: c
993
- }) : /* @__PURE__ */ F(Ae, {
1021
+ }) : /* @__PURE__ */ R(Ie, {
994
1022
  dataset: String(e.dataset ?? ""),
995
- rows: Y(e.rows),
996
- values: Y(e.values),
1023
+ rows: X(e.rows),
1024
+ values: X(e.values),
997
1025
  runtimeFilter: r,
998
1026
  dataSource: t,
999
1027
  onDrill: s,
1000
1028
  order: c,
1001
1029
  withTotals: l === "summary" || l === "matrix"
1002
1030
  });
1003
- return /* @__PURE__ */ I("section", {
1031
+ return /* @__PURE__ */ z("section", {
1004
1032
  "data-testid": "dataset-report-block",
1005
1033
  "data-block-id": e.name ?? `block-${n}`,
1006
1034
  className: "flex flex-col gap-2 rounded-lg border bg-card p-4",
1007
- children: [/* @__PURE__ */ I("header", {
1035
+ children: [/* @__PURE__ */ z("header", {
1008
1036
  className: "flex flex-col gap-0.5",
1009
- children: [/* @__PURE__ */ F("h3", {
1037
+ children: [/* @__PURE__ */ R("h3", {
1010
1038
  className: "text-sm font-semibold",
1011
- children: we(e.label, e.name ?? `Block ${n + 1}`)
1012
- }), e.description ? /* @__PURE__ */ F("p", {
1039
+ children: ke(e.label, e.name ?? `Block ${n + 1}`)
1040
+ }), e.description ? /* @__PURE__ */ R("p", {
1013
1041
  className: "text-xs text-muted-foreground",
1014
- children: we(e.description, "")
1042
+ children: ke(e.description, "")
1015
1043
  }) : null]
1016
1044
  }), u]
1017
1045
  }, e.name ?? `block-${n}`);
1018
1046
  })
1019
1047
  });
1020
- let l = Y(e.columns), u = Te(e.order);
1021
- if (c === "matrix" && l.length > 0) return /* @__PURE__ */ F("div", {
1022
- className: i,
1023
- "data-testid": "dataset-report",
1024
- "data-report-name": e.name,
1025
- children: /* @__PURE__ */ F(Le, {
1026
- dataset: String(e.dataset ?? ""),
1027
- rows: Y(e.rows),
1028
- columnsAcross: l,
1029
- values: Y(e.values),
1030
- runtimeFilter: o,
1031
- dataSource: t,
1032
- onDrill: s,
1033
- order: u
1034
- })
1048
+ let l = X(e.columns), u = Ae(e.order), d = c === "matrix" && l.length > 0, f = e.chart && typeof e.chart == "object" && e.chart.type ? e.chart : null, p = f ? /* @__PURE__ */ R(Ve, {
1049
+ dataset: String(e.dataset ?? ""),
1050
+ chart: f,
1051
+ runtimeFilter: o,
1052
+ dataSource: t,
1053
+ order: u
1054
+ }) : null, h = d ? /* @__PURE__ */ R(Ue, {
1055
+ dataset: String(e.dataset ?? ""),
1056
+ rows: X(e.rows),
1057
+ columnsAcross: l,
1058
+ values: X(e.values),
1059
+ runtimeFilter: o,
1060
+ dataSource: t,
1061
+ onDrill: s,
1062
+ order: u
1063
+ }) : /* @__PURE__ */ R(Ie, {
1064
+ dataset: String(e.dataset ?? ""),
1065
+ rows: X(e.rows),
1066
+ values: X(e.values),
1067
+ runtimeFilter: o,
1068
+ dataSource: t,
1069
+ onDrill: s,
1070
+ order: u,
1071
+ withTotals: c === "summary" || c === "matrix"
1035
1072
  });
1036
- let d = e.chart && typeof e.chart == "object" && e.chart.type ? e.chart : null;
1037
- return /* @__PURE__ */ I("div", {
1073
+ return /* @__PURE__ */ z("div", {
1038
1074
  className: `${i ?? ""} flex flex-col gap-3`,
1039
1075
  "data-testid": "dataset-report",
1040
1076
  "data-report-name": e.name,
1041
1077
  "data-report-presentation": c,
1042
- children: [d ? /* @__PURE__ */ F(Fe, {
1043
- dataset: String(e.dataset ?? ""),
1044
- chart: d,
1045
- runtimeFilter: o,
1046
- dataSource: t,
1047
- order: u
1048
- }) : null, /* @__PURE__ */ F(Ae, {
1049
- dataset: String(e.dataset ?? ""),
1050
- rows: Y(e.rows),
1051
- values: Y(e.values),
1052
- runtimeFilter: o,
1053
- dataSource: t,
1054
- onDrill: s,
1055
- order: u,
1056
- withTotals: c === "summary" || c === "matrix"
1057
- })]
1078
+ children: [d ? h : p, d ? p : h]
1058
1079
  });
1059
- }, $ = (e) => {
1060
- let { dataSource: t, rows: n, runtimeFilter: r, onDrill: i, className: a } = e, o = v.useContext(C), s = t ?? o?.dataSource, c = e.schema;
1061
- if (c && typeof c == "object" && c.type === "spec-report" && c.report && typeof c.report == "object" && (c = c.report), ye(c)) return /* @__PURE__ */ F(Re, {
1080
+ }, Ge = (e) => {
1081
+ let { dataSource: t, rows: n, runtimeFilter: r, onDrill: i, className: a } = e, o = b.useContext(T), s = t ?? o?.dataSource, c = e.schema;
1082
+ if (c && typeof c == "object" && c.type === "report" && c.report && typeof c.report == "object" && (c = c.report), we(c)) return /* @__PURE__ */ R(We, {
1062
1083
  report: c,
1063
1084
  dataSource: s,
1064
1085
  runtimeFilter: r,
1065
1086
  onDrill: i,
1066
1087
  className: a
1067
1088
  });
1068
- if (b(c)) {
1089
+ if (S(c)) {
1069
1090
  let e = {
1070
1091
  type: "report-viewer",
1071
- report: x(c),
1092
+ report: C(c),
1072
1093
  data: n ?? [],
1073
1094
  showToolbar: !1
1074
1095
  };
1075
- return /* @__PURE__ */ F("div", {
1096
+ return /* @__PURE__ */ R("div", {
1076
1097
  className: a,
1077
1098
  "data-testid": "report-presentation-bridge",
1078
- children: /* @__PURE__ */ F(J, { schema: e })
1099
+ children: /* @__PURE__ */ R(Ce, { schema: e })
1079
1100
  });
1080
1101
  }
1081
- return /* @__PURE__ */ F(H, { schema: c });
1102
+ return /* @__PURE__ */ R(ue, { schema: c });
1082
1103
  };
1083
1104
  //#endregion
1084
1105
  //#region src/LiveReportExporter.ts
1085
- async function ze(e, t) {
1086
- let { dataSource: n, resource: r, queryParams: i, format: a, exportConfig: o } = t, s = a || e.defaultExportFormat || "pdf";
1106
+ async function Ke(e, t) {
1107
+ let { dataSource: n, resource: r, queryParams: i, format: a, exportConfig: o, locale: s } = t, c = a || e.defaultExportFormat || "pdf";
1087
1108
  try {
1088
1109
  let t = (await n.find(r, i)).data || [];
1089
- return W(s, e, t, {
1090
- format: s,
1091
- ...e.exportConfigs?.[s],
1110
+ return he(c, e, t, {
1111
+ format: c,
1112
+ ...e.exportConfigs?.[c],
1092
1113
  ...o
1093
- }), {
1114
+ }, s), {
1094
1115
  success: !0,
1095
1116
  recordCount: t.length,
1096
- format: s
1117
+ format: c
1097
1118
  };
1098
1119
  } catch (e) {
1099
1120
  return {
1100
1121
  success: !1,
1101
1122
  recordCount: 0,
1102
- format: s,
1123
+ format: c,
1103
1124
  error: e.message
1104
1125
  };
1105
1126
  }
1106
1127
  }
1107
- function Be(e, t, n = {}) {
1108
- let { columns: r, filename: i, includeAggregationRow: a = !1 } = n, o = r || (e.fields || []).map(He), s = o.map((e) => e.header), c = t.map((e, t) => o.map((n) => {
1128
+ function qe(e, t, n = {}) {
1129
+ let { columns: r, filename: i, includeAggregationRow: a = !1, locale: o = "en" } = n, s = r || (e.fields || []).map(Ye), c = s.map((e) => e.header), l = t.map((e, t) => s.map((n) => {
1109
1130
  if (n.formula) return n.formula.replace(/\{ROW\}/g, String(t + 2));
1110
1131
  let r = e[n.name];
1111
- return Ue(r, n.numberFormat);
1132
+ return Xe(r, n.numberFormat, o);
1112
1133
  }));
1113
1134
  if (a && t.length > 0) {
1114
- let n = o.map((n, r) => {
1135
+ let n = s.map((n, r) => {
1115
1136
  let i = (e.fields || []).find((e) => e.name === n.name);
1116
1137
  if (i?.aggregation) {
1117
- let e = Ge(r), n = t.length + 1;
1138
+ let e = Qe(r), n = t.length + 1;
1118
1139
  switch (i.aggregation) {
1119
1140
  case "sum": return `=SUM(${e}2:${e}${n})`;
1120
1141
  case "avg": return `=AVERAGE(${e}2:${e}${n})`;
@@ -1126,17 +1147,17 @@ function Be(e, t, n = {}) {
1126
1147
  }
1127
1148
  return "";
1128
1149
  });
1129
- c.push(n);
1150
+ l.push(n);
1130
1151
  }
1131
- qe("" + [s.join(" "), ...c.map((e) => e.join(" "))].join("\n"), i || `${e.title || "report"}.tsv`, "text/tab-separated-values");
1152
+ et("" + [c.join(" "), ...l.map((e) => e.join(" "))].join("\n"), i || `${e.title || "report"}.tsv`, "text/tab-separated-values");
1132
1153
  }
1133
- function Ve(e, t, n, r) {
1154
+ function Je(e, t, n, r) {
1134
1155
  return async () => {
1135
1156
  let i = e.schedule;
1136
1157
  if (!i?.enabled) return [];
1137
1158
  let a = i.formats || [e.defaultExportFormat || "pdf"], o = [];
1138
1159
  for (let r of a) {
1139
- let i = await ze(e, {
1160
+ let i = await Ke(e, {
1140
1161
  dataSource: t,
1141
1162
  resource: n,
1142
1163
  format: r
@@ -1146,16 +1167,16 @@ function Ve(e, t, n, r) {
1146
1167
  return r(e, i), o;
1147
1168
  };
1148
1169
  }
1149
- function He(e) {
1170
+ function Ye(e) {
1150
1171
  return {
1151
1172
  name: e.name,
1152
1173
  header: e.label || e.name
1153
1174
  };
1154
1175
  }
1155
- function Ue(e, t) {
1156
- return e == null ? "" : typeof e == "number" && t ? e.toLocaleString("en-US", We(t)) : Ke(String(e));
1176
+ function Xe(e, t, n = "en") {
1177
+ return e == null ? "" : typeof e == "number" && t ? G(e, n, Ze(t)) : $e(String(e));
1157
1178
  }
1158
- function We(e) {
1179
+ function Ze(e) {
1159
1180
  if (e.includes("%")) return {
1160
1181
  style: "percent",
1161
1182
  minimumFractionDigits: 0
@@ -1166,69 +1187,56 @@ function We(e) {
1166
1187
  maximumFractionDigits: Math.max(0, t - 1)
1167
1188
  };
1168
1189
  }
1169
- function Ge(e) {
1190
+ function Qe(e) {
1170
1191
  let t = "", n = e;
1171
1192
  for (; n >= 0;) t = String.fromCharCode(n % 26 + 65) + t, n = Math.floor(n / 26) - 1;
1172
1193
  return t;
1173
1194
  }
1174
- function Ke(e) {
1195
+ function $e(e) {
1175
1196
  if (e.length > 0) {
1176
1197
  let t = e.charAt(0);
1177
1198
  if (t === "=" || t === "+" || t === "-" || t === "@" || t === "|") return `'${e}`;
1178
1199
  }
1179
1200
  return e;
1180
1201
  }
1181
- function qe(e, t, n) {
1202
+ function et(e, t, n) {
1182
1203
  let r = new Blob([e], { type: `${n};charset=utf-8` }), i = URL.createObjectURL(r), a = document.createElement("a");
1183
1204
  a.href = i, a.download = t, document.body.appendChild(a), a.click(), document.body.removeChild(a), URL.revokeObjectURL(i);
1184
1205
  }
1185
- e.register("report", $, {
1186
- namespace: "report",
1206
+ e.register("report", Ge, {
1207
+ namespace: "plugin-report",
1187
1208
  label: "Report",
1188
1209
  category: "Report",
1189
1210
  inputs: [
1190
1211
  {
1191
1212
  name: "title",
1192
- type: "string",
1193
- label: "Title"
1213
+ type: "string"
1194
1214
  },
1195
1215
  {
1196
1216
  name: "description",
1197
- type: "string",
1198
- label: "Description"
1217
+ type: "string"
1199
1218
  },
1200
1219
  {
1201
1220
  name: "chart",
1202
- type: "code",
1203
- label: "Chart Configuration"
1221
+ type: "code"
1222
+ },
1223
+ {
1224
+ name: "report",
1225
+ type: "object",
1226
+ description: "The report to render, as `@objectstack/spec` declares it (`ReportSchema`: `name`, `label`, `type`, `dataset`, `rows`, `values`, …). When present, the block renders this report and reads none of its own presentation inputs."
1204
1227
  }
1205
1228
  ]
1206
- }), e.register("spec-report", $, {
1207
- namespace: "report",
1208
- label: "Spec Report",
1209
- category: "Report",
1210
- inputs: [{
1211
- name: "dataset",
1212
- type: "string",
1213
- label: "Dataset"
1214
- }, {
1215
- name: "type",
1216
- type: "string",
1217
- label: "Report Type"
1218
- }]
1219
- }), e.register("report-viewer", J, {
1220
- namespace: "report",
1229
+ }), e.register("report-viewer", Ce, {
1230
+ namespace: "plugin-report",
1221
1231
  label: "Report Viewer",
1222
1232
  category: "Report",
1223
1233
  inputs: [{
1224
1234
  name: "report",
1225
- type: "code",
1226
- label: "Report Definition"
1235
+ type: "code"
1227
1236
  }, {
1228
1237
  name: "showToolbar",
1229
- type: "boolean",
1230
- label: "Show Toolbar"
1238
+ type: "boolean"
1231
1239
  }]
1232
1240
  });
1233
1241
  //#endregion
1234
- export { Re as DatasetReportRenderer, H as LegacyReportRenderer, $ as ReportRenderer, J as ReportViewer, Ve as createScheduleTrigger, ce as exportAsCSV, de as exportAsExcel, U as exportAsHTML, le as exportAsJSON, ue as exportAsPDF, Be as exportExcelWithFormulas, W as exportReport, ze as exportWithLiveData, q as formatValue, ye as isDatasetReport, p as mergeFilters };
1242
+ export { We as DatasetReportRenderer, ue as LegacyReportRenderer, Ge as ReportRenderer, Ce as ReportViewer, Je as createScheduleTrigger, de as exportAsCSV, me as exportAsExcel, K as exportAsHTML, fe as exportAsJSON, pe as exportAsPDF, qe as exportExcelWithFormulas, he as exportReport, Ke as exportWithLiveData, Y as formatValue, we as isDatasetReport, m as mergeFilters };