@quillsql/react 2.16.64 → 2.16.65

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. package/dist/index.cjs +153 -61
  2. package/dist/index.js +154 -62
  3. package/package.json +1 -1
package/dist/index.cjs CHANGED
@@ -22972,6 +22972,7 @@ var fetchReportBuilderDataFromState = async ({
22972
22972
  customFields,
22973
22973
  skipUniqueValues,
22974
22974
  skipRowCount,
22975
+ rowCountOnly,
22975
22976
  processing,
22976
22977
  dashboardName,
22977
22978
  getToken,
@@ -23048,7 +23049,7 @@ var fetchReportBuilderDataFromState = async ({
23048
23049
  processing ?? { page: DEFAULT_PAGINATION },
23049
23050
  customFields,
23050
23051
  skipRowCount,
23051
- void 0,
23052
+ rowCountOnly,
23052
23053
  curReport?.id ? String(curReport.id).trim() : void 0,
23053
23054
  draftSessionId ? String(draftSessionId).trim() : void 0
23054
23055
  );
@@ -63042,7 +63043,9 @@ async function loadViaReportBuilderState({
63042
63043
  report,
63043
63044
  draftSessionId,
63044
63045
  pagination,
63045
- paginationSort
63046
+ paginationSort,
63047
+ rowsOnly,
63048
+ rowCountOnly
63046
63049
  }) {
63047
63050
  const baseReport = {
63048
63051
  ...EMPTY_INTERNAL_REPORT,
@@ -63062,6 +63065,8 @@ async function loadViaReportBuilderState({
63062
63065
  // Unique values are fetched separately via `filterUniqueValuesQuery` so chart/table
63063
63066
  // refresh queries are not blocked on `report-builder-unique-values`.
63064
63067
  skipUniqueValues: true,
63068
+ skipRowCount: rowsOnly,
63069
+ rowCountOnly,
63065
63070
  previousRelevant: previousRelevantWhenSkippingInlineUniqueFetch(report),
63066
63071
  processing: pagination ? {
63067
63072
  page: {
@@ -63125,6 +63130,9 @@ async function loadViaReportBuilderState({
63125
63130
  report: {
63126
63131
  ...baseReport,
63127
63132
  ...reportBuilderInfo.report,
63133
+ // A rows-only response intentionally has no count; retain the previous
63134
+ // value until the independent count query completes.
63135
+ rowCount: rowsOnly ? baseReport.rowCount : reportBuilderInfo.report.rowCount,
63128
63136
  reportBuilderState: normalizedReportBuilderState,
63129
63137
  pivot: reportBuilderState.pivot,
63130
63138
  pivotRows: refreshedPivotData?.rows ?? compatibleReportPivotRows ?? (canReuseBasePivotRowsAndColumns ? baseReport.pivotRows : []) ?? [],
@@ -63154,7 +63162,8 @@ async function loadReportForUseForm({
63154
63162
  customFields,
63155
63163
  dashboardName,
63156
63164
  useInMemoryEngines,
63157
- draftSessionId
63165
+ draftSessionId,
63166
+ rowsOnly = false
63158
63167
  }) {
63159
63168
  const effectivePivot = pivot ?? initialReportBuilderState?.pivot ?? void 0;
63160
63169
  const hasPivot = Boolean(effectivePivot);
@@ -63251,7 +63260,9 @@ async function loadReportForUseForm({
63251
63260
  schema,
63252
63261
  customFields,
63253
63262
  dashboardName,
63254
- draftSessionId
63263
+ report: baseReport,
63264
+ draftSessionId,
63265
+ rowsOnly
63255
63266
  });
63256
63267
  }
63257
63268
  function generateDraftSessionId() {
@@ -63259,8 +63270,8 @@ function generateDraftSessionId() {
63259
63270
  }
63260
63271
  function useReport(reportIdArg, options = {}) {
63261
63272
  const propReportId = String(reportIdArg ?? "").trim();
63262
- const [createdReportId, setCreatedReportId] = (0, import_react61.useState)(null);
63263
- const effectiveReportId = propReportId || createdReportId || "";
63273
+ const [createdReportBootstrap, setCreatedReportBootstrap] = (0, import_react61.useState)(null);
63274
+ const effectiveReportId = propReportId || createdReportBootstrap?.reportId || "";
63264
63275
  const { eventTracking } = (0, import_react61.useContext)(EventTrackingContext);
63265
63276
  const [draftSessionId, setDraftSessionId] = (0, import_react61.useState)(generateDraftSessionId);
63266
63277
  const useInMemoryEngines = options.useInMemoryEngines ?? false;
@@ -63477,13 +63488,57 @@ function useReport(reportIdArg, options = {}) {
63477
63488
  const dashboardNameForNewReport = (0, import_react61.useMemo)(() => {
63478
63489
  return [clientDefaultDashboardName, destinationDashboardName].map((entry) => String(entry ?? "").trim()).find((entry) => entry.length > 0) ?? "";
63479
63490
  }, [clientDefaultDashboardName, destinationDashboardName]);
63491
+ const { mutate: createReport } = (0, import_react_query2.useMutation)({
63492
+ mutationKey: ["useReport", "create-report", draftSessionId],
63493
+ mutationFn: async ({
63494
+ reportBuilderState,
63495
+ tables
63496
+ }) => {
63497
+ if (!client) {
63498
+ throw new Error("Missing client for create-report");
63499
+ }
63500
+ const fallbackName = tables[0]?.name ? snakeAndCamelCaseToTitleCase(tables[0].name) : "New report";
63501
+ const resp = await saveReport({
63502
+ report: {
63503
+ ...EMPTY_INTERNAL_REPORT,
63504
+ name: fallbackName,
63505
+ chartType: "table",
63506
+ dashboardName: "quill-draft-reports",
63507
+ reportBuilderState
63508
+ },
63509
+ client,
63510
+ getToken,
63511
+ eventTracking,
63512
+ tenants,
63513
+ draftSessionId: draftSessionId || void 0
63514
+ });
63515
+ const reportId = String(resp?.id ?? resp?._id ?? "").trim();
63516
+ if (!reportId) {
63517
+ throw new Error("create-report returned no report id");
63518
+ }
63519
+ return {
63520
+ reportId,
63521
+ reportBuilderState,
63522
+ report: {
63523
+ ...EMPTY_INTERNAL_REPORT,
63524
+ ...resp,
63525
+ id: reportId,
63526
+ name: String(resp?.name ?? "").trim() || fallbackName,
63527
+ dashboardName: String(resp?.dashboardName ?? "").trim() || "quill-draft-reports",
63528
+ chartType: resp?.chartType ?? "table",
63529
+ pivot: null,
63530
+ reportBuilderState
63531
+ }
63532
+ };
63533
+ }
63534
+ });
63480
63535
  const filterStackRef = (0, import_react61.useRef)(filterStack);
63481
63536
  filterStackRef.current = filterStack;
63482
63537
  const resolvedGroupRowsBy = decodePivotGroupOptionValue(groupRowsBy);
63483
63538
  const resolvedGroupColumnsBy = decodePivotGroupOptionValue(groupColumnsBy);
63484
63539
  (0, import_react61.useEffect)(() => {
63485
63540
  if (propReportId) {
63486
- setCreatedReportId(null);
63541
+ setCreatedReportBootstrap(null);
63487
63542
  }
63488
63543
  }, [propReportId]);
63489
63544
  (0, import_react61.useEffect)(() => {
@@ -63563,7 +63618,7 @@ function useReport(reportIdArg, options = {}) {
63563
63618
  (0, import_react61.useEffect)(() => {
63564
63619
  if (reportOverride) return;
63565
63620
  if (propReportId) return;
63566
- if (createdReportId) return;
63621
+ if (createdReportBootstrap) return;
63567
63622
  if (!client) return;
63568
63623
  if (!String(dashboardNameForNewReport ?? "").trim()) {
63569
63624
  return;
@@ -63594,59 +63649,34 @@ function useReport(reportIdArg, options = {}) {
63594
63649
  );
63595
63650
  }
63596
63651
  if (bootstrapColumns.length === 0) return;
63597
- let cancelled = false;
63598
- (async () => {
63599
- try {
63600
- const fkMapForMerge = getSchemaForeignKeyMapping(
63601
- schemaForReportBuilderState
63602
- );
63603
- const tables = mergeReportBuilderTables(
63604
- ids.map((name2) => ({ name: name2 })),
63605
- bootstrapColumns.map((col) => String(col.table ?? "").trim()).filter(Boolean),
63606
- fkMapForMerge
63607
- );
63608
- const reportBuilderState = {
63609
- tables,
63610
- columns: bootstrapColumns,
63611
- filterStack: [],
63612
- sort: [],
63613
- limit: null,
63614
- pivot: null
63615
- };
63616
- const resp = await saveReport({
63617
- report: {
63618
- ...EMPTY_INTERNAL_REPORT,
63619
- name: tables[0]?.name ? snakeAndCamelCaseToTitleCase(tables[0].name) : "New report",
63620
- chartType: "table",
63621
- dashboardName: "quill-draft-reports",
63622
- reportBuilderState
63623
- },
63624
- client,
63625
- getToken,
63626
- eventTracking,
63627
- tenants,
63628
- draftSessionId: draftSessionId || void 0
63629
- });
63630
- if (cancelled) return;
63631
- const id = String(resp?.id ?? resp?._id ?? "").trim();
63632
- if (id) setCreatedReportId(id);
63633
- } catch {
63634
- }
63635
- })();
63636
- return () => {
63637
- cancelled = true;
63652
+ const fkMapForMerge = getSchemaForeignKeyMapping(
63653
+ schemaForReportBuilderState
63654
+ );
63655
+ const tables = mergeReportBuilderTables(
63656
+ ids.map((name2) => ({ name: name2 })),
63657
+ bootstrapColumns.map((col) => String(col.table ?? "").trim()).filter(Boolean),
63658
+ fkMapForMerge
63659
+ );
63660
+ const reportBuilderState = {
63661
+ tables,
63662
+ columns: bootstrapColumns,
63663
+ filterStack: [],
63664
+ sort: [],
63665
+ limit: null,
63666
+ pivot: null
63638
63667
  };
63668
+ createReport(
63669
+ { reportBuilderState, tables },
63670
+ { onSuccess: setCreatedReportBootstrap }
63671
+ );
63639
63672
  }, [
63640
63673
  reportOverride,
63641
63674
  propReportId,
63642
- createdReportId,
63675
+ createdReportBootstrap,
63643
63676
  client,
63677
+ createReport,
63644
63678
  schemaDatasourceIdsKey,
63645
63679
  dashboardNameForNewReport,
63646
- draftSessionId,
63647
- getToken,
63648
- eventTracking,
63649
- tenants,
63650
63680
  schemaForReportBuilderState,
63651
63681
  queryColumnsBootstrapKey
63652
63682
  ]);
@@ -64521,19 +64551,27 @@ function useReport(reportIdArg, options = {}) {
64521
64551
  setExpandReportBuilderColumnsForFlatTable(false);
64522
64552
  prevPivotStateForColumnExpansionRef.current = null;
64523
64553
  }, [propReportId, reportOverride]);
64554
+ const createdBootstrapForInitialLoad = !propReportId && createdReportBootstrap?.reportId === effectiveReportId ? createdReportBootstrap : null;
64555
+ const initialReportBuilderStateForLoad = initialReportBuilderState ?? createdBootstrapForInitialLoad?.reportBuilderState ?? null;
64556
+ const initialBaseReportForLoad = createdBootstrapForInitialLoad?.report ?? null;
64557
+ const isCreatedReportBootstrapLoad = Boolean(
64558
+ createdBootstrapForInitialLoad && initialReportBuilderStateForLoad
64559
+ );
64524
64560
  const initialLoadQuery = (0, import_react_query2.useQuery)({
64525
64561
  queryKey: createUseFormInitialLoadQueryKey({
64526
64562
  reportId: effectiveReportId,
64527
64563
  draftSessionId,
64528
64564
  useInMemoryEngines,
64529
- hasInitialReportBuilderState: Boolean(initialReportBuilderState),
64565
+ hasInitialReportBuilderState: Boolean(
64566
+ initialReportBuilderStateForLoad
64567
+ ),
64530
64568
  reloadKeyHash,
64531
64569
  tenantHash,
64532
64570
  flagHash,
64533
64571
  clientHash
64534
64572
  }),
64535
64573
  queryFn: createUseFormQueryFn(async () => {
64536
- const allowReportTaskBootstrap = !initialReportBuilderState && bootstrapReportTaskUsedForReportIdRef.current !== effectiveReportId;
64574
+ const allowReportTaskBootstrap = !initialReportBuilderStateForLoad && bootstrapReportTaskUsedForReportIdRef.current !== effectiveReportId;
64537
64575
  const loadTargetId = String(effectiveReportId ?? "").trim();
64538
64576
  const sourceReportIdentity = String(
64539
64577
  sourceReport?.id ?? sourceReport?._id ?? ""
@@ -64545,7 +64583,8 @@ function useReport(reportIdArg, options = {}) {
64545
64583
  }
64546
64584
  const loadResult = await loadReportForUseForm({
64547
64585
  reportId: effectiveReportId,
64548
- initialReportBuilderState,
64586
+ initialReportBuilderState: initialReportBuilderStateForLoad,
64587
+ baseReport: initialBaseReportForLoad,
64549
64588
  allowReportTaskBootstrap,
64550
64589
  client,
64551
64590
  getToken,
@@ -64556,7 +64595,8 @@ function useReport(reportIdArg, options = {}) {
64556
64595
  customFields: customFieldsRef.current,
64557
64596
  dashboardName: resolvedSourceDashboardName,
64558
64597
  useInMemoryEngines,
64559
- draftSessionId: draftSessionId || void 0
64598
+ draftSessionId: draftSessionId || void 0,
64599
+ rowsOnly: isCreatedReportBootstrapLoad
64560
64600
  });
64561
64601
  return loadResult;
64562
64602
  }),
@@ -65177,6 +65217,7 @@ function useReport(reportIdArg, options = {}) {
65177
65217
  () => stableSerializeForQueryKey(effectiveReportBuilderState),
65178
65218
  [effectiveReportBuilderState]
65179
65219
  );
65220
+ const createdBootstrapStateMatchesEffectiveState = isCreatedReportBootstrapLoad && stableSerializeForQueryKey(initialReportBuilderStateForLoad) === effectiveReportBuilderStateHash;
65180
65221
  const prevPaginationResetStateHashRef = (0, import_react61.useRef)(null);
65181
65222
  (0, import_react61.useEffect)(() => {
65182
65223
  const prevHash = prevPaginationResetStateHashRef.current;
@@ -65283,12 +65324,61 @@ function useReport(reportIdArg, options = {}) {
65283
65324
  enabled: tableRefreshQueryEnabled,
65284
65325
  retry: false
65285
65326
  });
65327
+ const createdBootstrapRowCountQuery = (0, import_react_query2.useQuery)({
65328
+ queryKey: [
65329
+ "useReport",
65330
+ "created-bootstrap-row-count",
65331
+ effectiveReportId,
65332
+ stableSerializeForQueryKey(initialReportBuilderStateForLoad),
65333
+ tenantHash,
65334
+ clientHash
65335
+ ],
65336
+ queryFn: createUseFormQueryFn(async () => {
65337
+ if (!createdBootstrapForInitialLoad || !initialReportBuilderStateForLoad || !client) {
65338
+ return { report: null, error: "Missing bootstrap count prerequisites" };
65339
+ }
65340
+ return loadViaReportBuilderState({
65341
+ reportId: effectiveReportId,
65342
+ reportBuilderState: initialReportBuilderStateForLoad,
65343
+ client,
65344
+ getToken,
65345
+ tenants,
65346
+ schema: schemaForReportBuilderState,
65347
+ customFields: schemaData.customFields,
65348
+ dashboardName: resolvedSourceDashboardName,
65349
+ report: createdBootstrapForInitialLoad.report,
65350
+ draftSessionId: draftSessionId || void 0,
65351
+ rowCountOnly: true
65352
+ });
65353
+ }),
65354
+ enabled: createdBootstrapStateMatchesEffectiveState && Boolean(client) && !reportOverride,
65355
+ retry: false
65356
+ });
65286
65357
  (0, import_react61.useEffect)(() => {
65287
65358
  if (!tableRefreshQueryEnabled) return;
65288
65359
  const report = tableRefreshQuery.data?.report;
65289
65360
  if (tableRefreshQuery.data?.error || !report) return;
65290
65361
  setSourceReport(report);
65291
65362
  }, [effectiveReportId, tableRefreshQuery.data, tableRefreshQueryEnabled]);
65363
+ (0, import_react61.useEffect)(() => {
65364
+ if (!createdBootstrapStateMatchesEffectiveState) return;
65365
+ const countReport = createdBootstrapRowCountQuery.data?.report;
65366
+ if (createdBootstrapRowCountQuery.data?.error || !countReport) return;
65367
+ setSourceReport((currentReport) => {
65368
+ if (!currentReport || currentReport.id !== effectiveReportId) {
65369
+ return currentReport;
65370
+ }
65371
+ if (currentReport.rowCount === countReport.rowCount) {
65372
+ return currentReport;
65373
+ }
65374
+ return { ...currentReport, rowCount: countReport.rowCount };
65375
+ });
65376
+ }, [
65377
+ createdBootstrapRowCountQuery.data,
65378
+ createdBootstrapStateMatchesEffectiveState,
65379
+ effectiveReportId,
65380
+ sourceReport?.id
65381
+ ]);
65292
65382
  const chartTypes = (0, import_react61.useMemo)(() => {
65293
65383
  return getChartTypeOptions2({ pivot: pivotState });
65294
65384
  }, [pivotState]);
@@ -65957,7 +66047,8 @@ function useReport(reportIdArg, options = {}) {
65957
66047
  pageIndex: pagination.pageIndex,
65958
66048
  pageSize: pagination.pageSize
65959
66049
  },
65960
- paginationSort: tablePaginationSort
66050
+ paginationSort: tablePaginationSort,
66051
+ rowsOnly: true
65961
66052
  });
65962
66053
  }),
65963
66054
  enabled: tablePageQueryEnabled,
@@ -67468,11 +67559,12 @@ function useReport(reportIdArg, options = {}) {
67468
67559
  const isClearingRowGrouping = effectiveNextState.groupRowsBy !== void 0 && String(effectiveNextState.groupRowsBy ?? "").trim().length === 0;
67469
67560
  const queuePromoteColumnToRow = isClearingRowGrouping && !sourceReport;
67470
67561
  const shouldRefreshExpandedTableData = useInMemoryEngines && (hasRowGroupSelection || hasColumnGroupSelection || hasAggregationSelection) || !useInMemoryEngines && !nextPivot && effectiveNextState.sort !== void 0;
67471
- const dispatchTouchesPivot = touchesPivotState || isDatasourceUpdate;
67562
+ const hasReportIdentity = Boolean(effectiveReportId);
67563
+ const dispatchTouchesPivot = touchesPivotState || hasReportIdentity && isDatasourceUpdate;
67472
67564
  dispatchFormRuntime({
67473
67565
  type: "APPLY_SET_REPORT",
67474
67566
  touchesPivotState: dispatchTouchesPivot,
67475
- shouldRefreshExpandedTableData: shouldRefreshExpandedTableData || isDatasourceUpdate || addedRequestedDisplayColumns.length > 0,
67567
+ shouldRefreshExpandedTableData: shouldRefreshExpandedTableData || hasReportIdentity && (isDatasourceUpdate || addedRequestedDisplayColumns.length > 0),
67476
67568
  queuePromoteColumnToRow,
67477
67569
  updater: (prev) => {
67478
67570
  const next = {
package/dist/index.js CHANGED
@@ -22969,6 +22969,7 @@ var fetchReportBuilderDataFromState = async ({
22969
22969
  customFields,
22970
22970
  skipUniqueValues,
22971
22971
  skipRowCount,
22972
+ rowCountOnly,
22972
22973
  processing,
22973
22974
  dashboardName,
22974
22975
  getToken,
@@ -23045,7 +23046,7 @@ var fetchReportBuilderDataFromState = async ({
23045
23046
  processing ?? { page: DEFAULT_PAGINATION },
23046
23047
  customFields,
23047
23048
  skipRowCount,
23048
- void 0,
23049
+ rowCountOnly,
23049
23050
  curReport?.id ? String(curReport.id).trim() : void 0,
23050
23051
  draftSessionId ? String(draftSessionId).trim() : void 0
23051
23052
  );
@@ -58821,7 +58822,7 @@ import {
58821
58822
  useRef as useRef24,
58822
58823
  useState as useState41
58823
58824
  } from "react";
58824
- import { keepPreviousData, useQuery } from "@tanstack/react-query";
58825
+ import { keepPreviousData, useMutation, useQuery } from "@tanstack/react-query";
58825
58826
  init_util();
58826
58827
  init_columnType();
58827
58828
  init_columnProcessing();
@@ -63254,7 +63255,9 @@ async function loadViaReportBuilderState({
63254
63255
  report,
63255
63256
  draftSessionId,
63256
63257
  pagination,
63257
- paginationSort
63258
+ paginationSort,
63259
+ rowsOnly,
63260
+ rowCountOnly
63258
63261
  }) {
63259
63262
  const baseReport = {
63260
63263
  ...EMPTY_INTERNAL_REPORT,
@@ -63274,6 +63277,8 @@ async function loadViaReportBuilderState({
63274
63277
  // Unique values are fetched separately via `filterUniqueValuesQuery` so chart/table
63275
63278
  // refresh queries are not blocked on `report-builder-unique-values`.
63276
63279
  skipUniqueValues: true,
63280
+ skipRowCount: rowsOnly,
63281
+ rowCountOnly,
63277
63282
  previousRelevant: previousRelevantWhenSkippingInlineUniqueFetch(report),
63278
63283
  processing: pagination ? {
63279
63284
  page: {
@@ -63337,6 +63342,9 @@ async function loadViaReportBuilderState({
63337
63342
  report: {
63338
63343
  ...baseReport,
63339
63344
  ...reportBuilderInfo.report,
63345
+ // A rows-only response intentionally has no count; retain the previous
63346
+ // value until the independent count query completes.
63347
+ rowCount: rowsOnly ? baseReport.rowCount : reportBuilderInfo.report.rowCount,
63340
63348
  reportBuilderState: normalizedReportBuilderState,
63341
63349
  pivot: reportBuilderState.pivot,
63342
63350
  pivotRows: refreshedPivotData?.rows ?? compatibleReportPivotRows ?? (canReuseBasePivotRowsAndColumns ? baseReport.pivotRows : []) ?? [],
@@ -63366,7 +63374,8 @@ async function loadReportForUseForm({
63366
63374
  customFields,
63367
63375
  dashboardName,
63368
63376
  useInMemoryEngines,
63369
- draftSessionId
63377
+ draftSessionId,
63378
+ rowsOnly = false
63370
63379
  }) {
63371
63380
  const effectivePivot = pivot ?? initialReportBuilderState?.pivot ?? void 0;
63372
63381
  const hasPivot = Boolean(effectivePivot);
@@ -63463,7 +63472,9 @@ async function loadReportForUseForm({
63463
63472
  schema,
63464
63473
  customFields,
63465
63474
  dashboardName,
63466
- draftSessionId
63475
+ report: baseReport,
63476
+ draftSessionId,
63477
+ rowsOnly
63467
63478
  });
63468
63479
  }
63469
63480
  function generateDraftSessionId() {
@@ -63471,8 +63482,8 @@ function generateDraftSessionId() {
63471
63482
  }
63472
63483
  function useReport(reportIdArg, options = {}) {
63473
63484
  const propReportId = String(reportIdArg ?? "").trim();
63474
- const [createdReportId, setCreatedReportId] = useState41(null);
63475
- const effectiveReportId = propReportId || createdReportId || "";
63485
+ const [createdReportBootstrap, setCreatedReportBootstrap] = useState41(null);
63486
+ const effectiveReportId = propReportId || createdReportBootstrap?.reportId || "";
63476
63487
  const { eventTracking } = useContext36(EventTrackingContext);
63477
63488
  const [draftSessionId, setDraftSessionId] = useState41(generateDraftSessionId);
63478
63489
  const useInMemoryEngines = options.useInMemoryEngines ?? false;
@@ -63689,13 +63700,57 @@ function useReport(reportIdArg, options = {}) {
63689
63700
  const dashboardNameForNewReport = useMemo32(() => {
63690
63701
  return [clientDefaultDashboardName, destinationDashboardName].map((entry) => String(entry ?? "").trim()).find((entry) => entry.length > 0) ?? "";
63691
63702
  }, [clientDefaultDashboardName, destinationDashboardName]);
63703
+ const { mutate: createReport } = useMutation({
63704
+ mutationKey: ["useReport", "create-report", draftSessionId],
63705
+ mutationFn: async ({
63706
+ reportBuilderState,
63707
+ tables
63708
+ }) => {
63709
+ if (!client) {
63710
+ throw new Error("Missing client for create-report");
63711
+ }
63712
+ const fallbackName = tables[0]?.name ? snakeAndCamelCaseToTitleCase(tables[0].name) : "New report";
63713
+ const resp = await saveReport({
63714
+ report: {
63715
+ ...EMPTY_INTERNAL_REPORT,
63716
+ name: fallbackName,
63717
+ chartType: "table",
63718
+ dashboardName: "quill-draft-reports",
63719
+ reportBuilderState
63720
+ },
63721
+ client,
63722
+ getToken,
63723
+ eventTracking,
63724
+ tenants,
63725
+ draftSessionId: draftSessionId || void 0
63726
+ });
63727
+ const reportId = String(resp?.id ?? resp?._id ?? "").trim();
63728
+ if (!reportId) {
63729
+ throw new Error("create-report returned no report id");
63730
+ }
63731
+ return {
63732
+ reportId,
63733
+ reportBuilderState,
63734
+ report: {
63735
+ ...EMPTY_INTERNAL_REPORT,
63736
+ ...resp,
63737
+ id: reportId,
63738
+ name: String(resp?.name ?? "").trim() || fallbackName,
63739
+ dashboardName: String(resp?.dashboardName ?? "").trim() || "quill-draft-reports",
63740
+ chartType: resp?.chartType ?? "table",
63741
+ pivot: null,
63742
+ reportBuilderState
63743
+ }
63744
+ };
63745
+ }
63746
+ });
63692
63747
  const filterStackRef = useRef24(filterStack);
63693
63748
  filterStackRef.current = filterStack;
63694
63749
  const resolvedGroupRowsBy = decodePivotGroupOptionValue(groupRowsBy);
63695
63750
  const resolvedGroupColumnsBy = decodePivotGroupOptionValue(groupColumnsBy);
63696
63751
  useEffect31(() => {
63697
63752
  if (propReportId) {
63698
- setCreatedReportId(null);
63753
+ setCreatedReportBootstrap(null);
63699
63754
  }
63700
63755
  }, [propReportId]);
63701
63756
  useEffect31(() => {
@@ -63775,7 +63830,7 @@ function useReport(reportIdArg, options = {}) {
63775
63830
  useEffect31(() => {
63776
63831
  if (reportOverride) return;
63777
63832
  if (propReportId) return;
63778
- if (createdReportId) return;
63833
+ if (createdReportBootstrap) return;
63779
63834
  if (!client) return;
63780
63835
  if (!String(dashboardNameForNewReport ?? "").trim()) {
63781
63836
  return;
@@ -63806,59 +63861,34 @@ function useReport(reportIdArg, options = {}) {
63806
63861
  );
63807
63862
  }
63808
63863
  if (bootstrapColumns.length === 0) return;
63809
- let cancelled = false;
63810
- (async () => {
63811
- try {
63812
- const fkMapForMerge = getSchemaForeignKeyMapping(
63813
- schemaForReportBuilderState
63814
- );
63815
- const tables = mergeReportBuilderTables(
63816
- ids.map((name2) => ({ name: name2 })),
63817
- bootstrapColumns.map((col) => String(col.table ?? "").trim()).filter(Boolean),
63818
- fkMapForMerge
63819
- );
63820
- const reportBuilderState = {
63821
- tables,
63822
- columns: bootstrapColumns,
63823
- filterStack: [],
63824
- sort: [],
63825
- limit: null,
63826
- pivot: null
63827
- };
63828
- const resp = await saveReport({
63829
- report: {
63830
- ...EMPTY_INTERNAL_REPORT,
63831
- name: tables[0]?.name ? snakeAndCamelCaseToTitleCase(tables[0].name) : "New report",
63832
- chartType: "table",
63833
- dashboardName: "quill-draft-reports",
63834
- reportBuilderState
63835
- },
63836
- client,
63837
- getToken,
63838
- eventTracking,
63839
- tenants,
63840
- draftSessionId: draftSessionId || void 0
63841
- });
63842
- if (cancelled) return;
63843
- const id = String(resp?.id ?? resp?._id ?? "").trim();
63844
- if (id) setCreatedReportId(id);
63845
- } catch {
63846
- }
63847
- })();
63848
- return () => {
63849
- cancelled = true;
63864
+ const fkMapForMerge = getSchemaForeignKeyMapping(
63865
+ schemaForReportBuilderState
63866
+ );
63867
+ const tables = mergeReportBuilderTables(
63868
+ ids.map((name2) => ({ name: name2 })),
63869
+ bootstrapColumns.map((col) => String(col.table ?? "").trim()).filter(Boolean),
63870
+ fkMapForMerge
63871
+ );
63872
+ const reportBuilderState = {
63873
+ tables,
63874
+ columns: bootstrapColumns,
63875
+ filterStack: [],
63876
+ sort: [],
63877
+ limit: null,
63878
+ pivot: null
63850
63879
  };
63880
+ createReport(
63881
+ { reportBuilderState, tables },
63882
+ { onSuccess: setCreatedReportBootstrap }
63883
+ );
63851
63884
  }, [
63852
63885
  reportOverride,
63853
63886
  propReportId,
63854
- createdReportId,
63887
+ createdReportBootstrap,
63855
63888
  client,
63889
+ createReport,
63856
63890
  schemaDatasourceIdsKey,
63857
63891
  dashboardNameForNewReport,
63858
- draftSessionId,
63859
- getToken,
63860
- eventTracking,
63861
- tenants,
63862
63892
  schemaForReportBuilderState,
63863
63893
  queryColumnsBootstrapKey
63864
63894
  ]);
@@ -64733,19 +64763,27 @@ function useReport(reportIdArg, options = {}) {
64733
64763
  setExpandReportBuilderColumnsForFlatTable(false);
64734
64764
  prevPivotStateForColumnExpansionRef.current = null;
64735
64765
  }, [propReportId, reportOverride]);
64766
+ const createdBootstrapForInitialLoad = !propReportId && createdReportBootstrap?.reportId === effectiveReportId ? createdReportBootstrap : null;
64767
+ const initialReportBuilderStateForLoad = initialReportBuilderState ?? createdBootstrapForInitialLoad?.reportBuilderState ?? null;
64768
+ const initialBaseReportForLoad = createdBootstrapForInitialLoad?.report ?? null;
64769
+ const isCreatedReportBootstrapLoad = Boolean(
64770
+ createdBootstrapForInitialLoad && initialReportBuilderStateForLoad
64771
+ );
64736
64772
  const initialLoadQuery = useQuery({
64737
64773
  queryKey: createUseFormInitialLoadQueryKey({
64738
64774
  reportId: effectiveReportId,
64739
64775
  draftSessionId,
64740
64776
  useInMemoryEngines,
64741
- hasInitialReportBuilderState: Boolean(initialReportBuilderState),
64777
+ hasInitialReportBuilderState: Boolean(
64778
+ initialReportBuilderStateForLoad
64779
+ ),
64742
64780
  reloadKeyHash,
64743
64781
  tenantHash,
64744
64782
  flagHash,
64745
64783
  clientHash
64746
64784
  }),
64747
64785
  queryFn: createUseFormQueryFn(async () => {
64748
- const allowReportTaskBootstrap = !initialReportBuilderState && bootstrapReportTaskUsedForReportIdRef.current !== effectiveReportId;
64786
+ const allowReportTaskBootstrap = !initialReportBuilderStateForLoad && bootstrapReportTaskUsedForReportIdRef.current !== effectiveReportId;
64749
64787
  const loadTargetId = String(effectiveReportId ?? "").trim();
64750
64788
  const sourceReportIdentity = String(
64751
64789
  sourceReport?.id ?? sourceReport?._id ?? ""
@@ -64757,7 +64795,8 @@ function useReport(reportIdArg, options = {}) {
64757
64795
  }
64758
64796
  const loadResult = await loadReportForUseForm({
64759
64797
  reportId: effectiveReportId,
64760
- initialReportBuilderState,
64798
+ initialReportBuilderState: initialReportBuilderStateForLoad,
64799
+ baseReport: initialBaseReportForLoad,
64761
64800
  allowReportTaskBootstrap,
64762
64801
  client,
64763
64802
  getToken,
@@ -64768,7 +64807,8 @@ function useReport(reportIdArg, options = {}) {
64768
64807
  customFields: customFieldsRef.current,
64769
64808
  dashboardName: resolvedSourceDashboardName,
64770
64809
  useInMemoryEngines,
64771
- draftSessionId: draftSessionId || void 0
64810
+ draftSessionId: draftSessionId || void 0,
64811
+ rowsOnly: isCreatedReportBootstrapLoad
64772
64812
  });
64773
64813
  return loadResult;
64774
64814
  }),
@@ -65389,6 +65429,7 @@ function useReport(reportIdArg, options = {}) {
65389
65429
  () => stableSerializeForQueryKey(effectiveReportBuilderState),
65390
65430
  [effectiveReportBuilderState]
65391
65431
  );
65432
+ const createdBootstrapStateMatchesEffectiveState = isCreatedReportBootstrapLoad && stableSerializeForQueryKey(initialReportBuilderStateForLoad) === effectiveReportBuilderStateHash;
65392
65433
  const prevPaginationResetStateHashRef = useRef24(null);
65393
65434
  useEffect31(() => {
65394
65435
  const prevHash = prevPaginationResetStateHashRef.current;
@@ -65495,12 +65536,61 @@ function useReport(reportIdArg, options = {}) {
65495
65536
  enabled: tableRefreshQueryEnabled,
65496
65537
  retry: false
65497
65538
  });
65539
+ const createdBootstrapRowCountQuery = useQuery({
65540
+ queryKey: [
65541
+ "useReport",
65542
+ "created-bootstrap-row-count",
65543
+ effectiveReportId,
65544
+ stableSerializeForQueryKey(initialReportBuilderStateForLoad),
65545
+ tenantHash,
65546
+ clientHash
65547
+ ],
65548
+ queryFn: createUseFormQueryFn(async () => {
65549
+ if (!createdBootstrapForInitialLoad || !initialReportBuilderStateForLoad || !client) {
65550
+ return { report: null, error: "Missing bootstrap count prerequisites" };
65551
+ }
65552
+ return loadViaReportBuilderState({
65553
+ reportId: effectiveReportId,
65554
+ reportBuilderState: initialReportBuilderStateForLoad,
65555
+ client,
65556
+ getToken,
65557
+ tenants,
65558
+ schema: schemaForReportBuilderState,
65559
+ customFields: schemaData.customFields,
65560
+ dashboardName: resolvedSourceDashboardName,
65561
+ report: createdBootstrapForInitialLoad.report,
65562
+ draftSessionId: draftSessionId || void 0,
65563
+ rowCountOnly: true
65564
+ });
65565
+ }),
65566
+ enabled: createdBootstrapStateMatchesEffectiveState && Boolean(client) && !reportOverride,
65567
+ retry: false
65568
+ });
65498
65569
  useEffect31(() => {
65499
65570
  if (!tableRefreshQueryEnabled) return;
65500
65571
  const report = tableRefreshQuery.data?.report;
65501
65572
  if (tableRefreshQuery.data?.error || !report) return;
65502
65573
  setSourceReport(report);
65503
65574
  }, [effectiveReportId, tableRefreshQuery.data, tableRefreshQueryEnabled]);
65575
+ useEffect31(() => {
65576
+ if (!createdBootstrapStateMatchesEffectiveState) return;
65577
+ const countReport = createdBootstrapRowCountQuery.data?.report;
65578
+ if (createdBootstrapRowCountQuery.data?.error || !countReport) return;
65579
+ setSourceReport((currentReport) => {
65580
+ if (!currentReport || currentReport.id !== effectiveReportId) {
65581
+ return currentReport;
65582
+ }
65583
+ if (currentReport.rowCount === countReport.rowCount) {
65584
+ return currentReport;
65585
+ }
65586
+ return { ...currentReport, rowCount: countReport.rowCount };
65587
+ });
65588
+ }, [
65589
+ createdBootstrapRowCountQuery.data,
65590
+ createdBootstrapStateMatchesEffectiveState,
65591
+ effectiveReportId,
65592
+ sourceReport?.id
65593
+ ]);
65504
65594
  const chartTypes = useMemo32(() => {
65505
65595
  return getChartTypeOptions2({ pivot: pivotState });
65506
65596
  }, [pivotState]);
@@ -66169,7 +66259,8 @@ function useReport(reportIdArg, options = {}) {
66169
66259
  pageIndex: pagination.pageIndex,
66170
66260
  pageSize: pagination.pageSize
66171
66261
  },
66172
- paginationSort: tablePaginationSort
66262
+ paginationSort: tablePaginationSort,
66263
+ rowsOnly: true
66173
66264
  });
66174
66265
  }),
66175
66266
  enabled: tablePageQueryEnabled,
@@ -67680,11 +67771,12 @@ function useReport(reportIdArg, options = {}) {
67680
67771
  const isClearingRowGrouping = effectiveNextState.groupRowsBy !== void 0 && String(effectiveNextState.groupRowsBy ?? "").trim().length === 0;
67681
67772
  const queuePromoteColumnToRow = isClearingRowGrouping && !sourceReport;
67682
67773
  const shouldRefreshExpandedTableData = useInMemoryEngines && (hasRowGroupSelection || hasColumnGroupSelection || hasAggregationSelection) || !useInMemoryEngines && !nextPivot && effectiveNextState.sort !== void 0;
67683
- const dispatchTouchesPivot = touchesPivotState || isDatasourceUpdate;
67774
+ const hasReportIdentity = Boolean(effectiveReportId);
67775
+ const dispatchTouchesPivot = touchesPivotState || hasReportIdentity && isDatasourceUpdate;
67684
67776
  dispatchFormRuntime({
67685
67777
  type: "APPLY_SET_REPORT",
67686
67778
  touchesPivotState: dispatchTouchesPivot,
67687
- shouldRefreshExpandedTableData: shouldRefreshExpandedTableData || isDatasourceUpdate || addedRequestedDisplayColumns.length > 0,
67779
+ shouldRefreshExpandedTableData: shouldRefreshExpandedTableData || hasReportIdentity && (isDatasourceUpdate || addedRequestedDisplayColumns.length > 0),
67688
67780
  queuePromoteColumnToRow,
67689
67781
  updater: (prev) => {
67690
67782
  const next = {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@quillsql/react",
3
- "version": "2.16.64",
3
+ "version": "2.16.65",
4
4
  "type": "module",
5
5
  "exports": {
6
6
  ".": {