@firecms/core 3.4.0-canary.8635253 → 3.4.0-canary.d20cc85

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 (87) hide show
  1. package/dist/components/EntityCollectionTable/internal/CollectionTableToolbar.d.ts +6 -1
  2. package/dist/components/EntityCollectionTable/internal/popup_field/PopupFormField.d.ts +3 -1
  3. package/dist/components/EntityCollectionView/EntityCollectionBoardView.d.ts +3 -1
  4. package/dist/components/EntityCollectionView/EntityCollectionView.d.ts +7 -0
  5. package/dist/components/EntityCollectionView/useBoardDataController.d.ts +3 -1
  6. package/dist/components/ReferenceTable/ReferenceSelectionTable.d.ts +10 -1
  7. package/dist/components/SelectableTable/filters/filter_text_input.d.ts +30 -0
  8. package/dist/components/SelectableTable/filters/filter_text_input.test.d.ts +1 -0
  9. package/dist/components/common/table_url_params.d.ts +24 -0
  10. package/dist/components/common/useDataSourceTableController.d.ts +7 -1
  11. package/dist/components/common/useTableSearchHelper.d.ts +7 -1
  12. package/dist/core/EntityEditView.d.ts +7 -1
  13. package/dist/form/EntityForm.d.ts +6 -1
  14. package/dist/hooks/data/save.d.ts +1 -1
  15. package/dist/hooks/data/useCollectionFetch.d.ts +7 -1
  16. package/dist/hooks/data/useEntityFetch.d.ts +6 -1
  17. package/dist/index.es.js +949 -622
  18. package/dist/index.es.js.map +1 -1
  19. package/dist/index.umd.js +948 -621
  20. package/dist/index.umd.js.map +1 -1
  21. package/dist/types/collections.d.ts +7 -0
  22. package/dist/types/datasource.d.ts +59 -4
  23. package/dist/types/entities.d.ts +21 -1
  24. package/dist/types/properties.d.ts +17 -1
  25. package/dist/types/side_entity_controller.d.ts +6 -0
  26. package/dist/types/translations.d.ts +6 -0
  27. package/dist/util/__tests__/collections.test.d.ts +1 -0
  28. package/dist/util/__tests__/urls.test.d.ts +1 -0
  29. package/dist/util/collections.d.ts +1 -1
  30. package/dist/util/index.d.ts +1 -0
  31. package/dist/util/navigation_from_path.d.ts +7 -0
  32. package/dist/util/navigation_utils.d.ts +3 -1
  33. package/dist/util/parent_references_from_path.d.ts +1 -0
  34. package/dist/util/urls.d.ts +22 -0
  35. package/package.json +4 -4
  36. package/src/components/EntityCollectionTable/EntityCollectionTable.tsx +1 -0
  37. package/src/components/EntityCollectionTable/internal/CollectionTableToolbar.tsx +7 -0
  38. package/src/components/EntityCollectionTable/internal/popup_field/PopupFormField.tsx +5 -1
  39. package/src/components/EntityCollectionView/EntityCollectionBoardView.tsx +4 -0
  40. package/src/components/EntityCollectionView/EntityCollectionView.tsx +29 -3
  41. package/src/components/EntityCollectionView/useBoardDataController.tsx +11 -0
  42. package/src/components/ReferenceTable/ReferenceSelectionTable.tsx +11 -0
  43. package/src/components/SelectableTable/filters/StringNumberFilterField.tsx +33 -7
  44. package/src/components/SelectableTable/filters/filter_text_input.test.ts +184 -0
  45. package/src/components/SelectableTable/filters/filter_text_input.ts +71 -0
  46. package/src/components/common/table_url_params.ts +172 -0
  47. package/src/components/common/useDataSourceTableController.tsx +64 -175
  48. package/src/components/common/useTableSearchHelper.ts +21 -2
  49. package/src/contexts/SnackbarProvider.tsx +14 -1
  50. package/src/core/EntityEditView.tsx +21 -0
  51. package/src/core/EntitySidePanel.tsx +2 -0
  52. package/src/form/EntityForm.tsx +9 -3
  53. package/src/hooks/data/delete.ts +2 -0
  54. package/src/hooks/data/save.ts +2 -0
  55. package/src/hooks/data/useCollectionFetch.tsx +13 -0
  56. package/src/hooks/data/useEntityFetch.tsx +18 -0
  57. package/src/hooks/useResolvedNavigationFrom.tsx +2 -0
  58. package/src/hooks/useValidateAuthenticator.tsx +4 -0
  59. package/src/internal/useBuildDataSource.ts +25 -4
  60. package/src/internal/useBuildSideEntityController.tsx +6 -0
  61. package/src/locales/de.ts +5 -0
  62. package/src/locales/en.ts +5 -0
  63. package/src/locales/es.ts +5 -0
  64. package/src/locales/fr.ts +5 -0
  65. package/src/locales/hi.ts +5 -0
  66. package/src/locales/it.ts +5 -0
  67. package/src/locales/pl.ts +5 -0
  68. package/src/locales/pt.ts +5 -0
  69. package/src/preview/components/StorageThumbnail.tsx +24 -2
  70. package/src/routes/FireCMSRoute.tsx +3 -0
  71. package/src/types/collections.ts +8 -0
  72. package/src/types/datasource.ts +59 -4
  73. package/src/types/entities.ts +24 -1
  74. package/src/types/properties.ts +17 -0
  75. package/src/types/side_entity_controller.tsx +6 -0
  76. package/src/types/translations.ts +6 -0
  77. package/src/util/__tests__/collections.test.ts +32 -0
  78. package/src/util/__tests__/urls.test.ts +131 -0
  79. package/src/util/collections.ts +1 -1
  80. package/src/util/entities.ts +3 -1
  81. package/src/util/index.ts +1 -0
  82. package/src/util/navigation_from_path.ts +19 -1
  83. package/src/util/navigation_utils.ts +4 -0
  84. package/src/util/parent_references_from_path.ts +10 -2
  85. package/src/util/previews.ts +8 -1
  86. package/src/util/resolutions.ts +8 -0
  87. package/src/util/urls.ts +52 -0
package/dist/index.umd.js CHANGED
@@ -23,19 +23,35 @@
23
23
  const yup__namespace = /* @__PURE__ */ _interopNamespaceDefault(yup);
24
24
  const Portal__namespace = /* @__PURE__ */ _interopNamespaceDefault(Portal);
25
25
  const SnackbarProvider = (t0) => {
26
- const $ = reactCompilerRuntime.c(2);
26
+ const $ = reactCompilerRuntime.c(5);
27
27
  const {
28
28
  children
29
29
  } = t0;
30
+ const [domRoot, setDomRoot] = React.useState(void 0);
30
31
  let t1;
31
- if ($[0] !== children) {
32
- t1 = /* @__PURE__ */ jsxRuntime.jsx(notistack.SnackbarProvider, { maxSnack: 3, autoHideDuration: 3500, children });
33
- $[0] = children;
34
- $[1] = t1;
32
+ let t2;
33
+ if ($[0] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
34
+ t1 = () => {
35
+ setDomRoot(document.body);
36
+ };
37
+ t2 = [];
38
+ $[0] = t1;
39
+ $[1] = t2;
35
40
  } else {
36
- t1 = $[1];
41
+ t1 = $[0];
42
+ t2 = $[1];
37
43
  }
38
- return t1;
44
+ React.useEffect(t1, t2);
45
+ let t3;
46
+ if ($[2] !== children || $[3] !== domRoot) {
47
+ t3 = /* @__PURE__ */ jsxRuntime.jsx(notistack.SnackbarProvider, { maxSnack: 3, domRoot, autoHideDuration: 3500, children });
48
+ $[2] = children;
49
+ $[3] = domRoot;
50
+ $[4] = t3;
51
+ } else {
52
+ t3 = $[4];
53
+ }
54
+ return t3;
39
55
  };
40
56
  const DEFAULT_MODE_STATE = {
41
57
  mode: "light",
@@ -284,6 +300,7 @@
284
300
  copy,
285
301
  path,
286
302
  fullIdPath,
303
+ pathSegments,
287
304
  selectedTab,
288
305
  sideEntityController,
289
306
  onClose,
@@ -294,6 +311,7 @@
294
311
  entityId,
295
312
  path,
296
313
  fullIdPath,
314
+ pathSegments,
297
315
  copy,
298
316
  selectedTab,
299
317
  collection,
@@ -328,10 +346,21 @@
328
346
  * Optional database ID where the entity is stored (if multiple databases are used)
329
347
  */
330
348
  databaseId;
331
- constructor(id, path, databaseId) {
349
+ /**
350
+ * `path` split at its real segment boundaries, e.g. `["nodes", "node/42", "edges"]`.
351
+ *
352
+ * `path` is a single flattened string, so a parent entity id containing "/" cannot be
353
+ * recovered from it. This keeps each segment whole.
354
+ *
355
+ * Optional, and never derived by splitting `path` — a guess would be wrong in exactly
356
+ * the case the field exists for. Absent means "not known here", not "no slashes".
357
+ */
358
+ pathSegments;
359
+ constructor(id, path, databaseId, pathSegments) {
332
360
  this.id = id;
333
361
  this.path = path;
334
362
  this.databaseId = databaseId;
363
+ this.pathSegments = pathSegments;
335
364
  }
336
365
  get pathWithId() {
337
366
  return `${this.path}/${this.id}`;
@@ -702,7 +731,7 @@
702
731
  if (!entity) {
703
732
  throw new Error("getReferenceFrom: entity is null or undefined");
704
733
  }
705
- return new EntityReference(entity.id, entity.path, entity.databaseId);
734
+ return new EntityReference(entity.id, entity.path, entity.databaseId, entity.pathSegments);
706
735
  }
707
736
  function traverseValuesProperties(inputValues, properties, operation) {
708
737
  const safeInputValues = inputValues ?? {};
@@ -998,6 +1027,7 @@
998
1027
  ...props
999
1028
  });
1000
1029
  const ofProperty = resolveProperty({
1030
+ propertyKey,
1001
1031
  propertyOrBuilder: of,
1002
1032
  ignoreMissingFields,
1003
1033
  ...props
@@ -1126,7 +1156,8 @@
1126
1156
  collections = [],
1127
1157
  currentFullPath,
1128
1158
  currentFullIdPath,
1129
- currentFullUrlPath
1159
+ currentFullUrlPath,
1160
+ currentPathSegments = []
1130
1161
  } = props;
1131
1162
  const subpaths = removeInitialAndTrailingSlashes(path).split("/");
1132
1163
  const subpathCombinations = getCollectionPathsCombinations(subpaths);
@@ -1142,12 +1173,14 @@
1142
1173
  const collectionPath = currentFullPath && currentFullPath.length > 0 ? currentFullPath + "/" + collection.path : collection.path;
1143
1174
  const collectionUrlPath = currentFullUrlPath && currentFullUrlPath.length > 0 ? currentFullUrlPath + "/" + collection.path : collection.path;
1144
1175
  const fullIdPath = currentFullIdPath && currentFullIdPath.length > 0 ? currentFullIdPath + "/" + collection.id : collection.id;
1176
+ const collectionSegments = [...currentPathSegments, ...collection.path.split("/")];
1145
1177
  result.push({
1146
1178
  type: "collection",
1147
1179
  id: collection.id,
1148
1180
  path: collectionPath,
1149
1181
  fullPath: collectionUrlPath,
1150
1182
  fullIdPath,
1183
+ pathSegments: collectionSegments,
1151
1184
  collection
1152
1185
  });
1153
1186
  const restOfThePath = removeInitialAndTrailingSlashes(removeInitialAndTrailingSlashes(path).replace(subpathCombination, ""));
@@ -1157,12 +1190,14 @@
1157
1190
  const entityId = decodeEntityId(encodedEntityId);
1158
1191
  const fullPath = collectionPath + "/" + entityId;
1159
1192
  const fullUrlPath = collectionUrlPath + "/" + encodedEntityId;
1193
+ const entitySegments = [...collectionSegments, entityId];
1160
1194
  result.push({
1161
1195
  type: "entity",
1162
1196
  entityId,
1163
1197
  path: collectionPath,
1164
1198
  fullIdPath,
1165
1199
  fullPath: fullUrlPath,
1200
+ pathSegments: collectionSegments,
1166
1201
  parentCollection: collection
1167
1202
  });
1168
1203
  if (nextSegments.length > 1) {
@@ -1179,6 +1214,7 @@
1179
1214
  entityId,
1180
1215
  fullIdPath,
1181
1216
  fullPath: fullUrlPath + "/" + customView.key,
1217
+ pathSegments: collectionSegments,
1182
1218
  view: customView
1183
1219
  });
1184
1220
  } else if (collection.subcollections) {
@@ -1188,6 +1224,7 @@
1188
1224
  currentFullPath: fullPath,
1189
1225
  currentFullIdPath: fullIdPath,
1190
1226
  currentFullUrlPath: fullUrlPath,
1227
+ currentPathSegments: entitySegments,
1191
1228
  contextEntityViews: props.contextEntityViews
1192
1229
  }));
1193
1230
  }
@@ -1291,7 +1328,7 @@
1291
1328
  });
1292
1329
  };
