@xenosystem/blocks 0.13.10 → 0.13.12

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.
@@ -6,17 +6,14 @@ import {
6
6
  quoteLiteral,
7
7
  renderFilterGroup
8
8
  } from "../chunk-DJJGZ6U4.js";
9
- import {
10
- ICONS
11
- } from "../chunk-W4PTX2Y4.js";
12
9
  import {
13
10
  ChevronGlyph,
14
- DownloadGlyph,
11
+ ICONS,
15
12
  PlugGlyph,
16
13
  RefreshGlyph,
17
14
  SortAscGlyph,
18
15
  SortDescGlyph
19
- } from "../chunk-K7YLLV2W.js";
16
+ } from "../chunk-5BVZMAD2.js";
20
17
  import "../chunk-2KG3PWR4.js";
21
18
 
22
19
  // src/data/table/panel.ts
@@ -198,8 +195,8 @@ function moveCell(from, delta, bounds) {
198
195
  }
199
196
 
200
197
  // src/data/table/numeric.ts
201
- function parseNumeric(text3) {
202
- const trimmed = String(text3).trim();
198
+ function parseNumeric(text4) {
199
+ const trimmed = String(text4).trim();
203
200
  if (trimmed.length === 0) return { ok: false, reason: "empty" };
204
201
  const match = /^[+-]?(\d+\.?\d*|\.\d+)(?:[eE][+-]?\d+)?/.exec(trimmed);
205
202
  if (!match) return { ok: false, reason: "nan" };
@@ -553,11 +550,11 @@ var TableController = class {
553
550
  return true;
554
551
  }
555
552
  /** Update the in-flight draft. Emits `editPreview` only when `livePreview` is on. */
556
- updateDraft(text3) {
553
+ updateDraft(text4) {
557
554
  if (!this.editing) return;
558
- this.editing = { ...this.editing, draft: text3 };
555
+ this.editing = { ...this.editing, draft: text4 };
559
556
  if (this.livePreview) {
560
- const parsed = this.parseDraft(this.editing.columnId, text3);
557
+ const parsed = this.parseDraft(this.editing.columnId, text4);
561
558
  if (parsed.ok) {
562
559
  this.host.emit("editPreview", this.buildEdit(this.editing, parsed.value));
563
560
  }
@@ -609,12 +606,12 @@ var TableController = class {
609
606
  };
610
607
  }
611
608
  /** Parse a draft according to the column's declared type. */
612
- parseDraft(columnId, text3) {
609
+ parseDraft(columnId, text4) {
613
610
  const column = this.columnById(columnId);
614
- const trimmed = text3.trim();
611
+ const trimmed = text4.trim();
615
612
  if (column?.type === "number" || column?.type === "integer" || column?.type === "duration") {
616
613
  if (trimmed === "") return { ok: true, value: null };
617
- const parsed = parseNumeric(text3);
614
+ const parsed = parseNumeric(text4);
618
615
  if (!parsed.ok) return { ok: false, reason: parsed.reason };
619
616
  return { ok: true, value: normalizeNumeric(parsed.value, constraintsOfColumn(column)) };
620
617
  }
@@ -631,7 +628,7 @@ var TableController = class {
631
628
  value: trimmed === "" ? [] : trimmed.split(",").map((part) => part.trim()).filter(Boolean)
632
629
  };
633
630
  }
634
- return { ok: true, value: trimmed === "" ? null : text3 };
631
+ return { ok: true, value: trimmed === "" ? null : text4 };
635
632
  }
636
633
  rowById(rowId) {
637
634
  return this.result?.rows.find((r) => r.id === rowId);
@@ -2205,16 +2202,7 @@ var chartManifest = {
2205
2202
 
2206
2203
  // src/data/chart/react/ChartPanelView.tsx
2207
2204
  import { useEffect as useEffect2, useRef as useRef2, useSyncExternalStore as useSyncExternalStore2 } from "react";
2208
- import {
2209
- Badge as Badge2,
2210
- EmptyState as EmptyState2,
2211
- ErrorState as ErrorState2,
2212
- IconButton as IconButton2,
2213
- SegmentedControl as SegmentedControl2,
2214
- StatusBar as StatusBar2,
2215
- Toolbar as Toolbar2,
2216
- ToolbarGroup as ToolbarGroup2
2217
- } from "@xenosystem/components/chrome";
2205
+ import { Badge as Badge2, Column, EmptyState as EmptyState2, ErrorState as ErrorState2, IconButton as IconButton2, PlotSurface, SegmentedControl as SegmentedControl2, StatusBar as StatusBar2, Toolbar as Toolbar2, ToolbarGroup as ToolbarGroup2 } from "@xenosystem/components/chrome";
2218
2206
 
2219
2207
  // src/data/chart/renderer.ts
2220
2208
  var renderer = null;
@@ -2268,19 +2256,102 @@ function shade(index) {
2268
2256
  return MONO_PALETTE[index % MONO_PALETTE.length];
2269
2257
  }
2270
2258
 
2259
+ // src/data/chart/declaration.ts
2260
+ var CHART_TYPE_LABELS = { bar: "Bar", horizontalBar: "H-Bar", line: "Line", area: "Area", scatter: "Scatter", pie: "Pie", doughnut: "Ring" };
2261
+ var DEFAULT_CHART_OPTIONS = { showLegend: true, showGrid: true, showTooltip: true, stacked: false, smoothing: 0 };
2262
+ function chartViewState(c, options = {}) {
2263
+ const s = c.getState();
2264
+ const errored = !!s.errorMessage;
2265
+ const empty = !errored && s.empty;
2266
+ const unplottable = !errored && !empty && !!s.encodingProblem;
2267
+ const noRenderer = !errored && !empty && !unplottable && !getChartRenderer();
2268
+ return {
2269
+ types: s.allowedTypes.map((t) => ({ value: t, label: CHART_TYPE_LABELS[t] ?? t })),
2270
+ type: s.encoding.type,
2271
+ partial: s.partial,
2272
+ aggregating: !!s.data?.tooDense,
2273
+ aggregatingHint: s.data?.tooDense ? `${s.data.tooDense.points} points exceeds the ${s.data.tooDense.limit} plot limit \u2014 an aggregated query was requested.` : void 0,
2274
+ errorMessage: s.errorMessage ?? void 0,
2275
+ errored,
2276
+ empty,
2277
+ emptyHint: options.emptyHint ?? "Wire a result into this chart to plot it.",
2278
+ unplottable,
2279
+ encodingProblem: s.encodingProblem ?? void 0,
2280
+ noRenderer,
2281
+ plot: !errored && !empty && !unplottable && !noRenderer,
2282
+ countLabel: s.data ? `${s.data.series.length} series \xB7 ${s.data.labels.length} points` : void 0,
2283
+ highlightLabel: s.highlightedRowIds.length > 0 ? `${s.highlightedRowIds.length} highlighted` : void 0
2284
+ };
2285
+ }
2286
+ function applyChartUi(c, intent) {
2287
+ switch (intent.kind) {
2288
+ case "type":
2289
+ c.setType(intent.type);
2290
+ break;
2291
+ case "export":
2292
+ c.requestExport("png");
2293
+ break;
2294
+ }
2295
+ }
2296
+ var chartViewManifest = {
2297
+ id: chartManifest.id,
2298
+ version: "1.0.0",
2299
+ title: "Chart",
2300
+ category: "data",
2301
+ layout: { slot: "center" },
2302
+ inputs: [{ id: "view", type: "object", label: "View state", description: "The ChartViewModel the runtime derives from the controller on every draw." }],
2303
+ outputs: [{ id: "ui", type: "object", label: "UI intent", description: "{ kind: type | export, \u2026 } \u2014 applied by the runtime to the controller." }],
2304
+ commands: []
2305
+ };
2306
+ var EMPTY = { types: [], type: "bar", partial: false, aggregating: false, errored: false, empty: true, emptyHint: "Wire a result into this chart to plot it.", unplottable: false, noRenderer: false, plot: false };
2307
+ var BEHAVIOURS = {
2308
+ "data/chartPanelView": (inputs) => inputs.view ?? EMPTY
2309
+ };
2310
+ var CHART_RUNTIME_UNITS = ["chart/Plot"];
2311
+ var text = (b) => ({ component: "text", props: { text: b } });
2312
+ var ui = (kind, fields = {}) => ({ emit: "ui", value: { object: { kind: { value: kind }, ...fields } } });
2313
+ var CHART_DECLARATION = {
2314
+ format: "xeno.block@1",
2315
+ manifest: chartViewManifest,
2316
+ behaviour: "data/chartPanelView",
2317
+ composition: {
2318
+ component: "chrome/Column",
2319
+ children: [
2320
+ {
2321
+ component: "chrome/Toolbar",
2322
+ props: {
2323
+ left: { node: { component: "chrome/SegmentedControl", props: { size: { value: "sm" }, label: { value: "Chart type" }, options: { input: "view.types" }, value: { input: "view.type" } }, on: { onChange: ui("type", { type: { arg: "" } }) } } },
2324
+ right: {
2325
+ node: {
2326
+ component: "chrome/ToolbarGroup",
2327
+ props: { end: { value: true } },
2328
+ children: [
2329
+ { component: "chrome/Badge", when: { input: "view.partial" }, props: { tone: { value: "warning" }, title: { value: "Some measures have not synced yet." } }, children: [text({ value: "partial" })] },
2330
+ { component: "chrome/Badge", when: { input: "view.aggregating" }, props: { tone: { value: "warning" }, title: { input: "view.aggregatingHint" } }, children: [text({ value: "aggregating" })] },
2331
+ { component: "chrome/IconButton", props: { icon: { node: { component: "icons/Download" } }, label: { value: "Export chart" } }, on: { onClick: ui("export") } }
2332
+ ]
2333
+ }
2334
+ }
2335
+ }
2336
+ },
2337
+ { component: "chrome/ErrorState", when: { input: "view.errored" }, props: { title: { value: "Could not load data" }, message: { input: "view.errorMessage" } } },
2338
+ { component: "chrome/EmptyState", when: { input: "view.empty" }, props: { title: { value: "No data" }, hint: { input: "view.emptyHint" } } },
2339
+ { component: "chrome/EmptyState", when: { input: "view.unplottable" }, props: { title: { value: "Nothing to plot" }, hint: { input: "view.encodingProblem" } } },
2340
+ { component: "chrome/EmptyState", when: { input: "view.noRenderer" }, props: { title: { value: "No renderer installed" }, hint: { value: "Call setChartRenderer() with a Chart.js (or other) renderer \u2014 the panel ships the model, the host ships the marks." } } },
2341
+ { component: "chart/Plot", when: { input: "view.plot" } },
2342
+ { component: "chrome/StatusBar", props: { left: { input: "view.countLabel" }, right: { input: "view.highlightLabel" } } }
2343
+ ]
2344
+ }
2345
+ };
2346
+
2271
2347
  // src/data/chart/react/ChartPanelView.tsx
2272
2348
  import { jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
2273
- var DEFAULT_OPTIONS = {
2274
- showLegend: true,
2275
- showGrid: true,
2276
- showTooltip: true,
2277
- stacked: false,
2278
- smoothing: 0
2279
- };
2280
- function ChartPanelView({ controller, options, emptyHint }) {
2349
+ var DownloadGlyph = ICONS["icons/Download"];
2350
+ function ChartPlot({ controller, options }) {
2281
2351
  const state = useSyncExternalStore2(controller.subscribe, controller.getState, controller.getState);
2282
2352
  const plotRef = useRef2(null);
2283
- const resolved = { ...DEFAULT_OPTIONS, ...options };
2353
+ const resolved = { ...DEFAULT_CHART_OPTIONS, ...options };
2354
+ const resolvedKey = JSON.stringify(resolved);
2284
2355
  useEffect2(() => {
2285
2356
  const element = plotRef.current;
2286
2357
  const renderer2 = getChartRenderer();
@@ -2293,83 +2364,38 @@ function ChartPanelView({ controller, options, emptyHint }) {
2293
2364
  highlightedRowIds: state.highlightedRowIds,
2294
2365
  onMarkActivate: (label, seriesId) => controller.activateMark(label, seriesId)
2295
2366
  });
2296
- }, [state.data, state.highlightedRowIds, controller, JSON.stringify(resolved)]);
2297
- const toolbar = /* @__PURE__ */ jsx2(
2298
- Toolbar2,
2299
- {
2300
- left: /* @__PURE__ */ jsx2(
2301
- SegmentedControl2,
2302
- {
2303
- size: "sm",
2304
- label: "Chart type",
2305
- options: state.allowedTypes.map((t) => ({ value: t, label: LABELS[t] ?? t })),
2306
- value: state.encoding.type,
2307
- onChange: (t) => controller.setType(t)
2308
- }
2309
- ),
2310
- right: /* @__PURE__ */ jsxs2(ToolbarGroup2, { end: true, children: [
2311
- state.partial ? /* @__PURE__ */ jsx2(Badge2, { tone: "warning", title: "Some measures have not synced yet.", children: "partial" }) : null,
2312
- state.data?.tooDense ? /* @__PURE__ */ jsx2(
2313
- Badge2,
2314
- {
2315
- tone: "warning",
2316
- title: `${state.data.tooDense.points} points exceeds the ${state.data.tooDense.limit} plot limit \u2014 an aggregated query was requested.`,
2317
- children: "aggregating"
2318
- }
2319
- ) : null,
2320
- /* @__PURE__ */ jsx2(
2321
- IconButton2,
2322
- {
2323
- icon: /* @__PURE__ */ jsx2(DownloadGlyph, {}),
2324
- label: "Export chart",
2325
- onClick: () => controller.requestExport("png")
2326
- }
2327
- )
2328
- ] })
2329
- }
2330
- );
2331
- const body = (() => {
2332
- if (state.errorMessage) {
2333
- return /* @__PURE__ */ jsx2(ErrorState2, { title: "Could not load data", message: state.errorMessage });
2334
- }
2335
- if (state.empty) {
2336
- return /* @__PURE__ */ jsx2(EmptyState2, { title: "No data", hint: emptyHint ?? "Wire a result into this chart to plot it." });
2337
- }
2338
- if (state.encodingProblem) {
2339
- return /* @__PURE__ */ jsx2(EmptyState2, { title: "Nothing to plot", hint: state.encodingProblem });
2340
- }
2341
- if (!getChartRenderer()) {
2342
- return /* @__PURE__ */ jsx2(
2343
- EmptyState2,
2344
- {
2345
- title: "No renderer installed",
2346
- hint: "Call setChartRenderer() with a Chart.js (or other) renderer \u2014 the panel ships the model, the host ships the marks."
2347
- }
2348
- );
2349
- }
2350
- return /* @__PURE__ */ jsx2("div", { ref: plotRef, style: { flex: "1 1 0", minHeight: 0, position: "relative" } });
2351
- })();
2352
- return /* @__PURE__ */ jsxs2("div", { style: { display: "flex", flexDirection: "column", height: "100%", minHeight: 0 }, children: [
2353
- toolbar,
2354
- body,
2367
+ }, [state.data, state.highlightedRowIds, controller, resolvedKey]);
2368
+ return /* @__PURE__ */ jsx2(PlotSurface, { ref: plotRef, label: "Chart" });
2369
+ }
2370
+ function chartRuntimeComponents(controller, options) {
2371
+ return {
2372
+ "chart/Plot": () => /* @__PURE__ */ jsx2(ChartPlot, { controller, options })
2373
+ };
2374
+ }
2375
+ function ChartPanelView({ controller, options, emptyHint }) {
2376
+ useSyncExternalStore2(controller.subscribe, controller.getState, controller.getState);
2377
+ const view = chartViewState(controller, { emptyHint });
2378
+ const ui4 = (intent) => applyChartUi(controller, intent);
2379
+ return /* @__PURE__ */ jsxs2(Column, { children: [
2355
2380
  /* @__PURE__ */ jsx2(
2356
- StatusBar2,
2381
+ Toolbar2,
2357
2382
  {
2358
- left: state.data ? `${state.data.series.length} series \xB7 ${state.data.labels.length} points` : void 0,
2359
- right: state.highlightedRowIds.length > 0 ? `${state.highlightedRowIds.length} highlighted` : void 0
2383
+ left: /* @__PURE__ */ jsx2(SegmentedControl2, { size: "sm", label: "Chart type", options: view.types, value: view.type, onChange: (type) => ui4({ kind: "type", type }) }),
2384
+ right: /* @__PURE__ */ jsxs2(ToolbarGroup2, { end: true, children: [
2385
+ view.partial ? /* @__PURE__ */ jsx2(Badge2, { tone: "warning", title: "Some measures have not synced yet.", children: "partial" }) : null,
2386
+ view.aggregating ? /* @__PURE__ */ jsx2(Badge2, { tone: "warning", title: view.aggregatingHint, children: "aggregating" }) : null,
2387
+ /* @__PURE__ */ jsx2(IconButton2, { icon: /* @__PURE__ */ jsx2(DownloadGlyph, {}), label: "Export chart", onClick: () => ui4({ kind: "export" }) })
2388
+ ] })
2360
2389
  }
2361
- )
2390
+ ),
2391
+ view.errored ? /* @__PURE__ */ jsx2(ErrorState2, { title: "Could not load data", message: view.errorMessage }) : null,
2392
+ view.empty ? /* @__PURE__ */ jsx2(EmptyState2, { title: "No data", hint: view.emptyHint }) : null,
2393
+ view.unplottable ? /* @__PURE__ */ jsx2(EmptyState2, { title: "Nothing to plot", hint: view.encodingProblem }) : null,
2394
+ view.noRenderer ? /* @__PURE__ */ jsx2(EmptyState2, { title: "No renderer installed", hint: "Call setChartRenderer() with a Chart.js (or other) renderer \u2014 the panel ships the model, the host ships the marks." }) : null,
2395
+ view.plot ? /* @__PURE__ */ jsx2(ChartPlot, { controller, options }) : null,
2396
+ /* @__PURE__ */ jsx2(StatusBar2, { left: view.countLabel, right: view.highlightLabel })
2362
2397
  ] });
2363
2398
  }
2364
- var LABELS = {
2365
- bar: "Bar",
2366
- horizontalBar: "H-Bar",
2367
- line: "Line",
2368
- area: "Area",
2369
- scatter: "Scatter",
2370
- pie: "Pie",
2371
- doughnut: "Ring"
2372
- };
2373
2399
 
2374
2400
  // src/data/chart/panel.ts
2375
2401
  function createChartPanel(options = {}) {
@@ -2912,7 +2938,7 @@ var metricsManifest = {
2912
2938
  import { useSyncExternalStore as useSyncExternalStore3 } from "react";
2913
2939
  import {
2914
2940
  Badge as Badge3,
2915
- Column,
2941
+ Column as Column2,
2916
2942
  Delta,
2917
2943
  EmptyState as EmptyState3,
2918
2944
  ErrorState as ErrorState3,
@@ -2994,13 +3020,13 @@ var metricsViewManifest = {
2994
3020
  outputs: [{ id: "ui", type: "object", label: "UI intent", description: "{ kind: range | activate, \u2026 } \u2014 applied by the runtime to the controller." }],
2995
3021
  commands: []
2996
3022
  };
2997
- var EMPTY = { hasRanges: false, ranges: [], rangeId: "", partial: false, partialHint: "", errored: false, empty: true, emptyHint: "Configure a metric, or wire a result into this panel.", ready: false, layout: "grid", columns: 4, tiles: [], countLabel: "0 metrics" };
2998
- var BEHAVIOURS = {
2999
- "data/metricsPanelView": (inputs) => inputs.view ?? EMPTY
3023
+ var EMPTY2 = { hasRanges: false, ranges: [], rangeId: "", partial: false, partialHint: "", errored: false, empty: true, emptyHint: "Configure a metric, or wire a result into this panel.", ready: false, layout: "grid", columns: 4, tiles: [], countLabel: "0 metrics" };
3024
+ var BEHAVIOURS2 = {
3025
+ "data/metricsPanelView": (inputs) => inputs.view ?? EMPTY2
3000
3026
  };
3001
3027
  var METRICS_RUNTIME_UNITS = [];
3002
- var text = (b) => ({ component: "text", props: { text: b } });
3003
- var ui = (kind, fields = {}) => ({ emit: "ui", value: { object: { kind: { value: kind }, ...fields } } });
3028
+ var text2 = (b) => ({ component: "text", props: { text: b } });
3029
+ var ui2 = (kind, fields = {}) => ({ emit: "ui", value: { object: { kind: { value: kind }, ...fields } } });
3004
3030
  var METRICS_DECLARATION = {
3005
3031
  format: "xeno.block@1",
3006
3032
  manifest: metricsViewManifest,
@@ -3012,8 +3038,8 @@ var METRICS_DECLARATION = {
3012
3038
  component: "chrome/Toolbar",
3013
3039
  when: { input: "view.hasRanges" },
3014
3040
  props: {
3015
- left: { node: { component: "chrome/SegmentedControl", props: { size: { value: "sm" }, label: { value: "Range" }, options: { input: "view.ranges" }, value: { input: "view.rangeId" } }, on: { onChange: ui("range", { rangeId: { arg: "" } }) } } },
3016
- right: { node: { component: "chrome/Badge", when: { input: "view.partial" }, props: { tone: { value: "warning" }, title: { input: "view.partialHint" } }, children: [text({ value: "partial" })] } }
3041
+ left: { node: { component: "chrome/SegmentedControl", props: { size: { value: "sm" }, label: { value: "Range" }, options: { input: "view.ranges" }, value: { input: "view.rangeId" } }, on: { onChange: ui2("range", { rangeId: { arg: "" } }) } } },
3042
+ right: { node: { component: "chrome/Badge", when: { input: "view.partial" }, props: { tone: { value: "warning" }, title: { input: "view.partialHint" } }, children: [text2({ value: "partial" })] } }
3017
3043
  }
3018
3044
  },
3019
3045
  { component: "chrome/ErrorState", when: { input: "view.errored" }, props: { title: { value: "Could not load metrics" }, message: { input: "view.errorMessage" } } },
@@ -3033,20 +3059,20 @@ var METRICS_DECLARATION = {
3033
3059
  title: { item: "title" },
3034
3060
  label: { item: "label" },
3035
3061
  value: { item: "value" },
3036
- icon: { node: { component: "chrome/Badge", when: { item: "hasLevel" }, props: { tone: { item: "tone" } }, children: [text({ item: "level" })] } },
3062
+ icon: { node: { component: "chrome/Badge", when: { item: "hasLevel" }, props: { tone: { item: "tone" } }, children: [text2({ item: "level" })] } },
3037
3063
  sub: {
3038
3064
  node: {
3039
3065
  component: "chrome/Stack",
3040
3066
  props: { direction: { value: "row" }, pad: { value: "none" } },
3041
3067
  children: [
3042
3068
  { component: "chrome/Delta", when: { item: "hasDelta" }, props: { value: { item: "delta" }, tone: { item: "deltaTone" } } },
3043
- { component: "chrome/Text", when: { item: "partial" }, props: { role: { value: "meta" } }, children: [text({ input: "view.partialHint" })] },
3069
+ { component: "chrome/Text", when: { item: "partial" }, props: { role: { value: "meta" } }, children: [text2({ input: "view.partialHint" })] },
3044
3070
  { component: "chrome/Sparkline", when: { item: "hasSpark" }, props: { data: { item: "spark" }, label: { item: "sparkLabel" } } }
3045
3071
  ]
3046
3072
  }
3047
3073
  }
3048
3074
  },
3049
- on: { onActivate: ui("activate", { metricId: { item: "id" } }) }
3075
+ on: { onActivate: ui2("activate", { metricId: { item: "id" } }) }
3050
3076
  }
3051
3077
  ]
3052
3078
  }
@@ -3062,12 +3088,12 @@ import { jsx as jsx3, jsxs as jsxs3 } from "react/jsx-runtime";
3062
3088
  function MetricsPanelView({ controller, ...options }) {
3063
3089
  useSyncExternalStore3(controller.subscribe, controller.getState, controller.getState);
3064
3090
  const view = metricsViewState(controller, options);
3065
- const ui3 = (intent) => applyMetricsUi(controller, intent);
3066
- return /* @__PURE__ */ jsxs3(Column, { children: [
3091
+ const ui4 = (intent) => applyMetricsUi(controller, intent);
3092
+ return /* @__PURE__ */ jsxs3(Column2, { children: [
3067
3093
  view.hasRanges ? /* @__PURE__ */ jsx3(
3068
3094
  Toolbar3,
3069
3095
  {
3070
- left: /* @__PURE__ */ jsx3(SegmentedControl3, { size: "sm", label: "Range", options: view.ranges, value: view.rangeId, onChange: (rangeId) => ui3({ kind: "range", rangeId }) }),
3096
+ left: /* @__PURE__ */ jsx3(SegmentedControl3, { size: "sm", label: "Range", options: view.ranges, value: view.rangeId, onChange: (rangeId) => ui4({ kind: "range", rangeId }) }),
3071
3097
  right: view.partial ? /* @__PURE__ */ jsx3(Badge3, { tone: "warning", title: view.partialHint, children: "partial" }) : null
3072
3098
  }
3073
3099
  ) : null,
@@ -3085,7 +3111,7 @@ function MetricsPanelView({ controller, ...options }) {
3085
3111
  tile.partial ? /* @__PURE__ */ jsx3(Text, { role: "meta", children: view.partialHint }) : null,
3086
3112
  tile.hasSpark ? /* @__PURE__ */ jsx3(Sparkline, { data: tile.spark, label: tile.sparkLabel }) : null
3087
3113
  ] }),
3088
- onActivate: () => ui3({ kind: "activate", metricId: tile.id })
3114
+ onActivate: () => ui4({ kind: "activate", metricId: tile.id })
3089
3115
  },
3090
3116
  tile.id
3091
3117
  )) }) }) : null,
@@ -3287,7 +3313,7 @@ function emptyFilterGroup() {
3287
3313
  function offerableFilterOps(column, sourceOps = []) {
3288
3314
  const common = ["eq", "ne", "isEmpty", "isNotEmpty", "in", "notIn"];
3289
3315
  const ordered = ["gt", "gte", "lt", "lte", "between"];
3290
- const text3 = ["contains", "notContains", "startsWith", "endsWith"];
3316
+ const text4 = ["contains", "notContains", "startsWith", "endsWith"];
3291
3317
  const temporal = ["relative"];
3292
3318
  let ops = [...common];
3293
3319
  switch (column?.type) {
@@ -3305,10 +3331,10 @@ function offerableFilterOps(column, sourceOps = []) {
3305
3331
  case "url":
3306
3332
  case "select":
3307
3333
  case "multiselect":
3308
- ops = [...ops, ...text3];
3334
+ ops = [...ops, ...text4];
3309
3335
  break;
3310
3336
  default:
3311
- ops = [...ops, ...text3, ...ordered];
3337
+ ops = [...ops, ...text4, ...ordered];
3312
3338
  }
3313
3339
  if (sourceOps.length === 0) return ops;
3314
3340
  return ops.filter((op) => sourceOps.includes(op));
@@ -3939,7 +3965,7 @@ var fieldsManifest = {
3939
3965
  import { useSyncExternalStore as useSyncExternalStore4 } from "react";
3940
3966
  import {
3941
3967
  Badge as Badge4,
3942
- Column as Column2,
3968
+ Column as Column3,
3943
3969
  EmptyState as EmptyState4,
3944
3970
  IconButton as IconButton3,
3945
3971
  Note,
@@ -4074,13 +4100,13 @@ var fieldsViewManifest = {
4074
4100
  outputs: [{ id: "ui", type: "object", label: "UI intent", description: "{ kind, \u2026 } \u2014 applied by the runtime to the controller." }],
4075
4101
  commands: []
4076
4102
  };
4077
- var EMPTY2 = { hasColumns: false, noColumns: true, sampled: false, manualApply: false, applyDisabled: true, columns: [], shelves: [], filters: [], filterCount: 0, hasFilters: false, noFilters: true, combinator: "and", countLabel: "0 fields" };
4078
- var BEHAVIOURS2 = {
4079
- "data/fieldsPanelView": (inputs) => inputs.view ?? EMPTY2
4103
+ var EMPTY3 = { hasColumns: false, noColumns: true, sampled: false, manualApply: false, applyDisabled: true, columns: [], shelves: [], filters: [], filterCount: 0, hasFilters: false, noFilters: true, combinator: "and", countLabel: "0 fields" };
4104
+ var BEHAVIOURS3 = {
4105
+ "data/fieldsPanelView": (inputs) => inputs.view ?? EMPTY3
4080
4106
  };
4081
4107
  var FIELDS_RUNTIME_UNITS = [];
4082
- var text2 = (b) => ({ component: "text", props: { text: b } });
4083
- var ui2 = (kind, fields = {}) => ({ emit: "ui", value: { object: { kind: { value: kind }, ...fields } } });
4108
+ var text3 = (b) => ({ component: "text", props: { text: b } });
4109
+ var ui3 = (kind, fields = {}) => ({ emit: "ui", value: { object: { kind: { value: kind }, ...fields } } });
4084
4110
  var removeButton = (label, on) => ({
4085
4111
  component: "chrome/IconButton",
4086
4112
  props: { size: { value: "sm" }, icon: { node: { component: "icons/Close", props: { size: { value: 11 } } } }, label },
@@ -4101,14 +4127,14 @@ var FIELDS_DECLARATION = {
4101
4127
  {
4102
4128
  component: "chrome/Toolbar",
4103
4129
  props: {
4104
- left: { node: { component: "chrome/Badge", when: { input: "view.sampled" }, props: { tone: { value: "warning" }, title: { input: "view.sampleWarning" } }, children: [text2({ value: "sampled schema" })] } },
4130
+ left: { node: { component: "chrome/Badge", when: { input: "view.sampled" }, props: { tone: { value: "warning" }, title: { input: "view.sampleWarning" } }, children: [text3({ value: "sampled schema" })] } },
4105
4131
  right: {
4106
4132
  node: {
4107
4133
  component: "chrome/ToolbarGroup",
4108
4134
  props: { end: { value: true } },
4109
4135
  children: [
4110
- { component: "chrome/TextButton", on: { onClick: ui2("autoAssign") }, children: [text2({ value: "Auto-assign" })] },
4111
- { component: "chrome/TextButton", when: { input: "view.manualApply" }, props: { strong: { value: true }, disabled: { input: "view.applyDisabled" } }, on: { onClick: ui2("apply") }, children: [text2({ value: "Apply" })] }
4136
+ { component: "chrome/TextButton", on: { onClick: ui3("autoAssign") }, children: [text3({ value: "Auto-assign" })] },
4137
+ { component: "chrome/TextButton", when: { input: "view.manualApply" }, props: { strong: { value: true }, disabled: { input: "view.applyDisabled" } }, on: { onClick: ui3("apply") }, children: [text3({ value: "Apply" })] }
4112
4138
  ]
4113
4139
  }
4114
4140
  }
@@ -4128,8 +4154,8 @@ var FIELDS_DECLARATION = {
4128
4154
  {
4129
4155
  component: "chrome/Row",
4130
4156
  each: { input: "view.columns", key: "id" },
4131
- props: { label: { item: "name" }, meta: { item: "role" }, selected: { item: "focused" }, trailing: { node: { component: "chrome/Badge", when: { item: "stat" }, props: { title: { item: "statTitle" } }, children: [text2({ item: "stat" })] } } },
4132
- on: { onClick: ui2("focus", { columnId: { item: "id" } }) }
4157
+ props: { label: { item: "name" }, meta: { item: "role" }, selected: { item: "focused" }, trailing: { node: { component: "chrome/Badge", when: { item: "stat" }, props: { title: { item: "statTitle" } }, children: [text3({ item: "stat" })] } } },
4158
+ on: { onClick: ui3("focus", { columnId: { item: "id" } }) }
4133
4159
  }
4134
4160
  ]
4135
4161
  }
@@ -4138,9 +4164,9 @@ var FIELDS_DECLARATION = {
4138
4164
  {
4139
4165
  component: "chrome/Section",
4140
4166
  each: { input: "view.shelves", key: "id" },
4141
- props: { title: { item: "label" }, flush: { value: true }, badge: { node: { component: "chrome/Badge", when: { item: "hasEntries" }, children: [text2({ item: "count" })] } } },
4167
+ props: { title: { item: "label" }, flush: { value: true }, badge: { node: { component: "chrome/Badge", when: { item: "hasEntries" }, children: [text3({ item: "count" })] } } },
4142
4168
  children: [
4143
- { component: "chrome/Note", when: { item: "empty" }, children: [text2({ item: "hint" })] },
4169
+ { component: "chrome/Note", when: { item: "empty" }, children: [text3({ item: "hint" })] },
4144
4170
  {
4145
4171
  component: "chrome/RowList",
4146
4172
  when: { item: "hasEntries" },
@@ -4155,13 +4181,13 @@ var FIELDS_DECLARATION = {
4155
4181
  node: {
4156
4182
  component: "fragment",
4157
4183
  children: [
4158
- { component: "chrome/Select", when: { item: "aggregated" }, props: { size: { value: "sm" }, label: { value: "Aggregate" }, options: { item: "aggregates" }, value: { item: "fn" } }, on: { onChange: ui2("aggregate", { shelfId: { item: "shelfId" }, columnId: { item: "columnId" }, fn: { arg: "" } }) } },
4159
- { component: "chrome/TextButton", when: { item: "sortable" }, on: { onClick: ui2("direction", { shelfId: { item: "shelfId" }, columnId: { item: "columnId" } }) }, children: [text2({ item: "direction" })] },
4160
- { component: "chrome/Badge", when: { item: "granularity" }, children: [text2({ item: "granularity" })] }
4184
+ { component: "chrome/Select", when: { item: "aggregated" }, props: { size: { value: "sm" }, label: { value: "Aggregate" }, options: { item: "aggregates" }, value: { item: "fn" } }, on: { onChange: ui3("aggregate", { shelfId: { item: "shelfId" }, columnId: { item: "columnId" }, fn: { arg: "" } }) } },
4185
+ { component: "chrome/TextButton", when: { item: "sortable" }, on: { onClick: ui3("direction", { shelfId: { item: "shelfId" }, columnId: { item: "columnId" } }) }, children: [text3({ item: "direction" })] },
4186
+ { component: "chrome/Badge", when: { item: "granularity" }, children: [text3({ item: "granularity" })] }
4161
4187
  ]
4162
4188
  }
4163
4189
  },
4164
- trailing: { node: removeButton({ item: "removeLabel" }, ui2("remove", { shelfId: { item: "shelfId" }, columnId: { item: "columnId" } })) }
4190
+ trailing: { node: removeButton({ item: "removeLabel" }, ui3("remove", { shelfId: { item: "shelfId" }, columnId: { item: "columnId" } })) }
4165
4191
  }
4166
4192
  }
4167
4193
  ]
@@ -4173,11 +4199,11 @@ var FIELDS_DECLARATION = {
4173
4199
  props: {
4174
4200
  title: { value: "Filters" },
4175
4201
  flush: { value: true },
4176
- badge: { node: { component: "chrome/Badge", when: { input: "view.hasFilters" }, children: [text2({ input: "view.filterCount" })] } },
4177
- actions: { node: { component: "chrome/IconButton", props: { size: { value: "sm" }, icon: { node: { component: "icons/Plus", props: { size: { value: 11 } } } }, label: { value: "Add filter" } }, on: { onClick: ui2("addFilter") } } }
4202
+ badge: { node: { component: "chrome/Badge", when: { input: "view.hasFilters" }, children: [text3({ input: "view.filterCount" })] } },
4203
+ actions: { node: { component: "chrome/IconButton", props: { size: { value: "sm" }, icon: { node: { component: "icons/Plus", props: { size: { value: 11 } } } }, label: { value: "Add filter" } }, on: { onClick: ui3("addFilter") } } }
4178
4204
  },
4179
4205
  children: [
4180
- { component: "chrome/Note", when: { input: "view.noFilters" }, children: [text2({ value: "No filters. Everything passes." })] },
4206
+ { component: "chrome/Note", when: { input: "view.noFilters" }, children: [text3({ value: "No filters. Everything passes." })] },
4181
4207
  {
4182
4208
  component: "chrome/RowList",
4183
4209
  when: { input: "view.hasFilters" },
@@ -4187,8 +4213,8 @@ var FIELDS_DECLARATION = {
4187
4213
  each: { input: "view.filters", key: "key" },
4188
4214
  props: {
4189
4215
  label: { item: "label" },
4190
- meta: { node: { component: "chrome/Select", when: { item: "leaf" }, props: { size: { value: "sm" }, label: { value: "Operator" }, options: { item: "ops" }, value: { item: "op" } }, on: { onChange: ui2("filterOp", { index: { item: "index" }, op: { arg: "" } }) } } },
4191
- trailing: { node: removeButton({ item: "removeLabel" }, ui2("removeFilter", { index: { item: "index" } })) }
4216
+ meta: { node: { component: "chrome/Select", when: { item: "leaf" }, props: { size: { value: "sm" }, label: { value: "Operator" }, options: { item: "ops" }, value: { item: "op" } }, on: { onChange: ui3("filterOp", { index: { item: "index" }, op: { arg: "" } }) } } },
4217
+ trailing: { node: removeButton({ item: "removeLabel" }, ui3("removeFilter", { index: { item: "index" } })) }
4192
4218
  }
4193
4219
  }
4194
4220
  ]
@@ -4197,8 +4223,8 @@ var FIELDS_DECLARATION = {
4197
4223
  component: "chrome/Toolbar",
4198
4224
  props: {
4199
4225
  divided: { value: false },
4200
- left: { node: { component: "chrome/SegmentedControl", props: { size: { value: "sm" }, label: { value: "Combinator" }, options: { value: COMBINATORS }, value: { input: "view.combinator" } }, on: { onChange: ui2("combinator", { combinator: { arg: "" } }) } } },
4201
- right: { node: { component: "chrome/TextButton", on: { onClick: ui2("addGroup") }, children: [text2({ value: "+ group" })] } }
4226
+ left: { node: { component: "chrome/SegmentedControl", props: { size: { value: "sm" }, label: { value: "Combinator" }, options: { value: COMBINATORS }, value: { input: "view.combinator" } }, on: { onChange: ui3("combinator", { combinator: { arg: "" } }) } } },
4227
+ right: { node: { component: "chrome/TextButton", on: { onClick: ui3("addGroup") }, children: [text3({ value: "+ group" })] } }
4202
4228
  }
4203
4229
  }
4204
4230
  ]
@@ -4220,18 +4246,18 @@ var COMBINATORS2 = [{ value: "and", label: "All" }, { value: "or", label: "Any"
4220
4246
  function FieldsPanelView({ controller, showStats, manualApply }) {
4221
4247
  useSyncExternalStore4(controller.subscribe, controller.getState, controller.getState);
4222
4248
  const view = fieldsViewState(controller, { showStats, manualApply });
4223
- const ui3 = (intent) => applyFieldsUi(controller, intent);
4249
+ const ui4 = (intent) => applyFieldsUi(controller, intent);
4224
4250
  if (view.noColumns) {
4225
4251
  return /* @__PURE__ */ jsx4(EmptyState4, { title: "No fields", hint: "Connect a source \u2014 its columns appear here, ready to drop onto a shelf." });
4226
4252
  }
4227
- return /* @__PURE__ */ jsxs4(Column2, { children: [
4253
+ return /* @__PURE__ */ jsxs4(Column3, { children: [
4228
4254
  /* @__PURE__ */ jsx4(
4229
4255
  Toolbar4,
4230
4256
  {
4231
4257
  left: view.sampled ? /* @__PURE__ */ jsx4(Badge4, { tone: "warning", title: view.sampleWarning, children: "sampled schema" }) : null,
4232
4258
  right: /* @__PURE__ */ jsxs4(ToolbarGroup3, { end: true, children: [
4233
- /* @__PURE__ */ jsx4(TextButton, { onClick: () => ui3({ kind: "autoAssign" }), children: "Auto-assign" }),
4234
- view.manualApply ? /* @__PURE__ */ jsx4(TextButton, { strong: true, disabled: view.applyDisabled, onClick: () => ui3({ kind: "apply" }), children: "Apply" }) : null
4259
+ /* @__PURE__ */ jsx4(TextButton, { onClick: () => ui4({ kind: "autoAssign" }), children: "Auto-assign" }),
4260
+ view.manualApply ? /* @__PURE__ */ jsx4(TextButton, { strong: true, disabled: view.applyDisabled, onClick: () => ui4({ kind: "apply" }), children: "Apply" }) : null
4235
4261
  ] })
4236
4262
  }
4237
4263
  ),
@@ -4243,7 +4269,7 @@ function FieldsPanelView({ controller, showStats, manualApply }) {
4243
4269
  meta: column.role,
4244
4270
  selected: column.focused,
4245
4271
  trailing: column.stat ? /* @__PURE__ */ jsx4(Badge4, { title: column.statTitle, children: column.stat }) : null,
4246
- onClick: () => ui3({ kind: "focus", columnId: column.id })
4272
+ onClick: () => ui4({ kind: "focus", columnId: column.id })
4247
4273
  },
4248
4274
  column.id
4249
4275
  )) }) }),
@@ -4255,11 +4281,11 @@ function FieldsPanelView({ controller, showStats, manualApply }) {
4255
4281
  label: entry.label,
4256
4282
  dimmed: entry.suggested,
4257
4283
  meta: /* @__PURE__ */ jsxs4(Fragment2, { children: [
4258
- entry.aggregated ? /* @__PURE__ */ jsx4(Select, { size: "sm", label: "Aggregate", options: entry.aggregates, value: entry.fn, onChange: (fn) => ui3({ kind: "aggregate", shelfId: entry.shelfId, columnId: entry.columnId, fn }) }) : null,
4259
- entry.sortable ? /* @__PURE__ */ jsx4(TextButton, { onClick: () => ui3({ kind: "direction", shelfId: entry.shelfId, columnId: entry.columnId }), children: entry.direction }) : null,
4284
+ entry.aggregated ? /* @__PURE__ */ jsx4(Select, { size: "sm", label: "Aggregate", options: entry.aggregates, value: entry.fn, onChange: (fn) => ui4({ kind: "aggregate", shelfId: entry.shelfId, columnId: entry.columnId, fn }) }) : null,
4285
+ entry.sortable ? /* @__PURE__ */ jsx4(TextButton, { onClick: () => ui4({ kind: "direction", shelfId: entry.shelfId, columnId: entry.columnId }), children: entry.direction }) : null,
4260
4286
  entry.granularity ? /* @__PURE__ */ jsx4(Badge4, { children: entry.granularity }) : null
4261
4287
  ] }),
4262
- trailing: /* @__PURE__ */ jsx4(IconButton3, { size: "sm", icon: /* @__PURE__ */ jsx4(CloseGlyph, { size: 11 }), label: entry.removeLabel, onClick: () => ui3({ kind: "remove", shelfId: entry.shelfId, columnId: entry.columnId }) })
4288
+ trailing: /* @__PURE__ */ jsx4(IconButton3, { size: "sm", icon: /* @__PURE__ */ jsx4(CloseGlyph, { size: 11 }), label: entry.removeLabel, onClick: () => ui4({ kind: "remove", shelfId: entry.shelfId, columnId: entry.columnId }) })
4263
4289
  },
4264
4290
  entry.columnId
4265
4291
  )) }) : null
@@ -4270,15 +4296,15 @@ function FieldsPanelView({ controller, showStats, manualApply }) {
4270
4296
  title: "Filters",
4271
4297
  flush: true,
4272
4298
  badge: view.hasFilters ? /* @__PURE__ */ jsx4(Badge4, { children: view.filterCount }) : null,
4273
- actions: /* @__PURE__ */ jsx4(IconButton3, { size: "sm", icon: /* @__PURE__ */ jsx4(PlusGlyph, { size: 11 }), label: "Add filter", onClick: () => ui3({ kind: "addFilter" }) }),
4299
+ actions: /* @__PURE__ */ jsx4(IconButton3, { size: "sm", icon: /* @__PURE__ */ jsx4(PlusGlyph, { size: 11 }), label: "Add filter", onClick: () => ui4({ kind: "addFilter" }) }),
4274
4300
  children: [
4275
4301
  view.noFilters ? /* @__PURE__ */ jsx4(Note, { children: "No filters. Everything passes." }) : null,
4276
4302
  view.hasFilters ? /* @__PURE__ */ jsx4(RowList, { children: view.filters.map((filter) => /* @__PURE__ */ jsx4(
4277
4303
  Row,
4278
4304
  {
4279
4305
  label: filter.label,
4280
- meta: filter.leaf ? /* @__PURE__ */ jsx4(Select, { size: "sm", label: "Operator", options: filter.ops, value: filter.op, onChange: (op) => ui3({ kind: "filterOp", index: filter.index, op }) }) : null,
4281
- trailing: /* @__PURE__ */ jsx4(IconButton3, { size: "sm", icon: /* @__PURE__ */ jsx4(CloseGlyph, { size: 11 }), label: filter.removeLabel, onClick: () => ui3({ kind: "removeFilter", index: filter.index }) })
4306
+ meta: filter.leaf ? /* @__PURE__ */ jsx4(Select, { size: "sm", label: "Operator", options: filter.ops, value: filter.op, onChange: (op) => ui4({ kind: "filterOp", index: filter.index, op }) }) : null,
4307
+ trailing: /* @__PURE__ */ jsx4(IconButton3, { size: "sm", icon: /* @__PURE__ */ jsx4(CloseGlyph, { size: 11 }), label: filter.removeLabel, onClick: () => ui4({ kind: "removeFilter", index: filter.index }) })
4282
4308
  },
4283
4309
  filter.key
4284
4310
  )) }) : null,
@@ -4286,8 +4312,8 @@ function FieldsPanelView({ controller, showStats, manualApply }) {
4286
4312
  Toolbar4,
4287
4313
  {
4288
4314
  divided: false,
4289
- left: /* @__PURE__ */ jsx4(SegmentedControl4, { size: "sm", label: "Combinator", options: COMBINATORS2, value: view.combinator, onChange: (combinator) => ui3({ kind: "combinator", combinator }) }),
4290
- right: /* @__PURE__ */ jsx4(TextButton, { onClick: () => ui3({ kind: "addGroup" }), children: "+ group" })
4315
+ left: /* @__PURE__ */ jsx4(SegmentedControl4, { size: "sm", label: "Combinator", options: COMBINATORS2, value: view.combinator, onChange: (combinator) => ui4({ kind: "combinator", combinator }) }),
4316
+ right: /* @__PURE__ */ jsx4(TextButton, { onClick: () => ui4({ kind: "addGroup" }), children: "+ group" })
4291
4317
  }
4292
4318
  )
4293
4319
  ]
@@ -5423,10 +5449,10 @@ function parseJsonPath(path) {
5423
5449
  }
5424
5450
  return steps;
5425
5451
  }
5426
- function findBracketEnd(text3, start) {
5452
+ function findBracketEnd(text4, start) {
5427
5453
  let quote = null;
5428
- for (let i = start + 1; i < text3.length; i += 1) {
5429
- const char = text3[i];
5454
+ for (let i = start + 1; i < text4.length; i += 1) {
5455
+ const char = text4[i];
5430
5456
  if (quote) {
5431
5457
  if (char === "\\") i += 1;
5432
5458
  else if (char === quote) quote = null;
@@ -5850,9 +5876,9 @@ function firstGraphqlError(errors) {
5850
5876
  }
5851
5877
 
5852
5878
  // src/data/connectors/executors/csv.ts
5853
- function sniffDelimiter(text3) {
5879
+ function sniffDelimiter(text4) {
5854
5880
  const candidates = [",", ";", " ", "|"];
5855
- const line = firstLogicalLine(text3);
5881
+ const line = firstLogicalLine(text4);
5856
5882
  let best = ",";
5857
5883
  let bestCount = 0;
5858
5884
  for (const candidate of candidates) {
@@ -5874,21 +5900,21 @@ function sniffDelimiter(text3) {
5874
5900
  }
5875
5901
  return best;
5876
5902
  }
5877
- function firstLogicalLine(text3) {
5903
+ function firstLogicalLine(text4) {
5878
5904
  let inQuotes = false;
5879
- for (let i = 0; i < text3.length; i += 1) {
5880
- const char = text3[i];
5905
+ for (let i = 0; i < text4.length; i += 1) {
5906
+ const char = text4[i];
5881
5907
  if (char === '"') {
5882
- if (inQuotes && text3[i + 1] === '"') i += 1;
5908
+ if (inQuotes && text4[i + 1] === '"') i += 1;
5883
5909
  else inQuotes = !inQuotes;
5884
5910
  } else if ((char === "\n" || char === "\r") && !inQuotes) {
5885
- return text3.slice(0, i);
5911
+ return text4.slice(0, i);
5886
5912
  }
5887
5913
  }
5888
- return text3;
5914
+ return text4;
5889
5915
  }
5890
- function parseCsv(text3, options = {}) {
5891
- const source = text3.charCodeAt(0) === 65279 ? text3.slice(1) : text3;
5916
+ function parseCsv(text4, options = {}) {
5917
+ const source = text4.charCodeAt(0) === 65279 ? text4.slice(1) : text4;
5892
5918
  const delimiter = options.delimiter && options.delimiter.length > 0 ? options.delimiter : sniffDelimiter(source);
5893
5919
  const quote = options.quote && options.quote.length > 0 ? options.quote : '"';
5894
5920
  const hasHeader = options.hasHeader ?? true;
@@ -5923,17 +5949,17 @@ function dedupe(names) {
5923
5949
  return count === 0 ? name : `${name}_${count + 1}`;
5924
5950
  });
5925
5951
  }
5926
- function scanRecords(text3, delimiter, quote) {
5952
+ function scanRecords(text4, delimiter, quote) {
5927
5953
  const records = [];
5928
5954
  let fields = [];
5929
5955
  let field = "";
5930
5956
  let inQuotes = false;
5931
5957
  let i = 0;
5932
- while (i < text3.length) {
5933
- const char = text3[i];
5958
+ while (i < text4.length) {
5959
+ const char = text4[i];
5934
5960
  if (inQuotes) {
5935
5961
  if (char === quote) {
5936
- if (text3[i + 1] === quote) {
5962
+ if (text4[i + 1] === quote) {
5937
5963
  field += quote;
5938
5964
  i += 2;
5939
5965
  continue;
@@ -5951,7 +5977,7 @@ function scanRecords(text3, delimiter, quote) {
5951
5977
  i += 1;
5952
5978
  continue;
5953
5979
  }
5954
- if (text3.startsWith(delimiter, i)) {
5980
+ if (text4.startsWith(delimiter, i)) {
5955
5981
  fields.push(field);
5956
5982
  field = "";
5957
5983
  i += delimiter.length;
@@ -5962,7 +5988,7 @@ function scanRecords(text3, delimiter, quote) {
5962
5988
  records.push(fields);
5963
5989
  fields = [];
5964
5990
  field = "";
5965
- i += char === "\r" && text3[i + 1] === "\n" ? 2 : 1;
5991
+ i += char === "\r" && text4[i + 1] === "\n" ? 2 : 1;
5966
5992
  continue;
5967
5993
  }
5968
5994
  field += char;
@@ -7099,28 +7125,34 @@ export {
7099
7125
  AGENT_HIDDEN_COMMANDS,
7100
7126
  ALL_AGGREGATES,
7101
7127
  ALL_CHART_TYPES,
7128
+ BEHAVIOURS as CHART_BEHAVIOURS,
7129
+ CHART_DECLARATION,
7102
7130
  CHART_EMPTY_FILL,
7103
7131
  CHART_PALETTE_STEPS,
7104
7132
  CHART_PANEL_ID,
7133
+ CHART_RUNTIME_UNITS,
7134
+ CHART_TYPE_LABELS,
7105
7135
  CONNECTORS_PANEL_ID,
7106
7136
  ChartController,
7107
7137
  ChartPanelView,
7138
+ ChartPlot,
7108
7139
  ConnectorTransportError,
7109
7140
  ConnectorsController,
7110
7141
  ConnectorsPanelView,
7142
+ DEFAULT_CHART_OPTIONS,
7111
7143
  DEFAULT_COLUMN_WIDTH,
7112
7144
  DEFAULT_PAGE_SIZE,
7113
7145
  DEFAULT_RANGES,
7114
7146
  EMPTY_LAYOUT,
7115
7147
  EXPIRY_SKEW_MS,
7116
- BEHAVIOURS2 as FIELDS_BEHAVIOURS,
7148
+ BEHAVIOURS3 as FIELDS_BEHAVIOURS,
7117
7149
  FIELDS_DECLARATION,
7118
7150
  FIELDS_PANEL_ID,
7119
7151
  FIELDS_RUNTIME_UNITS,
7120
7152
  FieldsController,
7121
7153
  FieldsPanelView,
7122
7154
  IMPLEMENTED_VIEW_MODES,
7123
- BEHAVIOURS as METRICS_BEHAVIOURS,
7155
+ BEHAVIOURS2 as METRICS_BEHAVIOURS,
7124
7156
  METRICS_DECLARATION,
7125
7157
  METRICS_PANEL_ID,
7126
7158
  METRICS_RUNTIME_UNITS,
@@ -7134,6 +7166,7 @@ export {
7134
7166
  TABLE_PANEL_ID,
7135
7167
  TableController,
7136
7168
  TablePanelView,
7169
+ applyChartUi,
7137
7170
  applyFieldsUi,
7138
7171
  applyMetricsUi,
7139
7172
  applyPrecision,
@@ -7145,6 +7178,9 @@ export {
7145
7178
  buildSelect,
7146
7179
  chartManifest,
7147
7180
  chartPanel,
7181
+ chartRuntimeComponents,
7182
+ chartViewManifest,
7183
+ chartViewState,
7148
7184
  clamp,
7149
7185
  classifyBrowserFetchFailure,
7150
7186
  classifyHttpStatus,