@okf/ootils 1.40.0 → 1.41.1

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.
@@ -285,9 +285,10 @@ declare const collectMarkIdsInOrder: (editorState: any) => string[];
285
285
  * }
286
286
  * ]
287
287
  */
288
- declare function getRollupPossibilities({ tagType, allTpls }: {
288
+ declare function getRollupPossibilities({ tagType, allTpls, includeSelfHead, }: {
289
289
  tagType: string;
290
290
  allTpls: any[];
291
+ includeSelfHead?: boolean;
291
292
  }): any[];
292
293
 
293
294
  declare namespace BASE_BULLMQ_CONFIG {
@@ -1241,6 +1242,27 @@ declare const processAuthorAndCommonFilters: (allTpls: any[], filterScopes: stri
1241
1242
 
1242
1243
  declare const _self_managed_getFixedAnnoTagBlock: (selectedTpls: any[], annotationTagsCount: any) => any[];
1243
1244
 
1245
+ /**
1246
+ * FOLLOWUP (consolidate the count->rollupPath rule into one source of truth):
1247
+ *
1248
+ * The rule "given annotationTagsCount, which self-managed anno rollupPaths exist"
1249
+ * (subThemes>0 -> ['tags','subThemes']; subThemes>0 && themes>0 -> ['tags','subThemes','themes'])
1250
+ * is currently duplicated in THREE places and will drift:
1251
+ * 1. here (_self_managed_getFixedAnnoRollupBlocks) -> filter blocks
1252
+ * 2. _self_managed_buildAnnoHierarchyConfig -> anno hierarchy filter UI
1253
+ * 3. okf-fe _extractAllAnnoBasedDimensionsAsOptions.js -> reports dimension dropdown
1254
+ *
1255
+ * (#3 was added to fix a crash: the reports widget previously discovered these rollups
1256
+ * from publishing-segment tpls via getRollupPossibilities, but self-managed taxonomy lives
1257
+ * on `collections`-segment tpls which isTplAnnotationEnabled excludes -> empty list ->
1258
+ * unguarded .find('subThemes') returned undefined -> crash. The FE now builds them from the
1259
+ * count, mirroring this function.)
1260
+ *
1261
+ * Extract a pure helper here in ootils:
1262
+ * export const getSelfManagedAnnoRollupPaths = (annotationTagsCount): string[][] => [...]
1263
+ * then have all three call sites consume it (each maps paths -> its own shape:
1264
+ * filter-blocks / hierarchy levels / dropdown options). One rule, three presentations.
1265
+ */
1244
1266
  declare const _self_managed_getFixedAnnoRollupBlocks: ({ selectedTpls, allTpls, annotationTagsCount }: {
1245
1267
  selectedTpls: any[];
1246
1268
  allTpls: any[];
@@ -1342,6 +1364,7 @@ declare const _self_managed_buildDocHierarchyConfig: ({ combinedDocumentBlocks,
1342
1364
  display: any;
1343
1365
  filters: any[];
1344
1366
  rollups: any[];
1367
+ rollupDisplayMap: Record<string, string>;
1345
1368
  }[];
1346
1369
  };
1347
1370
  target: {
@@ -1501,6 +1524,7 @@ declare const autoGenFilterConfigsFromTpl: ({ selectedTpls, allTpls, filterScope
1501
1524
  display: any;
1502
1525
  filters: any[];
1503
1526
  rollups: any[];
1527
+ rollupDisplayMap: Record<string, string>;
1504
1528
  }[];
1505
1529
  };
1506
1530
  target: {
package/dist/browser.d.ts CHANGED
@@ -285,9 +285,10 @@ declare const collectMarkIdsInOrder: (editorState: any) => string[];
285
285
  * }
286
286
  * ]
287
287
  */
288
- declare function getRollupPossibilities({ tagType, allTpls }: {
288
+ declare function getRollupPossibilities({ tagType, allTpls, includeSelfHead, }: {
289
289
  tagType: string;
290
290
  allTpls: any[];
291
+ includeSelfHead?: boolean;
291
292
  }): any[];
292
293
 
293
294
  declare namespace BASE_BULLMQ_CONFIG {
@@ -1241,6 +1242,27 @@ declare const processAuthorAndCommonFilters: (allTpls: any[], filterScopes: stri
1241
1242
 
1242
1243
  declare const _self_managed_getFixedAnnoTagBlock: (selectedTpls: any[], annotationTagsCount: any) => any[];
1243
1244
 
1245
+ /**
1246
+ * FOLLOWUP (consolidate the count->rollupPath rule into one source of truth):
1247
+ *
1248
+ * The rule "given annotationTagsCount, which self-managed anno rollupPaths exist"
1249
+ * (subThemes>0 -> ['tags','subThemes']; subThemes>0 && themes>0 -> ['tags','subThemes','themes'])
1250
+ * is currently duplicated in THREE places and will drift:
1251
+ * 1. here (_self_managed_getFixedAnnoRollupBlocks) -> filter blocks
1252
+ * 2. _self_managed_buildAnnoHierarchyConfig -> anno hierarchy filter UI
1253
+ * 3. okf-fe _extractAllAnnoBasedDimensionsAsOptions.js -> reports dimension dropdown
1254
+ *
1255
+ * (#3 was added to fix a crash: the reports widget previously discovered these rollups
1256
+ * from publishing-segment tpls via getRollupPossibilities, but self-managed taxonomy lives
1257
+ * on `collections`-segment tpls which isTplAnnotationEnabled excludes -> empty list ->
1258
+ * unguarded .find('subThemes') returned undefined -> crash. The FE now builds them from the
1259
+ * count, mirroring this function.)
1260
+ *
1261
+ * Extract a pure helper here in ootils:
1262
+ * export const getSelfManagedAnnoRollupPaths = (annotationTagsCount): string[][] => [...]
1263
+ * then have all three call sites consume it (each maps paths -> its own shape:
1264
+ * filter-blocks / hierarchy levels / dropdown options). One rule, three presentations.
1265
+ */
1244
1266
  declare const _self_managed_getFixedAnnoRollupBlocks: ({ selectedTpls, allTpls, annotationTagsCount }: {
1245
1267
  selectedTpls: any[];
1246
1268
  allTpls: any[];
@@ -1342,6 +1364,7 @@ declare const _self_managed_buildDocHierarchyConfig: ({ combinedDocumentBlocks,
1342
1364
  display: any;
1343
1365
  filters: any[];
1344
1366
  rollups: any[];
1367
+ rollupDisplayMap: Record<string, string>;
1345
1368
  }[];
1346
1369
  };
1347
1370
  target: {
@@ -1501,6 +1524,7 @@ declare const autoGenFilterConfigsFromTpl: ({ selectedTpls, allTpls, filterScope
1501
1524
  display: any;
1502
1525
  filters: any[];
1503
1526
  rollups: any[];
1527
+ rollupDisplayMap: Record<string, string>;
1504
1528
  }[];
1505
1529
  };
1506
1530
  target: {
package/dist/browser.js CHANGED
@@ -722,7 +722,8 @@ var collectMarkIdsInOrder = (editorState) => {
722
722
  var MAX_DEPTH_ROLLUP_POSSIBILITIES = 10;
723
723
  function getRollupPossibilities({
724
724
  tagType,
725
- allTpls
725
+ allTpls,
726
+ includeSelfHead = false
726
727
  }) {
727
728
  const thisTagTpl = allTpls.find((d) => d.kp_content_type === tagType);
728
729
  if (!thisTagTpl) return [];
@@ -754,7 +755,8 @@ function getRollupPossibilities({
754
755
  chains.push({
755
756
  rollupType: "tagType",
756
757
  tagTypeCollectionToRollup: tagType,
757
- rollupPath: [...visited, startTagType, nextTagType]
758
+ rollupPath: [...visited, startTagType, nextTagType],
759
+ filterDisplay: block.props?.shortLabel || block.props?.label
758
760
  });
759
761
  if (visited.length < maxDepth - 1) {
760
762
  const nextChains = findTagChains(
@@ -800,7 +802,8 @@ function getRollupPossibilities({
800
802
  const directChain = {
801
803
  rollupType: "tagType",
802
804
  tagTypeCollectionToRollup: tagType,
803
- rollupPath: [tagType, block.props.tagType]
805
+ rollupPath: [tagType, block.props.tagType],
806
+ filterDisplay: block.props?.shortLabel || block.props?.label
804
807
  };
805
808
  const deeperChains = findTagChains(
806
809
  block.props?.tagType,
@@ -809,7 +812,14 @@ function getRollupPossibilities({
809
812
  );
810
813
  return [directChain, ...deeperChains];
811
814
  });
812
- return [...singleLevelValuePathRollups, ...nestedTagRollups];
815
+ const selfHeadRollup = includeSelfHead && nestedTagRollups.length > 0 && singleLevelValuePathRollups.length === 0 ? [
816
+ {
817
+ rollupType: "tagType",
818
+ tagTypeCollectionToRollup: tagType,
819
+ rollupPath: [tagType]
820
+ }
821
+ ] : [];
822
+ return [...singleLevelValuePathRollups, ...selfHeadRollup, ...nestedTagRollups];
813
823
  }
814
824
 
815
825
  // src/bullmq/GLOBAL_BULLMQ_CONFIG.js
@@ -1714,6 +1724,7 @@ var buildFilterConfigurations = ({ groups, type, selectedTpls, allTpls, isRollup
1714
1724
  if (isTerminalValuePath) {
1715
1725
  return element.filterDisplay || lastItemInPath;
1716
1726
  }
1727
+ if (element.filterDisplay) return element.filterDisplay;
1717
1728
  const lastTag = rollupPath[rollupPath.length - 1];
1718
1729
  const lastTagTpl = allTpls.find(
1719
1730
  (tpl) => tpl.kp_content_type === lastTag
@@ -1758,6 +1769,7 @@ var buildFilterConfigurations = ({ groups, type, selectedTpls, allTpls, isRollup
1758
1769
  scope: section.filterScope
1759
1770
  };
1760
1771
  };
1772
+ const isSelfTerminalTag = element.rollupPath.length === 1 && !isLastTagProfile && !isTerminalValuePath;
1761
1773
  return {
1762
1774
  filterId: `ROLLUP_${section.filterScope}_${element.rollupPath.join(
1763
1775
  "_"
@@ -1771,9 +1783,14 @@ var buildFilterConfigurations = ({ groups, type, selectedTpls, allTpls, isRollup
1771
1783
  scope: section.filterScope
1772
1784
  }),
1773
1785
  contentType: element.rollupPath[0],
1774
- path: `tags.${element.rollupPath[1]}`,
1786
+ path: `tags.${isSelfTerminalTag ? element.rollupPath[0] : element.rollupPath[1]}`,
1775
1787
  source: getSourceConfig(),
1776
- target: {
1788
+ target: isSelfTerminalTag ? {
1789
+ filterType: "tagType",
1790
+ tagType: element.rollupPath[0],
1791
+ rollupPath: element.rollupPath,
1792
+ ...isAnno && { isAnno: true }
1793
+ } : {
1777
1794
  filterType: "nestedRollupTagType",
1778
1795
  rollupPath: element.rollupPath,
1779
1796
  ...isAnno && { isAnno: true }
@@ -1980,7 +1997,7 @@ var extractAndOrganizeBlocks = (selectedTpls, allTpls, { smTagTypesConfig } = {}
1980
1997
  return {
1981
1998
  contentType: tpl.kp_content_type,
1982
1999
  blocks: allBlocks.filter((block) => block.valuePath.startsWith("tags.") && ["TagsInputSingle", "TagsInputMulti"].includes(block.comp)).flatMap((block) => {
1983
- const possibilities = getRollupPossibilities({ tagType: block.props.tagType, allTpls });
2000
+ const possibilities = getRollupPossibilities({ tagType: block.props.tagType, allTpls, includeSelfHead: true });
1984
2001
  return possibilities.map((p) => ({
1985
2002
  ...p,
1986
2003
  filterType: p.rollupPath ? "nestedRollupTagType" : "rollupValuePathType"
@@ -2313,13 +2330,16 @@ var buildTagTypeParentMap = (tagTypesInGroup, allTpls) => {
2313
2330
  const tagBlocks = blocks.filter(
2314
2331
  (block) => block.valuePath?.startsWith("tags.") && block.props?.tagType
2315
2332
  );
2333
+ const referencedTagTypes = /* @__PURE__ */ new Set();
2316
2334
  for (const block of tagBlocks) {
2317
2335
  const referencedTagType = block.props.tagType;
2318
2336
  if (tagTypeSet.has(referencedTagType) && referencedTagType !== tagType) {
2319
- parentMap.set(tagType, referencedTagType);
2320
- break;
2337
+ referencedTagTypes.add(referencedTagType);
2321
2338
  }
2322
2339
  }
2340
+ if (referencedTagTypes.size === 1) {
2341
+ parentMap.set(tagType, [...referencedTagTypes][0]);
2342
+ }
2323
2343
  }
2324
2344
  for (const child of parentMap.keys()) {
2325
2345
  const visited = /* @__PURE__ */ new Set();
@@ -2393,6 +2413,34 @@ var sortFiltersHierarchically = (filters) => {
2393
2413
  return sorted;
2394
2414
  };
2395
2415
 
2416
+ // src/utils/autoGenFilterConfigsFromTpl/utils/deduplicateRollupTagFilters.ts
2417
+ var deduplicateRollupTagFilters = (rollups) => {
2418
+ const tagTerminals = [];
2419
+ const nonTag = [];
2420
+ for (const r of rollups) {
2421
+ const rp = r.target?.rollupPath;
2422
+ if (rp?.length && !rp[rp.length - 1].startsWith("main.")) {
2423
+ tagTerminals.push(r);
2424
+ } else {
2425
+ nonTag.push({ ...r, isTagRollup: false });
2426
+ }
2427
+ }
2428
+ if (tagTerminals.length === 0) return nonTag;
2429
+ const byTerminal = /* @__PURE__ */ new Map();
2430
+ for (const r of tagTerminals) {
2431
+ const terminal = r.target.rollupPath[r.target.rollupPath.length - 1];
2432
+ const existing = byTerminal.get(terminal);
2433
+ if (!existing || r.target.rollupPath.length < existing.target.rollupPath.length) {
2434
+ byTerminal.set(terminal, r);
2435
+ }
2436
+ }
2437
+ const dedupedTags = [...byTerminal.values()].map((r) => ({
2438
+ ...r,
2439
+ isTagRollup: true
2440
+ }));
2441
+ return [...nonTag, ...dedupedTags];
2442
+ };
2443
+
2396
2444
  // src/utils/autoGenFilterConfigsFromTpl/utils/_self_managed_buildDocHierarchyConfig.ts
2397
2445
  var injectFilterOptionsBy = (filters) => filters.map(
2398
2446
  (f) => f.parentFilterId ? { ...f, source: { ...f.source, filterOptionsBy: { filterId: f.parentFilterId } } } : f
@@ -2499,24 +2547,34 @@ var _self_managed_buildDocHierarchyConfig = ({
2499
2547
  const dedupedFilters = filtersWithCommonFlag.filter(
2500
2548
  (f) => !rollupSourceKeys.has(JSON.stringify(f.source))
2501
2549
  );
2502
- const combined = [...dedupedFilters, ...rollupConfigs];
2550
+ const dedupedRollupConfigs = deduplicateRollupTagFilters(rollupConfigs);
2551
+ const combined = [...dedupedFilters, ...dedupedRollupConfigs];
2503
2552
  const combinedWithParents = injectFilterOptionsBy(
2504
2553
  sortFiltersHierarchically(
2505
2554
  attachParentFields(combined, allTpls)
2506
2555
  )
2507
2556
  );
2508
- const rollupFilterIds = new Set(rollupConfigs.map((r) => r.filterId));
2557
+ const rollupFilterIds = new Set(dedupedRollupConfigs.map((r) => r.filterId));
2509
2558
  const filtersWithParents = combinedWithParents.filter(
2510
2559
  (f) => !rollupFilterIds.has(f.filterId)
2511
2560
  );
2512
2561
  const rollupsWithParents = combinedWithParents.filter(
2513
2562
  (f) => rollupFilterIds.has(f.filterId)
2514
2563
  );
2564
+ const rollupContentTypes = new Set(
2565
+ rollupsWithParents.filter((r) => r.target?.rollupPath).flatMap((r) => r.target.rollupPath)
2566
+ );
2567
+ const rollupDisplayMap = {};
2568
+ for (const ct of rollupContentTypes) {
2569
+ const t = allTpls.find((tp) => tp.kp_content_type === ct);
2570
+ if (t?.general?.content?.title) rollupDisplayMap[ct] = t.general.content.title;
2571
+ }
2515
2572
  return {
2516
2573
  contentType: tpl.kp_content_type,
2517
2574
  display: tplData?.general?.content?.title || tpl.kp_content_type,
2518
2575
  filters: filtersWithParents,
2519
- rollups: rollupsWithParents
2576
+ rollups: rollupsWithParents,
2577
+ rollupDisplayMap
2520
2578
  };
2521
2579
  });
2522
2580
  const filteredPerDataset = perDataset.filter(
package/dist/browser.mjs CHANGED
@@ -652,7 +652,8 @@ var collectMarkIdsInOrder = (editorState) => {
652
652
  var MAX_DEPTH_ROLLUP_POSSIBILITIES = 10;
653
653
  function getRollupPossibilities({
654
654
  tagType,
655
- allTpls
655
+ allTpls,
656
+ includeSelfHead = false
656
657
  }) {
657
658
  const thisTagTpl = allTpls.find((d) => d.kp_content_type === tagType);
658
659
  if (!thisTagTpl) return [];
@@ -684,7 +685,8 @@ function getRollupPossibilities({
684
685
  chains.push({
685
686
  rollupType: "tagType",
686
687
  tagTypeCollectionToRollup: tagType,
687
- rollupPath: [...visited, startTagType, nextTagType]
688
+ rollupPath: [...visited, startTagType, nextTagType],
689
+ filterDisplay: block.props?.shortLabel || block.props?.label
688
690
  });
689
691
  if (visited.length < maxDepth - 1) {
690
692
  const nextChains = findTagChains(
@@ -730,7 +732,8 @@ function getRollupPossibilities({
730
732
  const directChain = {
731
733
  rollupType: "tagType",
732
734
  tagTypeCollectionToRollup: tagType,
733
- rollupPath: [tagType, block.props.tagType]
735
+ rollupPath: [tagType, block.props.tagType],
736
+ filterDisplay: block.props?.shortLabel || block.props?.label
734
737
  };
735
738
  const deeperChains = findTagChains(
736
739
  block.props?.tagType,
@@ -739,7 +742,14 @@ function getRollupPossibilities({
739
742
  );
740
743
  return [directChain, ...deeperChains];
741
744
  });
742
- return [...singleLevelValuePathRollups, ...nestedTagRollups];
745
+ const selfHeadRollup = includeSelfHead && nestedTagRollups.length > 0 && singleLevelValuePathRollups.length === 0 ? [
746
+ {
747
+ rollupType: "tagType",
748
+ tagTypeCollectionToRollup: tagType,
749
+ rollupPath: [tagType]
750
+ }
751
+ ] : [];
752
+ return [...singleLevelValuePathRollups, ...selfHeadRollup, ...nestedTagRollups];
743
753
  }
744
754
 
745
755
  // src/bullmq/GLOBAL_BULLMQ_CONFIG.js
@@ -1644,6 +1654,7 @@ var buildFilterConfigurations = ({ groups, type, selectedTpls, allTpls, isRollup
1644
1654
  if (isTerminalValuePath) {
1645
1655
  return element.filterDisplay || lastItemInPath;
1646
1656
  }
1657
+ if (element.filterDisplay) return element.filterDisplay;
1647
1658
  const lastTag = rollupPath[rollupPath.length - 1];
1648
1659
  const lastTagTpl = allTpls.find(
1649
1660
  (tpl) => tpl.kp_content_type === lastTag
@@ -1688,6 +1699,7 @@ var buildFilterConfigurations = ({ groups, type, selectedTpls, allTpls, isRollup
1688
1699
  scope: section.filterScope
1689
1700
  };
1690
1701
  };
1702
+ const isSelfTerminalTag = element.rollupPath.length === 1 && !isLastTagProfile && !isTerminalValuePath;
1691
1703
  return {
1692
1704
  filterId: `ROLLUP_${section.filterScope}_${element.rollupPath.join(
1693
1705
  "_"
@@ -1701,9 +1713,14 @@ var buildFilterConfigurations = ({ groups, type, selectedTpls, allTpls, isRollup
1701
1713
  scope: section.filterScope
1702
1714
  }),
1703
1715
  contentType: element.rollupPath[0],
1704
- path: `tags.${element.rollupPath[1]}`,
1716
+ path: `tags.${isSelfTerminalTag ? element.rollupPath[0] : element.rollupPath[1]}`,
1705
1717
  source: getSourceConfig(),
1706
- target: {
1718
+ target: isSelfTerminalTag ? {
1719
+ filterType: "tagType",
1720
+ tagType: element.rollupPath[0],
1721
+ rollupPath: element.rollupPath,
1722
+ ...isAnno && { isAnno: true }
1723
+ } : {
1707
1724
  filterType: "nestedRollupTagType",
1708
1725
  rollupPath: element.rollupPath,
1709
1726
  ...isAnno && { isAnno: true }
@@ -1910,7 +1927,7 @@ var extractAndOrganizeBlocks = (selectedTpls, allTpls, { smTagTypesConfig } = {}
1910
1927
  return {
1911
1928
  contentType: tpl.kp_content_type,
1912
1929
  blocks: allBlocks.filter((block) => block.valuePath.startsWith("tags.") && ["TagsInputSingle", "TagsInputMulti"].includes(block.comp)).flatMap((block) => {
1913
- const possibilities = getRollupPossibilities({ tagType: block.props.tagType, allTpls });
1930
+ const possibilities = getRollupPossibilities({ tagType: block.props.tagType, allTpls, includeSelfHead: true });
1914
1931
  return possibilities.map((p) => ({
1915
1932
  ...p,
1916
1933
  filterType: p.rollupPath ? "nestedRollupTagType" : "rollupValuePathType"
@@ -2243,13 +2260,16 @@ var buildTagTypeParentMap = (tagTypesInGroup, allTpls) => {
2243
2260
  const tagBlocks = blocks.filter(
2244
2261
  (block) => block.valuePath?.startsWith("tags.") && block.props?.tagType
2245
2262
  );
2263
+ const referencedTagTypes = /* @__PURE__ */ new Set();
2246
2264
  for (const block of tagBlocks) {
2247
2265
  const referencedTagType = block.props.tagType;
2248
2266
  if (tagTypeSet.has(referencedTagType) && referencedTagType !== tagType) {
2249
- parentMap.set(tagType, referencedTagType);
2250
- break;
2267
+ referencedTagTypes.add(referencedTagType);
2251
2268
  }
2252
2269
  }
2270
+ if (referencedTagTypes.size === 1) {
2271
+ parentMap.set(tagType, [...referencedTagTypes][0]);
2272
+ }
2253
2273
  }
2254
2274
  for (const child of parentMap.keys()) {
2255
2275
  const visited = /* @__PURE__ */ new Set();
@@ -2323,6 +2343,34 @@ var sortFiltersHierarchically = (filters) => {
2323
2343
  return sorted;
2324
2344
  };
2325
2345
 
2346
+ // src/utils/autoGenFilterConfigsFromTpl/utils/deduplicateRollupTagFilters.ts
2347
+ var deduplicateRollupTagFilters = (rollups) => {
2348
+ const tagTerminals = [];
2349
+ const nonTag = [];
2350
+ for (const r of rollups) {
2351
+ const rp = r.target?.rollupPath;
2352
+ if (rp?.length && !rp[rp.length - 1].startsWith("main.")) {
2353
+ tagTerminals.push(r);
2354
+ } else {
2355
+ nonTag.push({ ...r, isTagRollup: false });
2356
+ }
2357
+ }
2358
+ if (tagTerminals.length === 0) return nonTag;
2359
+ const byTerminal = /* @__PURE__ */ new Map();
2360
+ for (const r of tagTerminals) {
2361
+ const terminal = r.target.rollupPath[r.target.rollupPath.length - 1];
2362
+ const existing = byTerminal.get(terminal);
2363
+ if (!existing || r.target.rollupPath.length < existing.target.rollupPath.length) {
2364
+ byTerminal.set(terminal, r);
2365
+ }
2366
+ }
2367
+ const dedupedTags = [...byTerminal.values()].map((r) => ({
2368
+ ...r,
2369
+ isTagRollup: true
2370
+ }));
2371
+ return [...nonTag, ...dedupedTags];
2372
+ };
2373
+
2326
2374
  // src/utils/autoGenFilterConfigsFromTpl/utils/_self_managed_buildDocHierarchyConfig.ts
2327
2375
  var injectFilterOptionsBy = (filters) => filters.map(
2328
2376
  (f) => f.parentFilterId ? { ...f, source: { ...f.source, filterOptionsBy: { filterId: f.parentFilterId } } } : f
@@ -2429,24 +2477,34 @@ var _self_managed_buildDocHierarchyConfig = ({
2429
2477
  const dedupedFilters = filtersWithCommonFlag.filter(
2430
2478
  (f) => !rollupSourceKeys.has(JSON.stringify(f.source))
2431
2479
  );
2432
- const combined = [...dedupedFilters, ...rollupConfigs];
2480
+ const dedupedRollupConfigs = deduplicateRollupTagFilters(rollupConfigs);
2481
+ const combined = [...dedupedFilters, ...dedupedRollupConfigs];
2433
2482
  const combinedWithParents = injectFilterOptionsBy(
2434
2483
  sortFiltersHierarchically(
2435
2484
  attachParentFields(combined, allTpls)
2436
2485
  )
2437
2486
  );
2438
- const rollupFilterIds = new Set(rollupConfigs.map((r) => r.filterId));
2487
+ const rollupFilterIds = new Set(dedupedRollupConfigs.map((r) => r.filterId));
2439
2488
  const filtersWithParents = combinedWithParents.filter(
2440
2489
  (f) => !rollupFilterIds.has(f.filterId)
2441
2490
  );
2442
2491
  const rollupsWithParents = combinedWithParents.filter(
2443
2492
  (f) => rollupFilterIds.has(f.filterId)
2444
2493
  );
2494
+ const rollupContentTypes = new Set(
2495
+ rollupsWithParents.filter((r) => r.target?.rollupPath).flatMap((r) => r.target.rollupPath)
2496
+ );
2497
+ const rollupDisplayMap = {};
2498
+ for (const ct of rollupContentTypes) {
2499
+ const t = allTpls.find((tp) => tp.kp_content_type === ct);
2500
+ if (t?.general?.content?.title) rollupDisplayMap[ct] = t.general.content.title;
2501
+ }
2445
2502
  return {
2446
2503
  contentType: tpl.kp_content_type,
2447
2504
  display: tplData?.general?.content?.title || tpl.kp_content_type,
2448
2505
  filters: filtersWithParents,
2449
- rollups: rollupsWithParents
2506
+ rollups: rollupsWithParents,
2507
+ rollupDisplayMap
2450
2508
  };
2451
2509
  });
2452
2510
  const filteredPerDataset = perDataset.filter(
package/dist/node.d.mts CHANGED
@@ -293,9 +293,10 @@ declare const collectMarkIdsInOrder: (editorState: any) => string[];
293
293
  * }
294
294
  * ]
295
295
  */
296
- declare function getRollupPossibilities({ tagType, allTpls }: {
296
+ declare function getRollupPossibilities({ tagType, allTpls, includeSelfHead, }: {
297
297
  tagType: string;
298
298
  allTpls: any[];
299
+ includeSelfHead?: boolean;
299
300
  }): any[];
300
301
 
301
302
  declare namespace BASE_BULLMQ_CONFIG {
@@ -1249,6 +1250,27 @@ declare const processAuthorAndCommonFilters: (allTpls: any[], filterScopes: stri
1249
1250
 
1250
1251
  declare const _self_managed_getFixedAnnoTagBlock: (selectedTpls: any[], annotationTagsCount: any) => any[];
1251
1252
 
1253
+ /**
1254
+ * FOLLOWUP (consolidate the count->rollupPath rule into one source of truth):
1255
+ *
1256
+ * The rule "given annotationTagsCount, which self-managed anno rollupPaths exist"
1257
+ * (subThemes>0 -> ['tags','subThemes']; subThemes>0 && themes>0 -> ['tags','subThemes','themes'])
1258
+ * is currently duplicated in THREE places and will drift:
1259
+ * 1. here (_self_managed_getFixedAnnoRollupBlocks) -> filter blocks
1260
+ * 2. _self_managed_buildAnnoHierarchyConfig -> anno hierarchy filter UI
1261
+ * 3. okf-fe _extractAllAnnoBasedDimensionsAsOptions.js -> reports dimension dropdown
1262
+ *
1263
+ * (#3 was added to fix a crash: the reports widget previously discovered these rollups
1264
+ * from publishing-segment tpls via getRollupPossibilities, but self-managed taxonomy lives
1265
+ * on `collections`-segment tpls which isTplAnnotationEnabled excludes -> empty list ->
1266
+ * unguarded .find('subThemes') returned undefined -> crash. The FE now builds them from the
1267
+ * count, mirroring this function.)
1268
+ *
1269
+ * Extract a pure helper here in ootils:
1270
+ * export const getSelfManagedAnnoRollupPaths = (annotationTagsCount): string[][] => [...]
1271
+ * then have all three call sites consume it (each maps paths -> its own shape:
1272
+ * filter-blocks / hierarchy levels / dropdown options). One rule, three presentations.
1273
+ */
1252
1274
  declare const _self_managed_getFixedAnnoRollupBlocks: ({ selectedTpls, allTpls, annotationTagsCount }: {
1253
1275
  selectedTpls: any[];
1254
1276
  allTpls: any[];
@@ -1350,6 +1372,7 @@ declare const _self_managed_buildDocHierarchyConfig: ({ combinedDocumentBlocks,
1350
1372
  display: any;
1351
1373
  filters: any[];
1352
1374
  rollups: any[];
1375
+ rollupDisplayMap: Record<string, string>;
1353
1376
  }[];
1354
1377
  };
1355
1378
  target: {
@@ -1509,6 +1532,7 @@ declare const autoGenFilterConfigsFromTpl: ({ selectedTpls, allTpls, filterScope
1509
1532
  display: any;
1510
1533
  filters: any[];
1511
1534
  rollups: any[];
1535
+ rollupDisplayMap: Record<string, string>;
1512
1536
  }[];
1513
1537
  };
1514
1538
  target: {
package/dist/node.d.ts CHANGED
@@ -293,9 +293,10 @@ declare const collectMarkIdsInOrder: (editorState: any) => string[];
293
293
  * }
294
294
  * ]
295
295
  */
296
- declare function getRollupPossibilities({ tagType, allTpls }: {
296
+ declare function getRollupPossibilities({ tagType, allTpls, includeSelfHead, }: {
297
297
  tagType: string;
298
298
  allTpls: any[];
299
+ includeSelfHead?: boolean;
299
300
  }): any[];
300
301
 
301
302
  declare namespace BASE_BULLMQ_CONFIG {
@@ -1249,6 +1250,27 @@ declare const processAuthorAndCommonFilters: (allTpls: any[], filterScopes: stri
1249
1250
 
1250
1251
  declare const _self_managed_getFixedAnnoTagBlock: (selectedTpls: any[], annotationTagsCount: any) => any[];
1251
1252
 
1253
+ /**
1254
+ * FOLLOWUP (consolidate the count->rollupPath rule into one source of truth):
1255
+ *
1256
+ * The rule "given annotationTagsCount, which self-managed anno rollupPaths exist"
1257
+ * (subThemes>0 -> ['tags','subThemes']; subThemes>0 && themes>0 -> ['tags','subThemes','themes'])
1258
+ * is currently duplicated in THREE places and will drift:
1259
+ * 1. here (_self_managed_getFixedAnnoRollupBlocks) -> filter blocks
1260
+ * 2. _self_managed_buildAnnoHierarchyConfig -> anno hierarchy filter UI
1261
+ * 3. okf-fe _extractAllAnnoBasedDimensionsAsOptions.js -> reports dimension dropdown
1262
+ *
1263
+ * (#3 was added to fix a crash: the reports widget previously discovered these rollups
1264
+ * from publishing-segment tpls via getRollupPossibilities, but self-managed taxonomy lives
1265
+ * on `collections`-segment tpls which isTplAnnotationEnabled excludes -> empty list ->
1266
+ * unguarded .find('subThemes') returned undefined -> crash. The FE now builds them from the
1267
+ * count, mirroring this function.)
1268
+ *
1269
+ * Extract a pure helper here in ootils:
1270
+ * export const getSelfManagedAnnoRollupPaths = (annotationTagsCount): string[][] => [...]
1271
+ * then have all three call sites consume it (each maps paths -> its own shape:
1272
+ * filter-blocks / hierarchy levels / dropdown options). One rule, three presentations.
1273
+ */
1252
1274
  declare const _self_managed_getFixedAnnoRollupBlocks: ({ selectedTpls, allTpls, annotationTagsCount }: {
1253
1275
  selectedTpls: any[];
1254
1276
  allTpls: any[];
@@ -1350,6 +1372,7 @@ declare const _self_managed_buildDocHierarchyConfig: ({ combinedDocumentBlocks,
1350
1372
  display: any;
1351
1373
  filters: any[];
1352
1374
  rollups: any[];
1375
+ rollupDisplayMap: Record<string, string>;
1353
1376
  }[];
1354
1377
  };
1355
1378
  target: {
@@ -1509,6 +1532,7 @@ declare const autoGenFilterConfigsFromTpl: ({ selectedTpls, allTpls, filterScope
1509
1532
  display: any;
1510
1533
  filters: any[];
1511
1534
  rollups: any[];
1535
+ rollupDisplayMap: Record<string, string>;
1512
1536
  }[];
1513
1537
  };
1514
1538
  target: {