1293
1330
  function getLocalChangesBackup(collection) {
1294
- if (!collection.localChangesBackup) {
1331
+ if (collection.localChangesBackup === void 0) {
1295
1332
  return "manual_apply";
1296
1333
  }
1297
1334
  return collection.localChangesBackup;
@@ -1378,6 +1415,31 @@
1378
1415
  const simpleRegexp = input.match(/((?![*+?])(?:[^\r\n[/\\]|\\.|\[(?:[^\r\n\]\\]|\\.)*])+)/);
1379
1416
  return !!simpleRegexp;
1380
1417
  }
1418
+ const ABSOLUTE_HTTP_URL_REGEX = /^https?:\/\//i;
1419
+ const IMAGE_EXTENSIONS = ["jpg", "jpeg", "png", "gif", "webp", "avif", "bmp", "svg", "ico", "tif", "tiff", "heic", "heif"];
1420
+ const VIDEO_EXTENSIONS = ["mp4", "webm", "ogv", "mov", "m4v", "avi", "mkv", "mpeg", "mpg", "3gp"];
1421
+ const AUDIO_EXTENSIONS = ["mp3", "wav", "ogg", "oga", "m4a", "aac", "flac", "weba", "opus", "mid", "midi"];
1422
+ function isAbsoluteHttpUrl(value) {
1423
+ if (!value) return false;
1424
+ return ABSOLUTE_HTTP_URL_REGEX.test(value);
1425
+ }
1426
+ function getFileExtensionFromUrl(urlOrPath) {
1427
+ if (!urlOrPath) return void 0;
1428
+ const withoutQuery = urlOrPath.split(/[?#]/)[0];
1429
+ const lastSegment = withoutQuery.split("/").pop();
1430
+ if (!lastSegment) return void 0;
1431
+ const lastDot = lastSegment.lastIndexOf(".");
1432
+ if (lastDot <= 0 || lastDot === lastSegment.length - 1) return void 0;
1433
+ return lastSegment.substring(lastDot + 1).toLowerCase();
1434
+ }
1435
+ function getPreviewTypeFromUrl(urlOrPath) {
1436
+ const extension = getFileExtensionFromUrl(urlOrPath);
1437
+ if (!extension) return void 0;
1438
+ if (IMAGE_EXTENSIONS.includes(extension)) return "image";
1439
+ if (VIDEO_EXTENSIONS.includes(extension)) return "video";
1440
+ if (AUDIO_EXTENSIONS.includes(extension)) return "audio";
1441
+ return void 0;
1442
+ }
1381
1443
  const reservedKeys = ["edit", "copy", "delete"];
1382
1444
  function mergeEntityActions(currentActions, newActions) {
1383
1445
  const updatedActions = [];
@@ -3788,6 +3850,12 @@
3788
3850
  return void 0;
3789
3851
  }
3790
3852
  function getEntityImagePreviewPropertyKey(collection) {
3853
+ if (collection.imageProperty) {
3854
+ const imagePropertyKey = collection.imageProperty;
3855
+ if (collection.properties[imagePropertyKey]) {
3856
+ return collection.imageProperty;
3857
+ }
3858
+ }
3791
3859
  for (const key in collection.properties) {
3792
3860
  const property = collection.properties[key];
3793
3861
  if (property.dataType === "string" && property.storage?.acceptedFiles?.includes("image/*")) {
@@ -4556,9 +4624,10 @@
4556
4624
  return fireCMSContextRef.current;
4557
4625
  };
4558
4626
  function useCollectionFetch(t0) {
4559
- const $ = reactCompilerRuntime.c(26);
4627
+ const $ = reactCompilerRuntime.c(27);
4560
4628
  const {
4561
4629
  path: inputPath,
4630
+ pathSegments,
4562
4631
  collection,
4563
4632
  filterValues,
4564
4633
  sortBy,
@@ -4592,10 +4661,16 @@
4592
4661
  const [dataLoadingError, setDataLoadingError] = React.useState();
4593
4662
  const [noMoreToLoad, setNoMoreToLoad] = React.useState(false);
4594
4663
  let t3;
4595
- if ($[4] !== collection || $[5] !== context || $[6] !== currentSort || $[7] !== dataSource || $[8] !== filterValues || $[9] !== itemCount || $[10] !== path || $[11] !== searchString || $[12] !== sortByProperty) {
4664
+ if ($[4] !== collection || $[5] !== context || $[6] !== currentSort || $[7] !== dataSource || $[8] !== filterValues || $[9] !== itemCount || $[10] !== path || $[11] !== pathSegments || $[12] !== searchString || $[13] !== sortByProperty) {
4596
4665
  t3 = () => {
4597
4666
  setDataLoading(true);
4598
4667
  const onEntitiesUpdate = async (entities) => {
4668
+ if (pathSegments) {
4669
+ entities = entities.map((e) => e.pathSegments ? e : {
4670
+ ...e,
4671
+ pathSegments
4672
+ });
4673
+ }
4599
4674
  if (collection.callbacks?.onFetch) {
4600
4675
  try {
4601
4676
  entities = await Promise.all(entities.map((entity) => collection.callbacks.onFetch({
@@ -4605,8 +4680,8 @@
4605
4680
  context
4606
4681
  })));
4607
4682
  } catch (t42) {
4608
- const e = t42;
4609
- console.error(e);
4683
+ const e_0 = t42;
4684
+ console.error(e_0);
4610
4685
  }
4611
4686
  }
4612
4687
  setDataLoading(false);
@@ -4623,6 +4698,7 @@
4623
4698
  if (dataSource.listenCollection) {
4624
4699
  return dataSource.listenCollection({
4625
4700
  path,
4701
+ pathSegments,
4626
4702
  collection,
4627
4703
  onUpdate: onEntitiesUpdate,
4628
4704
  onError,
@@ -4636,6 +4712,7 @@
4636
4712
  } else {
4637
4713
  dataSource.fetchCollection({
4638
4714
  path,
4715
+ pathSegments,
4639
4716
  collection,
4640
4717
  searchString,
4641
4718
  filter: filterValues,
@@ -4654,56 +4731,58 @@
4654
4731
  $[8] = filterValues;
4655
4732
  $[9] = itemCount;
4656
4733
  $[10] = path;
4657
- $[11] = searchString;
4658
- $[12] = sortByProperty;
4659
- $[13] = t3;
4734
+ $[11] = pathSegments;
4735
+ $[12] = searchString;
4736
+ $[13] = sortByProperty;
4737
+ $[14] = t3;
4660
4738
  } else {
4661
- t3 = $[13];
4739
+ t3 = $[14];
4662
4740
  }
4663
4741
  let t4;
4664
- if ($[14] !== currentSort || $[15] !== filterValues || $[16] !== itemCount || $[17] !== path || $[18] !== searchString || $[19] !== sortByProperty) {
4742
+ if ($[15] !== currentSort || $[16] !== filterValues || $[17] !== itemCount || $[18] !== path || $[19] !== searchString || $[20] !== sortByProperty) {
4665
4743
  t4 = [path, itemCount, currentSort, sortByProperty, filterValues, searchString];
4666
- $[14] = currentSort;
4667
- $[15] = filterValues;
4668
- $[16] = itemCount;
4669
- $[17] = path;
4670
- $[18] = searchString;
4671
- $[19] = sortByProperty;
4672
- $[20] = t4;
4744
+ $[15] = currentSort;
4745
+ $[16] = filterValues;
4746
+ $[17] = itemCount;
4747
+ $[18] = path;
4748
+ $[19] = searchString;
4749
+ $[20] = sortByProperty;
4750
+ $[21] = t4;
4673
4751
  } else {
4674
- t4 = $[20];
4752
+ t4 = $[21];
4675
4753
  }
4676
4754
  React.useEffect(t3, t4);
4677
4755
  let t5;
4678
- if ($[21] !== data || $[22] !== dataLoading || $[23] !== dataLoadingError || $[24] !== noMoreToLoad) {
4756
+ if ($[22] !== data || $[23] !== dataLoading || $[24] !== dataLoadingError || $[25] !== noMoreToLoad) {
4679
4757
  t5 = {
4680
4758
  data,
4681
4759
  dataLoading,
4682
4760
  dataLoadingError,
4683
4761
  noMoreToLoad
4684
4762
  };
4685
- $[21] = data;
4686
- $[22] = dataLoading;
4687
- $[23] = dataLoadingError;
4688
- $[24] = noMoreToLoad;
4689
- $[25] = t5;
4763
+ $[22] = data;
4764
+ $[23] = dataLoading;
4765
+ $[24] = dataLoadingError;
4766
+ $[25] = noMoreToLoad;
4767
+ $[26] = t5;
4690
4768
  } else {
4691
- t5 = $[25];
4769
+ t5 = $[26];
4692
4770
  }
4693
4771
  return t5;
4694
4772
  }
4695
4773
  function _temp2$f() {
4696
4774
  }
4697
- function _temp$D(e_0) {
4775
+ function _temp$D(e_1) {
4698
4776
  return {
4699
- ...e_0
4777
+ ...e_1
4700
4778
  };
4701
4779
  }
4702
4780
  const CACHE = {};
4703
4781
  function useEntityFetch(t0) {
4704
- const $ = reactCompilerRuntime.c(18);
4782
+ const $ = reactCompilerRuntime.c(19);
4705
4783
  const {
4706
4784
  path: inputPath,
4785
+ pathSegments: inputPathSegments,
4707
4786
  entityId,
4708
4787
  collection,
4709
4788
  databaseId,
@@ -4722,15 +4801,22 @@
4722
4801
  t2 = $[2];
4723
4802
  }
4724
4803
  const path = t2;
4804
+ const pathSegments = inputPathSegments;
4725
4805
  const context = useFireCMSContext();
4726
4806
  const [entity, setEntity] = React.useState();
4727
4807
  const [dataLoading, setDataLoading] = React.useState(true);
4728
4808
  const [dataLoadingError, setDataLoadingError] = React.useState();
4729
4809
  let t3;
4730
- if ($[3] !== collection || $[4] !== context || $[5] !== dataSource || $[6] !== databaseId || $[7] !== entityId || $[8] !== path || $[9] !== useCache) {
4810
+ if ($[3] !== collection || $[4] !== context || $[5] !== dataSource || $[6] !== databaseId || $[7] !== entityId || $[8] !== path || $[9] !== pathSegments || $[10] !== useCache) {
4731
4811
  t3 = () => {
4732
4812
  setDataLoading(true);
4733
4813
  const onEntityUpdate = async (updatedEntity) => {
4814
+ if (updatedEntity && pathSegments && !updatedEntity.pathSegments) {
4815
+ updatedEntity = {
4816
+ ...updatedEntity,
4817
+ pathSegments
4818
+ };
4819
+ }
4734
4820
  if (collection.callbacks?.onFetch && updatedEntity) {
4735
4821
  try {
4736
4822
  updatedEntity = await collection.callbacks.onFetch({
@@ -4765,6 +4851,7 @@
4765
4851
  if (dataSource.listenEntity) {
4766
4852
  return dataSource.listenEntity({
4767
4853
  path,
4854
+ pathSegments,
4768
4855
  entityId,
4769
4856
  databaseId,
4770
4857
  collection,
@@ -4774,6 +4861,7 @@
4774
4861
  } else {
4775
4862
  dataSource.fetchEntity({
4776
4863
  path,
4864
+ pathSegments,
4777
4865
  entityId,
4778
4866
  databaseId,
4779
4867
  collection
@@ -4792,34 +4880,35 @@
4792
4880
  $[6] = databaseId;
4793
4881
  $[7] = entityId;
4794
4882
  $[8] = path;
4795
- $[9] = useCache;
4796
- $[10] = t3;
4883
+ $[9] = pathSegments;
4884
+ $[10] = useCache;
4885
+ $[11] = t3;
4797
4886
  } else {
4798
- t3 = $[10];
4887
+ t3 = $[11];
4799
4888
  }
4800
4889
  let t4;
4801
- if ($[11] !== entityId || $[12] !== path) {
4890
+ if ($[12] !== entityId || $[13] !== path) {
4802
4891
  t4 = [entityId, path];
4803
- $[11] = entityId;
4804
- $[12] = path;
4805
- $[13] = t4;
4892
+ $[12] = entityId;
4893
+ $[13] = path;
4894
+ $[14] = t4;
4806
4895
  } else {
4807
- t4 = $[13];
4896
+ t4 = $[14];
4808
4897
  }
4809
4898
  React.useEffect(t3, t4);
4810
4899
  let t5;
4811
- if ($[14] !== dataLoading || $[15] !== dataLoadingError || $[16] !== entity) {
4900
+ if ($[15] !== dataLoading || $[16] !== dataLoadingError || $[17] !== entity) {
4812
4901
  t5 = {
4813
4902
  entity,
4814
4903
  dataLoading,
4815
4904
  dataLoadingError
4816
4905
  };
4817
- $[14] = dataLoading;
4818
- $[15] = dataLoadingError;
4819
- $[16] = entity;
4820
- $[17] = t5;
4906
+ $[15] = dataLoading;
4907
+ $[16] = dataLoadingError;
4908
+ $[17] = entity;
4909
+ $[18] = t5;
4821
4910
  } else {
4822
- t5 = $[17];
4911
+ t5 = $[18];
4823
4912
  }
4824
4913
  return t5;
4825
4914
  }
@@ -4832,6 +4921,7 @@
4832
4921
  async function saveEntityWithCallbacks({
4833
4922
  collection,
4834
4923
  path,
4924
+ pathSegments,
4835
4925
  entityId,
4836
4926
  values,
4837
4927
  previousValues,
@@ -4881,6 +4971,7 @@
4881
4971
  return dataSource.saveEntity({
4882
4972
  collection,
4883
4973
  path: resolvedPath,
4974
+ pathSegments,
4884
4975
  entityId,
4885
4976
  values: updatedValues,
4886
4977
  previousValues,
@@ -4964,6 +5055,8 @@
4964
5055
  }
4965
5056
  }
4966
5057
  return dataSource.deleteEntity({
5058
+ // Carried by the entity from the fetch that produced it; undefined if unknown.
5059
+ pathSegments: entity.pathSegments,
4967
5060
  entity,
4968
5061
  collection
4969
5062
  }).then(() => {
@@ -5005,6 +5098,8 @@
5005
5098
  }
5006
5099
  return dataSource.fetchEntity({
5007
5100
  path: entry.path,
5101
+ // The navigation entry already knows the real segment boundaries.
5102
+ pathSegments: entry.pathSegments,
5008
5103
  entityId: entry.entityId,
5009
5104
  collection
5010
5105
  }).then((entity) => {
@@ -6057,8 +6152,9 @@
6057
6152
  }
6058
6153
  const URL_CACHE = {};
6059
6154
  function StorageThumbnailInternal(t0) {
6060
- const $ = reactCompilerRuntime.c(13);
6155
+ const $ = reactCompilerRuntime.c(26);
6061
6156
  const {
6157
+ storeUrl,
6062
6158
  interactive,
6063
6159
  storagePathOrDownloadUrl,
6064
6160
  size,
@@ -6066,11 +6162,21 @@
6066
6162
  } = t0;
6067
6163
  const [, setError] = React.useState(void 0);
6068
6164
  const storage = useStorageSource();
6069
- const [downloadConfig, setDownloadConfig] = React.useState(URL_CACHE[storagePathOrDownloadUrl]);
6070
6165
  let t1;
6071
- if ($[0] !== storage || $[1] !== storagePathOrDownloadUrl) {
6072
- t1 = () => {
6073
- if (!storagePathOrDownloadUrl) {
6166
+ if ($[0] !== storagePathOrDownloadUrl || $[1] !== storeUrl) {
6167
+ t1 = storeUrl || isAbsoluteHttpUrl(storagePathOrDownloadUrl);
6168
+ $[0] = storagePathOrDownloadUrl;
6169
+ $[1] = storeUrl;
6170
+ $[2] = t1;
6171
+ } else {
6172
+ t1 = $[2];
6173
+ }
6174
+ const valueIsUrl = t1;
6175
+ const [downloadConfig, setDownloadConfig] = React.useState(URL_CACHE[storagePathOrDownloadUrl]);
6176
+ let t2;
6177
+ if ($[3] !== storage || $[4] !== storagePathOrDownloadUrl || $[5] !== valueIsUrl) {
6178
+ t2 = () => {
6179
+ if (!storagePathOrDownloadUrl || valueIsUrl) {
6074
6180
  return;
6075
6181
  }
6076
6182
  let unmounted;
@@ -6085,50 +6191,75 @@
6085
6191
  unmounted = true;
6086
6192
  };
6087
6193
  };
6088
- $[0] = storage;
6089
- $[1] = storagePathOrDownloadUrl;
6090
- $[2] = t1;
6194
+ $[3] = storage;
6195
+ $[4] = storagePathOrDownloadUrl;
6196
+ $[5] = valueIsUrl;
6197
+ $[6] = t2;
6091
6198
  } else {
6092
- t1 = $[2];
6199
+ t2 = $[6];
6093
6200
  }
6094
- let t2;
6095
- if ($[3] !== storagePathOrDownloadUrl) {
6096
- t2 = [storagePathOrDownloadUrl];
6097
- $[3] = storagePathOrDownloadUrl;
6098
- $[4] = t2;
6201
+ let t3;
6202
+ if ($[7] !== storagePathOrDownloadUrl || $[8] !== valueIsUrl) {
6203
+ t3 = [storagePathOrDownloadUrl, valueIsUrl];
6204
+ $[7] = storagePathOrDownloadUrl;
6205
+ $[8] = valueIsUrl;
6206
+ $[9] = t3;
6099
6207
  } else {
6100
- t2 = $[4];
6208
+ t3 = $[9];
6101
6209
  }
6102
- React.useEffect(t1, t2);
6210
+ React.useEffect(t2, t3);
6103
6211
  if (!storagePathOrDownloadUrl) {
6104
6212
  return null;
6105
6213
  }
6214
+ if (valueIsUrl) {
6215
+ let t42;
6216
+ if ($[10] !== storagePathOrDownloadUrl) {
6217
+ t42 = getPreviewTypeFromUrl(storagePathOrDownloadUrl) ?? "file";
6218
+ $[10] = storagePathOrDownloadUrl;
6219
+ $[11] = t42;
6220
+ } else {
6221
+ t42 = $[11];
6222
+ }
6223
+ let t5;
6224
+ if ($[12] !== fill || $[13] !== interactive || $[14] !== size || $[15] !== storagePathOrDownloadUrl || $[16] !== t42) {
6225
+ t5 = /* @__PURE__ */ jsxRuntime.jsx(UrlComponentPreview, { previewType: t42, url: storagePathOrDownloadUrl, interactive, size, fill, hint: storagePathOrDownloadUrl });
6226
+ $[12] = fill;
6227
+ $[13] = interactive;
6228
+ $[14] = size;
6229
+ $[15] = storagePathOrDownloadUrl;
6230
+ $[16] = t42;
6231
+ $[17] = t5;
6232
+ } else {
6233
+ t5 = $[17];
6234
+ }
6235
+ return t5;
6236
+ }
6106
6237
  const filetype = downloadConfig?.metadata ? getFiletype(downloadConfig?.metadata.contentType) : void 0;
6107
6238
  const previewType = filetype?.startsWith("image") ? "image" : filetype?.startsWith("video") ? "video" : filetype?.startsWith("audio") ? "audio" : "file";
6108
6239
  if (downloadConfig?.fileNotFound) {
6109
- let t32;
6110
- if ($[5] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
6111
- t32 = /* @__PURE__ */ jsxRuntime.jsx(ErrorView, { error: "File not found" });
6112
- $[5] = t32;
6240
+ let t42;
6241
+ if ($[18] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
6242
+ t42 = /* @__PURE__ */ jsxRuntime.jsx(ErrorView, { error: "File not found" });
6243
+ $[18] = t42;
6113
6244
  } else {
6114
- t32 = $[5];
6245
+ t42 = $[18];
6115
6246
  }
6116
- return t32;
6247
+ return t42;
6117
6248
  }
6118
- let t3;
6119
- if ($[6] !== downloadConfig || $[7] !== fill || $[8] !== interactive || $[9] !== previewType || $[10] !== size || $[11] !== storagePathOrDownloadUrl) {
6120
- t3 = downloadConfig?.url ? /* @__PURE__ */ jsxRuntime.jsx(UrlComponentPreview, { previewType, url: downloadConfig.url, interactive, size, fill, hint: storagePathOrDownloadUrl }) : renderSkeletonImageThumbnail(size, fill);
6121
- $[6] = downloadConfig;
6122
- $[7] = fill;
6123
- $[8] = interactive;
6124
- $[9] = previewType;
6125
- $[10] = size;
6126
- $[11] = storagePathOrDownloadUrl;
6127
- $[12] = t3;
6249
+ let t4;
6250
+ if ($[19] !== downloadConfig || $[20] !== fill || $[21] !== interactive || $[22] !== previewType || $[23] !== size || $[24] !== storagePathOrDownloadUrl) {
6251
+ t4 = downloadConfig?.url ? /* @__PURE__ */ jsxRuntime.jsx(UrlComponentPreview, { previewType, url: downloadConfig.url, interactive, size, fill, hint: storagePathOrDownloadUrl }) : renderSkeletonImageThumbnail(size, fill);
6252
+ $[19] = downloadConfig;
6253
+ $[20] = fill;
6254
+ $[21] = interactive;
6255
+ $[22] = previewType;
6256
+ $[23] = size;
6257
+ $[24] = storagePathOrDownloadUrl;
6258
+ $[25] = t4;
6128
6259
  } else {
6129
- t3 = $[12];
6260
+ t4 = $[25];
6130
6261
  }
6131
- return t3;
6262
+ return t4;
6132
6263
  }
6133
6264
  function getFiletype(input) {
6134
6265
  if (input.startsWith("image")) return "image/*";
@@ -16615,6 +16746,7 @@
16615
16746
  }
16616
16747
  function EntityForm({
16617
16748
  path,
16749
+ pathSegments,
16618
16750
  fullIdPath,
16619
16751
  entityId: entityIdProp,
16620
16752
  collection,
@@ -16681,7 +16813,7 @@
16681
16813
  if (mustSetCustomId) {
16682
16814
  return void 0;
16683
16815
  } else {
16684
- return dataSource.generateEntityId(path, collection);
16816
+ return dataSource.generateEntityId(path, collection, pathSegments);
16685
16817
  }
16686
16818
  } else {
16687
16819
  return entityIdProp;
@@ -16755,7 +16887,7 @@
16755
16887
  },
16756
16888
  onValuesChangeDeferred: (values_0, controller) => {
16757
16889
  const key = status === "new" || status === "copy" ? path + "#new" : path + "/" + entityId;
16758
- if (controller.dirty) {
16890
+ if (controller.dirty && localChangesBackup !== false) {
16759
16891
  const touchedValues = removeEmptyContainers(extractTouchedValues(values_0, controller.touched));
16760
16892
  if (touchedValues && Object.keys(touchedValues).length > 0) {
16761
16893
  saveEntityToCache(key, touchedValues);
@@ -16994,7 +17126,7 @@
16994
17126
  const uniqueFieldValidator = React.useCallback(({
16995
17127
  name,
16996
17128
  value
16997
- }) => dataSource.checkUniqueField(path, name, value, entityId, collection), [dataSource, path, entityId]);
17129
+ }) => dataSource.checkUniqueField(path, name, value, entityId, collection, pathSegments), [dataSource, path, entityId]);
16998
17130
  const validationSchema = React.useMemo(() => entityId ? getYupEntitySchema(entityId, resolvedCollection.properties, uniqueFieldValidator) : void 0, [entityId, resolvedCollection.properties, uniqueFieldValidator]);
16999
17131
  useOnAutoSave(autoSave, formex$1, lastSavedValues, save);
17000
17132
  const prevEntityValuesRef = React.useRef(entity?.values);
@@ -17270,7 +17402,7 @@
17270
17402
  return content;
17271
17403
  };
17272
17404
  function CollectionTableToolbar(t0) {
17273
- const $ = reactCompilerRuntime.c(25);
17405
+ const $ = reactCompilerRuntime.c(26);
17274
17406
  const {
17275
17407
  actions,
17276
17408
  actionsStart,
@@ -17278,6 +17410,7 @@
17278
17410
  onTextSearch,
17279
17411
  onTextSearchClick,
17280
17412
  textSearchLoading,
17413
+ initialSearchString,
17281
17414
  title,
17282
17415
  viewModeToggle
17283
17416
  } = t0;
@@ -17344,41 +17477,42 @@
17344
17477
  t6 = $[12];
17345
17478
  }
17346
17479
  let t7;
17347
- if ($[13] !== onTextSearch || $[14] !== onTextSearchClick || $[15] !== t || $[16] !== textSearchLoading) {
17348
- t7 = (onTextSearch || onTextSearchClick) && /* @__PURE__ */ jsxRuntime.jsx(ui.SearchBar, { size: "small", inputRef: searchInputRef, loading: textSearchLoading, disabled: Boolean(onTextSearchClick), onClick: onTextSearchClick, onTextSearch: onTextSearchClick ? void 0 : onTextSearch, placeholder: t("search"), expandable: true }, "search-bar");
17349
- $[13] = onTextSearch;
17350
- $[14] = onTextSearchClick;
17351
- $[15] = t;
17352
- $[16] = textSearchLoading;
17353
- $[17] = t7;
17480
+ if ($[13] !== initialSearchString || $[14] !== onTextSearch || $[15] !== onTextSearchClick || $[16] !== t || $[17] !== textSearchLoading) {
17481
+ t7 = (onTextSearch || onTextSearchClick) && /* @__PURE__ */ jsxRuntime.jsx(ui.SearchBar, { size: "small", inputRef: searchInputRef, loading: textSearchLoading, disabled: Boolean(onTextSearchClick), onClick: onTextSearchClick, onTextSearch: onTextSearchClick ? void 0 : onTextSearch, initialValue: initialSearchString, placeholder: t("search"), expandable: true }, "search-bar");
17482
+ $[13] = initialSearchString;
17483
+ $[14] = onTextSearch;
17484
+ $[15] = onTextSearchClick;
17485
+ $[16] = t;
17486
+ $[17] = textSearchLoading;
17487
+ $[18] = t7;
17354
17488
  } else {
17355
- t7 = $[17];
17489
+ t7 = $[18];
17356
17490
  }
17357
17491
  let t8;
17358
- if ($[18] !== actions || $[19] !== t6 || $[20] !== t7) {
17492
+ if ($[19] !== actions || $[20] !== t6 || $[21] !== t7) {
17359
17493
  t8 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1", children: [
17360
17494
  t6,
17361
17495
  t7,
17362
17496
  actions
17363
17497
  ] });
17364
- $[18] = actions;
17365
- $[19] = t6;
17366
- $[20] = t7;
17367
- $[21] = t8;
17498
+ $[19] = actions;
17499
+ $[20] = t6;
17500
+ $[21] = t7;
17501
+ $[22] = t8;
17368
17502
  } else {
17369
- t8 = $[21];
17503
+ t8 = $[22];
17370
17504
  }
17371
17505
  let t9;
17372
- if ($[22] !== t5 || $[23] !== t8) {
17506
+ if ($[23] !== t5 || $[24] !== t8) {
17373
17507
  t9 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: t3, children: [
17374
17508
  t5,
17375
17509
  t8
17376
17510
  ] });
17377
- $[22] = t5;
17378
- $[23] = t8;
17379
- $[24] = t9;
17511
+ $[23] = t5;
17512
+ $[24] = t8;
17513
+ $[25] = t9;
17380
17514
  } else {
17381
- t9 = $[24];
17515
+ t9 = $[25];
17382
17516
  }
17383
17517
  return t9;
17384
17518
  }
@@ -18958,6 +19092,33 @@
18958
19092
  ] })
18959
19093
  ] });
18960
19094
  }
19095
+ const completeNumberRegex = /^[+-]?(?:\d+|\d*\.\d+)(?:[eE][+-]?\d+)?$/;
19096
+ function parseFilterTextInput(text, dataType) {
19097
+ if (dataType !== "number") return {
19098
+ updateValue: true,
19099
+ value: text
19100
+ };
19101
+ const trimmedText = text.trim();
19102
+ if (trimmedText === "") return {
19103
+ updateValue: true,
19104
+ value: void 0
19105
+ };
19106
+ if (!completeNumberRegex.test(trimmedText)) return {
19107
+ updateValue: false
19108
+ };
19109
+ const parsedValue = Number(trimmedText);
19110
+ if (!isFinite(parsedValue)) return {
19111
+ updateValue: false
19112
+ };
19113
+ return {
19114
+ updateValue: true,
19115
+ value: parsedValue
19116
+ };
19117
+ }
19118
+ function filterValueToText(value) {
19119
+ if (value === void 0 || value === null) return "";
19120
+ return String(value);
19121
+ }
18961
19122
  const operationLabels$1 = {
18962
19123
  "==": "==",
18963
19124
  "!=": "!=",
@@ -18973,7 +19134,7 @@
18973
19134
  };
18974
19135
  const multipleSelectOperations$1 = ["array-contains-any", "in", "not-in"];
18975
19136
  function StringNumberFilterField(t0) {
18976
- const $ = reactCompilerRuntime.c(56);
19137
+ const $ = reactCompilerRuntime.c(63);
18977
19138
  const {
18978
19139
  name,
18979
19140
  value,
@@ -19007,9 +19168,20 @@
19007
19168
  const [operation, setOperation] = React.useState(fieldOperation === "==" && fieldValue === null ? "is-null" : fieldOperation);
19008
19169
  const [internalValue, setInternalValue] = React.useState(fieldValue);
19009
19170
  let t2;
19171
+ if ($[6] !== fieldValue) {
19172
+ t2 = filterValueToText(fieldValue);
19173
+ $[6] = fieldValue;
19174
+ $[7] = t2;
19175
+ } else {
19176
+ t2 = $[7];
19177
+ }
19178
+ const [inputText, setInputText] = React.useState(t2);
19179
+ const syncedValueRef = React.useRef(fieldValue);
19010
19180
  let t3;
19011
- if ($[6] !== possibleOperations[0] || $[7] !== value) {
19012
- t2 = () => {
19181
+ let t4;
19182
+ if ($[8] !== possibleOperations[0] || $[9] !== value) {
19183
+ t3 = () => {
19184
+ const newValue = value ? value[1] : void 0;
19013
19185
  if (value) {
19014
19186
  const [op, val] = value;
19015
19187
  setOperation(op === "==" && val === null ? "is-null" : op);
@@ -19018,109 +19190,140 @@
19018
19190
  setOperation(possibleOperations[0]);
19019
19191
  setInternalValue(void 0);
19020
19192
  }
19193
+ if (syncedValueRef.current !== newValue) {
19194
+ syncedValueRef.current = newValue;
19195
+ setInputText(filterValueToText(newValue));
19196
+ }
19021
19197
  };
19022
- t3 = [value, possibleOperations[0]];
19023
- $[6] = possibleOperations[0];
19024
- $[7] = value;
19025
- $[8] = t2;
19026
- $[9] = t3;
19198
+ t4 = [value, possibleOperations[0]];
19199
+ $[8] = possibleOperations[0];
19200
+ $[9] = value;
19201
+ $[10] = t3;
19202
+ $[11] = t4;
19027
19203
  } else {
19028
- t2 = $[8];
19029
- t3 = $[9];
19204
+ t3 = $[10];
19205
+ t4 = $[11];
19030
19206
  }
19031
- React.useEffect(t2, t3);
19207
+ React.useEffect(t3, t4);
19032
19208
  const isNullOperation = operation === "is-null";
19033
- let t4;
19034
- if ($[10] !== operation || $[11] !== setValue) {
19035
- t4 = function updateFilter2(op_0, val_0) {
19209
+ let t5;
19210
+ if ($[12] !== operation || $[13] !== setValue) {
19211
+ t5 = function updateFilter2(op_0, val_0, t62) {
19212
+ const keepInputText = t62 === void 0 ? false : t62;
19036
19213
  if (op_0 === "is-null") {
19037
19214
  setOperation(op_0);
19038
19215
  setInternalValue(null);
19216
+ syncedValueRef.current = null;
19217
+ setInputText("");
19039
19218
  setValue(["==", null]);
19040
19219
  return;
19041
19220
  }
19042
- let newValue = val_0;
19221
+ let newValue_0 = val_0;
19043
19222
  const prevOpIsArray = multipleSelectOperations$1.includes(operation);
19044
19223
  const newOpIsArray = multipleSelectOperations$1.includes(op_0);
19045
19224
  if (prevOpIsArray !== newOpIsArray) {
19046
- newValue = newOpIsArray ? typeof val_0 === "string" || typeof val_0 === "number" ? [val_0] : [] : void 0;
19225
+ newValue_0 = newOpIsArray ? typeof val_0 === "string" || typeof val_0 === "number" ? [val_0] : [] : void 0;
19047
19226
  }
19048
- if (typeof newValue === "number" && isNaN(newValue)) {
19049
- newValue = void 0;
19227
+ if (typeof newValue_0 === "number" && isNaN(newValue_0)) {
19228
+ newValue_0 = void 0;
19050
19229
  }
19051
19230
  setOperation(op_0);
19052
- setInternalValue(newValue);
19053
- const hasNewValue = newValue !== null && Array.isArray(newValue) ? newValue.length > 0 : newValue !== void 0;
19231
+ setInternalValue(newValue_0);
19232
+ syncedValueRef.current = newValue_0;
19233
+ if (!keepInputText) {
19234
+ setInputText(filterValueToText(newValue_0));
19235
+ }
19236
+ const hasNewValue = newValue_0 !== null && Array.isArray(newValue_0) ? newValue_0.length > 0 : newValue_0 !== void 0;
19054
19237
  if (op_0 && hasNewValue) {
19055
- setValue([op_0, newValue]);
19238
+ setValue([op_0, newValue_0]);
19056
19239
  } else {
19057
19240
  setValue(void 0);
19058
19241
  }
19059
19242
  };
19060
- $[10] = operation;
19061
- $[11] = setValue;
19062
- $[12] = t4;
19063
- } else {
19064
- t4 = $[12];
19065
- }
19066
- const updateFilter = t4;
19067
- let t5;
19068
- if ($[13] !== operation) {
19069
- t5 = multipleSelectOperations$1.includes(operation);
19070
- $[13] = operation;
19243
+ $[12] = operation;
19244
+ $[13] = setValue;
19071
19245
  $[14] = t5;
19072
19246
  } else {
19073
19247
  t5 = $[14];
19074
19248
  }
19075
- const multiple = t5;
19249
+ const updateFilter = t5;
19076
19250
  let t6;
19077
- if ($[15] !== internalValue || $[16] !== updateFilter) {
19078
- t6 = (value_0) => {
19079
- updateFilter(value_0, internalValue);
19251
+ if ($[15] !== dataType || $[16] !== operation || $[17] !== updateFilter) {
19252
+ t6 = function updateFilterFromText2(text) {
19253
+ setInputText(text);
19254
+ const {
19255
+ updateValue,
19256
+ value: parsedValue
19257
+ } = parseFilterTextInput(text, dataType);
19258
+ if (updateValue) {
19259
+ updateFilter(operation, parsedValue, true);
19260
+ }
19080
19261
  };
19081
- $[15] = internalValue;
19082
- $[16] = updateFilter;
19083
- $[17] = t6;
19262
+ $[15] = dataType;
19263
+ $[16] = operation;
19264
+ $[17] = updateFilter;
19265
+ $[18] = t6;
19084
19266
  } else {
19085
- t6 = $[17];
19267
+ t6 = $[18];
19086
19268
  }
19269
+ const updateFilterFromText = t6;
19087
19270
  let t7;
19088
- if ($[18] !== possibleOperations) {
19089
- t7 = possibleOperations.map(_temp2$6);
19090
- $[18] = possibleOperations;
19091
- $[19] = t7;
19271
+ if ($[19] !== operation) {
19272
+ t7 = multipleSelectOperations$1.includes(operation);
19273
+ $[19] = operation;
19274
+ $[20] = t7;
19092
19275
  } else {
19093
- t7 = $[19];
19276
+ t7 = $[20];
19094
19277
  }
19278
+ const multiple = t7;
19095
19279
  let t8;
19096
- if ($[20] !== operation || $[21] !== t6 || $[22] !== t7) {
19097
- t8 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-[100px]", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Select, { value: operation, size: "medium", fullWidth: true, position: "item-aligned", onValueChange: t6, renderValue: _temp$m, children: t7 }) });
19098
- $[20] = operation;
19099
- $[21] = t6;
19100
- $[22] = t7;
19280
+ if ($[21] !== internalValue || $[22] !== updateFilter) {
19281
+ t8 = (value_0) => {
19282
+ updateFilter(value_0, internalValue);
19283
+ };
19284
+ $[21] = internalValue;
19285
+ $[22] = updateFilter;
19101
19286
  $[23] = t8;
19102
19287
  } else {
19103
19288
  t8 = $[23];
19104
19289
  }
19105
19290
  let t9;
19106
- if ($[24] !== dataType || $[25] !== enumValues || $[26] !== internalValue || $[27] !== isNullOperation || $[28] !== operation || $[29] !== updateFilter) {
19107
- t9 = !enumValues && /* @__PURE__ */ jsxRuntime.jsx(ui.TextField, { size: "medium", type: dataType === "number" ? "number" : void 0, value: internalValue !== void 0 && internalValue != null ? String(internalValue) : "", disabled: isNullOperation, placeholder: isNullOperation ? "null" : void 0, onChange: (evt) => {
19108
- const val_1 = dataType === "number" ? parseFloat(evt.target.value) : evt.target.value;
19109
- updateFilter(operation, val_1);
19110
- }, endAdornment: internalValue !== void 0 && internalValue != null && /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { onClick: (e) => updateFilter(operation, void 0), children: /* @__PURE__ */ jsxRuntime.jsx(ui.CloseIcon, {}) }) });
19111
- $[24] = dataType;
19112
- $[25] = enumValues;
19113
- $[26] = internalValue;
19114
- $[27] = isNullOperation;
19115
- $[28] = operation;
19116
- $[29] = updateFilter;
19117
- $[30] = t9;
19291
+ if ($[24] !== possibleOperations) {
19292
+ t9 = possibleOperations.map(_temp2$6);
19293
+ $[24] = possibleOperations;
19294
+ $[25] = t9;
19118
19295
  } else {
19119
- t9 = $[30];
19296
+ t9 = $[25];
19120
19297
  }
19121
19298
  let t10;
19122
- if ($[31] !== dataType || $[32] !== enumValues || $[33] !== internalValue || $[34] !== isNullOperation || $[35] !== multiple || $[36] !== name || $[37] !== operation || $[38] !== updateFilter) {
19123
- t10 = enumValues && !multiple && /* @__PURE__ */ jsxRuntime.jsx(ui.Select, { size: "medium", position: "item-aligned", fullWidth: true, disabled: isNullOperation, value: typeof internalValue === "string" ? internalValue : "", onValueChange: (value_1) => {
19299
+ if ($[26] !== operation || $[27] !== t8 || $[28] !== t9) {
19300
+ t10 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-[100px]", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Select, { value: operation, size: "medium", fullWidth: true, position: "item-aligned", onValueChange: t8, renderValue: _temp$m, children: t9 }) });
19301
+ $[26] = operation;
19302
+ $[27] = t8;
19303
+ $[28] = t9;
19304
+ $[29] = t10;
19305
+ } else {
19306
+ t10 = $[29];
19307
+ }
19308
+ let t11;
19309
+ if ($[30] !== dataType || $[31] !== enumValues || $[32] !== inputText || $[33] !== isNullOperation || $[34] !== operation || $[35] !== updateFilter || $[36] !== updateFilterFromText) {
19310
+ t11 = !enumValues && /* @__PURE__ */ jsxRuntime.jsx(ui.TextField, { size: "medium", type: dataType === "number" ? "number" : void 0, value: inputText, disabled: isNullOperation, placeholder: isNullOperation ? "null" : void 0, onChange: (evt) => {
19311
+ updateFilterFromText(evt.target.value);
19312
+ }, endAdornment: inputText !== "" && /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { onClick: (e) => updateFilter(operation, void 0), children: /* @__PURE__ */ jsxRuntime.jsx(ui.CloseIcon, {}) }) });
19313
+ $[30] = dataType;
19314
+ $[31] = enumValues;
19315
+ $[32] = inputText;
19316
+ $[33] = isNullOperation;
19317
+ $[34] = operation;
19318
+ $[35] = updateFilter;
19319
+ $[36] = updateFilterFromText;
19320
+ $[37] = t11;
19321
+ } else {
19322
+ t11 = $[37];
19323
+ }
19324
+ let t12;
19325
+ if ($[38] !== dataType || $[39] !== enumValues || $[40] !== internalValue || $[41] !== isNullOperation || $[42] !== multiple || $[43] !== name || $[44] !== operation || $[45] !== updateFilter) {
19326
+ t12 = enumValues && !multiple && /* @__PURE__ */ jsxRuntime.jsx(ui.Select, { size: "medium", position: "item-aligned", fullWidth: true, disabled: isNullOperation, value: typeof internalValue === "string" ? internalValue : "", onValueChange: (value_1) => {
19124
19327
  if (value_1 !== "") {
19125
19328
  updateFilter(operation, dataType === "number" ? parseInt(value_1) : value_1);
19126
19329
  }
@@ -19133,62 +19336,62 @@
19133
19336
  }
19134
19337
  return /* @__PURE__ */ jsxRuntime.jsx(EnumValuesChip, { enumKey, enumValues, size: "small" }, `select_value_${name}_${enumKey}`);
19135
19338
  }, children: enumValues.map((enumConfig) => /* @__PURE__ */ jsxRuntime.jsx(ui.SelectItem, { value: String(enumConfig.id), children: /* @__PURE__ */ jsxRuntime.jsx(EnumValuesChip, { enumKey: String(enumConfig.id), enumValues, size: "small" }) }, `select_item_${name}_${enumConfig.id}`)) });
19136
- $[31] = dataType;
19137
- $[32] = enumValues;
19138
- $[33] = internalValue;
19139
- $[34] = isNullOperation;
19140
- $[35] = multiple;
19141
- $[36] = name;
19142
- $[37] = operation;
19143
- $[38] = updateFilter;
19144
- $[39] = t10;
19145
- } else {
19146
- t10 = $[39];
19339
+ $[38] = dataType;
19340
+ $[39] = enumValues;
19341
+ $[40] = internalValue;
19342
+ $[41] = isNullOperation;
19343
+ $[42] = multiple;
19344
+ $[43] = name;
19345
+ $[44] = operation;
19346
+ $[45] = updateFilter;
19347
+ $[46] = t12;
19348
+ } else {
19349
+ t12 = $[46];
19147
19350
  }
19148
- let t11;
19149
- if ($[40] !== dataType || $[41] !== enumValues || $[42] !== internalValue || $[43] !== isNullOperation || $[44] !== multiple || $[45] !== name || $[46] !== operation || $[47] !== updateFilter) {
19150
- t11 = enumValues && multiple && /* @__PURE__ */ jsxRuntime.jsx(ui.MultiSelect, { size: "medium", position: "item-aligned", value: Array.isArray(internalValue) ? internalValue.map(_temp3$3) : [], disabled: isNullOperation, onValueChange: (value_2) => {
19351
+ let t13;
19352
+ if ($[47] !== dataType || $[48] !== enumValues || $[49] !== internalValue || $[50] !== isNullOperation || $[51] !== multiple || $[52] !== name || $[53] !== operation || $[54] !== updateFilter) {
19353
+ t13 = enumValues && multiple && /* @__PURE__ */ jsxRuntime.jsx(ui.MultiSelect, { size: "medium", position: "item-aligned", value: Array.isArray(internalValue) ? internalValue.map(_temp3$3) : [], disabled: isNullOperation, onValueChange: (value_2) => {
19151
19354
  updateFilter(operation, dataType === "number" ? value_2.map(_temp4$3) : value_2);
19152
19355
  }, multiple, endAdornment: internalValue && /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { className: "absolute right-2 top-3", onClick: (e_2) => updateFilter(operation, void 0), children: /* @__PURE__ */ jsxRuntime.jsx(ui.CloseIcon, {}) }), children: enumValues.map((enumConfig_0) => /* @__PURE__ */ jsxRuntime.jsx(ui.MultiSelectItem, { value: String(enumConfig_0.id), children: /* @__PURE__ */ jsxRuntime.jsx(EnumValuesChip, { enumKey: String(enumConfig_0.id), enumValues, size: "small" }) }, `select_value_${name}_${enumConfig_0.id}`)) });
19153
- $[40] = dataType;
19154
- $[41] = enumValues;
19155
- $[42] = internalValue;
19156
- $[43] = isNullOperation;
19157
- $[44] = multiple;
19158
- $[45] = name;
19159
- $[46] = operation;
19160
- $[47] = updateFilter;
19161
- $[48] = t11;
19356
+ $[47] = dataType;
19357
+ $[48] = enumValues;
19358
+ $[49] = internalValue;
19359
+ $[50] = isNullOperation;
19360
+ $[51] = multiple;
19361
+ $[52] = name;
19362
+ $[53] = operation;
19363
+ $[54] = updateFilter;
19364
+ $[55] = t13;
19162
19365
  } else {
19163
- t11 = $[48];
19366
+ t13 = $[55];
19164
19367
  }
19165
- let t12;
19166
- if ($[49] !== t10 || $[50] !== t11 || $[51] !== t9) {
19167
- t12 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-grow ml-2 flex flex-col gap-2", children: [
19168
- t9,
19169
- t10,
19170
- t11
19368
+ let t14;
19369
+ if ($[56] !== t11 || $[57] !== t12 || $[58] !== t13) {
19370
+ t14 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-grow ml-2 flex flex-col gap-2", children: [
19371
+ t11,
19372
+ t12,
19373
+ t13
19171
19374
  ] });
19172
- $[49] = t10;
19173
- $[50] = t11;
19174
- $[51] = t9;
19175
- $[52] = t12;
19375
+ $[56] = t11;
19376
+ $[57] = t12;
19377
+ $[58] = t13;
19378
+ $[59] = t14;
19176
19379
  } else {
19177
- t12 = $[52];
19380
+ t14 = $[59];
19178
19381
  }
19179
- let t13;
19180
- if ($[53] !== t12 || $[54] !== t8) {
19181
- t13 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex w-full", children: [
19182
- t8,
19183
- t12
19382
+ let t15;
19383
+ if ($[60] !== t10 || $[61] !== t14) {
19384
+ t15 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex w-full", children: [
19385
+ t10,
19386
+ t14
19184
19387
  ] });
19185
- $[53] = t12;
19186
- $[54] = t8;
19187
- $[55] = t13;
19388
+ $[60] = t10;
19389
+ $[61] = t14;
19390
+ $[62] = t15;
19188
19391
  } else {
19189
- t13 = $[55];
19392
+ t15 = $[62];
19190
19393
  }
19191
- return t13;
19394
+ return t15;
19192
19395
  }
19193
19396
  function _temp4$3(v) {
19194
19397
  return parseInt(v);
@@ -19723,7 +19926,7 @@
19723
19926
  }
19724
19927
  }, [tableRowActionsBuilder, additionalCellRenderer, propertyCellRenderer, size]);
19725
19928
  return /* @__PURE__ */ jsxRuntime.jsxs("div", { ref, style, className: ui.cls("h-full w-full flex flex-col bg-white dark:bg-surface-950", className), children: [
19726
- !hideToolbar && /* @__PURE__ */ jsxRuntime.jsx(CollectionTableToolbar, { onTextSearch: textSearchEnabled ? onTextSearch : void 0, textSearchLoading, onTextSearchClick: textSearchEnabled ? onTextSearchClick : void 0, title, actionsStart, actions, viewModeToggle, loading: tableController.dataLoading }),
19929
+ !hideToolbar && /* @__PURE__ */ jsxRuntime.jsx(CollectionTableToolbar, { onTextSearch: textSearchEnabled ? onTextSearch : void 0, textSearchLoading, onTextSearchClick: textSearchEnabled ? onTextSearchClick : void 0, initialSearchString: tableController.searchString, title, actionsStart, actions, viewModeToggle, loading: tableController.dataLoading }),
19727
19930
  /* @__PURE__ */ jsxRuntime.jsx(SelectableTable, { columns, size, inlineEditing, cellRenderer, onEntityClick, highlightedRow: (entity_1) => Boolean(selectedEntities?.find((e_0) => e_0.id === entity_1.id && e_0.path === entity_1.path)), tableController, onValueChange, initialScroll, onScroll, onColumnResize, hoverRow, filterable, emptyComponent, endAdornment, AddColumnComponent, onColumnsOrderChange })
19728
19931
  ] });
19729
19932
  };
@@ -19762,9 +19965,119 @@
19762
19965
  }, [data, timeoutMs, deps, immediateUpdate]);
19763
19966
  return immediateUpdate ? data : deferredData;
19764
19967
  }
19968
+ function encodeFilterAndSort(filterValues, sortBy, searchString) {
19969
+ const entries = {};
19970
+ if (sortBy) {
19971
+ entries["__sort"] = encodeURIComponent(sortBy[0]);
19972
+ entries["__sort_order"] = encodeURIComponent(sortBy[1]);
19973
+ }
19974
+ if (filterValues) {
19975
+ Object.entries(filterValues).forEach(([key, value]) => {
19976
+ if (value) {
19977
+ const [op, val] = value;
19978
+ let encodedValue = val;
19979
+ try {
19980
+ if (typeof val === "object") {
19981
+ if (val instanceof Date) {
19982
+ encodedValue = val.toISOString();
19983
+ } else if (Array.isArray(val)) {
19984
+ encodedValue = JSON.stringify(val, (key2, value2) => {
19985
+ if (value2 instanceof EntityReference) {
19986
+ return encodeRef(value2);
19987
+ }
19988
+ return value2;
19989
+ });
19990
+ } else if (val instanceof EntityReference) {
19991
+ encodedValue = encodeRef(val);
19992
+ }
19993
+ } else if (typeof val === "string") {
19994
+ encodedValue = JSON.stringify(val);
19995
+ }
19996
+ } catch (e) {
19997
+ encodedValue = val;
19998
+ }
19999
+ if (encodedValue !== void 0) {
20000
+ entries[encodeURIComponent(`${key}_op`)] = encodeURIComponent(op);
20001
+ entries[encodeURIComponent(`${key}_value`)] = encodedValue !== null && encodedValue !== void 0 ? encodeURIComponent(encodedValue.toString()) : "null";
20002
+ }
20003
+ }
20004
+ });
20005
+ }
20006
+ if (searchString) {
20007
+ entries["search"] = encodeURIComponent(searchString);
20008
+ }
20009
+ if (!Object.keys(entries).length) {
20010
+ return "";
20011
+ }
20012
+ return Object.entries(entries).map(([key, value]) => `${key}=${value}`).join("&");
20013
+ }
20014
+ function parseFilterAndSort(search) {
20015
+ const entries = new URLSearchParams(search);
20016
+ const filterValues = {};
20017
+ let sortBy = void 0;
20018
+ entries.forEach((value, key) => {
20019
+ if (key === "__sort") {
20020
+ sortBy = [decodeURIComponent(value), entries.get("__sort_order")];
20021
+ } else if (key.endsWith("_op")) {
20022
+ const field = key.replace("_op", "");
20023
+ const filterOp = decodeURIComponent(value);
20024
+ const filterValStr = entries.get(`${field}_value`);
20025
+ if (filterValStr !== null) {
20026
+ filterValues[field] = [filterOp, decodeString(filterValStr)];
20027
+ }
20028
+ }
20029
+ });
20030
+ const searchString = entries.get("search") ?? void 0;
20031
+ return {
20032
+ filterValues: Object.keys(filterValues).length ? filterValues : void 0,
20033
+ sortBy,
20034
+ searchString: searchString ? searchString : void 0
20035
+ };
20036
+ }
20037
+ function isDate(dateString) {
20038
+ const regexPattern = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d{3}Z$/;
20039
+ if (!regexPattern.test(dateString)) {
20040
+ return false;
20041
+ }
20042
+ const date = new Date(dateString);
20043
+ return date.toISOString() === dateString;
20044
+ }
20045
+ function encodeRef(val) {
20046
+ return `ref::${val.path}/${encodeEntityId(val.id)}`;
20047
+ }
20048
+ function decodeRef(encoded) {
20049
+ const separatorIndex = encoded.lastIndexOf("/");
20050
+ if (separatorIndex < 0) return new EntityReference(encoded, "");
20051
+ return new EntityReference(decodeEntityId(encoded.substring(separatorIndex + 1)), encoded.substring(0, separatorIndex));
20052
+ }
20053
+ function decodeString(val) {
20054
+ let parsedFilterVal = val;
20055
+ if (isDate(val)) {
20056
+ try {
20057
+ parsedFilterVal = new Date(val);
20058
+ } catch (e) {
20059
+ }
20060
+ }
20061
+ if (typeof parsedFilterVal === "string") {
20062
+ try {
20063
+ parsedFilterVal = JSON.parse(parsedFilterVal, (key, value) => {
20064
+ if (typeof value === "string" && value.startsWith("ref::")) {
20065
+ return decodeRef(value.substring(5));
20066
+ }
20067
+ return value;
20068
+ });
20069
+ } catch (e) {
20070
+ }
20071
+ }
20072
+ if (typeof parsedFilterVal === "string" && parsedFilterVal.startsWith("ref::")) {
20073
+ return decodeRef(parsedFilterVal.substring(5));
20074
+ }
20075
+ return parsedFilterVal;
20076
+ }
19765
20077
  const DEFAULT_PAGE_SIZE$1 = 50;
19766
20078
  function useDataSourceTableController({
19767
20079
  fullPath,
20080
+ pathSegments,
19768
20081
  collection,
19769
20082
  scrollRestoration,
19770
20083
  entitiesDisplayedFirst,
@@ -19781,14 +20094,15 @@
19781
20094
  const navigation = useNavigationController();
19782
20095
  const dataSource = useDataSource();
19783
20096
  const resolvedPath = React.useMemo(() => navigation.resolveIdsFrom(fullPath), [fullPath, navigation.resolveIdsFrom]);
20097
+ const resolvedPathSegments = pathSegments;
19784
20098
  const forceFilter = forceFilterFromProps ?? forceFilterFromCollection;
19785
20099
  const paginationEnabled = collection.pagination === void 0 || Boolean(collection.pagination);
19786
20100
  const pageSize = typeof collection.pagination === "number" ? collection.pagination : DEFAULT_PAGE_SIZE$1;
19787
- const [searchString, setSearchString] = React.useState();
19788
20101
  const checkFilterCombination = React.useCallback((filterValues, sortBy) => {
19789
20102
  if (!dataSource.isFilterCombinationValid) return true;
19790
20103
  return dataSource.isFilterCombinationValid({
19791
20104
  path: resolvedPath,
20105
+ pathSegments: resolvedPathSegments,
19792
20106
  collection,
19793
20107
  filterValues,
19794
20108
  sortBy
@@ -19816,7 +20130,8 @@
19816
20130
  const location = reactRouterDom.useLocation();
19817
20131
  const {
19818
20132
  filterValues: initialFilterUrl,
19819
- sortBy: initialSortUrl
20133
+ sortBy: initialSortUrl,
20134
+ searchString: initialSearchUrl
19820
20135
  } = parseFilterAndSort(location.search);
19821
20136
  const availableFilterKeys = collection.allowedFilters ?? Object.keys(collection.properties);
19822
20137
  const forcedFilterKeys = collection.forceFilter ? Object.keys(collection.forceFilter) : [];
@@ -19839,6 +20154,7 @@
19839
20154
  const initFilters = forceFilter ?? (updateUrl ? initialFilterUrl : void 0) ?? initialFilter ?? void 0;
19840
20155
  const [filterValues_0, setFilterValues] = React.useState(removeUnallowedFilters(initFilters));
19841
20156
  const [sortBy_0, setSortBy] = React.useState((updateUrl ? initialSortUrl : void 0) ?? initialSortInternal);
20157
+ const [searchString, setSearchString] = React.useState(updateUrl ? initialSearchUrl : void 0);
19842
20158
  useUpdateUrl(filterValues_0, sortBy_0, searchString, updateUrl);
19843
20159
  const collectionScroll = scrollRestoration?.getCollectionScroll(fullPath, filterValues_0);
19844
20160
  const initialItemCount = collectionScroll?.data.length ?? pageSize;
@@ -19875,6 +20191,12 @@
19875
20191
  React.useEffect(() => {
19876
20192
  setDataLoading(true);
19877
20193
  const onEntitiesUpdate = async (entities) => {
20194
+ if (resolvedPathSegments) {
20195
+ entities = entities.map((e) => e.pathSegments ? e : {
20196
+ ...e,
20197
+ pathSegments: resolvedPathSegments
20198
+ });
20199
+ }
19878
20200
  if (collection.callbacks?.onFetch) {
19879
20201
  try {
19880
20202
  entities = await Promise.all(entities.map((entity) => collection.callbacks.onFetch({
@@ -19883,14 +20205,14 @@
19883
20205
  entity,
19884
20206
  context
19885
20207
  })));
19886
- } catch (e) {
19887
- console.error(e);
20208
+ } catch (e_0) {
20209
+ console.error(e_0);
19888
20210
  }
19889
20211
  }
19890
20212
  setDataLoading(false);
19891
20213
  setDataLoadingError(void 0);
19892
- setRawData(entities.map((e_0) => ({
19893
- ...e_0
20214
+ setRawData(entities.map((e_1) => ({
20215
+ ...e_1
19894
20216
  // values: sanitizeData(e.values, resolvedCollection.properties)
19895
20217
  })));
19896
20218
  setNoMoreToLoad(!itemCount || entities.length < itemCount);
@@ -19901,30 +20223,38 @@
19901
20223
  setRawData([]);
19902
20224
  setDataLoadingError(error);
19903
20225
  };
19904
- if (dataSource.listenCollection) {
19905
- return dataSource.listenCollection({
19906
- path: resolvedPath,
19907
- collection,
19908
- onUpdate: onEntitiesUpdate,
19909
- onError,
19910
- searchString,
19911
- filter: filterValues_0,
19912
- limit: itemCount,
19913
- startAfter: void 0,
19914
- orderBy: sortByProperty,
19915
- order: currentSort
19916
- });
19917
- } else {
19918
- dataSource.fetchCollection({
19919
- path: resolvedPath,
19920
- collection,
19921
- searchString,
19922
- filter: filterValues_0,
19923
- limit: itemCount,
19924
- startAfter: void 0,
19925
- orderBy: sortByProperty,
19926
- order: currentSort
19927
- }).then(onEntitiesUpdate).catch(onError);
20226
+ try {
20227
+ if (dataSource.listenCollection) {
20228
+ return dataSource.listenCollection({
20229
+ path: resolvedPath,
20230
+ pathSegments: resolvedPathSegments,
20231
+ collection,
20232
+ onUpdate: onEntitiesUpdate,
20233
+ onError,
20234
+ searchString,
20235
+ filter: filterValues_0,
20236
+ limit: itemCount,
20237
+ startAfter: void 0,
20238
+ orderBy: sortByProperty,
20239
+ order: currentSort
20240
+ });
20241
+ } else {
20242
+ dataSource.fetchCollection({
20243
+ path: resolvedPath,
20244
+ pathSegments: resolvedPathSegments,
20245
+ collection,
20246
+ searchString,
20247
+ filter: filterValues_0,
20248
+ limit: itemCount,
20249
+ startAfter: void 0,
20250
+ orderBy: sortByProperty,
20251
+ order: currentSort
20252
+ }).then(onEntitiesUpdate).catch(onError);
20253
+ return () => {
20254
+ };
20255
+ }
20256
+ } catch (e_2) {
20257
+ onError(e_2 instanceof Error ? e_2 : new Error(String(e_2)));
19928
20258
  return () => {
19929
20259
  };
19930
20260
  }
@@ -19971,9 +20301,7 @@
19971
20301
  if ($[0] !== filterValues || $[1] !== searchString || $[2] !== sortBy || $[3] !== updateUrl) {
19972
20302
  t0 = () => {
19973
20303
  if (updateUrl) {
19974
- const newUrl = encodeFilterAndSort(filterValues, sortBy);
19975
- const search = searchString ? `&search=${encodeURIComponent(searchString)}` : "";
19976
- const state = `${newUrl}${search}`;
20304
+ const state = encodeFilterAndSort(filterValues, sortBy, searchString);
19977
20305
  const hash2 = window.location.hash;
19978
20306
  if (state === "") {
19979
20307
  window.history.replaceState({}, "", `${window.location.pathname}${hash2}`);
@@ -19995,110 +20323,6 @@
19995
20323
  }
19996
20324
  React.useEffect(t0, t1);
19997
20325
  }
19998
- function encodeFilterAndSort(filterValues, sortBy) {
19999
- const entries = {};
20000
- if (sortBy) {
20001
- entries["__sort"] = encodeURIComponent(sortBy[0]);
20002
- entries["__sort_order"] = encodeURIComponent(sortBy[1]);
20003
- }
20004
- if (filterValues) {
20005
- Object.entries(filterValues).forEach(([key, value]) => {
20006
- if (value) {
20007
- const [op, val] = value;
20008
- let encodedValue = val;
20009
- try {
20010
- if (typeof val === "object") {
20011
- if (val instanceof Date) {
20012
- encodedValue = val.toISOString();
20013
- } else if (Array.isArray(val)) {
20014
- encodedValue = JSON.stringify(val, (key2, value2) => {
20015
- if (value2 instanceof EntityReference) {
20016
- return encodeRef(value2);
20017
- }
20018
- return value2;
20019
- });
20020
- } else if (val instanceof EntityReference) {
20021
- encodedValue = encodeRef(val);
20022
- }
20023
- } else if (typeof val === "string") {
20024
- encodedValue = JSON.stringify(val);
20025
- }
20026
- } catch (e) {
20027
- encodedValue = val;
20028
- }
20029
- if (encodedValue !== void 0) {
20030
- entries[encodeURIComponent(`${key}_op`)] = encodeURIComponent(op);
20031
- entries[encodeURIComponent(`${key}_value`)] = encodedValue !== null && encodedValue !== void 0 ? encodeURIComponent(encodedValue.toString()) : "null";
20032
- }
20033
- }
20034
- });
20035
- }
20036
- if (!Object.keys(entries).length) {
20037
- return "";
20038
- }
20039
- return Object.entries(entries).map(([key, value]) => `${key}=${value}`).join("&");
20040
- }
20041
- function parseFilterAndSort(search) {
20042
- const entries = new URLSearchParams(search);
20043
- const filterValues = {};
20044
- let sortBy = void 0;
20045
- entries.forEach((value, key) => {
20046
- if (key === "__sort") {
20047
- sortBy = [decodeURIComponent(value), entries.get("__sort_order")];
20048
- } else if (key.endsWith("_op")) {
20049
- const field = key.replace("_op", "");
20050
- const filterOp = decodeURIComponent(value);
20051
- const filterValStr = entries.get(`${field}_value`);
20052
- if (filterValStr !== null) {
20053
- filterValues[field] = [filterOp, decodeString(filterValStr)];
20054
- }
20055
- }
20056
- });
20057
- return {
20058
- filterValues: Object.keys(filterValues).length ? filterValues : void 0,
20059
- sortBy
20060
- };
20061
- }
20062
- function isDate(dateString) {
20063
- const regexPattern = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d{3}Z$/;
20064
- if (!regexPattern.test(dateString)) {
20065
- return false;
20066
- }
20067
- const date = new Date(dateString);
20068
- return date.toISOString() === dateString;
20069
- }
20070
- function encodeRef(val) {
20071
- return `ref::${val.path}/${encodeEntityId(val.id)}`;
20072
- }
20073
- function decodeRef(encoded) {
20074
- const separatorIndex = encoded.lastIndexOf("/");
20075
- if (separatorIndex < 0) return new EntityReference(encoded, "");
20076
- return new EntityReference(decodeEntityId(encoded.substring(separatorIndex + 1)), encoded.substring(0, separatorIndex));
20077
- }
20078
- function decodeString(val) {
20079
- let parsedFilterVal = val;
20080
- if (isDate(val)) {
20081
- try {
20082
- parsedFilterVal = new Date(val);
20083
- } catch (e) {
20084
- }
20085
- }
20086
- if (typeof parsedFilterVal === "string") {
20087
- try {
20088
- parsedFilterVal = JSON.parse(parsedFilterVal, (key, value) => {
20089
- if (typeof value === "string" && value.startsWith("ref::")) {
20090
- return decodeRef(value.substring(5));
20091
- }
20092
- return value;
20093
- });
20094
- } catch (e) {
20095
- }
20096
- }
20097
- if (typeof parsedFilterVal === "string" && parsedFilterVal.startsWith("ref::")) {
20098
- return decodeRef(parsedFilterVal.substring(5));
20099
- }
20100
- return parsedFilterVal;
20101
- }
20102
20326
  function useSelectionController(onSelectionChange) {
20103
20327
  const [selectedEntities, setSelectedEntities] = React.useState([]);
20104
20328
  const toggleEntitySelection = React.useCallback((entity, newSelectedState) => {
@@ -20134,95 +20358,57 @@
20134
20358
  };
20135
20359
  }
20136
20360
  function useTableSearchHelper(t0) {
20137
- const $ = reactCompilerRuntime.c(33);
20361
+ const $ = reactCompilerRuntime.c(18);
20138
20362
  const {
20139
20363
  collection,
20140
20364
  fullPath,
20141
- parentCollectionIds
20365
+ parentCollectionIds,
20366
+ initialSearchString
20142
20367
  } = t0;
20143
20368
  const context = useFireCMSContext();
20144
20369
  const customizationController = useCustomizationController();
20145
20370
  const dataSource = useDataSource();
20146
20371
  const [textSearchLoading, setTextSearchLoading] = React.useState(false);
20147
20372
  const [textSearchInitialised, setTextSearchInitialised] = React.useState(false);
20373
+ const autoInitialisedRef = React.useRef(false);
20148
20374
  let onTextSearchClick;
20149
20375
  let textSearchEnabled;
20150
20376
  if ($[0] !== collection || $[1] !== context || $[2] !== customizationController.plugins || $[3] !== dataSource || $[4] !== fullPath || $[5] !== parentCollectionIds) {
20151
20377
  textSearchEnabled = Boolean(collection.textSearchEnabled);
20152
- let props;
20153
- let t12;
20154
- if ($[8] !== collection || $[9] !== context || $[10] !== customizationController.plugins || $[11] !== fullPath || $[12] !== parentCollectionIds) {
20155
- props = {
20156
- context,
20157
- path: fullPath,
20158
- databaseId: collection.databaseId,
20159
- collection,
20160
- parentCollectionIds
20161
- };
20162
- t12 = customizationController.plugins?.find((p) => p.collectionView?.blockSearch?.(props));
20163
- $[8] = collection;
20164
- $[9] = context;
20165
- $[10] = customizationController.plugins;
20166
- $[11] = fullPath;
20167
- $[12] = parentCollectionIds;
20168
- $[13] = props;
20169
- $[14] = t12;
20170
- } else {
20171
- props = $[13];
20172
- t12 = $[14];
20173
- }
20174
- const searchBlocked = t12;
20175
- let t2;
20176
- if ($[15] !== customizationController.plugins || $[16] !== dataSource?.initTextSearch) {
20177
- t2 = Boolean(dataSource?.initTextSearch) || customizationController.plugins?.find(_temp$k);
20178
- $[15] = customizationController.plugins;
20179
- $[16] = dataSource?.initTextSearch;
20180
- $[17] = t2;
20181
- } else {
20182
- t2 = $[17];
20183
- }
20184
- const addTextSearchClickListener = t2;
20378
+ const props = {
20379
+ context,
20380
+ path: fullPath,
20381
+ databaseId: collection.databaseId,
20382
+ collection,
20383
+ parentCollectionIds
20384
+ };
20385
+ const searchBlocked = customizationController.plugins?.find((p) => p.collectionView?.blockSearch?.(props));
20386
+ const addTextSearchClickListener = Boolean(dataSource?.initTextSearch) || customizationController.plugins?.find(_temp$k);
20185
20387
  if (addTextSearchClickListener) {
20186
- let t3;
20187
- if ($[18] !== addTextSearchClickListener || $[19] !== collection || $[20] !== context || $[21] !== customizationController.plugins || $[22] !== dataSource || $[23] !== fullPath || $[24] !== parentCollectionIds || $[25] !== props || $[26] !== searchBlocked) {
20188
- t3 = addTextSearchClickListener ? () => {
20189
- setTextSearchLoading(true);
20190
- const promises = [];
20191
- if (dataSource?.initTextSearch && !searchBlocked) {
20192
- promises.push(dataSource.initTextSearch(props));
20193
- }
20194
- if (searchBlocked) {
20195
- customizationController.plugins?.forEach((p_1) => {
20196
- if (p_1.collectionView?.onTextSearchClick) {
20197
- promises.push(p_1.collectionView.onTextSearchClick({
20198
- context,
20199
- path: fullPath,
20200
- collection,
20201
- parentCollectionIds
20202
- }));
20203
- }
20204
- });
20205
- }
20206
- return Promise.all(promises).then((res) => {
20207
- if (res.every(Boolean)) {
20208
- setTextSearchInitialised(true);
20388
+ onTextSearchClick = addTextSearchClickListener ? () => {
20389
+ setTextSearchLoading(true);
20390
+ const promises = [];
20391
+ if (dataSource?.initTextSearch && !searchBlocked) {
20392
+ promises.push(dataSource.initTextSearch(props));
20393
+ }
20394
+ if (searchBlocked) {
20395
+ customizationController.plugins?.forEach((p_1) => {
20396
+ if (p_1.collectionView?.onTextSearchClick) {
20397
+ promises.push(p_1.collectionView.onTextSearchClick({
20398
+ context,
20399
+ path: fullPath,
20400
+ collection,
20401
+ parentCollectionIds
20402
+ }));
20209
20403
  }
20210
- }).finally(() => setTextSearchLoading(false));
20211
- } : void 0;
20212
- $[18] = addTextSearchClickListener;
20213
- $[19] = collection;
20214
- $[20] = context;
20215
- $[21] = customizationController.plugins;
20216
- $[22] = dataSource;
20217
- $[23] = fullPath;
20218
- $[24] = parentCollectionIds;
20219
- $[25] = props;
20220
- $[26] = searchBlocked;
20221
- $[27] = t3;
20222
- } else {
20223
- t3 = $[27];
20224
- }
20225
- onTextSearchClick = t3;
20404
+ });
20405
+ }
20406
+ return Promise.all(promises).then((res) => {
20407
+ if (res.every(Boolean)) {
20408
+ setTextSearchInitialised(true);
20409
+ }
20410
+ }).finally(() => setTextSearchLoading(false));
20411
+ } : void 0;
20226
20412
  customizationController.plugins?.forEach((p_2) => {
20227
20413
  if (!textSearchEnabled) {
20228
20414
  if (p_2.collectionView?.showTextSearchBar) {
@@ -20242,29 +20428,54 @@
20242
20428
  $[3] = dataSource;
20243
20429
  $[4] = fullPath;
20244
20430
  $[5] = parentCollectionIds;
20245
- $[6] = textSearchEnabled;
20246
- $[7] = onTextSearchClick;
20431
+ $[6] = onTextSearchClick;
20432
+ $[7] = textSearchEnabled;
20247
20433
  } else {
20248
- textSearchEnabled = $[6];
20249
- onTextSearchClick = $[7];
20434
+ onTextSearchClick = $[6];
20435
+ textSearchEnabled = $[7];
20250
20436
  }
20437
+ const shouldAutoInitialise = Boolean(initialSearchString) && textSearchEnabled && !textSearchInitialised && Boolean(onTextSearchClick);
20251
20438
  let t1;
20252
- if ($[28] !== onTextSearchClick || $[29] !== textSearchEnabled || $[30] !== textSearchInitialised || $[31] !== textSearchLoading) {
20253
- t1 = {
20439
+ if ($[8] !== onTextSearchClick || $[9] !== shouldAutoInitialise) {
20440
+ t1 = () => {
20441
+ if (autoInitialisedRef.current || !shouldAutoInitialise) {
20442
+ return;
20443
+ }
20444
+ autoInitialisedRef.current = true;
20445
+ onTextSearchClick?.();
20446
+ };
20447
+ $[8] = onTextSearchClick;
20448
+ $[9] = shouldAutoInitialise;
20449
+ $[10] = t1;
20450
+ } else {
20451
+ t1 = $[10];
20452
+ }
20453
+ let t2;
20454
+ if ($[11] !== shouldAutoInitialise) {
20455
+ t2 = [shouldAutoInitialise];
20456
+ $[11] = shouldAutoInitialise;
20457
+ $[12] = t2;
20458
+ } else {
20459
+ t2 = $[12];
20460
+ }
20461
+ React.useEffect(t1, t2);
20462
+ let t3;
20463
+ if ($[13] !== onTextSearchClick || $[14] !== textSearchEnabled || $[15] !== textSearchInitialised || $[16] !== textSearchLoading) {
20464
+ t3 = {
20254
20465
  textSearchLoading,
20255
20466
  textSearchInitialised,
20256
20467
  onTextSearchClick,
20257
20468
  textSearchEnabled
20258
20469
  };
20259
- $[28] = onTextSearchClick;
20260
- $[29] = textSearchEnabled;
20261
- $[30] = textSearchInitialised;
20262
- $[31] = textSearchLoading;
20263
- $[32] = t1;
20470
+ $[13] = onTextSearchClick;
20471
+ $[14] = textSearchEnabled;
20472
+ $[15] = textSearchInitialised;
20473
+ $[16] = textSearchLoading;
20474
+ $[17] = t3;
20264
20475
  } else {
20265
- t1 = $[32];
20476
+ t3 = $[17];
20266
20477
  }
20267
- return t1;
20478
+ return t3;
20268
20479
  }
20269
20480
  function _temp$k(p_0) {
20270
20481
  return Boolean(p_0.collectionView?.onTextSearchClick);
@@ -20555,6 +20766,7 @@
20555
20766
  multiselect,
20556
20767
  collection,
20557
20768
  path: pathInput,
20769
+ pathSegments,
20558
20770
  selectedEntityIds: selectedEntityIdsProp,
20559
20771
  description,
20560
20772
  forceFilter,
@@ -20597,6 +20809,7 @@
20597
20809
  if (selectedEntityIds && collection) {
20598
20810
  Promise.all(selectedEntityIds.map((entityId) => dataSource.fetchEntity({
20599
20811
  path: fullPath,
20812
+ pathSegments,
20600
20813
  entityId,
20601
20814
  collection
20602
20815
  }))).then((entities) => {
@@ -24195,6 +24408,7 @@
24195
24408
  const DEFAULT_PAGE_SIZE = 20;
24196
24409
  function useBoardDataController({
24197
24410
  fullPath,
24411
+ pathSegments,
24198
24412
  collection,
24199
24413
  columnProperty,
24200
24414
  columns,
@@ -24207,6 +24421,7 @@
24207
24421
  const dataSource = useDataSource();
24208
24422
  const navigation = useNavigationController();
24209
24423
  const resolvedPath = React.useMemo(() => navigation.resolveIdsFrom(fullPath), [fullPath, navigation.resolveIdsFrom]);
24424
+ const resolvedPathSegments = pathSegments;
24210
24425
  const dataSourceRef = React.useRef(dataSource);
24211
24426
  const collectionRef = React.useRef(collection);
24212
24427
  const contextRef = React.useRef(context);
@@ -24218,11 +24433,13 @@
24218
24433
  const orderPropertyRef = React.useRef(orderProperty);
24219
24434
  const searchStringRef = React.useRef(searchString);
24220
24435
  const resolvedPathRef = React.useRef(resolvedPath);
24436
+ const resolvedPathSegmentsRef = React.useRef(resolvedPathSegments);
24221
24437
  filterValuesRef.current = filterValues;
24222
24438
  columnPropertyRef.current = columnProperty;
24223
24439
  orderPropertyRef.current = orderProperty;
24224
24440
  searchStringRef.current = searchString;
24225
24441
  resolvedPathRef.current = resolvedPath;
24442
+ resolvedPathSegmentsRef.current = resolvedPathSegments;
24226
24443
  const [columnItemCounts, setColumnItemCounts] = React.useState(() => {
24227
24444
  const initial = {};
24228
24445
  columns.forEach((col) => {
@@ -24269,6 +24486,7 @@
24269
24486
  const currentOrderProperty = orderPropertyRef.current;
24270
24487
  const currentSearchString = searchStringRef.current;
24271
24488
  const currentResolvedPath = resolvedPathRef.current;
24489
+ const currentPathSegments = resolvedPathSegmentsRef.current;
24272
24490
  const columnFilter = {
24273
24491
  ...currentFilterValues,
24274
24492
  [currentColumnProperty]: ["==", column]
@@ -24325,6 +24543,7 @@
24325
24543
  if (currentDataSource.listenCollection) {
24326
24544
  const unsubscribe = currentDataSource.listenCollection({
24327
24545
  path: currentResolvedPath,
24546
+ pathSegments: currentPathSegments,
24328
24547
  collection: currentCollection,
24329
24548
  onUpdate,
24330
24549
  onError,
@@ -24339,6 +24558,7 @@
24339
24558
  } else {
24340
24559
  currentDataSource.fetchCollection({
24341
24560
  path: currentResolvedPath,
24561
+ pathSegments: currentPathSegments,
24342
24562
  collection: currentCollection,
24343
24563
  searchString: currentSearchString,
24344
24564
  filter: columnFilter,
@@ -24367,6 +24587,7 @@
24367
24587
  const currentColumnProperty = columnPropertyRef.current;
24368
24588
  const currentSearchString = searchStringRef.current;
24369
24589
  const currentResolvedPath = resolvedPathRef.current;
24590
+ const currentPathSegments = resolvedPathSegmentsRef.current;
24370
24591
  const currentColumns = columns;
24371
24592
  const currentColumnItemCounts = columnItemCounts;
24372
24593
  const timeoutId = setTimeout(() => {
@@ -24381,6 +24602,7 @@
24381
24602
  };
24382
24603
  currentDataSource.countEntities({
24383
24604
  path: currentResolvedPath,
24605
+ pathSegments: currentPathSegments,
24384
24606
  collection: currentCollection,
24385
24607
  filter: columnFilter,
24386
24608
  searchString: currentSearchString
@@ -24625,6 +24847,7 @@
24625
24847
  collection,
24626
24848
  tableController,
24627
24849
  fullPath,
24850
+ pathSegments,
24628
24851
  parentCollectionIds = [],
24629
24852
  columnProperty,
24630
24853
  onEntityClick,
@@ -24718,6 +24941,7 @@
24718
24941
  const columns = localColumnsOrder;
24719
24942
  const boardDataController = useBoardDataController({
24720
24943
  fullPath,
24944
+ pathSegments,
24721
24945
  collection,
24722
24946
  columnProperty,
24723
24947
  columns,
@@ -25263,7 +25487,7 @@
25263
25487
  return t0;
25264
25488
  }
25265
25489
  function PopupFormFieldLoading(t0) {
25266
- const $ = reactCompilerRuntime.c(21);
25490
+ const $ = reactCompilerRuntime.c(22);
25267
25491
  const {
25268
25492
  tableKey,
25269
25493
  entityId,
@@ -25271,6 +25495,7 @@
25271
25495
  propertyKey,
25272
25496
  collection: inputCollection,
25273
25497
  path,
25498
+ pathSegments,
25274
25499
  cellRect,
25275
25500
  open,
25276
25501
  onClose,
@@ -25281,33 +25506,35 @@
25281
25506
  const [entity, setEntity] = React.useState(void 0);
25282
25507
  let t1;
25283
25508
  let t2;
25284
- if ($[0] !== dataSource || $[1] !== entityId || $[2] !== inputCollection || $[3] !== path) {
25509
+ if ($[0] !== dataSource || $[1] !== entityId || $[2] !== inputCollection || $[3] !== path || $[4] !== pathSegments) {
25285
25510
  t1 = () => {
25286
25511
  if (entityId && inputCollection) {
25287
25512
  dataSource.fetchEntity({
25288
25513
  path,
25514
+ pathSegments,
25289
25515
  entityId,
25290
25516
  collection: inputCollection
25291
25517
  }).then(setEntity);
25292
25518
  }
25293
25519
  };
25294
- t2 = [entityId, inputCollection, dataSource, path];
25520
+ t2 = [entityId, inputCollection, dataSource, path, pathSegments];
25295
25521
  $[0] = dataSource;
25296
25522
  $[1] = entityId;
25297
25523
  $[2] = inputCollection;
25298
25524
  $[3] = path;
25299
- $[4] = t1;
25300
- $[5] = t2;
25525
+ $[4] = pathSegments;
25526
+ $[5] = t1;
25527
+ $[6] = t2;
25301
25528
  } else {
25302
- t1 = $[4];
25303
- t2 = $[5];
25529
+ t1 = $[5];
25530
+ t2 = $[6];
25304
25531
  }
25305
25532
  React.useEffect(t1, t2);
25306
25533
  if (!entity) {
25307
25534
  return null;
25308
25535
  }
25309
25536
  let t3;
25310
- if ($[6] !== cellRect || $[7] !== container || $[8] !== customFieldValidator || $[9] !== entityId || $[10] !== inputCollection || $[11] !== onCellValueChange || $[12] !== onClose || $[13] !== open || $[14] !== path || $[15] !== propertyKey || $[16] !== tableKey) {
25537
+ if ($[7] !== cellRect || $[8] !== container || $[9] !== customFieldValidator || $[10] !== entityId || $[11] !== inputCollection || $[12] !== onCellValueChange || $[13] !== onClose || $[14] !== open || $[15] !== path || $[16] !== propertyKey || $[17] !== tableKey) {
25311
25538
  t3 = {
25312
25539
  tableKey,
25313
25540
  entityId,
@@ -25321,29 +25548,29 @@
25321
25548
  onCellValueChange,
25322
25549
  container
25323
25550
  };
25324
- $[6] = cellRect;
25325
- $[7] = container;
25326
- $[8] = customFieldValidator;
25327
- $[9] = entityId;
25328
- $[10] = inputCollection;
25329
- $[11] = onCellValueChange;
25330
- $[12] = onClose;
25331
- $[13] = open;
25332
- $[14] = path;
25333
- $[15] = propertyKey;
25334
- $[16] = tableKey;
25335
- $[17] = t3;
25551
+ $[7] = cellRect;
25552
+ $[8] = container;
25553
+ $[9] = customFieldValidator;
25554
+ $[10] = entityId;
25555
+ $[11] = inputCollection;
25556
+ $[12] = onCellValueChange;
25557
+ $[13] = onClose;
25558
+ $[14] = open;
25559
+ $[15] = path;
25560
+ $[16] = propertyKey;
25561
+ $[17] = tableKey;
25562
+ $[18] = t3;
25336
25563
  } else {
25337
- t3 = $[17];
25564
+ t3 = $[18];
25338
25565
  }
25339
25566
  let t4;
25340
- if ($[18] !== entity || $[19] !== t3) {
25567
+ if ($[19] !== entity || $[20] !== t3) {
25341
25568
  t4 = /* @__PURE__ */ jsxRuntime.jsx(PopupFormFieldInternal, { ...t3, entity });
25342
- $[18] = entity;
25343
- $[19] = t3;
25344
- $[20] = t4;
25569
+ $[19] = entity;
25570
+ $[20] = t3;
25571
+ $[21] = t4;
25345
25572
  } else {
25346
- t4 = $[20];
25573
+ t4 = $[21];
25347
25574
  }
25348
25575
  return t4;
25349
25576
  }
@@ -25915,6 +26142,7 @@
25915
26142
  const EntityCollectionView$1 = React.memo(function EntityCollectionView2({
25916
26143
  fullPath: fullPathProp,
25917
26144
  fullIdPath,
26145
+ pathSegments,
25918
26146
  parentCollectionIds,
25919
26147
  isSubCollection,
25920
26148
  className,
@@ -26037,6 +26265,7 @@
26037
26265
  } = usedSelectionController;
26038
26266
  const tableController = useDataSourceTableController({
26039
26267
  fullPath,
26268
+ pathSegments,
26040
26269
  collection,
26041
26270
  lastDeleteTimestamp,
26042
26271
  scrollRestoration,
@@ -26078,6 +26307,7 @@
26078
26307
  collection: collection_2,
26079
26308
  entityId: void 0,
26080
26309
  path: fullPath,
26310
+ pathSegments,
26081
26311
  fullIdPath,
26082
26312
  sideEntityController,
26083
26313
  navigation,
@@ -26136,6 +26366,7 @@
26136
26366
  const onViewModeChange = React.useCallback((mode) => {
26137
26367
  analyticsController.onAnalyticsEvent?.("view_mode_changed", {
26138
26368
  path: fullPath,
26369
+ pathSegments,
26139
26370
  from: viewMode,
26140
26371
  to: mode
26141
26372
  });
@@ -26250,6 +26481,7 @@
26250
26481
  const onKanbanPropertyChange = React.useCallback((property_1) => {
26251
26482
  analyticsController.onAnalyticsEvent?.("kanban_property_changed", {
26252
26483
  path: fullPath,
26484
+ pathSegments,
26253
26485
  property: property_1
26254
26486
  });
26255
26487
  setSelectedKanbanProperty(property_1);
@@ -26304,6 +26536,7 @@
26304
26536
  entityId: entity_3.id,
26305
26537
  selectedTab: subcollection.id ?? subcollection.path,
26306
26538
  path: fullPath,
26539
+ pathSegments,
26307
26540
  fullIdPath,
26308
26541
  navigation,
26309
26542
  sideEntityController
@@ -26377,7 +26610,7 @@
26377
26610
  breadcrumbs.updateCount(fullPath, docsCount);
26378
26611
  }
26379
26612
  }, [docsCount, fullPath, breadcrumbs.updateCount]);
26380
- const countFetcher = /* @__PURE__ */ jsxRuntime.jsx(EntitiesCount, { fullPath, collection, filter: tableController.filterValues, sortBy: tableController.sortBy, onCountChange: setDocsCount });
26613
+ const countFetcher = /* @__PURE__ */ jsxRuntime.jsx(EntitiesCount, { fullPath, pathSegments, collection, filter: tableController.filterValues, sortBy: tableController.sortBy, onCountChange: setDocsCount });
26381
26614
  const buildAdditionalHeaderWidget = React.useCallback(({
26382
26615
  property: property_2,
26383
26616
  propertyKey: propertyKey_1,
@@ -26402,7 +26635,11 @@
26402
26635
  } = useTableSearchHelper({
26403
26636
  collection,
26404
26637
  fullPath: resolvedFullPath,
26405
- parentCollectionIds
26638
+ parentCollectionIds,
26639
+ // When the search term comes from the URL instead of the search bar, text search
26640
+ // has never been initialised for this collection. Initialise it so the search bar
26641
+ // is usable (editable and clearable) right away.
26642
+ initialSearchString: tableController.searchString
26406
26643
  });
26407
26644
  const [viewModePopoverOpen, setViewModePopoverOpen] = React.useState(false);
26408
26645
  const viewModeToggleElement = /* @__PURE__ */ jsxRuntime.jsx(ViewModeToggle, { viewMode, onViewModeChange, enabledViews, size: viewMode === "table" ? tableSize : viewMode === "cards" ? cardSize : void 0, onSizeChanged: viewMode === "table" ? onTableSizeChanged : viewMode === "cards" ? setCardSize : void 0, open: viewModePopoverOpen, onOpenChange: setViewModePopoverOpen, kanbanPropertyOptions, selectedKanbanProperty, onKanbanPropertyChange });
@@ -26419,8 +26656,8 @@
26419
26656
  }, [tableController.dataLoadingError, customizationController.plugins, fullPath, collection, parentCollectionIds]);
26420
26657
  return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("overflow-hidden h-full w-full rounded-md flex flex-col", className), ref: containerRef, children: [
26421
26658
  countFetcher,
26422
- /* @__PURE__ */ jsxRuntime.jsx(CollectionTableToolbar, { loading: tableController.dataLoading, onTextSearch: textSearchEnabled && textSearchInitialised ? tableController.setSearchString : void 0, onTextSearchClick: textSearchEnabled && !textSearchInitialised ? onTextSearchClick : void 0, textSearchLoading, viewModeToggle: viewModeToggleElement, actionsStart: /* @__PURE__ */ jsxRuntime.jsx(EntityCollectionViewStartActions, { parentCollectionIds: parentCollectionIds ?? [], collection, tableController, path: fullPath, relativePath: collection.path, selectionController: usedSelectionController, collectionEntitiesCount: docsCount, resolvedProperties: resolvedCollection.properties }), actions: /* @__PURE__ */ jsxRuntime.jsx(EntityCollectionViewActions, { parentCollectionIds: parentCollectionIds ?? [], collection, tableController, onMultipleDeleteClick, onNewClick, path: fullPath, relativePath: collection.path, selectionController: usedSelectionController, selectionEnabled, collectionEntitiesCount: docsCount }) }),
26423
- tableController.dataLoadingError ? pluginErrorView ?? /* @__PURE__ */ jsxRuntime.jsx(CollectionDataErrorBanner, { error: tableController.dataLoadingError }) : viewMode === "kanban" && enabledViews.includes("kanban") ? /* @__PURE__ */ jsxRuntime.jsx(EntityCollectionBoardView, { collection, tableController, fullPath, parentCollectionIds, columnProperty: selectedKanbanProperty, onEntityClick, selectionController: usedSelectionController, selectionEnabled, highlightedEntities: highlightedEntity ? [highlightedEntity] : [], deletedEntities, emptyComponent: canCreateEntities && tableController.filterValues === void 0 && tableController.sortBy === void 0 ? /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center justify-center", children: [
26659
+ /* @__PURE__ */ jsxRuntime.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__ */ jsxRuntime.jsx(EntityCollectionViewStartActions, { parentCollectionIds: parentCollectionIds ?? [], collection, tableController, path: fullPath, relativePath: collection.path, selectionController: usedSelectionController, collectionEntitiesCount: docsCount, resolvedProperties: resolvedCollection.properties }), actions: /* @__PURE__ */ jsxRuntime.jsx(EntityCollectionViewActions, { parentCollectionIds: parentCollectionIds ?? [], collection, tableController, onMultipleDeleteClick, onNewClick, path: fullPath, relativePath: collection.path, selectionController: usedSelectionController, selectionEnabled, collectionEntitiesCount: docsCount }) }),
26660
+ tableController.dataLoadingError ? pluginErrorView ?? /* @__PURE__ */ jsxRuntime.jsx(CollectionDataErrorBanner, { error: tableController.dataLoadingError }) : viewMode === "kanban" && enabledViews.includes("kanban") ? /* @__PURE__ */ jsxRuntime.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__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center justify-center", children: [
26424
26661
  /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle2", children: t("so_empty") }),
26425
26662
  /* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { onClick: onNewClick, className: "mt-4", children: [
26426
26663
  /* @__PURE__ */ jsxRuntime.jsx(ui.AddIcon, {}),
@@ -26457,7 +26694,7 @@
26457
26694
  });
26458
26695
  }
26459
26696
  } }, `collection_table_${fullPath}`),
26460
- popupCell && /* @__PURE__ */ jsxRuntime.jsx(PopupFormField, { open: Boolean(popupCell), onClose: onPopupClose, cellRect: popupCell?.cellRect, propertyKey: popupCell?.propertyKey, collection, entityId: popupCell.entityId, tableKey: tableKey.current, customFieldValidator: uniqueFieldValidator, path: resolvedFullPath, onCellValueChange: onValueChange, container: containerRef.current }, `popup_form_${popupCell?.propertyKey}_${popupCell?.entityId}`),
26697
+ popupCell && /* @__PURE__ */ jsxRuntime.jsx(PopupFormField, { pathSegments, open: Boolean(popupCell), onClose: onPopupClose, cellRect: popupCell?.cellRect, propertyKey: popupCell?.propertyKey, collection, entityId: popupCell.entityId, tableKey: tableKey.current, customFieldValidator: uniqueFieldValidator, path: resolvedFullPath, onCellValueChange: onValueChange, container: containerRef.current }, `popup_form_${popupCell?.propertyKey}_${popupCell?.entityId}`),
26461
26698
  deleteEntityClicked && /* @__PURE__ */ jsxRuntime.jsx(DeleteEntityDialog, { entityOrEntitiesToDelete: deleteEntityClicked, path: fullPath, collection, callbacks: collection.callbacks, open: Boolean(deleteEntityClicked), onEntityDelete: internalOnEntityDelete, onMultipleEntitiesDelete: internalOnMultipleEntitiesDelete, onClose: () => setDeleteEntityClicked(void 0) })
26462
26699
  ] });
26463
26700
  }, (a, b) => {
@@ -26468,7 +26705,8 @@
26468
26705
  collection,
26469
26706
  filter,
26470
26707
  sortBy,
26471
- onCountChange
26708
+ onCountChange,
26709
+ pathSegments
26472
26710
  }) {
26473
26711
  const dataSource = useDataSource();
26474
26712
  const navigation = useNavigationController();
@@ -26477,15 +26715,17 @@
26477
26715
  const sortByProperty = sortBy ? sortBy[0] : void 0;
26478
26716
  const currentSort = sortBy ? sortBy[1] : void 0;
26479
26717
  const resolvedPath = React.useMemo(() => navigation.resolveIdsFrom(fullPath), [fullPath, navigation.resolveIdsFrom]);
26718
+ const resolvedPathSegments = pathSegments;
26480
26719
  React.useEffect(() => {
26481
26720
  if (dataSource.countEntities) dataSource.countEntities({
26482
26721
  path: resolvedPath,
26722
+ pathSegments: resolvedPathSegments,
26483
26723
  collection,
26484
26724
  filter,
26485
26725
  orderBy: sortByProperty,
26486
26726
  order: currentSort
26487
26727
  }).then(setCount).catch(setError);
26488
- }, [fullPath, dataSource.countEntities, resolvedPath, collection, filter, sortByProperty, currentSort]);
26728
+ }, [fullPath, dataSource.countEntities, resolvedPath, resolvedPathSegments, collection, filter, sortByProperty, currentSort]);
26489
26729
  React.useEffect(() => {
26490
26730
  if (onCountChange && count !== void 0) {
26491
26731
  setError(void 0);
@@ -28273,7 +28513,8 @@
28273
28513
  const {
28274
28514
  path,
28275
28515
  collections = [],
28276
- currentFullPath
28516
+ currentFullPath,
28517
+ currentPathSegments = []
28277
28518
  } = props;
28278
28519
  const subpaths = removeInitialAndTrailingSlashes(path).split("/");
28279
28520
  const subpathCombinations = getCollectionPathsCombinations(subpaths);
@@ -28283,12 +28524,14 @@
28283
28524
  const collection = collections && collections.find((entry) => entry.id === subpathCombination || entry.path === subpathCombination);
28284
28525
  if (collection) {
28285
28526
  const collectionPath = currentFullPath && currentFullPath.length > 0 ? currentFullPath + "/" + collection.path : collection.path;
28527
+ const collectionSegments = [...currentPathSegments, ...collection.path.split("/")];
28286
28528
  const restOfThePath = removeInitialAndTrailingSlashes(removeInitialAndTrailingSlashes(path).replace(subpathCombination, ""));
28287
28529
  const nextSegments = restOfThePath.length > 0 ? restOfThePath.split("/") : [];
28288
28530
  if (nextSegments.length > 0) {
28289
28531
  const entityId = decodeEntityId(nextSegments[0]);
28290
28532
  const fullPath = collectionPath + "/" + entityId;
28291
- result.push(new EntityReference(entityId, collectionPath));
28533
+ const entitySegments = [...collectionSegments, entityId];
28534
+ result.push(new EntityReference(entityId, collectionPath, void 0, collectionSegments));
28292
28535
  if (nextSegments.length > 1) {
28293
28536
  const newPath = nextSegments.slice(1).join("/");
28294
28537
  if (!collection) {
@@ -28298,7 +28541,8 @@
28298
28541
  result.push(...getParentReferencesFromPath({
28299
28542
  path: newPath,
28300
28543
  collections: collection.subcollections,
28301
- currentFullPath: fullPath
28544
+ currentFullPath: fullPath,
28545
+ currentPathSegments: entitySegments
28302
28546
  }));
28303
28547
  }
28304
28548
  }
@@ -29082,6 +29326,7 @@
29082
29326
  const delegateUser = authController.user;
29083
29327
  if (authenticator instanceof Function && delegateUser && !equal(checkedUserRef.current?.uid, delegateUser.uid)) {
29084
29328
  setAuthLoading(true);
29329
+ setNotAllowedError(false);
29085
29330
  try {
29086
29331
  const allowed = await authenticator({
29087
29332
  user: delegateUser,
@@ -29361,6 +29606,7 @@
29361
29606
  path,
29362
29607
  entityId,
29363
29608
  fullIdPath,
29609
+ pathSegments,
29364
29610
  formProps
29365
29611
  } = props;
29366
29612
  const {
@@ -29428,7 +29674,7 @@
29428
29674
  if (!props || !collection) {
29429
29675
  return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-full" });
29430
29676
  }
29431
- return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children: /* @__PURE__ */ jsxRuntime.jsx(ErrorBoundary, { children: /* @__PURE__ */ jsxRuntime.jsx(EntityEditView$1, { ...props, fullIdPath, layout: "side_panel", collection, parentCollectionIds, onValuesModified, onSaved: onUpdate, barActions: ({
29677
+ return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children: /* @__PURE__ */ jsxRuntime.jsx(ErrorBoundary, { children: /* @__PURE__ */ jsxRuntime.jsx(EntityEditView$1, { ...props, fullIdPath, pathSegments, layout: "side_panel", collection, parentCollectionIds, onValuesModified, onSaved: onUpdate, barActions: ({
29432
29678
  status,
29433
29679
  values
29434
29680
  }) => /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
@@ -29934,6 +30180,7 @@
29934
30180
  dataLoadingError
29935
30181
  } = useEntityFetch({
29936
30182
  path: props.path,
30183
+ pathSegments: props.pathSegments,
29937
30184
  entityId,
29938
30185
  collection: props.collection,
29939
30186
  databaseId: props.databaseId,
@@ -29961,6 +30208,7 @@
29961
30208
  function EntityEditViewInner({
29962
30209
  path,
29963
30210
  fullIdPath,
30211
+ pathSegments,
29964
30212
  entityId,
29965
30213
  selectedTab: selectedTabProp,
29966
30214
  collection,
@@ -30094,10 +30342,11 @@
30094
30342
  const subcollectionId = subcollection.id ?? subcollection.path;
30095
30343
  const newFullPath = usedEntity ? `${path}/${usedEntity?.id}/${removeInitialAndTrailingSlashes(subcollection.path)}` : void 0;
30096
30344
  const newFullIdPath = fullIdPath && usedEntity ? `${fullIdPath}/${encodeEntityId(usedEntity.id)}/${removeInitialAndTrailingSlashes(subcollectionId)}` : void 0;
30345
+ const newPathSegments = usedEntity && pathSegments ? [...pathSegments, usedEntity.id, ...removeInitialAndTrailingSlashes(subcollection.path).split("/")] : void 0;
30097
30346
  if (selectedTab !== subcollectionId) return null;
30098
30347
  return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "relative flex-1 h-full overflow-auto w-full", role: "tabpanel", children: [
30099
30348
  globalLoading && /* @__PURE__ */ jsxRuntime.jsx(CircularProgressCenter, {}),
30100
- !globalLoading && (usedEntity && newFullPath ? /* @__PURE__ */ jsxRuntime.jsx(EntityCollectionView$1, { fullPath: newFullPath, fullIdPath: newFullIdPath, parentCollectionIds: [...parentCollectionIds, collection.id], isSubCollection: true, updateUrl: false, ...subcollection, openEntityMode: layout }) : /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-center justify-center w-full h-full p-3", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "label", children: t("youd_need_to_save_before_additional_collections") }) }))
30349
+ !globalLoading && (usedEntity && newFullPath ? /* @__PURE__ */ jsxRuntime.jsx(EntityCollectionView$1, { fullPath: newFullPath, pathSegments: newPathSegments, fullIdPath: newFullIdPath, parentCollectionIds: [...parentCollectionIds, collection.id], isSubCollection: true, updateUrl: false, ...subcollection, openEntityMode: layout }) : /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-center justify-center w-full h-full p-3", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "label", children: t("youd_need_to_save_before_additional_collections") }) }))
30101
30350
  ] }, `subcol_${subcollectionId}`);
30102
30351
  }).filter(Boolean);
30103
30352
  const onSideTabClick = (value_0) => {
@@ -30116,7 +30365,7 @@
30116
30365
  /* @__PURE__ */ jsxRuntime.jsx(EntityView, { className: "px-8 h-full overflow-auto", entity, path, collection }),
30117
30366
  /* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-16" })
30118
30367
  ] }) }) : null;
30119
- const entityView = /* @__PURE__ */ jsxRuntime.jsx(EntityForm, { fullIdPath, collection, path, entityId: entityId ?? usedEntity?.id, onValuesModified, entity, initialDirtyValues, openEntityMode: layout, forceActionsAtTheBottom: actionsAtTheBottom, initialStatus: status, className: ui.cls((!mainViewVisible || !canEdit) && !selectedSecondaryForm ? "hidden" : "", formProps?.className), EntityFormActionsComponent: EntityEditViewFormActions, disabled: !canEdit, ...formProps, onEntityChange: (entity_0) => {
30368
+ const entityView = /* @__PURE__ */ jsxRuntime.jsx(EntityForm, { fullIdPath, collection, path, pathSegments, entityId: entityId ?? usedEntity?.id, onValuesModified, entity, initialDirtyValues, openEntityMode: layout, forceActionsAtTheBottom: actionsAtTheBottom, initialStatus: status, className: ui.cls((!mainViewVisible || !canEdit) && !selectedSecondaryForm ? "hidden" : "", formProps?.className), EntityFormActionsComponent: EntityEditViewFormActions, disabled: !canEdit, ...formProps, onEntityChange: (entity_0) => {
30120
30369
  setUsedEntity(entity_0);
30121
30370
  formProps?.onEntityChange?.(entity_0);
30122
30371
  }, onStatusChange: (status_0) => {
@@ -30346,17 +30595,20 @@
30346
30595
  let sidePanel = void 0;
30347
30596
  let lastCollectionPath = "";
30348
30597
  let lastCollectionId = void 0;
30598
+ let lastCollectionSegments = void 0;
30349
30599
  for (let i = 0; i < navigationViewsForPath.length; i++) {
30350
30600
  const navigationEntry = navigationViewsForPath[i];
30351
30601
  if (navigationEntry.type === "collection") {
30352
30602
  lastCollectionPath = navigationEntry.path;
30353
30603
  lastCollectionId = navigationEntry.collection.id;
30604
+ lastCollectionSegments = navigationEntry.pathSegments;
30354
30605
  }
30355
30606
  const previousEntry = navigationViewsForPath[i - 1];
30356
30607
  if (navigationEntry.type === "entity") {
30357
30608
  sidePanel = {
30358
30609
  path: navigationEntry.path,
30359
30610
  fullIdPath: navigationEntry.fullIdPath,
30611
+ pathSegments: navigationEntry.pathSegments,
30360
30612
  entityId: navigationEntry.entityId,
30361
30613
  copy: false,
30362
30614
  width: navigationEntry.parentCollection?.sideDialogWidth
@@ -30375,6 +30627,9 @@
30375
30627
  sidePanel = {
30376
30628
  path: lastCollectionPath,
30377
30629
  fullIdPath: lastCollectionId,
30630
+ // A new entity still needs unambiguous segments: it may be created inside a
30631
+ // subcollection whose parent id contains "/".
30632
+ pathSegments: lastCollectionSegments,
30378
30633
  copy: false
30379
30634
  };
30380
30635
  }
@@ -30611,6 +30866,7 @@
30611
30866
  */
30612
30867
  fetchCollection: React.useCallback(({
30613
30868
  path,
30869
+ pathSegments,
30614
30870
  collection,
30615
30871
  filter,
30616
30872
  limit,
@@ -30622,6 +30878,7 @@
30622
30878
  const usedDelegate = collection?.overrides?.dataSourceDelegate ?? delegate;
30623
30879
  return usedDelegate.fetchCollection({
30624
30880
  path,
30881
+ pathSegments,
30625
30882
  filter,
30626
30883
  limit,
30627
30884
  startAfter,
@@ -30649,6 +30906,7 @@
30649
30906
  */
30650
30907
  listenCollection: delegate.listenCollection ? React.useCallback(({
30651
30908
  path: path_0,
30909
+ pathSegments: pathSegments_0,
30652
30910
  collection: collectionProp,
30653
30911
  filter: filter_0,
30654
30912
  limit: limit_0,
@@ -30664,6 +30922,7 @@
30664
30922
  if (!usedDelegate_0.listenCollection) throw Error("useBuildDataSource delegate not initialised");
30665
30923
  return usedDelegate_0.listenCollection({
30666
30924
  path: path_0,
30925
+ pathSegments: pathSegments_0,
30667
30926
  filter: filter_0,
30668
30927
  limit: limit_0,
30669
30928
  startAfter: startAfter_0,
@@ -30684,12 +30943,14 @@
30684
30943
  */
30685
30944
  fetchEntity: React.useCallback(({
30686
30945
  path: path_1,
30946
+ pathSegments: pathSegments_1,
30687
30947
  entityId,
30688
30948
  collection: collection_1
30689
30949
  }) => {
30690
30950
  const usedDelegate_1 = collection_1?.overrides?.dataSourceDelegate ?? delegate;
30691
30951
  return usedDelegate_1.fetchEntity({
30692
30952
  path: path_1,
30953
+ pathSegments: pathSegments_1,
30693
30954
  entityId,
30694
30955
  collection: collection_1
30695
30956
  });
@@ -30706,6 +30967,7 @@
30706
30967
  */
30707
30968
  listenEntity: delegate.listenEntity ? React.useCallback(({
30708
30969
  path: path_2,
30970
+ pathSegments: pathSegments_2,
30709
30971
  entityId: entityId_0,
30710
30972
  collection: collection_2,
30711
30973
  onUpdate: onUpdate_0,
@@ -30715,6 +30977,7 @@
30715
30977
  if (!usedDelegate_2.listenEntity) throw Error("useBuildDataSource delegate not initialised");
30716
30978
  return usedDelegate_2.listenEntity({
30717
30979
  path: path_2,
30980
+ pathSegments: pathSegments_2,
30718
30981
  entityId: entityId_0,
30719
30982
  onUpdate: onUpdate_0,
30720
30983
  onError: onError_0,
@@ -30734,6 +30997,7 @@
30734
30997
  */
30735
30998
  saveEntity: React.useCallback(async ({
30736
30999
  path: path_3,
31000
+ pathSegments: pathSegments_3,
30737
31001
  entityId: entityId_1,
30738
31002
  values,
30739
31003
  collection: collectionProp_0,
@@ -30766,6 +31030,7 @@
30766
31030
  try {
30767
31031
  const entities = await usedDelegate_3.fetchCollection({
30768
31032
  path: path_3,
31033
+ pathSegments: pathSegments_3,
30769
31034
  orderBy: orderProperty,
30770
31035
  order: "asc",
30771
31036
  limit: 1,
@@ -30788,6 +31053,7 @@
30788
31053
  }
30789
31054
  return usedDelegate_3.saveEntity({
30790
31055
  path: path_3,
31056
+ pathSegments: pathSegments_3,
30791
31057
  collection: collection_3,
30792
31058
  entityId: entityId_1,
30793
31059
  values: finalValues,
@@ -30808,11 +31074,14 @@
30808
31074
  */
30809
31075
  deleteEntity: React.useCallback(({
30810
31076
  entity,
31077
+ pathSegments: pathSegments_4,
30811
31078
  collection: collection_4
30812
31079
  }) => {
30813
31080
  const usedDelegate_4 = collection_4?.overrides?.dataSourceDelegate ?? delegate;
30814
31081
  return usedDelegate_4.deleteEntity({
30815
31082
  entity,
31083
+ // Falls back to what the entity carries from the fetch that produced it.
31084
+ pathSegments: pathSegments_4 ?? entity.pathSegments,
30816
31085
  collection: collection_4
30817
31086
  });
30818
31087
  }, [delegate.deleteEntity]),
@@ -30826,16 +31095,17 @@
30826
31095
  * @return `true` if there are no other fields besides the given entity
30827
31096
  * @group Firestore
30828
31097
  */
30829
- checkUniqueField: React.useCallback((path_4, name, value, entityId_2, collection_5) => {
31098
+ checkUniqueField: React.useCallback((path_4, name, value, entityId_2, collection_5, pathSegments_5) => {
30830
31099
  const usedDelegate_5 = collection_5?.overrides?.dataSourceDelegate ?? delegate;
30831
- return usedDelegate_5.checkUniqueField(path_4, name, value, entityId_2, collection_5);
31100
+ return usedDelegate_5.checkUniqueField(path_4, name, value, entityId_2, collection_5, pathSegments_5);
30832
31101
  }, [delegate.checkUniqueField]),
30833
- generateEntityId: React.useCallback((path_5, collection_6) => {
31102
+ generateEntityId: React.useCallback((path_5, collection_6, pathSegments_6) => {
30834
31103
  const usedDelegate_6 = collection_6?.overrides?.dataSourceDelegate ?? delegate;
30835
- return usedDelegate_6.generateEntityId(path_5, collection_6);
31104
+ return usedDelegate_6.generateEntityId(path_5, collection_6, pathSegments_6);
30836
31105
  }, [delegate.generateEntityId]),
30837
31106
  countEntities: delegate.countEntities ? async ({
30838
31107
  path: path_6,
31108
+ pathSegments: pathSegments_7,
30839
31109
  collection: collection_7,
30840
31110
  filter: filter_1,
30841
31111
  order: order_1,
@@ -30844,6 +31114,7 @@
30844
31114
  const usedDelegate_7 = collection_7?.overrides?.dataSourceDelegate ?? delegate;
30845
31115
  return usedDelegate_7.countEntities({
30846
31116
  path: path_6,
31117
+ pathSegments: pathSegments_7,
30847
31118
  filter: filter_1,
30848
31119
  orderBy: orderBy_1,
30849
31120
  order: order_1,
@@ -30852,6 +31123,7 @@
30852
31123
  } : void 0,
30853
31124
  isFilterCombinationValid: React.useCallback(({
30854
31125
  path: path_7,
31126
+ pathSegments: pathSegments_8,
30855
31127
  databaseId,
30856
31128
  filterValues,
30857
31129
  sortBy
@@ -30859,6 +31131,7 @@
30859
31131
  if (!delegate.isFilterCombinationValid) return true;
30860
31132
  return delegate.isFilterCombinationValid({
30861
31133
  path: path_7,
31134
+ pathSegments: pathSegments_8,
30862
31135
  databaseId,
30863
31136
  filterValues,
30864
31137
  sortBy
@@ -32221,7 +32494,7 @@
32221
32494
  const EntityEditView = lazyEager(() => Promise.resolve().then(() => EntityEditView$2), "EntityEditView");
32222
32495
  const EntityCollectionView = lazyEager(() => Promise.resolve().then(() => EntityCollectionView$2), "EntityCollectionView");
32223
32496
  function FireCMSRoute() {
32224
- const $ = reactCompilerRuntime.c(82);
32497
+ const $ = reactCompilerRuntime.c(87);
32225
32498
  const location = reactRouter.useLocation();
32226
32499
  const navigation = useNavigationController();
32227
32500
  const breadcrumbs = useBreadcrumbsController();
@@ -32345,12 +32618,13 @@
32345
32618
  let t13;
32346
32619
  let t14;
32347
32620
  let t15;
32621
+ let t16;
32348
32622
  let t62;
32349
32623
  let t7;
32350
32624
  let t8;
32351
32625
  let t9;
32352
- if ($[18] !== navigation || $[19] !== navigationEntries[0].id || $[20] !== navigationEntries[0].path) {
32353
- t15 = /* @__PURE__ */ Symbol.for("react.early_return_sentinel");
32626
+ if ($[18] !== navigation || $[19] !== navigationEntries[0].id || $[20] !== navigationEntries[0].path || $[21] !== navigationEntries[0].pathSegments) {
32627
+ t16 = /* @__PURE__ */ Symbol.for("react.early_return_sentinel");
32354
32628
  bb0: {
32355
32629
  let collection;
32356
32630
  collection = navigation.getCollectionById(navigationEntries[0].id);
@@ -32358,85 +32632,90 @@
32358
32632
  collection = navigation.getCollection(navigationEntries[0].path);
32359
32633
  }
32360
32634
  if (!collection) {
32361
- t15 = null;
32635
+ t16 = null;
32362
32636
  break bb0;
32363
32637
  }
32364
32638
  T1 = React.Suspense;
32365
- t14 = null;
32639
+ t15 = null;
32366
32640
  T0 = EntityCollectionView;
32367
32641
  t62 = `collection_view_${collection.id ?? collection.path}`;
32368
32642
  t7 = false;
32369
- if ($[33] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
32643
+ if ($[35] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
32370
32644
  t8 = [];
32371
- $[33] = t8;
32645
+ $[35] = t8;
32372
32646
  } else {
32373
- t8 = $[33];
32647
+ t8 = $[35];
32374
32648
  }
32375
32649
  t9 = collection.path;
32376
- t10 = collection.id;
32377
- t11 = true;
32378
- t12 = collection;
32379
- t13 = toArray(collection.Actions);
32650
+ t10 = navigationEntries[0].pathSegments;
32651
+ t11 = collection.id;
32652
+ t12 = true;
32653
+ t13 = collection;
32654
+ t14 = toArray(collection.Actions);
32380
32655
  }
32381
32656
  $[18] = navigation;
32382
32657
  $[19] = navigationEntries[0].id;
32383
32658
  $[20] = navigationEntries[0].path;
32384
- $[21] = T0;
32385
- $[22] = T1;
32386
- $[23] = t10;
32387
- $[24] = t11;
32388
- $[25] = t12;
32389
- $[26] = t13;
32390
- $[27] = t14;
32391
- $[28] = t15;
32392
- $[29] = t62;
32393
- $[30] = t7;
32394
- $[31] = t8;
32395
- $[32] = t9;
32659
+ $[21] = navigationEntries[0].pathSegments;
32660
+ $[22] = T0;
32661
+ $[23] = T1;
32662
+ $[24] = t10;
32663
+ $[25] = t11;
32664
+ $[26] = t12;
32665
+ $[27] = t13;
32666
+ $[28] = t14;
32667
+ $[29] = t15;
32668
+ $[30] = t16;
32669
+ $[31] = t62;
32670
+ $[32] = t7;
32671
+ $[33] = t8;
32672
+ $[34] = t9;
32396
32673
  } else {
32397
- T0 = $[21];
32398
- T1 = $[22];
32399
- t10 = $[23];
32400
- t11 = $[24];
32401
- t12 = $[25];
32402
- t13 = $[26];
32403
- t14 = $[27];
32404
- t15 = $[28];
32405
- t62 = $[29];
32406
- t7 = $[30];
32407
- t8 = $[31];
32408
- t9 = $[32];
32409
- }
32410
- if (t15 !== /* @__PURE__ */ Symbol.for("react.early_return_sentinel")) {
32411
- return t15;
32674
+ T0 = $[22];
32675
+ T1 = $[23];
32676
+ t10 = $[24];
32677
+ t11 = $[25];
32678
+ t12 = $[26];
32679
+ t13 = $[27];
32680
+ t14 = $[28];
32681
+ t15 = $[29];
32682
+ t16 = $[30];
32683
+ t62 = $[31];
32684
+ t7 = $[32];
32685
+ t8 = $[33];
32686
+ t9 = $[34];
32412
32687
  }
32413
- let t16;
32414
- if ($[34] !== T0 || $[35] !== t10 || $[36] !== t11 || $[37] !== t12 || $[38] !== t13 || $[39] !== t62 || $[40] !== t7 || $[41] !== t8 || $[42] !== t9) {
32415
- t16 = /* @__PURE__ */ jsxRuntime.jsx(T0, { isSubCollection: t7, parentCollectionIds: t8, fullPath: t9, fullIdPath: t10, updateUrl: t11, ...t12, Actions: t13 }, t62);
32416
- $[34] = T0;
32417
- $[35] = t10;
32418
- $[36] = t11;
32419
- $[37] = t12;
32420
- $[38] = t13;
32421
- $[39] = t62;
32422
- $[40] = t7;
32423
- $[41] = t8;
32424
- $[42] = t9;
32425
- $[43] = t16;
32426
- } else {
32427
- t16 = $[43];
32688
+ if (t16 !== /* @__PURE__ */ Symbol.for("react.early_return_sentinel")) {
32689
+ return t16;
32428
32690
  }
32429
32691
  let t17;
32430
- if ($[44] !== T1 || $[45] !== t14 || $[46] !== t16) {
32431
- t17 = /* @__PURE__ */ jsxRuntime.jsx(T1, { fallback: t14, children: t16 });
32432
- $[44] = T1;
32433
- $[45] = t14;
32434
- $[46] = t16;
32435
- $[47] = t17;
32692
+ if ($[36] !== T0 || $[37] !== t10 || $[38] !== t11 || $[39] !== t12 || $[40] !== t13 || $[41] !== t14 || $[42] !== t62 || $[43] !== t7 || $[44] !== t8 || $[45] !== t9) {
32693
+ t17 = /* @__PURE__ */ jsxRuntime.jsx(T0, { isSubCollection: t7, parentCollectionIds: t8, fullPath: t9, pathSegments: t10, fullIdPath: t11, updateUrl: t12, ...t13, Actions: t14 }, t62);
32694
+ $[36] = T0;
32695
+ $[37] = t10;
32696
+ $[38] = t11;
32697
+ $[39] = t12;
32698
+ $[40] = t13;
32699
+ $[41] = t14;
32700
+ $[42] = t62;
32701
+ $[43] = t7;
32702
+ $[44] = t8;
32703
+ $[45] = t9;
32704
+ $[46] = t17;
32705
+ } else {
32706
+ t17 = $[46];
32707
+ }
32708
+ let t18;
32709
+ if ($[47] !== T1 || $[48] !== t15 || $[49] !== t17) {
32710
+ t18 = /* @__PURE__ */ jsxRuntime.jsx(T1, { fallback: t15, children: t17 });
32711
+ $[47] = T1;
32712
+ $[48] = t15;
32713
+ $[49] = t17;
32714
+ $[50] = t18;
32436
32715
  } else {
32437
- t17 = $[47];
32716
+ t18 = $[50];
32438
32717
  }
32439
- return t17;
32718
+ return t18;
32440
32719
  }
32441
32720
  if (isSidePanel) {
32442
32721
  const lastCollectionEntry = navigationEntries.findLast(_temp2$2);
@@ -32449,12 +32728,13 @@
32449
32728
  let t13;
32450
32729
  let t14;
32451
32730
  let t15;
32731
+ let t16;
32452
32732
  let t62;
32453
32733
  let t7;
32454
32734
  let t8;
32455
32735
  let t9;
32456
- if ($[48] !== navigation || $[49] !== navigationEntries[0]) {
32457
- t15 = /* @__PURE__ */ Symbol.for("react.early_return_sentinel");
32736
+ if ($[51] !== navigation || $[52] !== navigationEntries[0]) {
32737
+ t16 = /* @__PURE__ */ Symbol.for("react.early_return_sentinel");
32458
32738
  bb1: {
32459
32739
  let collection_0;
32460
32740
  const firstEntry = navigationEntries[0];
@@ -32463,96 +32743,100 @@
32463
32743
  collection_0 = navigation.getCollection(firstEntry.path);
32464
32744
  }
32465
32745
  if (!collection_0) {
32466
- t15 = null;
32746
+ t16 = null;
32467
32747
  break bb1;
32468
32748
  }
32469
32749
  T1 = React.Suspense;
32470
- t14 = null;
32750
+ t15 = null;
32471
32751
  T0 = EntityCollectionView;
32472
32752
  t62 = `collection_view_${collection_0.id ?? collection_0.path}`;
32473
32753
  t7 = collection_0.id;
32474
32754
  t8 = false;
32475
- if ($[62] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
32755
+ if ($[66] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
32476
32756
  t9 = [];
32477
- $[62] = t9;
32757
+ $[66] = t9;
32478
32758
  } else {
32479
- t9 = $[62];
32759
+ t9 = $[66];
32480
32760
  }
32481
32761
  t10 = collection_0.path;
32482
- t11 = true;
32483
- t12 = collection_0;
32484
- t13 = toArray(collection_0.Actions);
32762
+ t11 = firstEntry.pathSegments;
32763
+ t12 = true;
32764
+ t13 = collection_0;
32765
+ t14 = toArray(collection_0.Actions);
32485
32766
  }
32486
- $[48] = navigation;
32487
- $[49] = navigationEntries[0];
32488
- $[50] = T0;
32489
- $[51] = T1;
32490
- $[52] = t10;
32491
- $[53] = t11;
32492
- $[54] = t12;
32493
- $[55] = t13;
32494
- $[56] = t14;
32495
- $[57] = t15;
32496
- $[58] = t62;
32497
- $[59] = t7;
32498
- $[60] = t8;
32499
- $[61] = t9;
32767
+ $[51] = navigation;
32768
+ $[52] = navigationEntries[0];
32769
+ $[53] = T0;
32770
+ $[54] = T1;
32771
+ $[55] = t10;
32772
+ $[56] = t11;
32773
+ $[57] = t12;
32774
+ $[58] = t13;
32775
+ $[59] = t14;
32776
+ $[60] = t15;
32777
+ $[61] = t16;
32778
+ $[62] = t62;
32779
+ $[63] = t7;
32780
+ $[64] = t8;
32781
+ $[65] = t9;
32500
32782
  } else {
32501
- T0 = $[50];
32502
- T1 = $[51];
32503
- t10 = $[52];
32504
- t11 = $[53];
32505
- t12 = $[54];
32506
- t13 = $[55];
32507
- t14 = $[56];
32508
- t15 = $[57];
32509
- t62 = $[58];
32510
- t7 = $[59];
32511
- t8 = $[60];
32512
- t9 = $[61];
32513
- }
32514
- if (t15 !== /* @__PURE__ */ Symbol.for("react.early_return_sentinel")) {
32515
- return t15;
32516
- }
32517
- let t16;
32518
- if ($[63] !== T0 || $[64] !== t10 || $[65] !== t11 || $[66] !== t12 || $[67] !== t13 || $[68] !== t62 || $[69] !== t7 || $[70] !== t8 || $[71] !== t9) {
32519
- t16 = /* @__PURE__ */ jsxRuntime.jsx(T0, { fullIdPath: t7, isSubCollection: t8, parentCollectionIds: t9, fullPath: t10, updateUrl: t11, ...t12, Actions: t13 }, t62);
32520
- $[63] = T0;
32521
- $[64] = t10;
32522
- $[65] = t11;
32523
- $[66] = t12;
32524
- $[67] = t13;
32525
- $[68] = t62;
32526
- $[69] = t7;
32527
- $[70] = t8;
32528
- $[71] = t9;
32529
- $[72] = t16;
32530
- } else {
32531
- t16 = $[72];
32783
+ T0 = $[53];
32784
+ T1 = $[54];
32785
+ t10 = $[55];
32786
+ t11 = $[56];
32787
+ t12 = $[57];
32788
+ t13 = $[58];
32789
+ t14 = $[59];
32790
+ t15 = $[60];
32791
+ t16 = $[61];
32792
+ t62 = $[62];
32793
+ t7 = $[63];
32794
+ t8 = $[64];
32795
+ t9 = $[65];
32796
+ }
32797
+ if (t16 !== /* @__PURE__ */ Symbol.for("react.early_return_sentinel")) {
32798
+ return t16;
32532
32799
  }
32533
32800
  let t17;
32534
- if ($[73] !== T1 || $[74] !== t14 || $[75] !== t16) {
32535
- t17 = /* @__PURE__ */ jsxRuntime.jsx(T1, { fallback: t14, children: t16 });
32536
- $[73] = T1;
32537
- $[74] = t14;
32538
- $[75] = t16;
32539
- $[76] = t17;
32801
+ if ($[67] !== T0 || $[68] !== t10 || $[69] !== t11 || $[70] !== t12 || $[71] !== t13 || $[72] !== t14 || $[73] !== t62 || $[74] !== t7 || $[75] !== t8 || $[76] !== t9) {
32802
+ t17 = /* @__PURE__ */ jsxRuntime.jsx(T0, { fullIdPath: t7, isSubCollection: t8, parentCollectionIds: t9, fullPath: t10, pathSegments: t11, updateUrl: t12, ...t13, Actions: t14 }, t62);
32803
+ $[67] = T0;
32804
+ $[68] = t10;
32805
+ $[69] = t11;
32806
+ $[70] = t12;
32807
+ $[71] = t13;
32808
+ $[72] = t14;
32809
+ $[73] = t62;
32810
+ $[74] = t7;
32811
+ $[75] = t8;
32812
+ $[76] = t9;
32813
+ $[77] = t17;
32814
+ } else {
32815
+ t17 = $[77];
32816
+ }
32817
+ let t18;
32818
+ if ($[78] !== T1 || $[79] !== t15 || $[80] !== t17) {
32819
+ t18 = /* @__PURE__ */ jsxRuntime.jsx(T1, { fallback: t15, children: t17 });
32820
+ $[78] = T1;
32821
+ $[79] = t15;
32822
+ $[80] = t17;
32823
+ $[81] = t18;
32540
32824
  } else {
32541
- t17 = $[76];
32825
+ t18 = $[81];
32542
32826
  }
32543
- return t17;
32827
+ return t18;
32544
32828
  }
32545
32829
  }
32546
32830
  let t6;
32547
- if ($[77] !== isCopy || $[78] !== isNew || $[79] !== navigationEntries || $[80] !== pathname) {
32831
+ if ($[82] !== isCopy || $[83] !== isNew || $[84] !== navigationEntries || $[85] !== pathname) {
32548
32832
  t6 = /* @__PURE__ */ jsxRuntime.jsx(EntityFullScreenRoute, { pathname, navigationEntries, isNew, isCopy });
32549
- $[77] = isCopy;
32550
- $[78] = isNew;
32551
- $[79] = navigationEntries;
32552
- $[80] = pathname;
32553
- $[81] = t6;
32833
+ $[82] = isCopy;
32834
+ $[83] = isNew;
32835
+ $[84] = navigationEntries;
32836
+ $[85] = pathname;
32837
+ $[86] = t6;
32554
32838
  } else {
32555
- t6 = $[81];
32839
+ t6 = $[86];
32556
32840
  }
32557
32841
  return t6;
32558
32842
  }
@@ -32631,7 +32915,7 @@
32631
32915
  const fullIdPath = isNew ? lastCollectionEntry.fullPath : parentCollectionEntry?.fullPath ?? lastEntityEntry.fullPath;
32632
32916
  const collectionPath = navigation.resolveIdsFrom(isNew ? lastCollectionEntry.path : lastEntityEntry.path);
32633
32917
  return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
32634
- /* @__PURE__ */ jsxRuntime.jsx(React.Suspense, { fallback: null, children: /* @__PURE__ */ jsxRuntime.jsx(EntityEditView, { entityId: isNew ? void 0 : entityId, fullIdPath, collection, layout: "full_screen", path: collectionPath, copy: isCopy, selectedTab: selectedTab ?? void 0, onValuesModified: (modified) => blocked.current = modified, onSaved: (params) => {
32918
+ /* @__PURE__ */ jsxRuntime.jsx(React.Suspense, { fallback: null, children: /* @__PURE__ */ jsxRuntime.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) => {
32635
32919
  const newEntityId = params.entityId;
32636
32920
  if (!newEntityId) return;
32637
32921
  navigate(buildEntityUrl(newEntityId, params.selectedTab), {
@@ -33611,6 +33895,7 @@
33611
33895
  download: "Download",
33612
33896
  large_number_of_documents: "This collections has a large number of documents ({{count}}).",
33613
33897
  include_undefined_values: "Include undefined values",
33898
+ export_apply_filter_sort: "Only export results matching the current filter/sort",
33614
33899
  submit: "Submit",
33615
33900
  no_filterable_properties: "No filterable properties available",
33616
33901
  apply_filters: "Apply filters",
@@ -33798,6 +34083,10 @@
33798
34083
  order_property_not_found: 'Property "{{property}}" does not exist or is not a number property. Please select a valid property or clear the selection.',
33799
34084
  no_number_properties: "No number properties found. Add a number property to enable ordering.",
33800
34085
  order_property_description: "Select a number property to persist the order of items",
34086
+ image_property: "Image Property",
34087
+ image_property_not_found: 'Property "{{property}}" does not exist or is not an image property. Please select a valid property or clear the selection.',
34088
+ no_image_properties: "No image properties found. Add a storage or URL image property to use as a thumbnail.",
34089
+ image_property_description: "Select the property used as the thumbnail image in Cards and Kanban view modes. If not set, the first matching image property will be used automatically.",
33801
34090
  display_settings: "Display settings",
33802
34091
  default_row_size: "Default row size",
33803
34092
  side_dialog_width: "Side dialog width",
@@ -34290,6 +34579,7 @@
34290
34579
  download: "Descargar",
34291
34580
  large_number_of_documents: "Esta colección posee un gran número de documentos ({{count}}).",
34292
34581
  include_undefined_values: "Incluir valores omitidos (undefined)",
34582
+ export_apply_filter_sort: "Exportar solo los resultados que coinciden con el filtro/orden actual",
34293
34583
  submit: "Enviar",
34294
34584
  no_filterable_properties: "No hay propiedades filtrables disponibles",
34295
34585
  apply_filters: "Aplicar filtros",
@@ -34477,6 +34767,10 @@
34477
34767
  order_property_not_found: 'La propiedad "{{property}}" no existe o no es una propiedad numérica. Selecciona una propiedad válida o borra la selección.',
34478
34768
  no_number_properties: "No se encontraron propiedades numéricas. Agrega una propiedad numérica para habilitar el ordenamiento.",
34479
34769
  order_property_description: "Selecciona una propiedad numérica para mantener el orden de los elementos",
34770
+ image_property: "Propiedad de imagen",
34771
+ image_property_not_found: 'La propiedad "{{property}}" no existe o no es una propiedad de imagen. Selecciona una propiedad válida o borra la selección.',
34772
+ no_image_properties: "No se encontraron propiedades de imagen. Agrega una propiedad de almacenamiento o URL de imagen para usarla como miniatura.",
34773
+ image_property_description: "Selecciona la propiedad usada como miniatura en las vistas de Tarjetas y Kanban. Si no se establece, se usará automáticamente la primera propiedad de imagen que coincida.",
34480
34774
  display_settings: "Configuración de visualización",
34481
34775
  default_row_size: "Tamaño de fila predeterminado",
34482
34776
  side_dialog_width: "Ancho del diálogo lateral",
@@ -34969,6 +35263,7 @@
34969
35263
  download: "Herunterladen",
34970
35264
  large_number_of_documents: "Diese Sammlung hat eine große Anzahl von Dokumenten ({{count}}).",
34971
35265
  include_undefined_values: "Undefinierte Werte einschließen",
35266
+ export_apply_filter_sort: "Nur Ergebnisse exportieren, die dem aktuellen Filter/der aktuellen Sortierung entsprechen",
34972
35267
  submit: "Einreichen",
34973
35268
  no_filterable_properties: "Keine filterbaren Eigenschaften verfügbar",
34974
35269
  apply_filters: "Filter anwenden",
@@ -35154,6 +35449,10 @@
35154
35449
  order_property_not_found: 'Eigenschaft "{{property}}" existiert nicht oder ist keine Zahlen-Eigenschaft. Bitte wählen Sie eine gültige Eigenschaft oder löschen Sie die Auswahl.',
35155
35450
  no_number_properties: "Keine Zahlen-Eigenschaften gefunden. Fügen Sie eine Zahlen-Eigenschaft hinzu, um die Sortierung zu aktivieren.",
35156
35451
  order_property_description: "Wählen Sie eine Zahlen-Eigenschaft, um die Reihenfolge der Elemente beizubehalten",
35452
+ image_property: "Bild-Eigenschaft",
35453
+ image_property_not_found: 'Eigenschaft "{{property}}" existiert nicht oder ist keine Bild-Eigenschaft. Bitte wählen Sie eine gültige Eigenschaft oder löschen Sie die Auswahl.',
35454
+ no_image_properties: "Keine Bild-Eigenschaften gefunden. Fügen Sie eine Speicher- oder Bild-URL-Eigenschaft hinzu, um sie als Vorschaubild zu verwenden.",
35455
+ image_property_description: "Wählen Sie die Eigenschaft, die als Vorschaubild in den Ansichten Karten und Kanban verwendet wird. Wenn nicht festgelegt, wird automatisch die erste passende Bild-Eigenschaft verwendet.",
35157
35456
  display_settings: "Anzeigeeinstellungen",
35158
35457
  default_row_size: "Standard-Zeilengröße",
35159
35458
  side_dialog_width: "Seitendialog-Breite",
@@ -35646,6 +35945,7 @@
35646
35945
  download: "Télécharger",
35647
35946
  large_number_of_documents: "Cette collection contient un grand nombre de documents ({{count}}).",
35648
35947
  include_undefined_values: "Inclure les valeurs non définies",
35948
+ export_apply_filter_sort: "N'exporter que les résultats correspondant au filtre/tri actuel",
35649
35949
  submit: "Soumettre",
35650
35950
  no_filterable_properties: "Aucune propriété filtrable disponible",
35651
35951
  apply_filters: "Appliquer les filtres",
@@ -35831,6 +36131,10 @@
35831
36131
  order_property_not_found: `La propriété "{{property}}" n'existe pas ou n'est pas une propriété numérique. Veuillez sélectionner une propriété valide ou effacer la sélection.`,
35832
36132
  no_number_properties: "Aucune propriété numérique trouvée. Ajoutez une propriété numérique pour activer le tri.",
35833
36133
  order_property_description: "Sélectionnez une propriété numérique pour conserver l'ordre des éléments",
36134
+ image_property: "Propriété d'image",
36135
+ image_property_not_found: `La propriété "{{property}}" n'existe pas ou n'est pas une propriété d'image. Veuillez sélectionner une propriété valide ou effacer la sélection.`,
36136
+ no_image_properties: "Aucune propriété d'image trouvée. Ajoutez une propriété de stockage ou d'URL d'image à utiliser comme miniature.",
36137
+ image_property_description: "Sélectionnez la propriété utilisée comme miniature dans les vues Cartes et Kanban. Si elle n'est pas définie, la première propriété d'image correspondante sera utilisée automatiquement.",
35834
36138
  display_settings: "Paramètres d'affichage",
35835
36139
  default_row_size: "Taille de ligne par défaut",
35836
36140
  side_dialog_width: "Largeur du dialogue latéral",
@@ -36323,6 +36627,7 @@
36323
36627
  download: "Scarica",
36324
36628
  large_number_of_documents: "Questa collezione contiene un numero elevato di documenti ({{count}})",
36325
36629
  include_undefined_values: "Includi valori non definiti",
36630
+ export_apply_filter_sort: "Esporta solo i risultati che corrispondono al filtro/ordinamento attuale",
36326
36631
  submit: "Invia",
36327
36632
  no_filterable_properties: "Nessuna proprietà filtrabile disponibile",
36328
36633
  apply_filters: "Applica filtri",
@@ -36508,6 +36813,10 @@
36508
36813
  order_property_not_found: 'La proprietà "{{property}}" non esiste o non è una proprietà numerica. Seleziona una proprietà valida o cancella la selezione.',
36509
36814
  no_number_properties: "Nessuna proprietà numerica trovata. Aggiungi una proprietà numerica per abilitare l'ordinamento.",
36510
36815
  order_property_description: "Seleziona una proprietà numerica per mantenere l'ordine degli elementi",
36816
+ image_property: "Proprietà immagine",
36817
+ image_property_not_found: 'La proprietà "{{property}}" non esiste o non è una proprietà immagine. Seleziona una proprietà valida o cancella la selezione.',
36818
+ no_image_properties: "Nessuna proprietà immagine trovata. Aggiungi una proprietà di archiviazione o URL immagine da usare come miniatura.",
36819
+ image_property_description: "Seleziona la proprietà utilizzata come miniatura nelle viste Schede e Kanban. Se non impostata, verrà utilizzata automaticamente la prima proprietà immagine corrispondente.",
36511
36820
  display_settings: "Impostazioni di visualizzazione",
36512
36821
  default_row_size: "Dimensione riga predefinita",
36513
36822
  side_dialog_width: "Larghezza del dialogo laterale",
@@ -37000,6 +37309,7 @@
37000
37309
  download: "डाउनलोड",
37001
37310
  large_number_of_documents: "इस संग्रह में बड़ी संख्या में दस्तावेज़ हैं ({{count}})।",
37002
37311
  include_undefined_values: "अपरिभाषित (undefined) मान शामिल करें",
37312
+ export_apply_filter_sort: "केवल वर्तमान फ़िल्टर/सॉर्ट से मेल खाने वाले परिणाम निर्यात करें",
37003
37313
  submit: "सबमिट करें",
37004
37314
  no_filterable_properties: "कोई फ़िल्टर करने योग्य गुण उपलब्ध नहीं हैं",
37005
37315
  apply_filters: "फ़िल्टर लागू करें",
@@ -37185,6 +37495,10 @@
37185
37495
  order_property_not_found: 'प्रॉपर्टी "{{property}}" मौजूद नहीं है या एक संख्या प्रॉपर्टी नहीं है। कृपया एक वैध प्रॉपर्टी चुनें या चयन साफ़ करें।',
37186
37496
  no_number_properties: "कोई संख्या प्रॉपर्टी नहीं मिली। क्रम सक्षम करने के लिए एक संख्या प्रॉपर्टी जोड़ें।",
37187
37497
  order_property_description: "आइटम का क्रम बनाए रखने के लिए एक संख्या प्रॉपर्टी चुनें",
37498
+ image_property: "इमेज प्रॉपर्टी",
37499
+ image_property_not_found: 'प्रॉपर्टी "{{property}}" मौजूद नहीं है या एक इमेज प्रॉपर्टी नहीं है। कृपया एक वैध प्रॉपर्टी चुनें या चयन साफ़ करें।',
37500
+ no_image_properties: "कोई इमेज प्रॉपर्टी नहीं मिली। थंबनेल के रूप में उपयोग करने के लिए एक स्टोरेज या URL इमेज प्रॉपर्टी जोड़ें।",
37501
+ image_property_description: "कार्ड्स और कानबन व्यू मोड में थंबनेल इमेज के रूप में उपयोग की जाने वाली प्रॉपर्टी चुनें। यदि सेट नहीं किया गया है, तो पहली मिलान वाली इमेज प्रॉपर्टी स्वचालित रूप से उपयोग की जाएगी।",
37188
37502
  display_settings: "प्रदर्शन सेटिंग्स",
37189
37503
  default_row_size: "डिफ़ॉल्ट पंक्ति आकार",
37190
37504
  side_dialog_width: "साइड डायलॉग चौड़ाई",
@@ -37677,6 +37991,7 @@
37677
37991
  download: "Descarregar",
37678
37992
  large_number_of_documents: "Esta coleção tem um grande número de documentos ({{count}}).",
37679
37993
  include_undefined_values: "Incluir valores indefinidos",
37994
+ export_apply_filter_sort: "Exportar apenas os resultados que correspondem ao filtro/ordenação atual",
37680
37995
  submit: "Submeter",
37681
37996
  no_filterable_properties: "Não há propriedades filtráveis disponíveis",
37682
37997
  apply_filters: "Aplicar filtros",
@@ -37864,6 +38179,10 @@
37864
38179
  order_property_not_found: 'A propriedade "{{property}}" não existe ou não é uma propriedade numérica. Selecione uma propriedade válida ou limpe a seleção.',
37865
38180
  no_number_properties: "Nenhuma propriedade numérica encontrada. Adicione uma propriedade numérica para habilitar a ordenação.",
37866
38181
  order_property_description: "Selecione uma propriedade numérica para manter a ordem dos itens",
38182
+ image_property: "Propriedade de imagem",
38183
+ image_property_not_found: 'A propriedade "{{property}}" não existe ou não é uma propriedade de imagem. Selecione uma propriedade válida ou limpe a seleção.',
38184
+ no_image_properties: "Nenhuma propriedade de imagem encontrada. Adicione uma propriedade de armazenamento ou URL de imagem para usar como miniatura.",
38185
+ image_property_description: "Selecione a propriedade usada como miniatura nas visualizações de Cartões e Kanban. Se não for definida, a primeira propriedade de imagem correspondente será usada automaticamente.",
37867
38186
  display_settings: "Configurações de exibição",
37868
38187
  default_row_size: "Tamanho de linha padrão",
37869
38188
  side_dialog_width: "Largura do diálogo lateral",
@@ -38356,6 +38675,7 @@
38356
38675
  download: "Pobierz",
38357
38676
  large_number_of_documents: "Ta kolekcja zawiera dużą liczbę dokumentów ({{count}}).",
38358
38677
  include_undefined_values: "Uwzględnij niezdefiniowane wartości",
38678
+ export_apply_filter_sort: "Eksportuj tylko wyniki zgodne z aktualnym filtrem/sortowaniem",
38359
38679
  submit: "Wyślij",
38360
38680
  no_filterable_properties: "Brak dostępnych właściwości do filtrowania",
38361
38681
  apply_filters: "Zastosuj filtry",
@@ -38543,6 +38863,10 @@
38543
38863
  order_property_not_found: "Właściwość „{{property}}” nie istnieje lub nie jest właściwością liczbową. Wybierz prawidłową właściwość lub wyczyść wybór.",
38544
38864
  no_number_properties: "Nie znaleziono właściwości liczbowych. Dodaj właściwość liczbową, aby włączyć sortowanie.",
38545
38865
  order_property_description: "Wybierz właściwość liczbową, aby zachować kolejność elementów",
38866
+ image_property: "Właściwość obrazu",
38867
+ image_property_not_found: "Właściwość „{{property}}” nie istnieje lub nie jest właściwością obrazu. Wybierz prawidłową właściwość lub wyczyść wybór.",
38868
+ no_image_properties: "Nie znaleziono właściwości obrazu. Dodaj właściwość przechowywania lub adresu URL obrazu, aby użyć jej jako miniatury.",
38869
+ image_property_description: "Wybierz właściwość używaną jako miniatura w widokach Karty i Kanban. Jeśli nie zostanie ustawiona, automatycznie zostanie użyta pierwsza pasująca właściwość obrazu.",
38546
38870
  display_settings: "Ustawienia wyświetlania",
38547
38871
  default_row_size: "Domyślny rozmiar wiersza",
38548
38872
  side_dialog_width: "Szerokość okna bocznego",
@@ -43513,6 +43837,7 @@ ul[data-type="taskList"] li[data-checked="true"] > div > p {
43513
43837
  exports2.getEntityTitlePropertyKey = getEntityTitlePropertyKey;
43514
43838
  exports2.getFieldConfig = getFieldConfig;
43515
43839
  exports2.getFieldId = getFieldId;
43840
+ exports2.getFileExtensionFromUrl = getFileExtensionFromUrl;
43516
43841
  exports2.getFormFieldKeys = getFormFieldKeys;
43517
43842
  exports2.getGeoPointCoordinates = getGeoPointCoordinates;
43518
43843
  exports2.getHashValue = getHashValue;
@@ -43523,6 +43848,7 @@ ul[data-type="taskList"] li[data-checked="true"] > div > p {
43523
43848
  exports2.getLabelOrConfigFrom = getLabelOrConfigFrom;
43524
43849
  exports2.getLastSegment = getLastSegment;
43525
43850
  exports2.getLocalChangesBackup = getLocalChangesBackup;
43851
+ exports2.getPreviewTypeFromUrl = getPreviewTypeFromUrl;
43526
43852
  exports2.getPropertiesWithPropertiesOrder = getPropertiesWithPropertiesOrder;
43527
43853
  exports2.getPropertyInPath = getPropertyInPath;
43528
43854
  exports2.getRandomId = getRandomId;
@@ -43532,6 +43858,7 @@ ul[data-type="taskList"] li[data-checked="true"] > div > p {
43532
43858
  exports2.hydrateRegExp = hydrateRegExp;
43533
43859
  exports2.iconSynonyms = iconSynonyms;
43534
43860
  exports2.iconsSearch = iconsSearch;
43861
+ exports2.isAbsoluteHttpUrl = isAbsoluteHttpUrl;
43535
43862
  exports2.isDataTypeFilterable = isDataTypeFilterable;
43536
43863
  exports2.isDefaultFieldConfigId = isDefaultFieldConfigId;
43537
43864
  exports2.isEmptyObject = isEmptyObject;