@firecms/core 3.4.0-canary.0ef7442 → 3.4.0-canary.2575a08

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 (74) hide show
  1. package/dist/components/EntityCollectionView/EntityCollectionView.d.ts +3 -2
  2. package/dist/components/EntityCollectionView/EntityCollectionViewActions.d.ts +3 -1
  3. package/dist/components/EntityCollectionView/EntityCollectionViewStartActions.d.ts +3 -1
  4. package/dist/components/common/useDataSourceTableController.d.ts +4 -2
  5. package/dist/components/common/useTableSearchHelper.d.ts +3 -1
  6. package/dist/core/EntityEditView.d.ts +2 -0
  7. package/dist/core/EntityEditViewFormActions.d.ts +1 -1
  8. package/dist/form/EntityForm.d.ts +2 -0
  9. package/dist/form/EntityFormActions.d.ts +2 -0
  10. package/dist/hooks/data/delete.d.ts +1 -1
  11. package/dist/hooks/data/useCollectionFetch.d.ts +1 -1
  12. package/dist/hooks/data/useEntityFetch.d.ts +4 -1
  13. package/dist/i18n/__tests__/FireCMSi18nProvider.test.d.ts +1 -0
  14. package/dist/i18n/__tests__/nested_provider_lifecycle.test.d.ts +1 -0
  15. package/dist/index.es.js +853 -600
  16. package/dist/index.es.js.map +1 -1
  17. package/dist/index.umd.js +852 -599
  18. package/dist/index.umd.js.map +1 -1
  19. package/dist/types/collections.d.ts +7 -0
  20. package/dist/types/datasource.d.ts +8 -0
  21. package/dist/types/entity_actions.d.ts +6 -0
  22. package/dist/types/entity_callbacks.d.ts +21 -0
  23. package/dist/types/navigation.d.ts +34 -5
  24. package/dist/types/plugins.d.ts +13 -0
  25. package/dist/types/side_entity_controller.d.ts +3 -2
  26. package/dist/util/entity_cache.d.ts +11 -0
  27. package/dist/util/navigation_utils.d.ts +84 -2
  28. package/dist/util/parent_references_from_path.d.ts +15 -0
  29. package/dist/util/paths.d.ts +28 -0
  30. package/dist/util/permissions.d.ts +10 -4
  31. package/package.json +3 -3
  32. package/src/components/DeleteEntityDialog.tsx +2 -0
  33. package/src/components/EntityCollectionTable/EntityCollectionRowActions.tsx +2 -2
  34. package/src/components/EntityCollectionView/EntityCollectionBoardView.tsx +8 -0
  35. package/src/components/EntityCollectionView/EntityCollectionView.tsx +40 -15
  36. package/src/components/EntityCollectionView/EntityCollectionViewActions.tsx +6 -2
  37. package/src/components/EntityCollectionView/EntityCollectionViewStartActions.tsx +4 -0
  38. package/src/components/EntityCollectionView/useBoardDataController.tsx +7 -2
  39. package/src/components/EntityPreview.tsx +4 -1
  40. package/src/components/ReferenceTable/ReferenceSelectionTable.tsx +8 -2
  41. package/src/components/common/default_entity_actions.tsx +22 -2
  42. package/src/components/common/useDataSourceTableController.tsx +26 -8
  43. package/src/components/common/useTableSearchHelper.ts +5 -0
  44. package/src/core/EntityEditView.tsx +8 -12
  45. package/src/core/EntityEditViewFormActions.tsx +3 -2
  46. package/src/core/EntitySidePanel.tsx +6 -4
  47. package/src/form/EntityForm.tsx +22 -7
  48. package/src/form/EntityFormActions.tsx +2 -0
  49. package/src/hooks/data/delete.ts +8 -2
  50. package/src/hooks/data/save.ts +4 -1
  51. package/src/hooks/data/useCollectionFetch.tsx +9 -2
  52. package/src/hooks/data/useEntityFetch.tsx +19 -6
  53. package/src/hooks/useBuildNavigationController.tsx +23 -8
  54. package/src/hooks/useResolvedNavigationFrom.tsx +1 -1
  55. package/src/i18n/FireCMSi18nProvider.tsx +48 -4
  56. package/src/i18n/__tests__/FireCMSi18nProvider.test.tsx +91 -0
  57. package/src/i18n/__tests__/nested_provider_lifecycle.test.tsx +67 -0
  58. package/src/internal/useBuildDataSource.ts +13 -12
  59. package/src/internal/useBuildSideEntityController.tsx +13 -5
  60. package/src/preview/components/ReferencePreview.tsx +7 -3
  61. package/src/routes/FireCMSRoute.tsx +9 -4
  62. package/src/types/collections.ts +8 -0
  63. package/src/types/datasource.ts +8 -0
  64. package/src/types/entity_actions.tsx +6 -0
  65. package/src/types/entity_callbacks.ts +24 -0
  66. package/src/types/navigation.ts +35 -5
  67. package/src/types/plugins.tsx +13 -0
  68. package/src/types/side_entity_controller.tsx +3 -2
  69. package/src/util/entity_cache.ts +18 -0
  70. package/src/util/navigation_from_path.ts +6 -1
  71. package/src/util/navigation_utils.ts +204 -2
  72. package/src/util/parent_references_from_path.ts +32 -1
  73. package/src/util/paths.ts +40 -3
  74. package/src/util/permissions.ts +22 -10
package/dist/index.es.js CHANGED
@@ -10,7 +10,7 @@ import { useLocation, useNavigate, Link, NavLink, Routes, Route, createBrowserRo
10
10
  import Fuse from "fuse.js";
11
11
  import equal from "react-fast-compare";
12
12
  import jsonLogic from "json-logic-js";
13
- import { useTranslation as useTranslation$1, initReactI18next, I18nextProvider } from "react-i18next";
13
+ import { useTranslation as useTranslation$1, I18nContext, initReactI18next, I18nextProvider } from "react-i18next";
14
14
  import { format } from "date-fns";
15
15
  import * as locales from "date-fns/locale";
16
16
  import { useDropzone } from "react-dropzone";
@@ -215,6 +215,11 @@ function encodeEntityId(entityId) {
215
215
  function decodeEntityId(encodedEntityId) {
216
216
  return encodedEntityId.replaceAll("%2F", "/").replaceAll("%23", "#").replaceAll("%3F", "?").replaceAll("%25", "%");
217
217
  }
218
+ function buildSubcollectionPathSegments(parentPathSegments, entityId, subcollectionPath) {
219
+ if (!parentPathSegments || !entityId) return void 0;
220
+ const ownSegments = removeInitialAndTrailingSlashes(subcollectionPath).split("/");
221
+ return [...parentPathSegments, entityId, ...ownSegments];
222
+ }
218
223
  function getLastSegment(path) {
219
224
  const cleanPath = removeInitialAndTrailingSlashes(path);
220
225
  if (cleanPath.includes("/")) {
@@ -223,7 +228,88 @@ function getLastSegment(path) {
223
228
  }
224
229
  return cleanPath;
225
230
  }
226
- function resolveCollectionPathIds(path, allCollections) {
231
+ function walkPathSegments(pathSegments, allCollections) {
232
+ const resolved = [];
233
+ const steps = [];
234
+ let currentCollections = allCollections;
235
+ let index = 0;
236
+ while (index < pathSegments.length) {
237
+ const remaining = pathSegments.slice(index);
238
+ if (!currentCollections || currentCollections.length === 0) {
239
+ resolved.push(...remaining);
240
+ return {
241
+ resolved,
242
+ steps,
243
+ unmatched: remaining[0]
244
+ };
245
+ }
246
+ let match;
247
+ for (const collection of currentCollections) {
248
+ for (const candidate of [collection.path, collection.id]) {
249
+ if (!candidate) continue;
250
+ const parts = removeInitialAndTrailingSlashes(candidate).split("/");
251
+ if (parts.length > remaining.length) continue;
252
+ if (parts.some((part, i) => part !== remaining[i])) continue;
253
+ if (!match || parts.length > match.length) match = {
254
+ collection,
255
+ length: parts.length
256
+ };
257
+ }
258
+ }
259
+ if (!match) {
260
+ resolved.push(...remaining);
261
+ return {
262
+ resolved,
263
+ steps,
264
+ unmatched: remaining[0]
265
+ };
266
+ }
267
+ resolved.push(...removeInitialAndTrailingSlashes(match.collection.path).split("/"));
268
+ index += match.length;
269
+ const step = {
270
+ collection: match.collection,
271
+ collectionPath: resolved.join("/"),
272
+ collectionSegments: [...resolved]
273
+ };
274
+ steps.push(step);
275
+ if (index >= pathSegments.length) {
276
+ return {
277
+ resolved,
278
+ steps,
279
+ collection: match.collection
280
+ };
281
+ }
282
+ step.entityId = pathSegments[index];
283
+ resolved.push(pathSegments[index]);
284
+ index += 1;
285
+ if (index >= pathSegments.length) {
286
+ return {
287
+ resolved,
288
+ steps,
289
+ collection: match.collection
290
+ };
291
+ }
292
+ currentCollections = match.collection.subcollections;
293
+ }
294
+ return {
295
+ resolved,
296
+ steps
297
+ };
298
+ }
299
+ function resolveCollectionPathSegments(pathSegments, allCollections) {
300
+ const walk = walkPathSegments(pathSegments, allCollections);
301
+ if (walk.unmatched !== void 0) {
302
+ console.warn(`resolveCollectionPathSegments: Collection definition not found for segment "${walk.unmatched}" in [${pathSegments.join(", ")}]. Carrying the remaining segments through unresolved.`);
303
+ }
304
+ return walk.resolved;
305
+ }
306
+ function getCollectionByPathSegments(pathSegments, collections) {
307
+ return walkPathSegments(pathSegments, collections).collection;
308
+ }
309
+ function resolveCollectionPathIds(path, allCollections, pathSegments) {
310
+ if (pathSegments) {
311
+ return resolveCollectionPathSegments(pathSegments, allCollections).join("/");
312
+ }
227
313
  let remainingPath = removeInitialAndTrailingSlashes(path);
228
314
  if (!remainingPath) {
229
315
  return "";
@@ -285,7 +371,10 @@ function resolveCollectionPathIds(path, allCollections) {
285
371
  }
286
372
  return resolvedPathParts.join("/");
287
373
  }
288
- function getCollectionByPathOrId(pathOrId, collections) {
374
+ function getCollectionByPathOrId(pathOrId, collections, pathSegments) {
375
+ if (pathSegments) {
376
+ return getCollectionByPathSegments(pathSegments, collections);
377
+ }
289
378
  const subpaths = removeInitialAndTrailingSlashes(pathOrId).split("/");
290
379
  if (subpaths.length % 2 === 0) {
291
380
  throw Error(`getCollectionByPathOrId: Collection paths must have an odd number of segments: ${pathOrId}`);
@@ -342,6 +431,9 @@ function navigateToEntity({
342
431
  onClose
343
432
  });
344
433
  } else {
434
+ if (!fullIdPath && pathSegments?.some((segment) => segment.includes("/"))) {
435
+ console.warn(`navigateToEntity: no "fullIdPath" was given and "${path}" contains an entity id with a "/", so no unambiguous URL can be built for it. The link will point at a different location. Pass "fullIdPath" — the escaped chain — alongside "path".`);
436
+ }
345
437
  let to = navigation.buildUrlCollectionPath(entityId ? `${fullIdPath ?? path}/${encodeEntityId(entityId)}` : fullIdPath ?? path);
346
438
  if (entityId && selectedTab) {
347
439
  to += `/${selectedTab}`;
@@ -1245,7 +1337,12 @@ function getNavigationEntriesFromPath(props) {
1245
1337
  path: newPath,
1246
1338
  collections: collection.subcollections,
1247
1339
  currentFullPath: fullPath,
1248
- currentFullIdPath: fullIdPath,
1340
+ // The entity id is a hop in the id chain exactly as it is in the
1341
+ // other two. Without it a nested `fullIdPath` was
1342
+ // "products/locales" rather than "products/pid/locales", so any
1343
+ // URL built from it pointed at a collection that does not exist.
1344
+ // Escaped, because `fullIdPath` is URL-facing.
1345
+ currentFullIdPath: fullIdPath + "/" + encodedEntityId,
1249
1346
  currentFullUrlPath: fullUrlPath,
1250
1347
  currentPathSegments: entitySegments,
1251
1348
  contextEntityViews: props.contextEntityViews
@@ -1417,7 +1514,16 @@ function segmentsToStrippedPath(paths) {
1417
1514
  return paths.reduce((a, b) => `${a}${COLLECTION_PATH_SEPARATOR}${b}`);
1418
1515
  }
1419
1516
  function fullPathToCollectionSegments(path) {
1420
- return path.split("/").filter((e, i) => i % 2 === 0);
1517
+ return positionalCollectionSegments(path);
1518
+ }
1519
+ function collectionSegmentsFrom(pathSegments) {
1520
+ return keepCollectionPositions(pathSegments);
1521
+ }
1522
+ function positionalCollectionSegments(path) {
1523
+ return keepCollectionPositions(path.split("/"));
1524
+ }
1525
+ function keepCollectionPositions(segments) {
1526
+ return segments.filter((e, i) => i % 2 === 0);
1421
1527
  }
1422
1528
  function serializeRegExp(input) {
1423
1529
  if (!input) return "";
@@ -1647,35 +1753,35 @@ const DEFAULT_PERMISSIONS = {
1647
1753
  create: true,
1648
1754
  delete: true
1649
1755
  };
1650
- function resolvePermissions(collection, authController, path, entity) {
1756
+ function resolvePermissions(collection, authController, path, entity, pathSegments) {
1651
1757
  const permission = collection.permissions;
1652
1758
  if (permission === void 0) {
1653
1759
  return DEFAULT_PERMISSIONS;
1654
1760
  } else if (typeof permission === "object") {
1655
1761
  return permission;
1656
1762
  } else if (typeof permission === "function") {
1657
- const pathSegments = fullPathToCollectionSegments(path);
1763
+ const collectionSegments = pathSegments ? collectionSegmentsFrom(pathSegments) : fullPathToCollectionSegments(path);
1658
1764
  return permission({
1659
1765
  entity,
1660
1766
  path,
1661
1767
  user: authController.user,
1662
1768
  authController,
1663
1769
  collection,
1664
- pathSegments
1770
+ pathSegments: collectionSegments
1665
1771
  });
1666
1772
  }
1667
1773
  console.error("Permissions:", permission);
1668
1774
  throw Error("New type of permission added and not mapped");
1669
1775
  }
1670
- function canEditEntity(collection, authController, path, entity) {
1671
- return resolvePermissions(collection, authController, path, entity)?.edit ?? DEFAULT_PERMISSIONS.edit;
1776
+ function canEditEntity(collection, authController, path, entity, pathSegments) {
1777
+ return resolvePermissions(collection, authController, path, entity, pathSegments)?.edit ?? DEFAULT_PERMISSIONS.edit;
1672
1778
  }
1673
- function canCreateEntity(collection, authController, path, entity) {
1779
+ function canCreateEntity(collection, authController, path, entity, pathSegments) {
1674
1780
  if (collection.collectionGroup) return false;
1675
- return resolvePermissions(collection, authController, path, entity)?.create ?? DEFAULT_PERMISSIONS.create;
1781
+ return resolvePermissions(collection, authController, path, entity, pathSegments)?.create ?? DEFAULT_PERMISSIONS.create;
1676
1782
  }
1677
- function canDeleteEntity(collection, authController, path, entity) {
1678
- return resolvePermissions(collection, authController, path, entity)?.delete ?? DEFAULT_PERMISSIONS.delete;
1783
+ function canDeleteEntity(collection, authController, path, entity, pathSegments) {
1784
+ return resolvePermissions(collection, authController, path, entity, pathSegments)?.delete ?? DEFAULT_PERMISSIONS.delete;
1679
1785
  }
1680
1786
  function toNumber(value) {
1681
1787
  return typeof value === "number" && Number.isFinite(value) ? value : void 0;
@@ -4647,10 +4753,10 @@ const useFireCMSContext = () => {
4647
4753
  return fireCMSContextRef.current;
4648
4754
  };
4649
4755
  function useCollectionFetch(t0) {
4650
- const $ = c(27);
4756
+ const $ = c(31);
4651
4757
  const {
4652
4758
  path: inputPath,
4653
- pathSegments,
4759
+ pathSegments: inputPathSegments,
4654
4760
  collection,
4655
4761
  filterValues,
4656
4762
  sortBy,
@@ -4660,32 +4766,43 @@ function useCollectionFetch(t0) {
4660
4766
  const dataSource = useDataSource();
4661
4767
  const navigationController = useNavigationController();
4662
4768
  let t1;
4663
- if ($[0] !== inputPath || $[1] !== navigationController) {
4664
- t1 = navigationController.resolveIdsFrom(inputPath);
4665
- $[0] = inputPath;
4769
+ if ($[0] !== inputPathSegments || $[1] !== navigationController) {
4770
+ t1 = inputPathSegments ? navigationController.resolveSegmentsFrom?.(inputPathSegments) ?? inputPathSegments : void 0;
4771
+ $[0] = inputPathSegments;
4666
4772
  $[1] = navigationController;
4667
4773
  $[2] = t1;
4668
4774
  } else {
4669
4775
  t1 = $[2];
4670
4776
  }
4671
- const path = t1;
4777
+ const pathSegments = t1;
4778
+ let t2;
4779
+ if ($[3] !== inputPath || $[4] !== inputPathSegments || $[5] !== navigationController) {
4780
+ t2 = navigationController.resolveIdsFrom(inputPath, inputPathSegments);
4781
+ $[3] = inputPath;
4782
+ $[4] = inputPathSegments;
4783
+ $[5] = navigationController;
4784
+ $[6] = t2;
4785
+ } else {
4786
+ t2 = $[6];
4787
+ }
4788
+ const path = t2;
4672
4789
  const sortByProperty = sortBy ? sortBy[0] : void 0;
4673
4790
  const currentSort = sortBy ? sortBy[1] : void 0;
4674
4791
  const context = useFireCMSContext();
4675
- let t2;
4676
- if ($[3] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
4677
- t2 = [];
4678
- $[3] = t2;
4792
+ let t3;
4793
+ if ($[7] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
4794
+ t3 = [];
4795
+ $[7] = t3;
4679
4796
  } else {
4680
- t2 = $[3];
4797
+ t3 = $[7];
4681
4798
  }
4682
- const [data, setData] = useState(t2);
4799
+ const [data, setData] = useState(t3);
4683
4800
  const [dataLoading, setDataLoading] = useState(false);
4684
4801
  const [dataLoadingError, setDataLoadingError] = useState();
4685
4802
  const [noMoreToLoad, setNoMoreToLoad] = useState(false);
4686
- let t3;
4687
- if ($[4] !== collection || $[5] !== context || $[6] !== currentSort || $[7] !== dataSource || $[8] !== filterValues || $[9] !== itemCount || $[10] !== path || $[11] !== pathSegments || $[12] !== searchString || $[13] !== sortByProperty) {
4688
- t3 = () => {
4803
+ let t4;
4804
+ if ($[8] !== collection || $[9] !== context || $[10] !== currentSort || $[11] !== dataSource || $[12] !== filterValues || $[13] !== itemCount || $[14] !== path || $[15] !== pathSegments || $[16] !== searchString || $[17] !== sortByProperty) {
4805
+ t4 = () => {
4689
4806
  setDataLoading(true);
4690
4807
  const onEntitiesUpdate = async (entities) => {
4691
4808
  if (pathSegments) {
@@ -4699,11 +4816,12 @@ function useCollectionFetch(t0) {
4699
4816
  entities = await Promise.all(entities.map((entity) => collection.callbacks.onFetch({
4700
4817
  collection,
4701
4818
  path,
4819
+ pathSegments,
4702
4820
  entity,
4703
4821
  context
4704
4822
  })));
4705
- } catch (t42) {
4706
- const e_0 = t42;
4823
+ } catch (t52) {
4824
+ const e_0 = t52;
4707
4825
  console.error(e_0);
4708
4826
  }
4709
4827
  }
@@ -4747,51 +4865,51 @@ function useCollectionFetch(t0) {
4747
4865
  return _temp2$f;
4748
4866
  }
4749
4867
  };
4750
- $[4] = collection;
4751
- $[5] = context;
4752
- $[6] = currentSort;
4753
- $[7] = dataSource;
4754
- $[8] = filterValues;
4755
- $[9] = itemCount;
4756
- $[10] = path;
4757
- $[11] = pathSegments;
4758
- $[12] = searchString;
4759
- $[13] = sortByProperty;
4760
- $[14] = t3;
4868
+ $[8] = collection;
4869
+ $[9] = context;
4870
+ $[10] = currentSort;
4871
+ $[11] = dataSource;
4872
+ $[12] = filterValues;
4873
+ $[13] = itemCount;
4874
+ $[14] = path;
4875
+ $[15] = pathSegments;
4876
+ $[16] = searchString;
4877
+ $[17] = sortByProperty;
4878
+ $[18] = t4;
4761
4879
  } else {
4762
- t3 = $[14];
4880
+ t4 = $[18];
4763
4881
  }
4764
- let t4;
4765
- if ($[15] !== currentSort || $[16] !== filterValues || $[17] !== itemCount || $[18] !== path || $[19] !== searchString || $[20] !== sortByProperty) {
4766
- t4 = [path, itemCount, currentSort, sortByProperty, filterValues, searchString];
4767
- $[15] = currentSort;
4768
- $[16] = filterValues;
4769
- $[17] = itemCount;
4770
- $[18] = path;
4771
- $[19] = searchString;
4772
- $[20] = sortByProperty;
4773
- $[21] = t4;
4882
+ let t5;
4883
+ if ($[19] !== currentSort || $[20] !== filterValues || $[21] !== itemCount || $[22] !== path || $[23] !== searchString || $[24] !== sortByProperty) {
4884
+ t5 = [path, itemCount, currentSort, sortByProperty, filterValues, searchString];
4885
+ $[19] = currentSort;
4886
+ $[20] = filterValues;
4887
+ $[21] = itemCount;
4888
+ $[22] = path;
4889
+ $[23] = searchString;
4890
+ $[24] = sortByProperty;
4891
+ $[25] = t5;
4774
4892
  } else {
4775
- t4 = $[21];
4893
+ t5 = $[25];
4776
4894
  }
4777
- useEffect(t3, t4);
4778
- let t5;
4779
- if ($[22] !== data || $[23] !== dataLoading || $[24] !== dataLoadingError || $[25] !== noMoreToLoad) {
4780
- t5 = {
4895
+ useEffect(t4, t5);
4896
+ let t6;
4897
+ if ($[26] !== data || $[27] !== dataLoading || $[28] !== dataLoadingError || $[29] !== noMoreToLoad) {
4898
+ t6 = {
4781
4899
  data,
4782
4900
  dataLoading,
4783
4901
  dataLoadingError,
4784
4902
  noMoreToLoad
4785
4903
  };
4786
- $[22] = data;
4787
- $[23] = dataLoading;
4788
- $[24] = dataLoadingError;
4789
- $[25] = noMoreToLoad;
4790
- $[26] = t5;
4904
+ $[26] = data;
4905
+ $[27] = dataLoading;
4906
+ $[28] = dataLoadingError;
4907
+ $[29] = noMoreToLoad;
4908
+ $[30] = t6;
4791
4909
  } else {
4792
- t5 = $[26];
4910
+ t6 = $[30];
4793
4911
  }
4794
- return t5;
4912
+ return t6;
4795
4913
  }
4796
4914
  function _temp2$f() {
4797
4915
  }
@@ -4800,9 +4918,132 @@ function _temp$D(e_1) {
4800
4918
  ...e_1
4801
4919
  };
4802
4920
  }
4921
+ function entityCacheKey(path, entityId) {
4922
+ return `${path}/${entityId === void 0 ? entityId : encodeEntityId(entityId)}`;
4923
+ }
4924
+ const LOCAL_STORAGE_PREFIX = "entity_cache::";
4925
+ const entityCache = /* @__PURE__ */ new Map();
4926
+ const isLocalStorageAvailable = typeof localStorage !== "undefined";
4927
+ function customReplacer(key) {
4928
+ const value = this[key];
4929
+ if (value instanceof Date) {
4930
+ return {
4931
+ __type: "Date",
4932
+ value: value.toISOString()
4933
+ };
4934
+ }
4935
+ if (value instanceof EntityReference) {
4936
+ return {
4937
+ __type: "EntityReference",
4938
+ id: value.id,
4939
+ path: value.path,
4940
+ databaseId: value.databaseId
4941
+ };
4942
+ }
4943
+ if (value instanceof GeoPoint) {
4944
+ return {
4945
+ __type: "GeoPoint",
4946
+ latitude: value.latitude,
4947
+ longitude: value.longitude
4948
+ };
4949
+ }
4950
+ if (value instanceof Vector) {
4951
+ return {
4952
+ __type: "Vector",
4953
+ value: value.value
4954
+ };
4955
+ }
4956
+ return value;
4957
+ }
4958
+ function customReviver(key, value) {
4959
+ if (value && typeof value === "object" && "__type" in value) {
4960
+ switch (value.__type) {
4961
+ case "Date":
4962
+ return new Date(value.value);
4963
+ case "EntityReference":
4964
+ return new EntityReference(value.id, value.path, value.databaseId);
4965
+ case "GeoPoint":
4966
+ return new GeoPoint(value.latitude, value.longitude);
4967
+ case "Vector":
4968
+ return new Vector(value.value);
4969
+ default:
4970
+ return value;
4971
+ }
4972
+ }
4973
+ return value;
4974
+ }
4975
+ function saveEntityToCache(path, data) {
4976
+ if (isLocalStorageAvailable) {
4977
+ try {
4978
+ const key = LOCAL_STORAGE_PREFIX + path;
4979
+ const entityString = JSON.stringify(data, customReplacer);
4980
+ console.debug("Saving entity to localStorage:", {
4981
+ key,
4982
+ entityString
4983
+ });
4984
+ localStorage.setItem(key, entityString);
4985
+ } catch (error) {
4986
+ console.error(`Failed to save entity for path "${path}" to localStorage:`, error);
4987
+ }
4988
+ }
4989
+ }
4990
+ function removeEntityFromMemoryCache(path) {
4991
+ entityCache.delete(path);
4992
+ }
4993
+ function saveEntityToMemoryCache(path, data) {
4994
+ entityCache.set(path, data);
4995
+ }
4996
+ function getEntityFromMemoryCache(path) {
4997
+ return entityCache.get(path);
4998
+ }
4999
+ function getEntityFromCache(path) {
5000
+ if (isLocalStorageAvailable) {
5001
+ try {
5002
+ const key = LOCAL_STORAGE_PREFIX + path;
5003
+ const entityString = localStorage.getItem(key);
5004
+ if (entityString) {
5005
+ const entity = JSON.parse(entityString, customReviver);
5006
+ return entity;
5007
+ }
5008
+ } catch (error) {
5009
+ console.error(`Failed to load entity for path "${path}" from localStorage:`, error);
5010
+ }
5011
+ }
5012
+ return void 0;
5013
+ }
5014
+ function removeEntityFromCache(path) {
5015
+ if (isLocalStorageAvailable) {
5016
+ try {
5017
+ const key = LOCAL_STORAGE_PREFIX + path;
5018
+ localStorage.removeItem(key);
5019
+ } catch (error) {
5020
+ console.error(`Failed to remove entity for path "${path}" from localStorage:`, error);
5021
+ }
5022
+ }
5023
+ }
5024
+ function flattenKeys(obj, prefix = "", result = []) {
5025
+ if (isObject(obj) || Array.isArray(obj)) {
5026
+ const plainObject = isPlainObject(obj);
5027
+ if (!plainObject && prefix) {
5028
+ result.push(prefix);
5029
+ } else {
5030
+ for (const key in obj) {
5031
+ if (Object.prototype.hasOwnProperty.call(obj, key)) {
5032
+ const newKey = prefix ? Array.isArray(obj) ? `${prefix}[${key}]` : `${prefix}.${key}` : key;
5033
+ if (isObject(obj[key]) || Array.isArray(obj[key])) {
5034
+ flattenKeys(obj[key], newKey, result);
5035
+ } else {
5036
+ result.push(newKey);
5037
+ }
5038
+ }
5039
+ }
5040
+ }
5041
+ }
5042
+ return result;
5043
+ }
4803
5044
  const CACHE = {};
4804
5045
  function useEntityFetch(t0) {
4805
- const $ = c(19);
5046
+ const $ = c(23);
4806
5047
  const {
4807
5048
  path: inputPath,
4808
5049
  pathSegments: inputPathSegments,
@@ -4815,23 +5056,33 @@ function useEntityFetch(t0) {
4815
5056
  const dataSource = useDataSource();
4816
5057
  const navigationController = useNavigationController();
4817
5058
  let t2;
4818
- if ($[0] !== inputPath || $[1] !== navigationController) {
4819
- t2 = navigationController.resolveIdsFrom(inputPath);
4820
- $[0] = inputPath;
5059
+ if ($[0] !== inputPathSegments || $[1] !== navigationController) {
5060
+ t2 = inputPathSegments ? navigationController.resolveSegmentsFrom?.(inputPathSegments) ?? inputPathSegments : void 0;
5061
+ $[0] = inputPathSegments;
4821
5062
  $[1] = navigationController;
4822
5063
  $[2] = t2;
4823
5064
  } else {
4824
5065
  t2 = $[2];
4825
5066
  }
4826
- const path = t2;
4827
- const pathSegments = inputPathSegments;
5067
+ const pathSegments = t2;
5068
+ let t3;
5069
+ if ($[3] !== inputPath || $[4] !== inputPathSegments || $[5] !== navigationController) {
5070
+ t3 = navigationController.resolveIdsFrom(inputPath, inputPathSegments);
5071
+ $[3] = inputPath;
5072
+ $[4] = inputPathSegments;
5073
+ $[5] = navigationController;
5074
+ $[6] = t3;
5075
+ } else {
5076
+ t3 = $[6];
5077
+ }
5078
+ const path = t3;
4828
5079
  const context = useFireCMSContext();
4829
5080
  const [entity, setEntity] = useState();
4830
5081
  const [dataLoading, setDataLoading] = useState(true);
4831
5082
  const [dataLoadingError, setDataLoadingError] = useState();
4832
- let t3;
4833
- if ($[3] !== collection || $[4] !== context || $[5] !== dataSource || $[6] !== databaseId || $[7] !== entityId || $[8] !== path || $[9] !== pathSegments || $[10] !== useCache) {
4834
- t3 = () => {
5083
+ let t4;
5084
+ if ($[7] !== collection || $[8] !== context || $[9] !== dataSource || $[10] !== databaseId || $[11] !== entityId || $[12] !== path || $[13] !== pathSegments || $[14] !== useCache) {
5085
+ t4 = () => {
4835
5086
  setDataLoading(true);
4836
5087
  const onEntityUpdate = async (updatedEntity) => {
4837
5088
  if (updatedEntity && pathSegments && !updatedEntity.pathSegments) {
@@ -4845,15 +5096,16 @@ function useEntityFetch(t0) {
4845
5096
  updatedEntity = await collection.callbacks.onFetch({
4846
5097
  collection,
4847
5098
  path,
5099
+ pathSegments,
4848
5100
  entity: updatedEntity,
4849
5101
  context
4850
5102
  });
4851
- } catch (t42) {
4852
- const e = t42;
5103
+ } catch (t52) {
5104
+ const e = t52;
4853
5105
  console.error(e);
4854
5106
  }
4855
5107
  }
4856
- CACHE[`${path}/${entityId}`] = updatedEntity;
5108
+ CACHE[entityCacheKey(path, entityId)] = updatedEntity;
4857
5109
  setEntity(updatedEntity);
4858
5110
  setDataLoading(false);
4859
5111
  setDataLoadingError(void 0);
@@ -4864,8 +5116,8 @@ function useEntityFetch(t0) {
4864
5116
  setEntity(void 0);
4865
5117
  setDataLoadingError(error);
4866
5118
  };
4867
- if (entityId && useCache && CACHE[`${path}/${entityId}`]) {
4868
- setEntity(CACHE[`${path}/${entityId}`]);
5119
+ if (entityId && useCache && CACHE[entityCacheKey(path, entityId)]) {
5120
+ setEntity(CACHE[entityCacheKey(path, entityId)]);
4869
5121
  setDataLoading(false);
4870
5122
  setDataLoadingError(void 0);
4871
5123
  return _temp$C;
@@ -4897,43 +5149,43 @@ function useEntityFetch(t0) {
4897
5149
  }
4898
5150
  }
4899
5151
  };
4900
- $[3] = collection;
4901
- $[4] = context;
4902
- $[5] = dataSource;
4903
- $[6] = databaseId;
4904
- $[7] = entityId;
4905
- $[8] = path;
4906
- $[9] = pathSegments;
4907
- $[10] = useCache;
4908
- $[11] = t3;
5152
+ $[7] = collection;
5153
+ $[8] = context;
5154
+ $[9] = dataSource;
5155
+ $[10] = databaseId;
5156
+ $[11] = entityId;
5157
+ $[12] = path;
5158
+ $[13] = pathSegments;
5159
+ $[14] = useCache;
5160
+ $[15] = t4;
4909
5161
  } else {
4910
- t3 = $[11];
5162
+ t4 = $[15];
4911
5163
  }
4912
- let t4;
4913
- if ($[12] !== entityId || $[13] !== path) {
4914
- t4 = [entityId, path];
4915
- $[12] = entityId;
4916
- $[13] = path;
4917
- $[14] = t4;
5164
+ let t5;
5165
+ if ($[16] !== entityId || $[17] !== path) {
5166
+ t5 = [entityId, path];
5167
+ $[16] = entityId;
5168
+ $[17] = path;
5169
+ $[18] = t5;
4918
5170
  } else {
4919
- t4 = $[14];
5171
+ t5 = $[18];
4920
5172
  }
4921
- useEffect(t3, t4);
4922
- let t5;
4923
- if ($[15] !== dataLoading || $[16] !== dataLoadingError || $[17] !== entity) {
4924
- t5 = {
5173
+ useEffect(t4, t5);
5174
+ let t6;
5175
+ if ($[19] !== dataLoading || $[20] !== dataLoadingError || $[21] !== entity) {
5176
+ t6 = {
4925
5177
  entity,
4926
5178
  dataLoading,
4927
5179
  dataLoadingError
4928
5180
  };
4929
- $[15] = dataLoading;
4930
- $[16] = dataLoadingError;
4931
- $[17] = entity;
4932
- $[18] = t5;
5181
+ $[19] = dataLoading;
5182
+ $[20] = dataLoadingError;
5183
+ $[21] = entity;
5184
+ $[22] = t6;
4933
5185
  } else {
4934
- t5 = $[18];
5186
+ t6 = $[22];
4935
5187
  }
4936
- return t5;
5188
+ return t6;
4937
5189
  }
4938
5190
  function _temp3$5() {
4939
5191
  }
@@ -4961,7 +5213,7 @@ async function saveEntityWithCallbacks({
4961
5213
  }
4962
5214
  let updatedValues;
4963
5215
  const customizationController = context.customizationController;
4964
- const resolvedPath = context.navigation.resolveIdsFrom(path);
5216
+ const resolvedPath = context.navigation.resolveIdsFrom(path, pathSegments);
4965
5217
  const callbacks = collection.callbacks;
4966
5218
  if (callbacks?.onPreSave) {
4967
5219
  try {
@@ -4976,6 +5228,7 @@ async function saveEntityWithCallbacks({
4976
5228
  updatedValues = await callbacks.onPreSave({
4977
5229
  collection: resolvedCollection,
4978
5230
  path,
5231
+ pathSegments,
4979
5232
  resolvedPath,
4980
5233
  entityId,
4981
5234
  values,
@@ -5013,6 +5266,7 @@ async function saveEntityWithCallbacks({
5013
5266
  callbacks.onSaveSuccess({
5014
5267
  collection: resolvedCollection,
5015
5268
  path,
5269
+ pathSegments,
5016
5270
  resolvedPath,
5017
5271
  entityId: entity.id,
5018
5272
  values: updatedValues,
@@ -5038,6 +5292,7 @@ async function saveEntityWithCallbacks({
5038
5292
  callbacks.onSaveFailure({
5039
5293
  collection: resolvedCollection,
5040
5294
  path,
5295
+ pathSegments,
5041
5296
  resolvedPath,
5042
5297
  entityId,
5043
5298
  values: updatedValues,
@@ -5052,6 +5307,7 @@ async function saveEntityWithCallbacks({
5052
5307
  async function deleteEntityWithCallbacks({
5053
5308
  dataSource,
5054
5309
  entity,
5310
+ pathSegments,
5055
5311
  collection,
5056
5312
  callbacks,
5057
5313
  onDeleteSuccess,
@@ -5061,11 +5317,13 @@ async function deleteEntityWithCallbacks({
5061
5317
  context
5062
5318
  }) {
5063
5319
  console.debug("Deleting entity", entity.path, entity.id);
5320
+ const resolvedPathSegments = pathSegments ?? entity.pathSegments;
5064
5321
  const entityDeleteProps = {
5065
5322
  entity,
5066
5323
  collection,
5067
5324
  entityId: entity.id,
5068
5325
  path: entity.path,
5326
+ pathSegments: resolvedPathSegments,
5069
5327
  context
5070
5328
  };
5071
5329
  if (callbacks?.onPreDelete) {
@@ -5078,8 +5336,7 @@ async function deleteEntityWithCallbacks({
5078
5336
  }
5079
5337
  }
5080
5338
  return dataSource.deleteEntity({
5081
- // Carried by the entity from the fetch that produced it; undefined if unknown.
5082
- pathSegments: entity.pathSegments,
5339
+ pathSegments: resolvedPathSegments,
5083
5340
  entity,
5084
5341
  collection
5085
5342
  }).then(() => {
@@ -5115,7 +5372,7 @@ function resolveNavigationFrom({
5115
5372
  if (entry.type === "collection") {
5116
5373
  return Promise.resolve(entry);
5117
5374
  } else if (entry.type === "entity") {
5118
- const collection = navigation.getCollection(entry.path);
5375
+ const collection = navigation.getCollection(entry.path, false, entry.pathSegments);
5119
5376
  if (!collection) {
5120
5377
  throw Error(`No collection defined in the navigation for the entity with path ${entry.path}`);
5121
5378
  }
@@ -6522,7 +6779,7 @@ function EntityPreview({
6522
6779
  const sideEntityController = useSideEntityController();
6523
6780
  const customizationController = useCustomizationController();
6524
6781
  const navigationController = useNavigationController();
6525
- const collection = collectionProp ?? navigationController.getCollection(entity.path);
6782
+ const collection = collectionProp ?? navigationController.getCollection(entity.path, false, entity.pathSegments);
6526
6783
  if (!collection) {
6527
6784
  throw Error(`Couldn't find the corresponding collection view for the path: ${entity.path}`);
6528
6785
  }
@@ -6565,6 +6822,9 @@ function EntityPreview({
6565
6822
  sideEntityController.open({
6566
6823
  entityId: entity.id,
6567
6824
  path: entity.path,
6825
+ // Paired with `entity.path` above; undefined if the entity was
6826
+ // loaded without them.
6827
+ pathSegments: entity.pathSegments,
6568
6828
  collection,
6569
6829
  updateUrl: true
6570
6830
  });
@@ -6689,7 +6949,7 @@ const ReferencePreview = function ReferencePreview2(props) {
6689
6949
  return t0;
6690
6950
  };
6691
6951
  function ReferencePreviewInternal(t0) {
6692
- const $ = c(22);
6952
+ const $ = c(23);
6693
6953
  const {
6694
6954
  disabled,
6695
6955
  reference,
@@ -6705,70 +6965,71 @@ function ReferencePreviewInternal(t0) {
6705
6965
  const customizationController = useCustomizationController();
6706
6966
  const navigationController = useNavigationController();
6707
6967
  let t3;
6708
- if ($[0] !== navigationController || $[1] !== reference.path) {
6709
- t3 = navigationController.getCollection(reference.path);
6968
+ if ($[0] !== navigationController || $[1] !== reference.path || $[2] !== reference.pathSegments) {
6969
+ t3 = navigationController.getCollection(reference.path, false, reference.pathSegments);
6710
6970
  $[0] = navigationController;
6711
6971
  $[1] = reference.path;
6712
- $[2] = t3;
6972
+ $[2] = reference.pathSegments;
6973
+ $[3] = t3;
6713
6974
  } else {
6714
- t3 = $[2];
6975
+ t3 = $[3];
6715
6976
  }
6716
6977
  const collection = t3;
6717
6978
  if (!collection) {
6718
6979
  if (customizationController.components?.missingReference) {
6719
6980
  let t42;
6720
- if ($[3] !== customizationController.components.missingReference || $[4] !== reference.path) {
6981
+ if ($[4] !== customizationController.components.missingReference || $[5] !== reference.path) {
6721
6982
  t42 = /* @__PURE__ */ jsx(customizationController.components.missingReference, { path: reference.path });
6722
- $[3] = customizationController.components.missingReference;
6723
- $[4] = reference.path;
6724
- $[5] = t42;
6983
+ $[4] = customizationController.components.missingReference;
6984
+ $[5] = reference.path;
6985
+ $[6] = t42;
6725
6986
  } else {
6726
- t42 = $[5];
6987
+ t42 = $[6];
6727
6988
  }
6728
6989
  return t42;
6729
6990
  } else {
6730
6991
  const t42 = size ?? "medium";
6731
6992
  let t5;
6732
- if ($[6] !== reference.pathWithId) {
6993
+ if ($[7] !== reference.pathWithId) {
6733
6994
  t5 = /* @__PURE__ */ jsx(ErrorView, { error: "Unexpected reference value. Click to edit", tooltip: reference.pathWithId });
6734
- $[6] = reference.pathWithId;
6735
- $[7] = t5;
6995
+ $[7] = reference.pathWithId;
6996
+ $[8] = t5;
6736
6997
  } else {
6737
- t5 = $[7];
6998
+ t5 = $[8];
6738
6999
  }
6739
7000
  let t6;
6740
- if ($[8] !== onClick || $[9] !== t42 || $[10] !== t5) {
7001
+ if ($[9] !== onClick || $[10] !== t42 || $[11] !== t5) {
6741
7002
  t6 = /* @__PURE__ */ jsx(EntityPreviewContainer, { onClick, size: t42, children: t5 });
6742
- $[8] = onClick;
6743
- $[9] = t42;
6744
- $[10] = t5;
6745
- $[11] = t6;
7003
+ $[9] = onClick;
7004
+ $[10] = t42;
7005
+ $[11] = t5;
7006
+ $[12] = t6;
6746
7007
  } else {
6747
- t6 = $[11];
7008
+ t6 = $[12];
6748
7009
  }
6749
7010
  return t6;
6750
7011
  }
6751
7012
  }
6752
7013
  let t4;
6753
- if ($[12] !== collection || $[13] !== disabled || $[14] !== hover || $[15] !== includeEntityLink || $[16] !== includeId || $[17] !== onClick || $[18] !== previewProperties || $[19] !== reference || $[20] !== size) {
7014
+ if ($[13] !== collection || $[14] !== disabled || $[15] !== hover || $[16] !== includeEntityLink || $[17] !== includeId || $[18] !== onClick || $[19] !== previewProperties || $[20] !== reference || $[21] !== size) {
6754
7015
  t4 = /* @__PURE__ */ jsx(ReferencePreviewExisting, { reference, collection, previewProperties, size, disabled, includeEntityLink, includeId, onClick, hover });
6755
- $[12] = collection;
6756
- $[13] = disabled;
6757
- $[14] = hover;
6758
- $[15] = includeEntityLink;
6759
- $[16] = includeId;
6760
- $[17] = onClick;
6761
- $[18] = previewProperties;
6762
- $[19] = reference;
6763
- $[20] = size;
6764
- $[21] = t4;
7016
+ $[13] = collection;
7017
+ $[14] = disabled;
7018
+ $[15] = hover;
7019
+ $[16] = includeEntityLink;
7020
+ $[17] = includeId;
7021
+ $[18] = onClick;
7022
+ $[19] = previewProperties;
7023
+ $[20] = reference;
7024
+ $[21] = size;
7025
+ $[22] = t4;
6765
7026
  } else {
6766
- t4 = $[21];
7027
+ t4 = $[22];
6767
7028
  }
6768
7029
  return t4;
6769
7030
  }
6770
7031
  function ReferencePreviewExisting(t0) {
6771
- const $ = c(35);
7032
+ const $ = c(37);
6772
7033
  const {
6773
7034
  reference,
6774
7035
  collection,
@@ -6781,9 +7042,10 @@ function ReferencePreviewExisting(t0) {
6781
7042
  hover
6782
7043
  } = t0;
6783
7044
  let t1;
6784
- if ($[0] !== collection || $[1] !== reference.id || $[2] !== reference.path) {
7045
+ if ($[0] !== collection || $[1] !== reference.id || $[2] !== reference.path || $[3] !== reference.pathSegments) {
6785
7046
  t1 = {
6786
7047
  path: reference.path,
7048
+ pathSegments: reference.pathSegments,
6787
7049
  entityId: reference.id,
6788
7050
  collection,
6789
7051
  useCache: true
@@ -6791,46 +7053,48 @@ function ReferencePreviewExisting(t0) {
6791
7053
  $[0] = collection;
6792
7054
  $[1] = reference.id;
6793
7055
  $[2] = reference.path;
6794
- $[3] = t1;
7056
+ $[3] = reference.pathSegments;
7057
+ $[4] = t1;
6795
7058
  } else {
6796
- t1 = $[3];
7059
+ t1 = $[4];
6797
7060
  }
6798
7061
  const {
6799
7062
  entity,
6800
7063
  dataLoading
6801
7064
  } = useEntityFetch(t1);
6802
7065
  if (entity) {
6803
- referencesCache.set(reference.pathWithId, entity);
7066
+ referencesCache.set(entityCacheKey(reference.path, reference.id), entity);
6804
7067
  }
6805
7068
  let t2;
6806
- if ($[4] !== entity || $[5] !== reference.pathWithId) {
6807
- t2 = entity ?? referencesCache.get(reference.pathWithId);
6808
- $[4] = entity;
6809
- $[5] = reference.pathWithId;
6810
- $[6] = t2;
7069
+ if ($[5] !== entity || $[6] !== reference.id || $[7] !== reference.path) {
7070
+ t2 = entity ?? referencesCache.get(entityCacheKey(reference.path, reference.id));
7071
+ $[5] = entity;
7072
+ $[6] = reference.id;
7073
+ $[7] = reference.path;
7074
+ $[8] = t2;
6811
7075
  } else {
6812
- t2 = $[6];
7076
+ t2 = $[8];
6813
7077
  }
6814
7078
  const usedEntity = t2;
6815
7079
  let body;
6816
7080
  if (!reference) {
6817
7081
  let t32;
6818
- if ($[7] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
7082
+ if ($[9] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
6819
7083
  t32 = /* @__PURE__ */ jsx(ErrorView, { error: "Reference not set" });
6820
- $[7] = t32;
7084
+ $[9] = t32;
6821
7085
  } else {
6822
- t32 = $[7];
7086
+ t32 = $[9];
6823
7087
  }
6824
7088
  body = t32;
6825
7089
  } else {
6826
7090
  if (usedEntity && !usedEntity.values) {
6827
7091
  let t32;
6828
- if ($[8] !== reference.path) {
7092
+ if ($[10] !== reference.path) {
6829
7093
  t32 = /* @__PURE__ */ jsx(ErrorView, { error: "Reference does not exist", tooltip: reference.path });
6830
- $[8] = reference.path;
6831
- $[9] = t32;
7094
+ $[10] = reference.path;
7095
+ $[11] = t32;
6832
7096
  } else {
6833
- t32 = $[9];
7097
+ t32 = $[11];
6834
7098
  }
6835
7099
  body = t32;
6836
7100
  }
@@ -6839,15 +7103,15 @@ function ReferencePreviewExisting(t0) {
6839
7103
  const t32 = disabled ? void 0 : onClick;
6840
7104
  const t4 = disabled ? void 0 : hover;
6841
7105
  let t5;
6842
- if ($[10] !== body || $[11] !== size || $[12] !== t32 || $[13] !== t4) {
7106
+ if ($[12] !== body || $[13] !== size || $[14] !== t32 || $[15] !== t4) {
6843
7107
  t5 = /* @__PURE__ */ jsx(EntityPreviewContainer, { onClick: t32, hover: t4, size, children: body });
6844
- $[10] = body;
6845
- $[11] = size;
6846
- $[12] = t32;
6847
- $[13] = t4;
6848
- $[14] = t5;
7108
+ $[12] = body;
7109
+ $[13] = size;
7110
+ $[14] = t32;
7111
+ $[15] = t4;
7112
+ $[16] = t5;
6849
7113
  } else {
6850
- t5 = $[14];
7114
+ t5 = $[16];
6851
7115
  }
6852
7116
  return t5;
6853
7117
  }
@@ -6855,21 +7119,21 @@ function ReferencePreviewExisting(t0) {
6855
7119
  const t32 = disabled ? void 0 : onClick;
6856
7120
  const t4 = disabled ? void 0 : hover;
6857
7121
  let t5;
6858
- if ($[15] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
7122
+ if ($[17] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
6859
7123
  t5 = /* @__PURE__ */ jsx(Skeleton, {});
6860
- $[15] = t5;
7124
+ $[17] = t5;
6861
7125
  } else {
6862
- t5 = $[15];
7126
+ t5 = $[17];
6863
7127
  }
6864
7128
  let t6;
6865
- if ($[16] !== size || $[17] !== t32 || $[18] !== t4) {
7129
+ if ($[18] !== size || $[19] !== t32 || $[20] !== t4) {
6866
7130
  t6 = /* @__PURE__ */ jsx(EntityPreviewContainer, { onClick: t32, hover: t4, size, children: t5 });
6867
- $[16] = size;
6868
- $[17] = t32;
6869
- $[18] = t4;
6870
- $[19] = t6;
7131
+ $[18] = size;
7132
+ $[19] = t32;
7133
+ $[20] = t4;
7134
+ $[21] = t6;
6871
7135
  } else {
6872
- t6 = $[19];
7136
+ t6 = $[21];
6873
7137
  }
6874
7138
  return t6;
6875
7139
  }
@@ -6877,39 +7141,39 @@ function ReferencePreviewExisting(t0) {
6877
7141
  const t32 = disabled ? void 0 : onClick;
6878
7142
  const t4 = disabled ? void 0 : hover;
6879
7143
  let t5;
6880
- if ($[20] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
7144
+ if ($[22] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
6881
7145
  t5 = /* @__PURE__ */ jsx(ErrorView, { error: "Entity not found" });
6882
- $[20] = t5;
7146
+ $[22] = t5;
6883
7147
  } else {
6884
- t5 = $[20];
7148
+ t5 = $[22];
6885
7149
  }
6886
7150
  let t6;
6887
- if ($[21] !== size || $[22] !== t32 || $[23] !== t4) {
7151
+ if ($[23] !== size || $[24] !== t32 || $[25] !== t4) {
6888
7152
  t6 = /* @__PURE__ */ jsx(EntityPreviewContainer, { onClick: t32, hover: t4, size, children: t5 });
6889
- $[21] = size;
6890
- $[22] = t32;
6891
- $[23] = t4;
6892
- $[24] = t6;
7153
+ $[23] = size;
7154
+ $[24] = t32;
7155
+ $[25] = t4;
7156
+ $[26] = t6;
6893
7157
  } else {
6894
- t6 = $[24];
7158
+ t6 = $[26];
6895
7159
  }
6896
7160
  return t6;
6897
7161
  }
6898
7162
  let t3;
6899
- if ($[25] !== collection || $[26] !== disabled || $[27] !== hover || $[28] !== includeEntityLink || $[29] !== includeId || $[30] !== onClick || $[31] !== previewProperties || $[32] !== size || $[33] !== usedEntity) {
7163
+ if ($[27] !== collection || $[28] !== disabled || $[29] !== hover || $[30] !== includeEntityLink || $[31] !== includeId || $[32] !== onClick || $[33] !== previewProperties || $[34] !== size || $[35] !== usedEntity) {
6900
7164
  t3 = /* @__PURE__ */ jsx(EntityPreview, { size, previewKeys: previewProperties, disabled, entity: usedEntity, collection, onClick, includeEntityLink, includeId, hover });
6901
- $[25] = collection;
6902
- $[26] = disabled;
6903
- $[27] = hover;
6904
- $[28] = includeEntityLink;
6905
- $[29] = includeId;
6906
- $[30] = onClick;
6907
- $[31] = previewProperties;
6908
- $[32] = size;
6909
- $[33] = usedEntity;
6910
- $[34] = t3;
7165
+ $[27] = collection;
7166
+ $[28] = disabled;
7167
+ $[29] = hover;
7168
+ $[30] = includeEntityLink;
7169
+ $[31] = includeId;
7170
+ $[32] = onClick;
7171
+ $[33] = previewProperties;
7172
+ $[34] = size;
7173
+ $[35] = usedEntity;
7174
+ $[36] = t3;
6911
7175
  } else {
6912
- t3 = $[34];
7176
+ t3 = $[36];
6913
7177
  }
6914
7178
  return t3;
6915
7179
  }
@@ -11206,126 +11470,6 @@ const PropertyTableCell = React__default.memo(function PropertyTableCell2({
11206
11470
  function areEqual(prevProps, nextProps) {
11207
11471
  return prevProps.height === nextProps.height && prevProps.propertyKey === nextProps.propertyKey && prevProps.align === nextProps.align && prevProps.width === nextProps.width && equal(prevProps.property, nextProps.property) && equal(prevProps.value, nextProps.value) && equal(prevProps.entity.id, nextProps.entity.id) && equal(prevProps.entity.values, nextProps.entity.values) && prevProps.isDragging === nextProps.isDragging && prevProps.isDraggable === nextProps.isDraggable && prevProps.frozen === nextProps.frozen;
11208
11472
  }
11209
- const LOCAL_STORAGE_PREFIX = "entity_cache::";
11210
- const entityCache = /* @__PURE__ */ new Map();
11211
- const isLocalStorageAvailable = typeof localStorage !== "undefined";
11212
- function customReplacer(key) {
11213
- const value = this[key];
11214
- if (value instanceof Date) {
11215
- return {
11216
- __type: "Date",
11217
- value: value.toISOString()
11218
- };
11219
- }
11220
- if (value instanceof EntityReference) {
11221
- return {
11222
- __type: "EntityReference",
11223
- id: value.id,
11224
- path: value.path,
11225
- databaseId: value.databaseId
11226
- };
11227
- }
11228
- if (value instanceof GeoPoint) {
11229
- return {
11230
- __type: "GeoPoint",
11231
- latitude: value.latitude,
11232
- longitude: value.longitude
11233
- };
11234
- }
11235
- if (value instanceof Vector) {
11236
- return {
11237
- __type: "Vector",
11238
- value: value.value
11239
- };
11240
- }
11241
- return value;
11242
- }
11243
- function customReviver(key, value) {
11244
- if (value && typeof value === "object" && "__type" in value) {
11245
- switch (value.__type) {
11246
- case "Date":
11247
- return new Date(value.value);
11248
- case "EntityReference":
11249
- return new EntityReference(value.id, value.path, value.databaseId);
11250
- case "GeoPoint":
11251
- return new GeoPoint(value.latitude, value.longitude);
11252
- case "Vector":
11253
- return new Vector(value.value);
11254
- default:
11255
- return value;
11256
- }
11257
- }
11258
- return value;
11259
- }
11260
- function saveEntityToCache(path, data) {
11261
- if (isLocalStorageAvailable) {
11262
- try {
11263
- const key = LOCAL_STORAGE_PREFIX + path;
11264
- const entityString = JSON.stringify(data, customReplacer);
11265
- console.debug("Saving entity to localStorage:", {
11266
- key,
11267
- entityString
11268
- });
11269
- localStorage.setItem(key, entityString);
11270
- } catch (error) {
11271
- console.error(`Failed to save entity for path "${path}" to localStorage:`, error);
11272
- }
11273
- }
11274
- }
11275
- function removeEntityFromMemoryCache(path) {
11276
- entityCache.delete(path);
11277
- }
11278
- function saveEntityToMemoryCache(path, data) {
11279
- entityCache.set(path, data);
11280
- }
11281
- function getEntityFromMemoryCache(path) {
11282
- return entityCache.get(path);
11283
- }
11284
- function getEntityFromCache(path) {
11285
- if (isLocalStorageAvailable) {
11286
- try {
11287
- const key = LOCAL_STORAGE_PREFIX + path;
11288
- const entityString = localStorage.getItem(key);
11289
- if (entityString) {
11290
- const entity = JSON.parse(entityString, customReviver);
11291
- return entity;
11292
- }
11293
- } catch (error) {
11294
- console.error(`Failed to load entity for path "${path}" from localStorage:`, error);
11295
- }
11296
- }
11297
- return void 0;
11298
- }
11299
- function removeEntityFromCache(path) {
11300
- if (isLocalStorageAvailable) {
11301
- try {
11302
- const key = LOCAL_STORAGE_PREFIX + path;
11303
- localStorage.removeItem(key);
11304
- } catch (error) {
11305
- console.error(`Failed to remove entity for path "${path}" from localStorage:`, error);
11306
- }
11307
- }
11308
- }
11309
- function flattenKeys(obj, prefix = "", result = []) {
11310
- if (isObject(obj) || Array.isArray(obj)) {
11311
- const plainObject = isPlainObject(obj);
11312
- if (!plainObject && prefix) {
11313
- result.push(prefix);
11314
- } else {
11315
- for (const key in obj) {
11316
- if (Object.prototype.hasOwnProperty.call(obj, key)) {
11317
- const newKey = prefix ? Array.isArray(obj) ? `${prefix}[${key}]` : `${prefix}.${key}` : key;
11318
- if (isObject(obj[key]) || Array.isArray(obj[key])) {
11319
- flattenKeys(obj[key], newKey, result);
11320
- } else {
11321
- result.push(newKey);
11322
- }
11323
- }
11324
- }
11325
- }
11326
- }
11327
- return result;
11328
- }
11329
11473
  function FieldHelperText(t0) {
11330
11474
  const $ = c(10);
11331
11475
  const {
@@ -16820,6 +16964,7 @@ function EntityForm({
16820
16964
  entityId: entityIdProp,
16821
16965
  collection,
16822
16966
  path,
16967
+ pathSegments,
16823
16968
  values: valuesToBeSaved
16824
16969
  });
16825
16970
  }, false, 2e3);
@@ -16847,7 +16992,7 @@ function EntityForm({
16847
16992
  const [savingError, setSavingError] = useState();
16848
16993
  const autoSave = collection.formAutoSave && !collection.customId;
16849
16994
  const baseInitialValues = useMemo(() => getInitialEntityValues(authController, collection, path, status, entity, customizationController.propertyConfigs), [authController, collection, path, status, entity, customizationController.propertyConfigs]);
16850
- const localChangesDataRaw = useMemo(() => entityId ? getEntityFromCache(path + "/" + entityId) : getEntityFromCache(path + "#new"), [entityId, path]);
16995
+ const localChangesDataRaw = useMemo(() => entityId ? getEntityFromCache(entityCacheKey(path, entityId)) : getEntityFromCache(path + "#new"), [entityId, path]);
16851
16996
  const [localChangesCleared, setLocalChangesCleared] = useState(false);
16852
16997
  const localChangesBackup = getLocalChangesBackup(collection);
16853
16998
  const autoApplyLocalChanges = localChangesBackup === "auto_apply";
@@ -16909,7 +17054,7 @@ function EntityForm({
16909
17054
  onValuesModified?.(false, initialValues_0);
16910
17055
  },
16911
17056
  onValuesChangeDeferred: (values_0, controller) => {
16912
- const key = status === "new" || status === "copy" ? path + "#new" : path + "/" + entityId;
17057
+ const key = status === "new" || status === "copy" ? path + "#new" : entityCacheKey(path, entityId);
16913
17058
  if (controller.dirty && localChangesBackup !== false) {
16914
17059
  const touchedValues = removeEmptyContainers(extractTouchedValues(values_0, controller.touched));
16915
17060
  if (touchedValues && Object.keys(touchedValues).length > 0) {
@@ -16974,8 +17119,8 @@ function EntityForm({
16974
17119
  removeEntityFromMemoryCache(path + "#new");
16975
17120
  removeEntityFromCache(path + "#new");
16976
17121
  } else {
16977
- removeEntityFromMemoryCache(path + "/" + entityId);
16978
- removeEntityFromCache(path + "/" + entityId);
17122
+ removeEntityFromMemoryCache(entityCacheKey(path, entityId));
17123
+ removeEntityFromCache(entityCacheKey(path, entityId));
16979
17124
  }
16980
17125
  }
16981
17126
  const onSaveSuccess = (updatedEntity) => {
@@ -16993,6 +17138,7 @@ function EntityForm({
16993
17138
  entity: updatedEntity,
16994
17139
  status,
16995
17140
  path,
17141
+ pathSegments,
16996
17142
  entityId: updatedEntity.id,
16997
17143
  collection
16998
17144
  });
@@ -17011,10 +17157,12 @@ function EntityForm({
17011
17157
  previousValues,
17012
17158
  entityId: entityId_0,
17013
17159
  collection: collection_0,
17014
- path: path_0
17160
+ path: path_0,
17161
+ pathSegments: pathSegments_0
17015
17162
  }) => {
17016
17163
  return saveEntityWithCallbacks({
17017
17164
  path: path_0,
17165
+ pathSegments: pathSegments_0,
17018
17166
  entityId: entityId_0,
17019
17167
  values: values_2,
17020
17168
  previousValues,
@@ -17031,6 +17179,7 @@ function EntityForm({
17031
17179
  const onSaveEntityRequest = async ({
17032
17180
  collection: collection_1,
17033
17181
  path: path_1,
17182
+ pathSegments: pathSegments_1,
17034
17183
  entityId: entityId_1,
17035
17184
  values: values_3,
17036
17185
  previousValues: previousValues_0,
@@ -17043,6 +17192,7 @@ function EntityForm({
17043
17192
  return saveEntity({
17044
17193
  collection: collection_1,
17045
17194
  path: path_1,
17195
+ pathSegments: pathSegments_1,
17046
17196
  entityId: entityId_1,
17047
17197
  values: values_3,
17048
17198
  previousValues: previousValues_0
@@ -17055,6 +17205,7 @@ function EntityForm({
17055
17205
  return onSaveEntityRequest({
17056
17206
  collection: resolvedCollection,
17057
17207
  path,
17208
+ pathSegments,
17058
17209
  entityId,
17059
17210
  values: values_4,
17060
17211
  previousValues: entity?.values,
@@ -17099,12 +17250,13 @@ function EntityForm({
17099
17250
  const pluginBeforeTitle = [];
17100
17251
  const plugins = customizationController.plugins;
17101
17252
  const actionsDisabled = disabled || formex.isSubmitting || status === "existing" && !formex.dirty || Boolean(disabledProp);
17102
- const parentCollectionIds = navigationController.getParentCollectionIds(path);
17253
+ const parentCollectionIds = navigationController.getParentCollectionIds(path, pathSegments);
17103
17254
  if (plugins && collection) {
17104
17255
  const actionProps = {
17105
17256
  entityId,
17106
17257
  parentCollectionIds,
17107
17258
  path,
17259
+ pathSegments,
17108
17260
  status,
17109
17261
  collection,
17110
17262
  context,
@@ -17253,13 +17405,13 @@ function EntityForm({
17253
17405
  if (!resolvedCollection || !path) {
17254
17406
  throw Error("INTERNAL: Collection and path must be defined in form context");
17255
17407
  }
17256
- const dialogActions = /* @__PURE__ */ jsx(EntityFormActionsComponent, { collection: resolvedCollection, path, fullPath: path, fullIdPath, entity, layout: forceActionsAtTheBottom ? "bottom" : "side", savingError, formex, disabled: actionsDisabled, status, pluginActions: pluginActions ?? [], openEntityMode, showDefaultActions, navigateBack, formContext });
17408
+ const dialogActions = /* @__PURE__ */ jsx(EntityFormActionsComponent, { collection: resolvedCollection, path, pathSegments, fullPath: path, fullIdPath, entity, layout: forceActionsAtTheBottom ? "bottom" : "side", savingError, formex, disabled: actionsDisabled, status, pluginActions: pluginActions ?? [], openEntityMode, showDefaultActions, navigateBack, formContext });
17257
17409
  return /* @__PURE__ */ jsx(Formex, { value: formex, children: /* @__PURE__ */ jsxs("form", { onSubmit: formex.handleSubmit, onReset: () => formex.resetForm({
17258
17410
  values: baseInitialValues
17259
17411
  }), noValidate: true, className: cls("flex-1 flex flex-row w-full overflow-y-auto justify-center", className), children: [
17260
17412
  /* @__PURE__ */ jsx("div", { id: `form_${path}`, className: cls("relative flex flex-row max-w-4xl lg:max-w-3xl xl:max-w-4xl 2xl:max-w-6xl w-full h-fit"), children: /* @__PURE__ */ jsxs("div", { className: cls("flex flex-col w-full pt-12 pb-16 px-4 sm:px-8 md:px-10"), children: [
17261
17413
  /* @__PURE__ */ jsxs("div", { className: "flex flex-row gap-4 self-end sticky top-4 z-10", children: [
17262
- manualApplyLocalChanges && hasLocalChanges && /* @__PURE__ */ jsx(LocalChangesMenu, { cacheKey: status === "new" || status === "copy" ? path + "#new" : path + "/" + entityId, properties: resolvedCollection.properties, cachedData: localChangesDataRaw, formex, onClearLocalChanges: () => setLocalChangesCleared(true) }),
17414
+ manualApplyLocalChanges && hasLocalChanges && /* @__PURE__ */ jsx(LocalChangesMenu, { cacheKey: status === "new" || status === "copy" ? path + "#new" : entityCacheKey(path, entityId), properties: resolvedCollection.properties, cachedData: localChangesDataRaw, formex, onClearLocalChanges: () => setLocalChangesCleared(true) }),
17263
17415
  formex.dirty ? /* @__PURE__ */ jsx(Tooltip, { title: "This form has been modified", children: /* @__PURE__ */ jsx(Chip, { size: "small", className: "py-1", colorScheme: "orangeDarker", children: /* @__PURE__ */ jsx(EditIcon, { size: "smallest" }) }) }) : /* @__PURE__ */ jsx(Tooltip, { title: "The current form is in sync with the database", children: /* @__PURE__ */ jsx(Chip, { size: "small", className: "py-1", children: /* @__PURE__ */ jsx(CheckIcon, { size: "smallest" }) }) })
17264
17416
  ] }),
17265
17417
  formView
@@ -17350,7 +17502,7 @@ const EntityCollectionRowActions = function EntityCollectionRowActions2({
17350
17502
  const collapsedActions = actions.filter((a_0) => a_0.collapsed || a_0.collapsed === void 0);
17351
17503
  const uncollapsedActions = actions.filter((a_1) => a_1.collapsed === false);
17352
17504
  const enableLocalChangesBackup = collection ? getLocalChangesBackup(collection) : false;
17353
- const cachedData = enableLocalChangesBackup ? getEntityFromCache(fullPath + "/" + entity.id) : void 0;
17505
+ const cachedData = enableLocalChangesBackup ? getEntityFromCache(entityCacheKey(fullPath, entity.id)) : void 0;
17354
17506
  const hasDraft = (() => {
17355
17507
  if (!cachedData || typeof cachedData !== "object" || Object.keys(cachedData).length === 0) return false;
17356
17508
  const realChanges = getChanges(cachedData, entity?.values ?? {});
@@ -20116,8 +20268,8 @@ function useDataSourceTableController({
20116
20268
  const [popupCell, setPopupCell] = React__default.useState(void 0);
20117
20269
  const navigation = useNavigationController();
20118
20270
  const dataSource = useDataSource();
20119
- const resolvedPath = useMemo(() => navigation.resolveIdsFrom(fullPath), [fullPath, navigation.resolveIdsFrom]);
20120
- const resolvedPathSegments = pathSegments;
20271
+ const resolvedPath = useMemo(() => navigation.resolveIdsFrom(fullPath, pathSegments), [fullPath, pathSegments, navigation.resolveIdsFrom]);
20272
+ const resolvedPathSegments = useMemo(() => pathSegments ? navigation.resolveSegmentsFrom?.(pathSegments) ?? pathSegments : void 0, [pathSegments, navigation.resolveSegmentsFrom]);
20121
20273
  const forceFilter = forceFilterFromProps ?? forceFilterFromCollection;
20122
20274
  const paginationEnabled = collection.pagination === void 0 || Boolean(collection.pagination);
20123
20275
  const pageSize = typeof collection.pagination === "number" ? collection.pagination : DEFAULT_PAGE_SIZE$1;
@@ -20179,10 +20331,10 @@ function useDataSourceTableController({
20179
20331
  const [sortBy_0, setSortBy] = React__default.useState((updateUrl ? initialSortUrl : void 0) ?? initialSortInternal);
20180
20332
  const [searchString, setSearchString] = React__default.useState(updateUrl ? initialSearchUrl : void 0);
20181
20333
  useUpdateUrl(filterValues_0, sortBy_0, searchString, updateUrl);
20182
- const collectionScroll = scrollRestoration?.getCollectionScroll(fullPath, filterValues_0);
20183
- const initialItemCount = collectionScroll?.data.length ?? pageSize;
20334
+ const collectionScroll = scrollRestoration?.getCollectionScroll(resolvedPath, filterValues_0);
20335
+ const initialItemCount = collectionScroll?.data.length || pageSize;
20184
20336
  useEffect(() => {
20185
- if (scrollRestoration) {
20337
+ if (scrollRestoration && rawData.length > 0) {
20186
20338
  scrollRestoration.updateCollectionScroll({
20187
20339
  fullPath: resolvedPath,
20188
20340
  scrollOffset: collectionScroll?.scrollOffset ?? 0,
@@ -20225,6 +20377,7 @@ function useDataSourceTableController({
20225
20377
  entities = await Promise.all(entities.map((entity) => collection.callbacks.onFetch({
20226
20378
  collection,
20227
20379
  path: resolvedPath,
20380
+ pathSegments: resolvedPathSegments,
20228
20381
  entity,
20229
20382
  context
20230
20383
  })));
@@ -20381,10 +20534,11 @@ function useSelectionController(onSelectionChange) {
20381
20534
  };
20382
20535
  }
20383
20536
  function useTableSearchHelper(t0) {
20384
- const $ = c(18);
20537
+ const $ = c(19);
20385
20538
  const {
20386
20539
  collection,
20387
20540
  fullPath,
20541
+ pathSegments,
20388
20542
  parentCollectionIds,
20389
20543
  initialSearchString
20390
20544
  } = t0;
@@ -20396,11 +20550,12 @@ function useTableSearchHelper(t0) {
20396
20550
  const autoInitialisedRef = useRef(false);
20397
20551
  let onTextSearchClick;
20398
20552
  let textSearchEnabled;
20399
- if ($[0] !== collection || $[1] !== context || $[2] !== customizationController.plugins || $[3] !== dataSource || $[4] !== fullPath || $[5] !== parentCollectionIds) {
20553
+ if ($[0] !== collection || $[1] !== context || $[2] !== customizationController.plugins || $[3] !== dataSource || $[4] !== fullPath || $[5] !== parentCollectionIds || $[6] !== pathSegments) {
20400
20554
  textSearchEnabled = Boolean(collection.textSearchEnabled);
20401
20555
  const props = {
20402
20556
  context,
20403
20557
  path: fullPath,
20558
+ pathSegments,
20404
20559
  databaseId: collection.databaseId,
20405
20560
  collection,
20406
20561
  parentCollectionIds
@@ -20420,6 +20575,7 @@ function useTableSearchHelper(t0) {
20420
20575
  promises.push(p_1.collectionView.onTextSearchClick({
20421
20576
  context,
20422
20577
  path: fullPath,
20578
+ pathSegments,
20423
20579
  collection,
20424
20580
  parentCollectionIds
20425
20581
  }));
@@ -20451,15 +20607,16 @@ function useTableSearchHelper(t0) {
20451
20607
  $[3] = dataSource;
20452
20608
  $[4] = fullPath;
20453
20609
  $[5] = parentCollectionIds;
20454
- $[6] = onTextSearchClick;
20455
- $[7] = textSearchEnabled;
20610
+ $[6] = pathSegments;
20611
+ $[7] = onTextSearchClick;
20612
+ $[8] = textSearchEnabled;
20456
20613
  } else {
20457
- onTextSearchClick = $[6];
20458
- textSearchEnabled = $[7];
20614
+ onTextSearchClick = $[7];
20615
+ textSearchEnabled = $[8];
20459
20616
  }
20460
20617
  const shouldAutoInitialise = Boolean(initialSearchString) && textSearchEnabled && !textSearchInitialised && Boolean(onTextSearchClick);
20461
20618
  let t1;
20462
- if ($[8] !== onTextSearchClick || $[9] !== shouldAutoInitialise) {
20619
+ if ($[9] !== onTextSearchClick || $[10] !== shouldAutoInitialise) {
20463
20620
  t1 = () => {
20464
20621
  if (autoInitialisedRef.current || !shouldAutoInitialise) {
20465
20622
  return;
@@ -20467,36 +20624,36 @@ function useTableSearchHelper(t0) {
20467
20624
  autoInitialisedRef.current = true;
20468
20625
  onTextSearchClick?.();
20469
20626
  };
20470
- $[8] = onTextSearchClick;
20471
- $[9] = shouldAutoInitialise;
20472
- $[10] = t1;
20627
+ $[9] = onTextSearchClick;
20628
+ $[10] = shouldAutoInitialise;
20629
+ $[11] = t1;
20473
20630
  } else {
20474
- t1 = $[10];
20631
+ t1 = $[11];
20475
20632
  }
20476
20633
  let t2;
20477
- if ($[11] !== shouldAutoInitialise) {
20634
+ if ($[12] !== shouldAutoInitialise) {
20478
20635
  t2 = [shouldAutoInitialise];
20479
- $[11] = shouldAutoInitialise;
20480
- $[12] = t2;
20636
+ $[12] = shouldAutoInitialise;
20637
+ $[13] = t2;
20481
20638
  } else {
20482
- t2 = $[12];
20639
+ t2 = $[13];
20483
20640
  }
20484
20641
  useEffect(t1, t2);
20485
20642
  let t3;
20486
- if ($[13] !== onTextSearchClick || $[14] !== textSearchEnabled || $[15] !== textSearchInitialised || $[16] !== textSearchLoading) {
20643
+ if ($[14] !== onTextSearchClick || $[15] !== textSearchEnabled || $[16] !== textSearchInitialised || $[17] !== textSearchLoading) {
20487
20644
  t3 = {
20488
20645
  textSearchLoading,
20489
20646
  textSearchInitialised,
20490
20647
  onTextSearchClick,
20491
20648
  textSearchEnabled
20492
20649
  };
20493
- $[13] = onTextSearchClick;
20494
- $[14] = textSearchEnabled;
20495
- $[15] = textSearchInitialised;
20496
- $[16] = textSearchLoading;
20497
- $[17] = t3;
20650
+ $[14] = onTextSearchClick;
20651
+ $[15] = textSearchEnabled;
20652
+ $[16] = textSearchInitialised;
20653
+ $[17] = textSearchLoading;
20654
+ $[18] = t3;
20498
20655
  } else {
20499
- t3 = $[17];
20656
+ t3 = $[18];
20500
20657
  }
20501
20658
  return t3;
20502
20659
  }
@@ -20565,6 +20722,8 @@ function DeleteEntityDialog({
20565
20722
  const performDelete = useCallback((entity_3) => deleteEntityWithCallbacks({
20566
20723
  dataSource,
20567
20724
  entity: entity_3,
20725
+ // The entity is the authority on where it lives; stated rather than left implicit.
20726
+ pathSegments: entity_3.pathSegments,
20568
20727
  collection: resolvedCollection,
20569
20728
  callbacks,
20570
20729
  onDeleteSuccess,
@@ -20666,6 +20825,7 @@ const editEntityAction = {
20666
20825
  entity,
20667
20826
  collection,
20668
20827
  fullPath,
20828
+ pathSegments,
20669
20829
  fullIdPath,
20670
20830
  context,
20671
20831
  highlightEntity,
@@ -20684,6 +20844,7 @@ const editEntityAction = {
20684
20844
  addRecentId(collection.id, entity.id);
20685
20845
  }
20686
20846
  const path = collection?.collectionGroup ? entity.path : fullPath ?? collection?.path ?? entity.path;
20847
+ const resolvedPathSegments = collection?.collectionGroup ? entity.pathSegments : pathSegments ?? entity.pathSegments;
20687
20848
  const newFullIdPath = collection?.collectionGroup ? collection.id : fullIdPath ?? collection?.id ?? entity.path;
20688
20849
  const defaultSelectedView = resolveDefaultSelectedView(collection ? collection.defaultSelectedView : void 0, {
20689
20850
  status: "existing",
@@ -20694,6 +20855,7 @@ const editEntityAction = {
20694
20855
  collection,
20695
20856
  entityId: entity.id,
20696
20857
  path,
20858
+ pathSegments: resolvedPathSegments,
20697
20859
  fullIdPath: newFullIdPath,
20698
20860
  sideEntityController: context.sideEntityController,
20699
20861
  onClose: () => unhighlightEntity?.(entity),
@@ -20715,6 +20877,8 @@ const copyEntityAction = {
20715
20877
  collection,
20716
20878
  context,
20717
20879
  fullPath,
20880
+ pathSegments,
20881
+ fullIdPath,
20718
20882
  highlightEntity,
20719
20883
  unhighlightEntity,
20720
20884
  openEntityMode
@@ -20728,13 +20892,15 @@ const copyEntityAction = {
20728
20892
  entityId: entity.id
20729
20893
  });
20730
20894
  const path = collection?.collectionGroup ? collection.path : fullPath ?? collection?.path ?? entity.path;
20731
- const fullIdPath = collection?.collectionGroup ? collection.id : fullPath ?? collection?.id ?? entity.path;
20895
+ const resolvedPathSegments = collection?.collectionGroup ? void 0 : pathSegments ?? entity.pathSegments;
20896
+ const newFullIdPath = collection?.collectionGroup ? collection.id : fullIdPath ?? collection?.id;
20732
20897
  navigateToEntity({
20733
20898
  openEntityMode,
20734
20899
  collection,
20735
20900
  entityId: entity.id,
20736
20901
  path,
20737
- fullIdPath,
20902
+ pathSegments: resolvedPathSegments,
20903
+ fullIdPath: newFullIdPath,
20738
20904
  copy: true,
20739
20905
  sideEntityController: context.sideEntityController,
20740
20906
  onClose: () => unhighlightEntity?.(entity),
@@ -20804,7 +20970,7 @@ function ReferenceSelectionTable({
20804
20970
  const navigation = useNavigationController();
20805
20971
  const analyticsController = useAnalyticsController();
20806
20972
  const customizationController = useCustomizationController();
20807
- const fullPath = navigation.resolveIdsFrom(pathInput);
20973
+ const fullPath = navigation.resolveIdsFrom(pathInput, pathSegments);
20808
20974
  const dataSource = useDataSource();
20809
20975
  const [entitiesDisplayedFirst, setEntitiesDisplayedFirst] = useState([]);
20810
20976
  const toggleEntitySelection = (entity) => {
@@ -20879,6 +21045,7 @@ function ReferenceSelectionTable({
20879
21045
  });
20880
21046
  sideEntityController.open({
20881
21047
  path: fullPath,
21048
+ pathSegments,
20882
21049
  collection,
20883
21050
  updateUrl: true,
20884
21051
  onUpdate: ({
@@ -20928,6 +21095,7 @@ function ReferenceSelectionTable({
20928
21095
  onTextSearchClick,
20929
21096
  textSearchEnabled
20930
21097
  } = useTableSearchHelper({
21098
+ pathSegments,
20931
21099
  collection,
20932
21100
  fullPath
20933
21101
  });
@@ -20939,7 +21107,7 @@ function ReferenceSelectionTable({
20939
21107
  }) : t("select_from", {
20940
21108
  name: collection.name
20941
21109
  })
20942
- ] }), defaultSize: collection.defaultSize, properties: resolvedCollection.properties, forceFilter, inlineEditing: false, selectionController, actions: /* @__PURE__ */ jsx(ReferenceDialogActions, { collection, path: fullPath, onNewClick, onClear }) }) }),
21110
+ ] }), defaultSize: collection.defaultSize, properties: resolvedCollection.properties, forceFilter, inlineEditing: false, selectionController, actions: /* @__PURE__ */ jsx(ReferenceDialogActions, { collection, path: fullPath, pathSegments, onNewClick, onClear }) }) }),
20943
21111
  /* @__PURE__ */ jsxs(DialogActions, { translucent: false, children: [
20944
21112
  description && /* @__PURE__ */ jsx(Typography, { variant: "body2", className: "flex-grow text-left", children: description }),
20945
21113
  /* @__PURE__ */ jsx(Button, { onClick: onDone, variant: "filled", children: t("done") })
@@ -20947,10 +21115,11 @@ function ReferenceSelectionTable({
20947
21115
  ] });
20948
21116
  }
20949
21117
  function ReferenceDialogActions(t0) {
20950
- const $ = c(17);
21118
+ const $ = c(18);
20951
21119
  const {
20952
21120
  collection,
20953
21121
  path,
21122
+ pathSegments,
20954
21123
  onClear,
20955
21124
  onNewClick
20956
21125
  } = t0;
@@ -20972,8 +21141,8 @@ function ReferenceDialogActions(t0) {
20972
21141
  }
20973
21142
  const onClick = t1;
20974
21143
  let t2;
20975
- if ($[2] !== authController || $[3] !== collection || $[4] !== largeLayout || $[5] !== onClick || $[6] !== path || $[7] !== t) {
20976
- t2 = canCreateEntity(collection, authController, path, null) && onClick && (largeLayout ? /* @__PURE__ */ jsx(Button, { onClick, startIcon: /* @__PURE__ */ jsx(AddIcon, {}), children: t("add_specific", {
21144
+ if ($[2] !== authController || $[3] !== collection || $[4] !== largeLayout || $[5] !== onClick || $[6] !== path || $[7] !== pathSegments || $[8] !== t) {
21145
+ t2 = canCreateEntity(collection, authController, path, null, pathSegments) && onClick && (largeLayout ? /* @__PURE__ */ jsx(Button, { onClick, startIcon: /* @__PURE__ */ jsx(AddIcon, {}), children: t("add_specific", {
20977
21146
  name: collection.singularName ?? collection.name
20978
21147
  }) }) : /* @__PURE__ */ jsx(Button, { onClick, children: /* @__PURE__ */ jsx(AddIcon, {}) }));
20979
21148
  $[2] = authController;
@@ -20981,40 +21150,41 @@ function ReferenceDialogActions(t0) {
20981
21150
  $[4] = largeLayout;
20982
21151
  $[5] = onClick;
20983
21152
  $[6] = path;
20984
- $[7] = t;
20985
- $[8] = t2;
21153
+ $[7] = pathSegments;
21154
+ $[8] = t;
21155
+ $[9] = t2;
20986
21156
  } else {
20987
- t2 = $[8];
21157
+ t2 = $[9];
20988
21158
  }
20989
21159
  const addButton = t2;
20990
21160
  let t3;
20991
- if ($[9] !== t) {
21161
+ if ($[10] !== t) {
20992
21162
  t3 = t("clear");
20993
- $[9] = t;
20994
- $[10] = t3;
21163
+ $[10] = t;
21164
+ $[11] = t3;
20995
21165
  } else {
20996
- t3 = $[10];
21166
+ t3 = $[11];
20997
21167
  }
20998
21168
  let t4;
20999
- if ($[11] !== onClear || $[12] !== t3) {
21169
+ if ($[12] !== onClear || $[13] !== t3) {
21000
21170
  t4 = /* @__PURE__ */ jsx(Button, { onClick: onClear, variant: "text", children: t3 });
21001
- $[11] = onClear;
21002
- $[12] = t3;
21003
- $[13] = t4;
21171
+ $[12] = onClear;
21172
+ $[13] = t3;
21173
+ $[14] = t4;
21004
21174
  } else {
21005
- t4 = $[13];
21175
+ t4 = $[14];
21006
21176
  }
21007
21177
  let t5;
21008
- if ($[14] !== addButton || $[15] !== t4) {
21178
+ if ($[15] !== addButton || $[16] !== t4) {
21009
21179
  t5 = /* @__PURE__ */ jsxs(Fragment, { children: [
21010
21180
  t4,
21011
21181
  addButton
21012
21182
  ] });
21013
- $[14] = addButton;
21014
- $[15] = t4;
21015
- $[16] = t5;
21183
+ $[15] = addButton;
21184
+ $[16] = t4;
21185
+ $[17] = t5;
21016
21186
  } else {
21017
- t5 = $[16];
21187
+ t5 = $[17];
21018
21188
  }
21019
21189
  return t5;
21020
21190
  }
@@ -22930,7 +23100,7 @@ const useBreadcrumbsController = () => {
22930
23100
  return useContext(BreadcrumbContext);
22931
23101
  };
22932
23102
  function EntityCollectionViewActions(t0) {
22933
- const $ = c(45);
23103
+ const $ = c(48);
22934
23104
  const {
22935
23105
  collection,
22936
23106
  relativePath,
@@ -22939,6 +23109,7 @@ function EntityCollectionViewActions(t0) {
22939
23109
  onMultipleDeleteClick,
22940
23110
  selectionEnabled,
22941
23111
  path,
23112
+ pathSegments,
22942
23113
  selectionController,
22943
23114
  tableController,
22944
23115
  collectionEntitiesCount
@@ -22961,8 +23132,8 @@ function EntityCollectionViewActions(t0) {
22961
23132
  const largeLayout = useLargeLayout();
22962
23133
  const selectedEntities = selectionController.selectedEntities;
22963
23134
  let t2;
22964
- if ($[2] !== authController || $[3] !== collection || $[4] !== largeLayout || $[5] !== onNewClick || $[6] !== path || $[7] !== t) {
22965
- t2 = canCreateEntity(collection, authController, path, null) && onNewClick && (largeLayout ? /* @__PURE__ */ jsxs(Button, { id: `add_entity_${path}`, onClick: onNewClick, startIcon: /* @__PURE__ */ jsx(AddIcon, { size: "small" }), variant: "filled", color: "primary", children: [
23135
+ if ($[2] !== authController || $[3] !== collection || $[4] !== largeLayout || $[5] !== onNewClick || $[6] !== path || $[7] !== pathSegments || $[8] !== t) {
23136
+ t2 = canCreateEntity(collection, authController, path, null, pathSegments) && onNewClick && (largeLayout ? /* @__PURE__ */ jsxs(Button, { id: `add_entity_${path}`, onClick: onNewClick, startIcon: /* @__PURE__ */ jsx(AddIcon, { size: "small" }), variant: "filled", color: "primary", children: [
22966
23137
  t("add"),
22967
23138
  " ",
22968
23139
  collection.singularName ?? collection.name
@@ -22972,65 +23143,68 @@ function EntityCollectionViewActions(t0) {
22972
23143
  $[4] = largeLayout;
22973
23144
  $[5] = onNewClick;
22974
23145
  $[6] = path;
22975
- $[7] = t;
22976
- $[8] = t2;
23146
+ $[7] = pathSegments;
23147
+ $[8] = t;
23148
+ $[9] = t2;
22977
23149
  } else {
22978
- t2 = $[8];
23150
+ t2 = $[9];
22979
23151
  }
22980
23152
  const addButton = t2;
22981
23153
  let t3;
22982
- if ($[9] !== authController || $[10] !== collection || $[11] !== path) {
22983
- t3 = canDeleteEntity(collection, authController, path, null);
22984
- $[9] = authController;
22985
- $[10] = collection;
22986
- $[11] = path;
22987
- $[12] = t3;
23154
+ if ($[10] !== authController || $[11] !== collection || $[12] !== path || $[13] !== pathSegments) {
23155
+ t3 = canDeleteEntity(collection, authController, path, null, pathSegments);
23156
+ $[10] = authController;
23157
+ $[11] = collection;
23158
+ $[12] = path;
23159
+ $[13] = pathSegments;
23160
+ $[14] = t3;
22988
23161
  } else {
22989
- t3 = $[12];
23162
+ t3 = $[14];
22990
23163
  }
22991
23164
  const multipleDeleteEnabled = t3;
22992
23165
  let multipleDeleteButton;
22993
23166
  if (selectionEnabled) {
22994
23167
  let t42;
22995
- if ($[13] !== largeLayout || $[14] !== multipleDeleteEnabled || $[15] !== onMultipleDeleteClick || $[16] !== selectedEntities?.length) {
23168
+ if ($[15] !== largeLayout || $[16] !== multipleDeleteEnabled || $[17] !== onMultipleDeleteClick || $[18] !== selectedEntities?.length) {
22996
23169
  t42 = largeLayout ? /* @__PURE__ */ jsxs(Button, { variant: "text", disabled: !selectedEntities?.length || !multipleDeleteEnabled, startIcon: /* @__PURE__ */ jsx(DeleteIcon, { size: "small" }), onClick: onMultipleDeleteClick, color: "primary", className: "lg:w-20", children: [
22997
23170
  "(",
22998
23171
  selectedEntities?.length,
22999
23172
  ")"
23000
23173
  ] }) : /* @__PURE__ */ jsx(IconButton, { size: "small", color: "primary", disabled: !selectedEntities?.length || !multipleDeleteEnabled, onClick: onMultipleDeleteClick, children: /* @__PURE__ */ jsx(DeleteIcon, { size: "small" }) });
23001
- $[13] = largeLayout;
23002
- $[14] = multipleDeleteEnabled;
23003
- $[15] = onMultipleDeleteClick;
23004
- $[16] = selectedEntities?.length;
23005
- $[17] = t42;
23174
+ $[15] = largeLayout;
23175
+ $[16] = multipleDeleteEnabled;
23176
+ $[17] = onMultipleDeleteClick;
23177
+ $[18] = selectedEntities?.length;
23178
+ $[19] = t42;
23006
23179
  } else {
23007
- t42 = $[17];
23180
+ t42 = $[19];
23008
23181
  }
23009
23182
  const button = t42;
23010
23183
  let t52;
23011
- if ($[18] !== multipleDeleteEnabled || $[19] !== t) {
23184
+ if ($[20] !== multipleDeleteEnabled || $[21] !== t) {
23012
23185
  t52 = multipleDeleteEnabled ? t("delete_selected") : t("cannot_delete_selected");
23013
- $[18] = multipleDeleteEnabled;
23014
- $[19] = t;
23015
- $[20] = t52;
23186
+ $[20] = multipleDeleteEnabled;
23187
+ $[21] = t;
23188
+ $[22] = t52;
23016
23189
  } else {
23017
- t52 = $[20];
23190
+ t52 = $[22];
23018
23191
  }
23019
23192
  let t62;
23020
- if ($[21] !== button || $[22] !== t52) {
23193
+ if ($[23] !== button || $[24] !== t52) {
23021
23194
  t62 = /* @__PURE__ */ jsx(Tooltip, { title: t52, children: button });
23022
- $[21] = button;
23023
- $[22] = t52;
23024
- $[23] = t62;
23195
+ $[23] = button;
23196
+ $[24] = t52;
23197
+ $[25] = t62;
23025
23198
  } else {
23026
- t62 = $[23];
23199
+ t62 = $[25];
23027
23200
  }
23028
23201
  multipleDeleteButton = t62;
23029
23202
  }
23030
23203
  let t4;
23031
- if ($[24] !== collection || $[25] !== collectionEntitiesCount || $[26] !== context || $[27] !== parentCollectionIds || $[28] !== path || $[29] !== relativePath || $[30] !== selectionController || $[31] !== tableController) {
23204
+ if ($[26] !== collection || $[27] !== collectionEntitiesCount || $[28] !== context || $[29] !== parentCollectionIds || $[30] !== path || $[31] !== pathSegments || $[32] !== relativePath || $[33] !== selectionController || $[34] !== tableController) {
23032
23205
  t4 = {
23033
23206
  path,
23207
+ pathSegments,
23034
23208
  relativePath,
23035
23209
  parentCollectionIds,
23036
23210
  collection,
@@ -23039,28 +23213,29 @@ function EntityCollectionViewActions(t0) {
23039
23213
  tableController,
23040
23214
  collectionEntitiesCount
23041
23215
  };
23042
- $[24] = collection;
23043
- $[25] = collectionEntitiesCount;
23044
- $[26] = context;
23045
- $[27] = parentCollectionIds;
23046
- $[28] = path;
23047
- $[29] = relativePath;
23048
- $[30] = selectionController;
23049
- $[31] = tableController;
23050
- $[32] = t4;
23216
+ $[26] = collection;
23217
+ $[27] = collectionEntitiesCount;
23218
+ $[28] = context;
23219
+ $[29] = parentCollectionIds;
23220
+ $[30] = path;
23221
+ $[31] = pathSegments;
23222
+ $[32] = relativePath;
23223
+ $[33] = selectionController;
23224
+ $[34] = tableController;
23225
+ $[35] = t4;
23051
23226
  } else {
23052
- t4 = $[32];
23227
+ t4 = $[35];
23053
23228
  }
23054
23229
  const actionProps = t4;
23055
23230
  let actions;
23056
- if ($[33] !== actionProps || $[34] !== collection.Actions || $[35] !== plugins) {
23231
+ if ($[36] !== actionProps || $[37] !== collection.Actions || $[38] !== plugins) {
23057
23232
  let t52;
23058
- if ($[37] !== actionProps) {
23233
+ if ($[40] !== actionProps) {
23059
23234
  t52 = (Action, i) => /* @__PURE__ */ jsx(ErrorBoundary, { children: /* @__PURE__ */ jsx(Action, { ...actionProps }) }, `actions_${i}`);
23060
- $[37] = actionProps;
23061
- $[38] = t52;
23235
+ $[40] = actionProps;
23236
+ $[41] = t52;
23062
23237
  } else {
23063
- t52 = $[38];
23238
+ t52 = $[41];
23064
23239
  }
23065
23240
  actions = toArray(collection.Actions).map(t52);
23066
23241
  if (plugins) {
@@ -23070,34 +23245,34 @@ function EntityCollectionViewActions(t0) {
23070
23245
  }
23071
23246
  });
23072
23247
  }
23073
- $[33] = actionProps;
23074
- $[34] = collection.Actions;
23075
- $[35] = plugins;
23076
- $[36] = actions;
23248
+ $[36] = actionProps;
23249
+ $[37] = collection.Actions;
23250
+ $[38] = plugins;
23251
+ $[39] = actions;
23077
23252
  } else {
23078
- actions = $[36];
23253
+ actions = $[39];
23079
23254
  }
23080
23255
  let t5;
23081
- if ($[39] !== actions) {
23256
+ if ($[42] !== actions) {
23082
23257
  t5 = /* @__PURE__ */ jsx(ErrorBoundary, { children: actions });
23083
- $[39] = actions;
23084
- $[40] = t5;
23258
+ $[42] = actions;
23259
+ $[43] = t5;
23085
23260
  } else {
23086
- t5 = $[40];
23261
+ t5 = $[43];
23087
23262
  }
23088
23263
  let t6;
23089
- if ($[41] !== addButton || $[42] !== multipleDeleteButton || $[43] !== t5) {
23264
+ if ($[44] !== addButton || $[45] !== multipleDeleteButton || $[46] !== t5) {
23090
23265
  t6 = /* @__PURE__ */ jsxs(Fragment, { children: [
23091
23266
  t5,
23092
23267
  multipleDeleteButton,
23093
23268
  addButton
23094
23269
  ] });
23095
- $[41] = addButton;
23096
- $[42] = multipleDeleteButton;
23097
- $[43] = t5;
23098
- $[44] = t6;
23270
+ $[44] = addButton;
23271
+ $[45] = multipleDeleteButton;
23272
+ $[46] = t5;
23273
+ $[47] = t6;
23099
23274
  } else {
23100
- t6 = $[44];
23275
+ t6 = $[47];
23101
23276
  }
23102
23277
  return t6;
23103
23278
  }
@@ -24443,8 +24618,8 @@ function useBoardDataController({
24443
24618
  const context = useFireCMSContext();
24444
24619
  const dataSource = useDataSource();
24445
24620
  const navigation = useNavigationController();
24446
- const resolvedPath = useMemo(() => navigation.resolveIdsFrom(fullPath), [fullPath, navigation.resolveIdsFrom]);
24447
- const resolvedPathSegments = pathSegments;
24621
+ const resolvedPath = useMemo(() => navigation.resolveIdsFrom(fullPath, pathSegments), [fullPath, pathSegments, navigation.resolveIdsFrom]);
24622
+ const resolvedPathSegments = useMemo(() => pathSegments ? navigation.resolveSegmentsFrom?.(pathSegments) ?? pathSegments : void 0, [pathSegments, navigation.resolveSegmentsFrom]);
24448
24623
  const dataSourceRef = useRef(dataSource);
24449
24624
  const collectionRef = useRef(collection);
24450
24625
  const contextRef = useRef(context);
@@ -24530,6 +24705,7 @@ function useBoardDataController({
24530
24705
  processed = await Promise.all(processed.map((entity) => currentCollection.callbacks.onFetch({
24531
24706
  collection: currentCollection,
24532
24707
  path: currentResolvedPath,
24708
+ pathSegments: currentPathSegments,
24533
24709
  entity,
24534
24710
  context: currentContext
24535
24711
  })));
@@ -25038,6 +25214,7 @@ function EntityCollectionBoardView({
25038
25214
  let completed = 0;
25039
25215
  currentDataSource.countEntities({
25040
25216
  path: fullPath,
25217
+ pathSegments,
25041
25218
  collection: currentCollection
25042
25219
  }).then((count) => {
25043
25220
  totalCount = count;
@@ -25048,6 +25225,7 @@ function EntityCollectionBoardView({
25048
25225
  }).catch((e) => console.warn("Failed to get total count:", e));
25049
25226
  currentDataSource.countEntities({
25050
25227
  path: fullPath,
25228
+ pathSegments,
25051
25229
  collection: currentCollection,
25052
25230
  filter: {
25053
25231
  [orderProperty]: ["!=", null]
@@ -25155,6 +25333,8 @@ function EntityCollectionBoardView({
25155
25333
  }
25156
25334
  const saveProps = {
25157
25335
  path: entity_2.path,
25336
+ // Paired with `entity.path`: the segments the entity was loaded with.
25337
+ pathSegments: entity_2.pathSegments,
25158
25338
  entityId: entity_2.id,
25159
25339
  values: updatedValues,
25160
25340
  previousValues: entity_2.values,
@@ -25192,6 +25372,7 @@ function EntityCollectionBoardView({
25192
25372
  console.log("Fetching all documents from collection...");
25193
25373
  const allDocs = await dataSource.fetchCollection({
25194
25374
  path: fullPath,
25375
+ pathSegments,
25195
25376
  collection,
25196
25377
  limit: 1e4
25197
25378
  // Fetch all
@@ -25210,6 +25391,8 @@ function EntityCollectionBoardView({
25210
25391
  }, orderProperty, index);
25211
25392
  const saveProps_0 = {
25212
25393
  path: entity_4.path,
25394
+ // Paired with `entity.path`: the segments the entity was loaded with.
25395
+ pathSegments: entity_4.pathSegments,
25213
25396
  entityId: entity_4.id,
25214
25397
  values: updatedValues_0,
25215
25398
  previousValues: entity_4.values,
@@ -25295,6 +25478,7 @@ function EntityCollectionBoardView({
25295
25478
  });
25296
25479
  sideEntityController.open({
25297
25480
  path: fullPath,
25481
+ pathSegments,
25298
25482
  collection,
25299
25483
  entityId: void 0,
25300
25484
  updateUrl: true,
@@ -25992,12 +26176,13 @@ function FiltersDialog({
25992
26176
  ] });
25993
26177
  }
25994
26178
  function EntityCollectionViewStartActions(t0) {
25995
- const $ = c(37);
26179
+ const $ = c(38);
25996
26180
  const {
25997
26181
  collection,
25998
26182
  relativePath,
25999
26183
  parentCollectionIds,
26000
26184
  path,
26185
+ pathSegments,
26001
26186
  selectionController,
26002
26187
  tableController,
26003
26188
  collectionEntitiesCount,
@@ -26032,9 +26217,10 @@ function EntityCollectionViewStartActions(t0) {
26032
26217
  }
26033
26218
  const activeFilterCount = t2;
26034
26219
  let t3;
26035
- if ($[5] !== collection || $[6] !== collectionEntitiesCount || $[7] !== context || $[8] !== parentCollectionIds || $[9] !== path || $[10] !== relativePath || $[11] !== selectionController || $[12] !== tableController) {
26220
+ if ($[5] !== collection || $[6] !== collectionEntitiesCount || $[7] !== context || $[8] !== parentCollectionIds || $[9] !== path || $[10] !== pathSegments || $[11] !== relativePath || $[12] !== selectionController || $[13] !== tableController) {
26036
26221
  t3 = {
26037
26222
  path,
26223
+ pathSegments,
26038
26224
  relativePath,
26039
26225
  parentCollectionIds,
26040
26226
  collection,
@@ -26048,44 +26234,45 @@ function EntityCollectionViewStartActions(t0) {
26048
26234
  $[7] = context;
26049
26235
  $[8] = parentCollectionIds;
26050
26236
  $[9] = path;
26051
- $[10] = relativePath;
26052
- $[11] = selectionController;
26053
- $[12] = tableController;
26054
- $[13] = t3;
26237
+ $[10] = pathSegments;
26238
+ $[11] = relativePath;
26239
+ $[12] = selectionController;
26240
+ $[13] = tableController;
26241
+ $[14] = t3;
26055
26242
  } else {
26056
- t3 = $[13];
26243
+ t3 = $[14];
26057
26244
  }
26058
26245
  const actionProps = t3;
26059
26246
  const hasAnyAllowedFilters = !tableController.allowedFilters || tableController.allowedFilters.length > 0;
26060
26247
  let t4;
26061
- if ($[14] !== activeFilterCount || $[15] !== hasAnyAllowedFilters || $[16] !== largeLayout || $[17] !== resolvedProperties || $[18] !== t || $[19] !== tableController.setFilterValues) {
26248
+ if ($[15] !== activeFilterCount || $[16] !== hasAnyAllowedFilters || $[17] !== largeLayout || $[18] !== resolvedProperties || $[19] !== t || $[20] !== tableController.setFilterValues) {
26062
26249
  t4 = resolvedProperties && tableController.setFilterValues && hasAnyAllowedFilters && /* @__PURE__ */ jsx(Tooltip, { title: t("filters"), children: /* @__PURE__ */ jsx(Badge, { color: "primary", invisible: activeFilterCount === 0, children: largeLayout ? /* @__PURE__ */ jsxs(Button, { variant: "text", size: "small", onClick: () => setFiltersDialogOpen(true), startIcon: /* @__PURE__ */ jsx(FilterListIcon, { size: "small" }), className: cls(activeFilterCount > 0 && "text-primary"), children: [
26063
26250
  t("filters"),
26064
26251
  activeFilterCount > 0 ? ` (${activeFilterCount})` : ""
26065
26252
  ] }) : /* @__PURE__ */ jsx(IconButton, { size: "small", onClick: () => setFiltersDialogOpen(true), className: cls(activeFilterCount > 0 && "text-primary"), children: /* @__PURE__ */ jsx(FilterListIcon, { size: "small" }) }) }) }, "filters_tooltip");
26066
- $[14] = activeFilterCount;
26067
- $[15] = hasAnyAllowedFilters;
26068
- $[16] = largeLayout;
26069
- $[17] = resolvedProperties;
26070
- $[18] = t;
26071
- $[19] = tableController.setFilterValues;
26072
- $[20] = t4;
26253
+ $[15] = activeFilterCount;
26254
+ $[16] = hasAnyAllowedFilters;
26255
+ $[17] = largeLayout;
26256
+ $[18] = resolvedProperties;
26257
+ $[19] = t;
26258
+ $[20] = tableController.setFilterValues;
26259
+ $[21] = t4;
26073
26260
  } else {
26074
- t4 = $[20];
26261
+ t4 = $[21];
26075
26262
  }
26076
26263
  const filtersButton = t4;
26077
26264
  const t5 = !collection.forceFilter;
26078
26265
  let t6;
26079
- if ($[21] !== t5 || $[22] !== tableController) {
26266
+ if ($[22] !== t5 || $[23] !== tableController) {
26080
26267
  t6 = /* @__PURE__ */ jsx(ClearFilterSortButton, { tableController, enabled: t5 }, "clear_filter");
26081
- $[21] = t5;
26082
- $[22] = tableController;
26083
- $[23] = t6;
26268
+ $[22] = t5;
26269
+ $[23] = tableController;
26270
+ $[24] = t6;
26084
26271
  } else {
26085
- t6 = $[23];
26272
+ t6 = $[24];
26086
26273
  }
26087
26274
  let actions;
26088
- if ($[24] !== actionProps || $[25] !== filtersButton || $[26] !== plugins || $[27] !== t6) {
26275
+ if ($[25] !== actionProps || $[26] !== filtersButton || $[27] !== plugins || $[28] !== t6) {
26089
26276
  actions = [filtersButton, t6];
26090
26277
  if (plugins) {
26091
26278
  plugins.forEach((plugin, i) => {
@@ -26094,36 +26281,36 @@ function EntityCollectionViewStartActions(t0) {
26094
26281
  }
26095
26282
  });
26096
26283
  }
26097
- $[24] = actionProps;
26098
- $[25] = filtersButton;
26099
- $[26] = plugins;
26100
- $[27] = t6;
26101
- $[28] = actions;
26284
+ $[25] = actionProps;
26285
+ $[26] = filtersButton;
26286
+ $[27] = plugins;
26287
+ $[28] = t6;
26288
+ $[29] = actions;
26102
26289
  } else {
26103
- actions = $[28];
26290
+ actions = $[29];
26104
26291
  }
26105
26292
  let t7;
26106
- if ($[29] !== collection.forceFilter || $[30] !== filtersDialogOpen || $[31] !== resolvedProperties || $[32] !== tableController) {
26293
+ if ($[30] !== collection.forceFilter || $[31] !== filtersDialogOpen || $[32] !== resolvedProperties || $[33] !== tableController) {
26107
26294
  t7 = resolvedProperties && tableController.setFilterValues && /* @__PURE__ */ jsx(FiltersDialog, { open: filtersDialogOpen, onOpenChange: setFiltersDialogOpen, properties: resolvedProperties, filterValues: tableController.filterValues, setFilterValues: (filterValues_0) => tableController.setFilterValues?.(filterValues_0 ?? {}), forceFilter: collection.forceFilter, allowedFilters: tableController.allowedFilters?.map(_temp$g) });
26108
- $[29] = collection.forceFilter;
26109
- $[30] = filtersDialogOpen;
26110
- $[31] = resolvedProperties;
26111
- $[32] = tableController;
26112
- $[33] = t7;
26295
+ $[30] = collection.forceFilter;
26296
+ $[31] = filtersDialogOpen;
26297
+ $[32] = resolvedProperties;
26298
+ $[33] = tableController;
26299
+ $[34] = t7;
26113
26300
  } else {
26114
- t7 = $[33];
26301
+ t7 = $[34];
26115
26302
  }
26116
26303
  let t8;
26117
- if ($[34] !== actions || $[35] !== t7) {
26304
+ if ($[35] !== actions || $[36] !== t7) {
26118
26305
  t8 = /* @__PURE__ */ jsxs(Fragment, { children: [
26119
26306
  actions,
26120
26307
  t7
26121
26308
  ] });
26122
- $[34] = actions;
26123
- $[35] = t7;
26124
- $[36] = t8;
26309
+ $[35] = actions;
26310
+ $[36] = t7;
26311
+ $[37] = t8;
26125
26312
  } else {
26126
- t8 = $[36];
26313
+ t8 = $[37];
26127
26314
  }
26128
26315
  return t8;
26129
26316
  }
@@ -26201,7 +26388,7 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26201
26388
  useEffect(() => {
26202
26389
  collectionRef.current = collection;
26203
26390
  }, [collection]);
26204
- const canCreateEntities = canCreateEntity(collection, authController, fullPath, null);
26391
+ const canCreateEntities = canCreateEntity(collection, authController, fullPath, null, pathSegments);
26205
26392
  const [highlightedEntity, setHighlightedEntity] = useState(void 0);
26206
26393
  const [deleteEntityClicked, setDeleteEntityClicked] = React__default.useState(void 0);
26207
26394
  const [lastDeleteTimestamp, setLastDeleteTimestamp] = React__default.useState(0);
@@ -26219,7 +26406,7 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26219
26406
  }, [highlightedEntity]);
26220
26407
  const checkInlineEditing = useCallback((entity) => {
26221
26408
  const collection_0 = collectionRef.current;
26222
- if (!canEditEntity(collection_0, authController, fullPath, entity ?? null)) {
26409
+ if (!canEditEntity(collection_0, authController, fullPath, entity ?? null, pathSegments)) {
26223
26410
  return false;
26224
26411
  }
26225
26412
  return collection_0.inlineEditing === void 0 || collection_0.inlineEditing;
@@ -26309,10 +26496,12 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26309
26496
  if (collection_1) {
26310
26497
  addRecentId(collection_1.id, clickedEntity.id);
26311
26498
  }
26312
- const path = collection_1?.collectionGroup ? clickedEntity.path : fullPath ?? clickedEntity.path;
26499
+ const isCollectionGroup = Boolean(collection_1?.collectionGroup);
26500
+ const path = isCollectionGroup ? clickedEntity.path : fullPath ?? clickedEntity.path;
26313
26501
  navigateToEntity({
26314
26502
  navigation,
26315
26503
  path,
26504
+ pathSegments: isCollectionGroup ? clickedEntity.pathSegments : pathSegments ?? clickedEntity.pathSegments,
26316
26505
  fullIdPath,
26317
26506
  sideEntityController,
26318
26507
  openEntityMode,
@@ -26400,13 +26589,13 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26400
26589
  });
26401
26590
  }
26402
26591
  }, [setViewMode, userConfigPersistence, onCollectionModifiedForUser, fullPath, analyticsController, viewMode]);
26403
- const createEnabled = canCreateEntity(collection, authController, fullPath, null);
26592
+ const createEnabled = canCreateEntity(collection, authController, fullPath, null, pathSegments);
26404
26593
  const uniqueFieldValidator = useCallback(({
26405
26594
  name,
26406
26595
  value,
26407
26596
  property,
26408
26597
  entityId
26409
- }) => dataSource.checkUniqueField(fullPath, name, value, entityId, collection), [fullPath]);
26598
+ }) => dataSource.checkUniqueField(fullPath, name, value, entityId, collection, pathSegments), [fullPath, pathSegments]);
26410
26599
  const onValueChange = ({
26411
26600
  value: value_0,
26412
26601
  propertyKey,
@@ -26419,6 +26608,8 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26419
26608
  }, propertyKey, value_0);
26420
26609
  const saveProps = {
26421
26610
  path: entity_1.path ?? fullPath,
26611
+ // Paired with the `path` above: the row's segments describe the row's path.
26612
+ pathSegments: entity_1.path ? entity_1.pathSegments : pathSegments,
26422
26613
  entityId: entity_1.id,
26423
26614
  values: updatedValues,
26424
26615
  previousValues: entity_1.values,
@@ -26446,7 +26637,7 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26446
26637
  }
26447
26638
  });
26448
26639
  };
26449
- const resolvedFullPath = navigation.resolveIdsFrom(fullPath);
26640
+ const resolvedFullPath = navigation.resolveIdsFrom(fullPath, pathSegments);
26450
26641
  const resolvedCollection = useMemo(() => resolveCollection({
26451
26642
  collection,
26452
26643
  path: fullPath,
@@ -26575,9 +26766,9 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26575
26766
  Builder: ({
26576
26767
  entity: entity_4
26577
26768
  }) => {
26578
- const collectionsWithPath = navigation.getParentReferencesFromPath(entity_4.path);
26769
+ const collectionsWithPath = navigation.getParentReferencesFromPath(entity_4.path, entity_4.pathSegments);
26579
26770
  return /* @__PURE__ */ jsx("div", { className: "flex flex-col gap-2 w-full", children: collectionsWithPath.map((reference) => {
26580
- return /* @__PURE__ */ jsx(ReferencePreview, { reference, size: "small" }, reference.path + "/" + reference.id);
26771
+ return /* @__PURE__ */ jsx(ReferencePreview, { reference, size: "small" }, entityCacheKey(reference.path, reference.id));
26581
26772
  }) });
26582
26773
  }
26583
26774
  }] : [];
@@ -26591,7 +26782,7 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26591
26782
  entity: entity_5,
26592
26783
  customEntityActions
26593
26784
  }) => {
26594
- const deleteEnabled = entity_5 ? canDeleteEntity(collection, authController, fullPath, entity_5) : true;
26785
+ const deleteEnabled = entity_5 ? canDeleteEntity(collection, authController, fullPath, entity_5, entity_5.pathSegments ?? pathSegments) : true;
26595
26786
  const actions = [{
26596
26787
  ...editEntityAction,
26597
26788
  name: t("edit")
@@ -26656,6 +26847,7 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26656
26847
  onTextSearchClick,
26657
26848
  textSearchEnabled
26658
26849
  } = useTableSearchHelper({
26850
+ pathSegments,
26659
26851
  collection,
26660
26852
  fullPath: resolvedFullPath,
26661
26853
  parentCollectionIds,
@@ -26679,7 +26871,7 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26679
26871
  }, [tableController.dataLoadingError, customizationController.plugins, fullPath, collection, parentCollectionIds]);
26680
26872
  return /* @__PURE__ */ jsxs("div", { className: cls("overflow-hidden h-full w-full rounded-md flex flex-col", className), ref: containerRef, children: [
26681
26873
  countFetcher,
26682
- /* @__PURE__ */ jsx(CollectionTableToolbar, { loading: tableController.dataLoading, onTextSearch: textSearchEnabled && textSearchInitialised ? tableController.setSearchString : void 0, onTextSearchClick: textSearchEnabled && !textSearchInitialised ? onTextSearchClick : void 0, initialSearchString: tableController.searchString, textSearchLoading, viewModeToggle: viewModeToggleElement, actionsStart: /* @__PURE__ */ jsx(EntityCollectionViewStartActions, { parentCollectionIds: parentCollectionIds ?? [], collection, tableController, path: fullPath, relativePath: collection.path, selectionController: usedSelectionController, collectionEntitiesCount: docsCount, resolvedProperties: resolvedCollection.properties }), actions: /* @__PURE__ */ jsx(EntityCollectionViewActions, { parentCollectionIds: parentCollectionIds ?? [], collection, tableController, onMultipleDeleteClick, onNewClick, path: fullPath, relativePath: collection.path, selectionController: usedSelectionController, selectionEnabled, collectionEntitiesCount: docsCount }) }),
26874
+ /* @__PURE__ */ jsx(CollectionTableToolbar, { loading: tableController.dataLoading, onTextSearch: textSearchEnabled && textSearchInitialised ? tableController.setSearchString : void 0, onTextSearchClick: textSearchEnabled && !textSearchInitialised ? onTextSearchClick : void 0, initialSearchString: tableController.searchString, textSearchLoading, viewModeToggle: viewModeToggleElement, actionsStart: /* @__PURE__ */ jsx(EntityCollectionViewStartActions, { parentCollectionIds: parentCollectionIds ?? [], collection, tableController, path: fullPath, pathSegments, relativePath: collection.path, selectionController: usedSelectionController, collectionEntitiesCount: docsCount, resolvedProperties: resolvedCollection.properties }), actions: /* @__PURE__ */ jsx(EntityCollectionViewActions, { parentCollectionIds: parentCollectionIds ?? [], collection, tableController, onMultipleDeleteClick, onNewClick, path: fullPath, pathSegments, relativePath: collection.path, selectionController: usedSelectionController, selectionEnabled, collectionEntitiesCount: docsCount }) }),
26683
26875
  tableController.dataLoadingError ? pluginErrorView ?? /* @__PURE__ */ jsx(CollectionDataErrorBanner, { error: tableController.dataLoadingError }) : viewMode === "kanban" && enabledViews.includes("kanban") ? /* @__PURE__ */ jsx(EntityCollectionBoardView, { collection, tableController, fullPath, pathSegments, parentCollectionIds, columnProperty: selectedKanbanProperty, onEntityClick, selectionController: usedSelectionController, selectionEnabled, highlightedEntities: highlightedEntity ? [highlightedEntity] : [], deletedEntities, emptyComponent: canCreateEntities && tableController.filterValues === void 0 && tableController.sortBy === void 0 ? /* @__PURE__ */ jsxs("div", { className: "flex flex-col items-center justify-center", children: [
26684
26876
  /* @__PURE__ */ jsx(Typography, { variant: "subtitle2", children: t("so_empty") }),
26685
26877
  /* @__PURE__ */ jsxs(Button, { onClick: onNewClick, className: "mt-4", children: [
@@ -26698,7 +26890,7 @@ const EntityCollectionView$1 = React__default.memo(function EntityCollectionView
26698
26890
  /* @__PURE__ */ jsx(AddIcon, {}),
26699
26891
  t("create_your_first_entry")
26700
26892
  ] })
26701
- ] }) : /* @__PURE__ */ jsx(Typography, { variant: "label", children: t("no_results_filter_sort") }), hoverRow, inlineEditing: checkInlineEditing(), AdditionalHeaderWidget: buildAdditionalHeaderWidget, AddColumnComponent: addColumnComponentInternal, getIdColumnWidth, additionalIDHeaderWidget: /* @__PURE__ */ jsx(EntityIdHeaderWidget, { path: fullPath, fullIdPath: fullIdPath ?? fullPath, collection }), openEntityMode, onColumnsOrderChange: (newColumns) => {
26893
+ ] }) : /* @__PURE__ */ jsx(Typography, { variant: "label", children: t("no_results_filter_sort") }), hoverRow, inlineEditing: checkInlineEditing(), AdditionalHeaderWidget: buildAdditionalHeaderWidget, AddColumnComponent: addColumnComponentInternal, getIdColumnWidth, additionalIDHeaderWidget: /* @__PURE__ */ jsx(EntityIdHeaderWidget, { path: fullPath, pathSegments, fullIdPath: fullIdPath ?? fullPath, collection }), openEntityMode, onColumnsOrderChange: (newColumns) => {
26702
26894
  const seenKeys = /* @__PURE__ */ new Set();
26703
26895
  const newPropertiesOrder = newColumns.filter((col) => !col.frozen && getPropertyInPath(collection.properties, col.key)).map((col_0) => col_0.key).filter((key_1) => {
26704
26896
  if (seenKeys.has(key_1)) return false;
@@ -26737,8 +26929,8 @@ function EntitiesCount({
26737
26929
  const [error, setError] = useState(void 0);
26738
26930
  const sortByProperty = sortBy ? sortBy[0] : void 0;
26739
26931
  const currentSort = sortBy ? sortBy[1] : void 0;
26740
- const resolvedPath = useMemo(() => navigation.resolveIdsFrom(fullPath), [fullPath, navigation.resolveIdsFrom]);
26741
- const resolvedPathSegments = pathSegments;
26932
+ const resolvedPath = useMemo(() => navigation.resolveIdsFrom(fullPath, pathSegments), [fullPath, pathSegments, navigation.resolveIdsFrom]);
26933
+ const resolvedPathSegments = useMemo(() => pathSegments ? navigation.resolveSegmentsFrom?.(pathSegments) ?? pathSegments : void 0, [pathSegments, navigation.resolveSegmentsFrom]);
26742
26934
  useEffect(() => {
26743
26935
  if (dataSource.countEntities) dataSource.countEntities({
26744
26936
  path: resolvedPath,
@@ -26778,10 +26970,11 @@ function buildPropertyWidthOverwrite(key, width) {
26778
26970
  };
26779
26971
  }
26780
26972
  function EntityIdHeaderWidget(t0) {
26781
- const $ = c(48);
26973
+ const $ = c(50);
26782
26974
  const {
26783
26975
  collection,
26784
26976
  path,
26977
+ pathSegments,
26785
26978
  fullIdPath
26786
26979
  } = t0;
26787
26980
  const navigation = useNavigationController();
@@ -26822,7 +27015,7 @@ function EntityIdHeaderWidget(t0) {
26822
27015
  t4 = $[6];
26823
27016
  }
26824
27017
  let t5;
26825
- if ($[7] !== collection || $[8] !== fullIdPath || $[9] !== navigation || $[10] !== openEntityMode || $[11] !== path || $[12] !== searchString || $[13] !== sideEntityController) {
27018
+ if ($[7] !== collection || $[8] !== fullIdPath || $[9] !== navigation || $[10] !== openEntityMode || $[11] !== path || $[12] !== pathSegments || $[13] !== searchString || $[14] !== sideEntityController) {
26826
27019
  t5 = (e) => {
26827
27020
  e.preventDefault();
26828
27021
  if (!searchString) {
@@ -26836,6 +27029,7 @@ function EntityIdHeaderWidget(t0) {
26836
27029
  collection,
26837
27030
  entityId,
26838
27031
  path,
27032
+ pathSegments,
26839
27033
  fullIdPath,
26840
27034
  sideEntityController,
26841
27035
  navigation
@@ -26846,130 +27040,133 @@ function EntityIdHeaderWidget(t0) {
26846
27040
  $[9] = navigation;
26847
27041
  $[10] = openEntityMode;
26848
27042
  $[11] = path;
26849
- $[12] = searchString;
26850
- $[13] = sideEntityController;
26851
- $[14] = t5;
27043
+ $[12] = pathSegments;
27044
+ $[13] = searchString;
27045
+ $[14] = sideEntityController;
27046
+ $[15] = t5;
26852
27047
  } else {
26853
- t5 = $[14];
27048
+ t5 = $[15];
26854
27049
  }
26855
27050
  let t6;
26856
- if ($[15] !== t) {
27051
+ if ($[16] !== t) {
26857
27052
  t6 = t("find_entity_by_id");
26858
- $[15] = t;
26859
- $[16] = t6;
27053
+ $[16] = t;
27054
+ $[17] = t6;
26860
27055
  } else {
26861
- t6 = $[16];
27056
+ t6 = $[17];
26862
27057
  }
26863
27058
  let t7;
26864
- if ($[17] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
27059
+ if ($[18] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
26865
27060
  t7 = (e_0) => {
26866
27061
  setSearchString(e_0.target.value);
26867
27062
  };
26868
- $[17] = t7;
27063
+ $[18] = t7;
26869
27064
  } else {
26870
- t7 = $[17];
27065
+ t7 = $[18];
26871
27066
  }
26872
27067
  let t8;
26873
- if ($[18] !== openPopup || $[19] !== searchString || $[20] !== t6) {
27068
+ if ($[19] !== openPopup || $[20] !== searchString || $[21] !== t6) {
26874
27069
  t8 = /* @__PURE__ */ jsx("input", { autoFocus: openPopup, placeholder: t6, onChange: t7, value: searchString, className: "rounded-lg bg-white dark:bg-surface-800 flex-grow bg-transparent outline-none p-2 " + focusedDisabled });
26875
- $[18] = openPopup;
26876
- $[19] = searchString;
26877
- $[20] = t6;
26878
- $[21] = t8;
27070
+ $[19] = openPopup;
27071
+ $[20] = searchString;
27072
+ $[21] = t6;
27073
+ $[22] = t8;
26879
27074
  } else {
26880
- t8 = $[21];
27075
+ t8 = $[22];
26881
27076
  }
26882
27077
  const t9 = !searchString.trim();
26883
27078
  let t10;
26884
- if ($[22] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
27079
+ if ($[23] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
26885
27080
  t10 = /* @__PURE__ */ jsx(KeyboardTabIcon, {});
26886
- $[22] = t10;
27081
+ $[23] = t10;
26887
27082
  } else {
26888
- t10 = $[22];
27083
+ t10 = $[23];
26889
27084
  }
26890
27085
  let t11;
26891
- if ($[23] !== t9) {
27086
+ if ($[24] !== t9) {
26892
27087
  t11 = /* @__PURE__ */ jsx(Button, { variant: "text", disabled: t9, type: "submit", children: t10 });
26893
- $[23] = t9;
26894
- $[24] = t11;
27088
+ $[24] = t9;
27089
+ $[25] = t11;
26895
27090
  } else {
26896
- t11 = $[24];
27091
+ t11 = $[25];
26897
27092
  }
26898
27093
  let t12;
26899
- if ($[25] !== t11 || $[26] !== t8) {
27094
+ if ($[26] !== t11 || $[27] !== t8) {
26900
27095
  t12 = /* @__PURE__ */ jsxs("div", { className: "flex p-2 w-full gap-2", children: [
26901
27096
  t8,
26902
27097
  t11
26903
27098
  ] });
26904
- $[25] = t11;
26905
- $[26] = t8;
26906
- $[27] = t12;
27099
+ $[26] = t11;
27100
+ $[27] = t8;
27101
+ $[28] = t12;
26907
27102
  } else {
26908
- t12 = $[27];
27103
+ t12 = $[28];
26909
27104
  }
26910
27105
  let t13;
26911
- if ($[28] !== t12 || $[29] !== t5) {
27106
+ if ($[29] !== t12 || $[30] !== t5) {
26912
27107
  t13 = /* @__PURE__ */ jsx("form", { noValidate: true, onSubmit: t5, className: "w-96 max-w-full", children: t12 });
26913
- $[28] = t12;
26914
- $[29] = t5;
26915
- $[30] = t13;
27108
+ $[29] = t12;
27109
+ $[30] = t5;
27110
+ $[31] = t13;
26916
27111
  } else {
26917
- t13 = $[30];
27112
+ t13 = $[31];
26918
27113
  }
26919
27114
  let t14;
26920
- if ($[31] !== collection || $[32] !== fullIdPath || $[33] !== navigation || $[34] !== openEntityMode || $[35] !== path || $[36] !== recentIds || $[37] !== sideEntityController) {
26921
- t14 = recentIds && recentIds.length > 0 && /* @__PURE__ */ jsx("div", { className: "flex flex-col gap-2 p-2", children: recentIds.map((id) => /* @__PURE__ */ jsx(ReferencePreview, { reference: new EntityReference(id, path), hover: true, onClick: () => {
27115
+ if ($[32] !== collection || $[33] !== fullIdPath || $[34] !== navigation || $[35] !== openEntityMode || $[36] !== path || $[37] !== pathSegments || $[38] !== recentIds || $[39] !== sideEntityController) {
27116
+ t14 = recentIds && recentIds.length > 0 && /* @__PURE__ */ jsx("div", { className: "flex flex-col gap-2 p-2", children: recentIds.map((id) => /* @__PURE__ */ jsx(ReferencePreview, { reference: new EntityReference(id, path, void 0, pathSegments), hover: true, onClick: () => {
26922
27117
  setOpenPopup(false);
26923
27118
  navigateToEntity({
26924
27119
  openEntityMode,
26925
27120
  collection,
26926
27121
  entityId: id,
26927
27122
  path,
27123
+ pathSegments,
26928
27124
  fullIdPath,
26929
27125
  sideEntityController,
26930
27126
  navigation
26931
27127
  });
26932
27128
  }, includeEntityLink: false, size: "small" }, id)) });
26933
- $[31] = collection;
26934
- $[32] = fullIdPath;
26935
- $[33] = navigation;
26936
- $[34] = openEntityMode;
26937
- $[35] = path;
26938
- $[36] = recentIds;
26939
- $[37] = sideEntityController;
26940
- $[38] = t14;
27129
+ $[32] = collection;
27130
+ $[33] = fullIdPath;
27131
+ $[34] = navigation;
27132
+ $[35] = openEntityMode;
27133
+ $[36] = path;
27134
+ $[37] = pathSegments;
27135
+ $[38] = recentIds;
27136
+ $[39] = sideEntityController;
27137
+ $[40] = t14;
26941
27138
  } else {
26942
- t14 = $[38];
27139
+ t14 = $[40];
26943
27140
  }
26944
27141
  let t15;
26945
- if ($[39] !== t13 || $[40] !== t14) {
27142
+ if ($[41] !== t13 || $[42] !== t14) {
26946
27143
  t15 = /* @__PURE__ */ jsxs("div", { className: t4, children: [
26947
27144
  t13,
26948
27145
  t14
26949
27146
  ] });
26950
- $[39] = t13;
26951
- $[40] = t14;
26952
- $[41] = t15;
27147
+ $[41] = t13;
27148
+ $[42] = t14;
27149
+ $[43] = t15;
26953
27150
  } else {
26954
- t15 = $[41];
27151
+ t15 = $[43];
26955
27152
  }
26956
27153
  let t16;
26957
- if ($[42] !== openPopup || $[43] !== t15) {
27154
+ if ($[44] !== openPopup || $[45] !== t15) {
26958
27155
  t16 = /* @__PURE__ */ jsx(Popover, { open: openPopup, onOpenChange: setOpenPopup, sideOffset: 0, align: "start", alignOffset: -117, trigger: t3, children: t15 });
26959
- $[42] = openPopup;
26960
- $[43] = t15;
26961
- $[44] = t16;
27156
+ $[44] = openPopup;
27157
+ $[45] = t15;
27158
+ $[46] = t16;
26962
27159
  } else {
26963
- t16 = $[44];
27160
+ t16 = $[46];
26964
27161
  }
26965
27162
  let t17;
26966
- if ($[45] !== t16 || $[46] !== t2) {
27163
+ if ($[47] !== t16 || $[48] !== t2) {
26967
27164
  t17 = /* @__PURE__ */ jsx(Tooltip, { title: t2, asChild: false, children: t16 });
26968
- $[45] = t16;
26969
- $[46] = t2;
26970
- $[47] = t17;
27165
+ $[47] = t16;
27166
+ $[48] = t2;
27167
+ $[49] = t17;
26971
27168
  } else {
26972
- t17 = $[47];
27169
+ t17 = $[49];
26973
27170
  }
26974
27171
  return t17;
26975
27172
  }
@@ -28537,8 +28734,12 @@ function getParentReferencesFromPath(props) {
28537
28734
  path,
28538
28735
  collections = [],
28539
28736
  currentFullPath,
28540
- currentPathSegments = []
28737
+ currentPathSegments = [],
28738
+ pathSegments
28541
28739
  } = props;
28740
+ if (pathSegments) {
28741
+ return getParentReferencesFromPathSegments(pathSegments, collections);
28742
+ }
28542
28743
  const subpaths = removeInitialAndTrailingSlashes(path).split("/");
28543
28744
  const subpathCombinations = getCollectionPathsCombinations(subpaths);
28544
28745
  const result = [];
@@ -28575,6 +28776,9 @@ function getParentReferencesFromPath(props) {
28575
28776
  }
28576
28777
  return result;
28577
28778
  }
28779
+ function getParentReferencesFromPathSegments(pathSegments, collections) {
28780
+ return walkPathSegments(pathSegments, collections).steps.filter((step) => step.entityId !== void 0).map((step) => new EntityReference(step.entityId, step.collectionPath, void 0, step.collectionSegments));
28781
+ }
28578
28782
  const DEFAULT_BASE_PATH = "/";
28579
28783
  const DEFAULT_COLLECTION_PATH = "/c";
28580
28784
  const NAVIGATION_ADMIN_GROUP_NAME = "Admin";
@@ -28779,10 +28983,10 @@ function useBuildNavigationController(props) {
28779
28983
  useEffect(() => {
28780
28984
  refreshNavigation();
28781
28985
  }, [refreshNavigation]);
28782
- const getCollection = useCallback((idOrPath, includeUserOverride = false) => {
28986
+ const getCollection = useCallback((idOrPath, includeUserOverride = false, pathSegments) => {
28783
28987
  const collections_0 = collectionsRef.current;
28784
28988
  if (!collections_0) return void 0;
28785
- const baseCollection = getCollectionByPathOrId(removeInitialAndTrailingSlashes(idOrPath), collections_0);
28989
+ const baseCollection = getCollectionByPathOrId(removeInitialAndTrailingSlashes(idOrPath), collections_0, pathSegments);
28786
28990
  const userOverride = includeUserOverride ? userConfigPersistence?.getCollectionConfig(idOrPath) : void 0;
28787
28991
  let overriddenCollection = baseCollection;
28788
28992
  if (baseCollection && userOverride) {
@@ -28817,16 +29021,16 @@ function useBuildNavigationController(props) {
28817
29021
  if (!collection_0) return void 0;
28818
29022
  return collection_0;
28819
29023
  }, []);
28820
- const getCollectionFromPaths = useCallback((pathSegments) => {
29024
+ const getCollectionFromPaths = useCallback((pathSegments_0) => {
28821
29025
  const collections_2 = collectionsRef.current;
28822
29026
  if (collections_2 === void 0) throw Error("getCollectionFromPaths: Collections have not been initialised yet");
28823
29027
  let currentCollections = [...collections_2 ?? []];
28824
- for (let i = 0; i < pathSegments.length; i++) {
28825
- const pathSegment = pathSegments[i];
29028
+ for (let i = 0; i < pathSegments_0.length; i++) {
29029
+ const pathSegment = pathSegments_0[i];
28826
29030
  const collection_1 = currentCollections.find((c_0) => c_0.id === pathSegment || c_0.path === pathSegment);
28827
29031
  if (!collection_1) return void 0;
28828
29032
  currentCollections = collection_1.subcollections;
28829
- if (i === pathSegments.length - 1) return collection_1;
29033
+ if (i === pathSegments_0.length - 1) return collection_1;
28830
29034
  }
28831
29035
  return void 0;
28832
29036
  }, []);
@@ -28851,33 +29055,37 @@ function useBuildNavigationController(props) {
28851
29055
  if (cleanPath_0.startsWith(fullCollectionPath)) return cleanPath_0.replace(fullCollectionPath, "");
28852
29056
  throw Error("Expected path starting with " + fullCollectionPath);
28853
29057
  }, [fullCollectionPath]);
28854
- const resolveIdsFrom = useCallback((path_3) => {
29058
+ const resolveIdsFrom = useCallback((path_3, pathSegments_1) => {
28855
29059
  const collections_4 = collectionsRef.current ?? [];
28856
- return resolveCollectionPathIds(path_3, collections_4);
29060
+ return resolveCollectionPathIds(path_3, collections_4, pathSegments_1);
28857
29061
  }, []);
28858
- const getAllParentReferencesForPath = useCallback((path_4) => {
29062
+ const resolveSegmentsFrom = useCallback((pathSegments_2) => {
28859
29063
  const collections_5 = collectionsRef.current ?? [];
29064
+ return resolveCollectionPathSegments(pathSegments_2, collections_5);
29065
+ }, []);
29066
+ const getAllParentReferencesForPath = useCallback((path_4, pathSegments_3) => {
29067
+ const collections_6 = collectionsRef.current ?? [];
28860
29068
  return getParentReferencesFromPath({
28861
29069
  path: path_4,
28862
- collections: collections_5
29070
+ pathSegments: pathSegments_3,
29071
+ collections: collections_6
28863
29072
  });
28864
29073
  }, []);
28865
- const getParentCollectionIds = useCallback((path_5) => {
28866
- const strings = path_5.split("/");
28867
- const oddPathSegments = strings.filter((_, i_1) => i_1 % 2 === 0);
29074
+ const getParentCollectionIds = useCallback((path_5, pathSegments_4) => {
29075
+ const oddPathSegments = pathSegments_4 ? collectionSegmentsFrom(pathSegments_4) : fullPathToCollectionSegments(path_5);
28868
29076
  oddPathSegments.pop();
28869
29077
  const result_0 = [];
28870
- for (let i_2 = 1; i_2 <= oddPathSegments.length; i_2++) {
28871
- result_0.push(oddPathSegments.slice(0, i_2));
29078
+ for (let i_1 = 1; i_1 <= oddPathSegments.length; i_1++) {
29079
+ result_0.push(oddPathSegments.slice(0, i_1));
28872
29080
  }
28873
29081
  return result_0.map((r) => getCollectionFromPaths(r)?.id).filter(Boolean);
28874
29082
  }, [getAllParentReferencesForPath]);
28875
29083
  const convertIdsToPaths = useCallback((ids_0) => {
28876
- const collections_6 = collectionsRef.current;
28877
- let currentCollections_1 = collections_6;
29084
+ const collections_7 = collectionsRef.current;
29085
+ let currentCollections_1 = collections_7;
28878
29086
  const paths = [];
28879
- for (let i_3 = 0; i_3 < ids_0.length; i_3++) {
28880
- const id_1 = ids_0[i_3];
29087
+ for (let i_2 = 0; i_2 < ids_0.length; i_2++) {
29088
+ const id_1 = ids_0[i_2];
28881
29089
  const collection_3 = currentCollections_1.find((c_2) => c_2.id === id_1);
28882
29090
  if (!collection_3) throw Error(`Collection with id ${id_1} not found`);
28883
29091
  paths.push(collection_3.path);
@@ -28903,6 +29111,7 @@ function useBuildNavigationController(props) {
28903
29111
  urlPathToDataPath,
28904
29112
  buildUrlCollectionPath,
28905
29113
  resolveIdsFrom,
29114
+ resolveSegmentsFrom,
28906
29115
  topLevelNavigation,
28907
29116
  refreshNavigation,
28908
29117
  getParentReferencesFromPath: getAllParentReferencesForPath,
@@ -29660,6 +29869,7 @@ function EntitySidePanel(props) {
29660
29869
  if (params.status !== "existing") {
29661
29870
  sideEntityController.replace({
29662
29871
  path: params.path,
29872
+ pathSegments: params.pathSegments ?? pathSegments,
29663
29873
  entityId: params.entityId,
29664
29874
  fullIdPath: props.fullIdPath,
29665
29875
  selectedTab: params.selectedTab,
@@ -29673,9 +29883,9 @@ function EntitySidePanel(props) {
29673
29883
  }
29674
29884
  };
29675
29885
  const parentCollectionIds = useMemo(() => {
29676
- return navigationController.getParentCollectionIds(path);
29886
+ return navigationController.getParentCollectionIds(path, pathSegments);
29677
29887
  }, [navigationController, path]);
29678
- const collection = props.collection ?? navigationController.getCollection(fullIdPath ?? path);
29888
+ const collection = props.collection ?? navigationController.getCollection(fullIdPath ?? path, false, pathSegments);
29679
29889
  useEffect(() => {
29680
29890
  function beforeunload(e) {
29681
29891
  if (blocked && collection) {
@@ -29703,7 +29913,7 @@ function EntitySidePanel(props) {
29703
29913
  }) => /* @__PURE__ */ jsxs(Fragment, { children: [
29704
29914
  /* @__PURE__ */ jsx(IconButton, { className: "self-center", size: "smallest", onClick: onClose, children: /* @__PURE__ */ jsx(CloseIcon, { size: "smallest" }) }),
29705
29915
  allowFullScreen && /* @__PURE__ */ jsx(IconButton, { className: "self-center", size: "smallest", onClick: () => {
29706
- const key = status === "new" || status === "copy" ? path + "#new" : path + "/" + entityId;
29916
+ const key = status === "new" || status === "copy" ? path + "#new" : entityCacheKey(path, entityId);
29707
29917
  saveEntityToMemoryCache(key, values);
29708
29918
  if (entityId) navigate(location.pathname + location.search);
29709
29919
  else navigate(location.pathname + location.search + "#new");
@@ -29715,6 +29925,7 @@ function EntitySidePanel(props) {
29715
29925
  }) => {
29716
29926
  sideEntityController.replace({
29717
29927
  path,
29928
+ pathSegments,
29718
29929
  entityId: entityId_0,
29719
29930
  fullIdPath: props.fullIdPath,
29720
29931
  selectedTab,
@@ -29830,6 +30041,7 @@ function SideDialogView({
29830
30041
  function EntityEditViewFormActions({
29831
30042
  collection,
29832
30043
  path,
30044
+ pathSegments,
29833
30045
  entity,
29834
30046
  layout,
29835
30047
  savingError,
@@ -29852,8 +30064,8 @@ function EntityEditViewFormActions({
29852
30064
  } = useTranslation();
29853
30065
  const entityActions = useMemo(() => {
29854
30066
  const customEntityActions = (collection.entityActions ?? []).map((action) => resolveEntityAction(action, customizationController.entityActions)).filter(Boolean);
29855
- const createEnabled = canCreateEntity(collection, authController, path, null);
29856
- const deleteEnabled = entity ? canDeleteEntity(collection, authController, path, entity) : false;
30067
+ const createEnabled = canCreateEntity(collection, authController, path, null, pathSegments);
30068
+ const deleteEnabled = entity ? canDeleteEntity(collection, authController, path, entity, entity.pathSegments ?? pathSegments) : false;
29857
30069
  const actions = [];
29858
30070
  if (createEnabled) actions.push(copyEntityAction);
29859
30071
  if (deleteEnabled) actions.push(deleteEntityAction);
@@ -30209,7 +30421,7 @@ function EntityEditView$1({
30209
30421
  databaseId: props.databaseId,
30210
30422
  useCache: false
30211
30423
  });
30212
- const initialDirtyValues = entityId ? getEntityFromMemoryCache(props.path + "/" + entityId) : getEntityFromMemoryCache(props.path + "#new");
30424
+ const initialDirtyValues = entityId ? getEntityFromMemoryCache(entityCacheKey(props.path, entityId)) : getEntityFromMemoryCache(props.path + "#new");
30213
30425
  const authController = useAuthController();
30214
30426
  const initialStatus = props.copy ? "copy" : entityId ? "existing" : "new";
30215
30427
  const [status, setStatus] = useState(initialStatus);
@@ -30217,7 +30429,7 @@ function EntityEditView$1({
30217
30429
  if (status === "new" || status === "copy") {
30218
30430
  return true;
30219
30431
  } else {
30220
- return entity ? canEditEntity(props.collection, authController, props.path, entity ?? null) : void 0;
30432
+ return entity ? canEditEntity(props.collection, authController, props.path, entity ?? null, props.pathSegments) : void 0;
30221
30433
  }
30222
30434
  }, [authController, entity, status]);
30223
30435
  if (dataLoading && !initialDirtyValues || (!entity || canEdit === void 0) && (status === "existing" || status === "copy")) {
@@ -30267,6 +30479,7 @@ function EntityEditViewInner({
30267
30479
  entityId,
30268
30480
  parentCollectionIds,
30269
30481
  path,
30482
+ pathSegments,
30270
30483
  status,
30271
30484
  collection,
30272
30485
  context,
@@ -30365,7 +30578,7 @@ function EntityEditViewInner({
30365
30578
  const subcollectionId = subcollection.id ?? subcollection.path;
30366
30579
  const newFullPath = usedEntity ? `${path}/${usedEntity?.id}/${removeInitialAndTrailingSlashes(subcollection.path)}` : void 0;
30367
30580
  const newFullIdPath = fullIdPath && usedEntity ? `${fullIdPath}/${encodeEntityId(usedEntity.id)}/${removeInitialAndTrailingSlashes(subcollectionId)}` : void 0;
30368
- const newPathSegments = usedEntity && pathSegments ? [...pathSegments, usedEntity.id, ...removeInitialAndTrailingSlashes(subcollection.path).split("/")] : void 0;
30581
+ const newPathSegments = buildSubcollectionPathSegments(pathSegments, usedEntity?.id, subcollection.path);
30369
30582
  if (selectedTab !== subcollectionId) return null;
30370
30583
  return /* @__PURE__ */ jsxs("div", { className: "relative flex-1 h-full overflow-auto w-full", role: "tabpanel", children: [
30371
30584
  globalLoading && /* @__PURE__ */ jsx(CircularProgressCenter, {}),
@@ -30659,19 +30872,21 @@ function buildSidePanelsFromUrl(path, collections, newFlag) {
30659
30872
  return sidePanel ? [sidePanel] : [];
30660
30873
  }
30661
30874
  const propsToSidePanel = (props, buildUrlCollectionPath, resolveIdsFrom, smallLayout, customizationController, authController, locationSearch) => {
30662
- const collectionPath = removeInitialAndTrailingSlashes(props.path);
30663
- const urlPath = props.entityId ? buildUrlCollectionPath(`${collectionPath}/${encodeEntityId(props.entityId)}${props.selectedTab ? "/" + props.selectedTab : ""}${locationSearch}#${SIDE_URL_HASH}`) : buildUrlCollectionPath(`${collectionPath}${locationSearch}#${NEW_URL_HASH}`);
30875
+ const urlChain = removeInitialAndTrailingSlashes(props.fullIdPath ?? props.path);
30876
+ const urlPath = props.entityId ? buildUrlCollectionPath(`${urlChain}/${encodeEntityId(props.entityId)}${props.selectedTab ? "/" + props.selectedTab : ""}${locationSearch}#${SIDE_URL_HASH}`) : buildUrlCollectionPath(`${urlChain}${locationSearch}#${NEW_URL_HASH}`);
30664
30877
  const resolvedPanelProps = {
30665
30878
  ...props,
30666
30879
  formProps: props.formProps
30667
30880
  };
30668
30881
  const entityViewWidth = getEntityViewWidth(props, smallLayout, customizationController, authController);
30669
30882
  return {
30670
- key: `${props.path}/${props.entityId}`,
30883
+ // Built from the escaped chain so that two different chains which happen to flatten
30884
+ // to the same raw string are still two different panels.
30885
+ key: `${urlChain}/${props.entityId ? encodeEntityId(props.entityId) : ""}`,
30671
30886
  component: void 0,
30672
30887
  // Lazy render in SideDialogs for better performance
30673
30888
  urlPath,
30674
- parentUrlPath: buildUrlCollectionPath(collectionPath),
30889
+ parentUrlPath: buildUrlCollectionPath(urlChain),
30675
30890
  width: entityViewWidth,
30676
30891
  onClose: props.onClose,
30677
30892
  additional: resolvedPanelProps
@@ -30940,7 +31155,7 @@ function useBuildDataSource({
30940
31155
  onUpdate,
30941
31156
  onError
30942
31157
  }) => {
30943
- const collection_0 = collectionProp ?? navigationController.getCollection(path_0);
31158
+ const collection_0 = collectionProp ?? navigationController.getCollection(path_0, false, pathSegments_0);
30944
31159
  const usedDelegate_0 = collection_0?.overrides?.dataSourceDelegate ?? delegate;
30945
31160
  if (!usedDelegate_0.listenCollection) throw Error("useBuildDataSource delegate not initialised");
30946
31161
  return usedDelegate_0.listenCollection({
@@ -31026,7 +31241,7 @@ function useBuildDataSource({
31026
31241
  collection: collectionProp_0,
31027
31242
  status
31028
31243
  }) => {
31029
- const collection_3 = collectionProp_0 ?? navigationController.getCollection(path_3);
31244
+ const collection_3 = collectionProp_0 ?? navigationController.getCollection(path_3, false, pathSegments_3);
31030
31245
  const usedDelegate_3 = collection_3?.overrides?.dataSourceDelegate ?? delegate;
31031
31246
  const resolvedCollection = collection_3 ? resolveCollection({
31032
31247
  collection: collection_3,
@@ -31083,8 +31298,11 @@ function useBuildDataSource({
31083
31298
  status
31084
31299
  }).then((res) => {
31085
31300
  return {
31086
- id: res.id,
31087
- path: res.path,
31301
+ ...res,
31302
+ // A delegate that predates `pathSegments` returns none; the segments we
31303
+ // just saved with describe exactly this entity's collection, so they are
31304
+ // the authoritative answer rather than a guess.
31305
+ pathSegments: res.pathSegments ?? pathSegments_3,
31088
31306
  values: usedDelegate_3.delegateToCMSModel(finalValues)
31089
31307
  };
31090
31308
  });
@@ -31126,6 +31344,8 @@ function useBuildDataSource({
31126
31344
  const usedDelegate_6 = collection_6?.overrides?.dataSourceDelegate ?? delegate;
31127
31345
  return usedDelegate_6.generateEntityId(path_5, collection_6, pathSegments_6);
31128
31346
  }, [delegate.generateEntityId]),
31347
+ // Typed with the declared props rather than an inline duplicate: the duplicate is
31348
+ // free to drift from the interface, and a field it forgets is dropped in silence.
31129
31349
  countEntities: delegate.countEntities ? async ({
31130
31350
  path: path_6,
31131
31351
  pathSegments: pathSegments_7,
@@ -32652,7 +32872,7 @@ function FireCMSRoute() {
32652
32872
  let collection;
32653
32873
  collection = navigation.getCollectionById(navigationEntries[0].id);
32654
32874
  if (!collection) {
32655
- collection = navigation.getCollection(navigationEntries[0].path);
32875
+ collection = navigation.getCollection(navigationEntries[0].path, false, navigationEntries[0].pathSegments);
32656
32876
  }
32657
32877
  if (!collection) {
32658
32878
  t16 = null;
@@ -32763,7 +32983,7 @@ function FireCMSRoute() {
32763
32983
  const firstEntry = navigationEntries[0];
32764
32984
  collection_0 = navigation.getCollectionById(firstEntry.id);
32765
32985
  if (!collection_0) {
32766
- collection_0 = navigation.getCollection(firstEntry.path);
32986
+ collection_0 = navigation.getCollection(firstEntry.path, false, firstEntry.pathSegments);
32767
32987
  }
32768
32988
  if (!collection_0) {
32769
32989
  t16 = null;
@@ -32936,9 +33156,10 @@ function EntityFullScreenRoute({
32936
33156
  }
32937
33157
  const collection = isNew ? lastCollectionEntry.collection : lastEntityEntry.parentCollection;
32938
33158
  const fullIdPath = isNew ? lastCollectionEntry.fullPath : parentCollectionEntry?.fullPath ?? lastEntityEntry.fullPath;
32939
- const collectionPath = navigation.resolveIdsFrom(isNew ? lastCollectionEntry.path : lastEntityEntry.path);
33159
+ const pathSegments = isNew ? lastCollectionEntry.pathSegments : lastEntityEntry.pathSegments;
33160
+ const collectionPath = navigation.resolveIdsFrom(isNew ? lastCollectionEntry.path : lastEntityEntry.path, pathSegments);
32940
33161
  return /* @__PURE__ */ jsxs(Fragment, { children: [
32941
- /* @__PURE__ */ jsx(React__default.Suspense, { fallback: null, children: /* @__PURE__ */ jsx(EntityEditView, { entityId: isNew ? void 0 : entityId, fullIdPath, pathSegments: isNew ? lastCollectionEntry.pathSegments : lastEntityEntry.pathSegments, collection, layout: "full_screen", path: collectionPath, copy: isCopy, selectedTab: selectedTab ?? void 0, onValuesModified: (modified) => blocked.current = modified, onSaved: (params) => {
33162
+ /* @__PURE__ */ jsx(React__default.Suspense, { fallback: null, children: /* @__PURE__ */ jsx(EntityEditView, { entityId: isNew ? void 0 : entityId, fullIdPath, pathSegments, collection, layout: "full_screen", path: collectionPath, copy: isCopy, selectedTab: selectedTab ?? void 0, onValuesModified: (modified) => blocked.current = modified, onSaved: (params) => {
32942
33163
  const newEntityId = params.entityId;
32943
33164
  if (!newEntityId) return;
32944
33165
  navigate(buildEntityUrl(newEntityId, params.selectedTab), {
@@ -39030,12 +39251,27 @@ function FireCMSi18nProvider({
39030
39251
  translations,
39031
39252
  children
39032
39253
  }) {
39254
+ const parentI18n = useContext(I18nContext)?.i18n;
39255
+ const parentInstance = parentI18n?.hasResourceBundle?.("en", FIRECMS_NS) ? parentI18n : void 0;
39033
39256
  const i18nRef = useRef(null);
39034
39257
  const [ready, setReady] = React__default.useState(false);
39035
39258
  if (!i18nRef.current) {
39036
39259
  const instance = i18next.createInstance();
39037
39260
  const resources = buildResources(translations);
39038
- let initialLocale = locale;
39261
+ if (parentInstance) {
39262
+ const inherited = parentInstance.services?.resourceStore?.data ?? {};
39263
+ for (const [lang, namespaces] of Object.entries(inherited)) {
39264
+ const bundle = namespaces?.[FIRECMS_NS];
39265
+ if (!bundle) continue;
39266
+ resources[lang] = {
39267
+ [FIRECMS_NS]: {
39268
+ ...bundle,
39269
+ ...translations?.[lang] ?? {}
39270
+ }
39271
+ };
39272
+ }
39273
+ }
39274
+ let initialLocale = parentInstance?.language ?? locale;
39039
39275
  if (typeof window !== "undefined") {
39040
39276
  const stored = localStorage.getItem(FIRECMS_LOCALE_STORAGE_KEY);
39041
39277
  if (stored) initialLocale = stored;
@@ -39060,6 +39296,17 @@ function FireCMSi18nProvider({
39060
39296
  });
39061
39297
  i18nRef.current = instance;
39062
39298
  }
39299
+ useEffect(() => {
39300
+ if (!parentInstance || !i18nRef.current) return;
39301
+ const instance_0 = i18nRef.current;
39302
+ const follow = (lng_0) => {
39303
+ if (instance_0.language !== lng_0) instance_0.changeLanguage(lng_0);
39304
+ };
39305
+ parentInstance.on("languageChanged", follow);
39306
+ return () => {
39307
+ parentInstance.off("languageChanged", follow);
39308
+ };
39309
+ }, [parentInstance]);
39063
39310
  useEffect(() => {
39064
39311
  if (i18nRef.current && i18nRef.current.language !== locale) {
39065
39312
  const hasUserPreference = typeof window !== "undefined" && Boolean(localStorage.getItem(FIRECMS_LOCALE_STORAGE_KEY));
@@ -39071,11 +39318,11 @@ function FireCMSi18nProvider({
39071
39318
  useEffect(() => {
39072
39319
  if (!i18nRef.current) return;
39073
39320
  const resources_0 = buildResources(translations);
39074
- for (const [lang, bundle] of Object.entries(resources_0)) {
39321
+ for (const [lang_0, bundle_0] of Object.entries(resources_0)) {
39075
39322
  i18nRef.current.addResourceBundle(
39076
- lang,
39323
+ lang_0,
39077
39324
  FIRECMS_NS,
39078
- bundle[FIRECMS_NS],
39325
+ bundle_0[FIRECMS_NS],
39079
39326
  true,
39080
39327
  // deep merge
39081
39328
  true
@@ -43825,9 +44072,11 @@ export {
43825
44072
  buildProperties,
43826
44073
  buildPropertiesOrBuilder,
43827
44074
  buildProperty,
44075
+ buildSubcollectionPathSegments,
43828
44076
  canCreateEntity,
43829
44077
  canDeleteEntity,
43830
44078
  canEditEntity,
44079
+ collectionSegmentsFrom,
43831
44080
  copyEntityAction,
43832
44081
  decodeEntityId,
43833
44082
  defaultDateFormat,
@@ -43846,6 +44095,7 @@ export {
43846
44095
  getArrayValuesCount,
43847
44096
  getBracketNotation,
43848
44097
  getCollectionByPathOrId,
44098
+ getCollectionByPathSegments,
43849
44099
  getCollectionPathsCombinations,
43850
44100
  getColorForProperty,
43851
44101
  getColorScheme,
@@ -43907,6 +44157,7 @@ export {
43907
44157
  parseGeoPoint,
43908
44158
  pick,
43909
44159
  plural,
44160
+ positionalCollectionSegments,
43910
44161
  prettifyIdentifier,
43911
44162
  printChanged,
43912
44163
  propertiesToColumns,
@@ -43928,6 +44179,7 @@ export {
43928
44179
  resolveArrayProperty,
43929
44180
  resolveCollection,
43930
44181
  resolveCollectionPathIds,
44182
+ resolveCollectionPathSegments,
43931
44183
  resolveDefaultSelectedView,
43932
44184
  resolveEntityAction,
43933
44185
  resolveEntityView,
@@ -43990,6 +44242,7 @@ export {
43990
44242
  useTraceUpdate,
43991
44243
  useTranslation,
43992
44244
  useValidateAuthenticator,
44245
+ walkPathSegments,
43993
44246
  yupToFormErrors
43994
44247
  };
43995
44248
  //# sourceMappingURL=index.es.js.map