@rebasepro/admin 0.9.0 → 0.9.1-canary.0de22e0

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 (264) hide show
  1. package/README.md +7 -7
  2. package/dist/{CollectionEditorDialog-B-7uW3iJ.js → CollectionEditorDialog-D7odTn0N.js} +150 -36
  3. package/dist/CollectionEditorDialog-D7odTn0N.js.map +1 -0
  4. package/dist/{PropertyEditView-7KMTcrqi.js → PropertyEditView-i51tFOfM.js} +6 -6
  5. package/dist/PropertyEditView-i51tFOfM.js.map +1 -0
  6. package/dist/{RouterCollectionsStudioView-epqIbZrJ.js → RouterCollectionsStudioView-B9AjTCjT.js} +5 -5
  7. package/dist/RouterCollectionsStudioView-B9AjTCjT.js.map +1 -0
  8. package/dist/collection_editor/api/generateCollectionApi.d.ts +4 -4
  9. package/dist/collection_editor/ui/collection_editor/PropertyEditView.d.ts +1 -1
  10. package/dist/collection_editor/ui/collection_editor/SwitchControl.d.ts +1 -1
  11. package/dist/collection_editor/useSafeSnackbarController.d.ts +1 -1
  12. package/dist/collection_editor_ui.js +5 -5
  13. package/dist/collection_editor_ui.js.map +1 -1
  14. package/dist/components/CollectionTableBinding/CollectionTableBindingProps.d.ts +1 -1
  15. package/dist/components/CollectionTableBinding/internal/EntityTableCell.d.ts +1 -1
  16. package/dist/components/CollectionTableBinding/internal/popup_field/PopupFormField.d.ts +1 -1
  17. package/dist/components/CollectionTableBinding/table_bindings.d.ts +1 -1
  18. package/dist/components/CollectionViewBinding/hooks/useCollectionInlineEditor.d.ts +1 -1
  19. package/dist/components/{RebaseCMS.d.ts → RebaseAdmin.d.ts} +2 -2
  20. package/dist/components/RebaseLayout.d.ts +5 -4
  21. package/dist/components/RebaseShell.d.ts +1 -0
  22. package/dist/components/SelectableTable/SelectableTable.d.ts +1 -1
  23. package/dist/components/SelectableTable/SelectableTableContext.d.ts +1 -1
  24. package/dist/components/SidePanelProvider.d.ts +1 -1
  25. package/dist/components/field_configs.d.ts +17 -0
  26. package/dist/components/index.d.ts +1 -1
  27. package/dist/contexts/BreacrumbsContext.d.ts +1 -1
  28. package/dist/editor.js +1 -1
  29. package/dist/editor.js.map +1 -1
  30. package/dist/export-BM6HPujv.js +518 -0
  31. package/dist/export-BM6HPujv.js.map +1 -0
  32. package/dist/form/components/LocalChangesMenu.d.ts +1 -1
  33. package/dist/form/components/StorageUploadProgress.d.ts +1 -1
  34. package/dist/form/field_bindings/StorageUploadFieldBinding.d.ts +1 -1
  35. package/dist/{history-7X5bON_n.js → history-CtIPJxvQ.js} +6 -6
  36. package/dist/history-CtIPJxvQ.js.map +1 -0
  37. package/dist/hooks/useSelectionDialog.d.ts +1 -1
  38. package/dist/import-DzQnT03v.js +328 -0
  39. package/dist/import-DzQnT03v.js.map +1 -0
  40. package/dist/index.d.ts +1 -1
  41. package/dist/index.js +3300 -2
  42. package/dist/index.js.map +1 -0
  43. package/dist/preview/components/UrlComponentPreview.d.ts +2 -1
  44. package/dist/preview/util.d.ts +1 -0
  45. package/dist/types/components/formex.d.ts +1 -1
  46. package/dist/util/view_mode.d.ts +54 -0
  47. package/dist/{src-sUZfe29F.js → util-XFwQ9FEc.js} +17554 -21391
  48. package/dist/util-XFwQ9FEc.js.map +1 -0
  49. package/package.json +12 -17
  50. package/src/collection_editor/ConfigControllerProvider.tsx +1 -1
  51. package/src/collection_editor/api/generateCollectionApi.ts +4 -4
  52. package/src/collection_editor/ui/AddKanbanColumnAction.tsx +1 -1
  53. package/src/collection_editor/ui/CollectionViewHeaderAction.tsx +1 -1
  54. package/src/collection_editor/ui/EditorCollectionAction.tsx +1 -1
  55. package/src/collection_editor/ui/EditorCollectionActionStart.tsx +1 -1
  56. package/src/collection_editor/ui/EditorEntityAction.tsx +1 -1
  57. package/src/collection_editor/ui/HomePageEditorCollectionAction.tsx +1 -1
  58. package/src/collection_editor/ui/KanbanSetupAction.tsx +1 -1
  59. package/src/collection_editor/ui/MissingReferenceWidget.tsx +1 -1
  60. package/src/collection_editor/ui/NewCollectionButton.tsx +1 -1
  61. package/src/collection_editor/ui/NewCollectionCard.tsx +1 -1
  62. package/src/collection_editor/ui/PropertyAddColumnComponent.tsx +1 -1
  63. package/src/collection_editor/ui/collection_editor/AICollectionGeneratorPopover.tsx +1 -1
  64. package/src/collection_editor/ui/collection_editor/CollectionDetailsForm.tsx +3 -3
  65. package/src/collection_editor/ui/collection_editor/CollectionEditorDialog.tsx +3 -3
  66. package/src/collection_editor/ui/collection_editor/CollectionEditorWelcomeView.tsx +2 -2
  67. package/src/collection_editor/ui/collection_editor/CollectionPropertiesEditorForm.tsx +2 -2
  68. package/src/collection_editor/ui/collection_editor/CollectionRLSTab.tsx +139 -13
  69. package/src/collection_editor/ui/collection_editor/CollectionRelationsTab.tsx +1 -1
  70. package/src/collection_editor/ui/collection_editor/CollectionStudioView.tsx +1 -1
  71. package/src/collection_editor/ui/collection_editor/CollectionsStudioView.tsx +1 -1
  72. package/src/collection_editor/ui/collection_editor/DisplaySettingsForm.tsx +2 -2
  73. package/src/collection_editor/ui/collection_editor/EntityActionsEditTab.tsx +2 -2
  74. package/src/collection_editor/ui/collection_editor/EntityActionsSelectDialog.tsx +1 -1
  75. package/src/collection_editor/ui/collection_editor/EntityCustomViewsSelectDialog.tsx +1 -1
  76. package/src/collection_editor/ui/collection_editor/EnumForm.tsx +2 -2
  77. package/src/collection_editor/ui/collection_editor/GeneralSettingsForm.tsx +2 -2
  78. package/src/collection_editor/ui/collection_editor/GetCodeDialog.tsx +2 -2
  79. package/src/collection_editor/ui/collection_editor/KanbanConfigSection.tsx +2 -2
  80. package/src/collection_editor/ui/collection_editor/PropertyEditView.tsx +2 -2
  81. package/src/collection_editor/ui/collection_editor/PropertyFieldPreview.tsx +1 -1
  82. package/src/collection_editor/ui/collection_editor/PropertyTree.tsx +1 -1
  83. package/src/collection_editor/ui/collection_editor/RouterCollectionStudioView.tsx +1 -1
  84. package/src/collection_editor/ui/collection_editor/SubcollectionsEditTab.tsx +2 -2
  85. package/src/collection_editor/ui/collection_editor/SwitchControl.tsx +1 -1
  86. package/src/collection_editor/ui/collection_editor/import/CollectionEditorImportDataPreview.tsx +1 -1
  87. package/src/collection_editor/ui/collection_editor/import/CollectionEditorImportMapping.tsx +2 -2
  88. package/src/collection_editor/ui/collection_editor/properties/BlockPropertyField.tsx +1 -1
  89. package/src/collection_editor/ui/collection_editor/properties/BooleanPropertyField.tsx +1 -1
  90. package/src/collection_editor/ui/collection_editor/properties/CommonPropertyFields.tsx +3 -3
  91. package/src/collection_editor/ui/collection_editor/properties/DateTimePropertyField.tsx +2 -2
  92. package/src/collection_editor/ui/collection_editor/properties/EnumPropertyField.tsx +3 -3
  93. package/src/collection_editor/ui/collection_editor/properties/MapPropertyField.tsx +2 -2
  94. package/src/collection_editor/ui/collection_editor/properties/MarkdownPropertyField.tsx +2 -2
  95. package/src/collection_editor/ui/collection_editor/properties/NumberPropertyField.tsx +2 -2
  96. package/src/collection_editor/ui/collection_editor/properties/ReferencePropertyField.tsx +2 -2
  97. package/src/collection_editor/ui/collection_editor/properties/RelationPropertyField.tsx +1 -1
  98. package/src/collection_editor/ui/collection_editor/properties/RepeatPropertyField.tsx +1 -1
  99. package/src/collection_editor/ui/collection_editor/properties/StoragePropertyField.tsx +2 -2
  100. package/src/collection_editor/ui/collection_editor/properties/StringPropertyField.tsx +2 -2
  101. package/src/collection_editor/ui/collection_editor/properties/UrlPropertyField.tsx +1 -1
  102. package/src/collection_editor/ui/collection_editor/properties/VectorPropertyField.tsx +1 -1
  103. package/src/collection_editor/ui/collection_editor/properties/advanced/AdvancedPropertyValidation.tsx +1 -1
  104. package/src/collection_editor/ui/collection_editor/properties/conditions/ConditionsEditor.tsx +1 -1
  105. package/src/collection_editor/ui/collection_editor/properties/conditions/EnumConditionsEditor.tsx +1 -1
  106. package/src/collection_editor/ui/collection_editor/properties/validation/ArrayPropertyValidation.tsx +2 -2
  107. package/src/collection_editor/ui/collection_editor/properties/validation/GeneralPropertyValidation.tsx +2 -2
  108. package/src/collection_editor/ui/collection_editor/properties/validation/NumberPropertyValidation.tsx +2 -2
  109. package/src/collection_editor/ui/collection_editor/properties/validation/StringPropertyValidation.tsx +2 -2
  110. package/src/collection_editor/useSafeSnackbarController.ts +1 -1
  111. package/src/components/AdminModeSyncer.tsx +1 -1
  112. package/src/components/ArrayContainer.tsx +1 -1
  113. package/src/components/ClearFilterSortButton.tsx +1 -1
  114. package/src/components/CollectionPanel.tsx +1 -1
  115. package/src/components/CollectionTableBinding/CollectionRowActions.tsx +3 -3
  116. package/src/components/CollectionTableBinding/CollectionTableBinding.tsx +3 -3
  117. package/src/components/CollectionTableBinding/CollectionTableBindingProps.tsx +1 -1
  118. package/src/components/CollectionTableBinding/PropertyTableCell.tsx +1 -1
  119. package/src/components/CollectionTableBinding/column_utils.tsx +1 -1
  120. package/src/components/CollectionTableBinding/fields/TableMultipleRelationField.tsx +2 -2
  121. package/src/components/CollectionTableBinding/fields/TableReferenceField.tsx +2 -2
  122. package/src/components/CollectionTableBinding/fields/TableRelationField.tsx +2 -2
  123. package/src/components/CollectionTableBinding/fields/TableStorageUpload.tsx +1 -1
  124. package/src/components/CollectionTableBinding/internal/CollectionTableToolbar.tsx +1 -1
  125. package/src/components/CollectionTableBinding/internal/EntityTableCell.tsx +2 -2
  126. package/src/components/CollectionTableBinding/internal/EntityTableCellActions.tsx +1 -1
  127. package/src/components/CollectionTableBinding/internal/popup_field/PopupFormField.tsx +4 -4
  128. package/src/components/CollectionTableBinding/table_bindings.tsx +1 -1
  129. package/src/components/CollectionViewBinding/BoardCardBinding.tsx +2 -2
  130. package/src/components/CollectionViewBinding/CollectionBoardViewBinding.tsx +4 -4
  131. package/src/components/CollectionViewBinding/CollectionCardViewBinding.tsx +1 -1
  132. package/src/components/CollectionViewBinding/CollectionListViewBinding.tsx +3 -3
  133. package/src/components/CollectionViewBinding/CollectionViewActions.tsx +3 -3
  134. package/src/components/CollectionViewBinding/CollectionViewBinding.tsx +77 -127
  135. package/src/components/CollectionViewBinding/CollectionViewStartActions.tsx +5 -9
  136. package/src/components/CollectionViewBinding/EntityCardBinding.tsx +3 -3
  137. package/src/components/CollectionViewBinding/FiltersDialog.tsx +19 -1
  138. package/src/components/CollectionViewBinding/SplitListView.tsx +114 -63
  139. package/src/components/CollectionViewBinding/ViewModeToggle.tsx +1 -1
  140. package/src/components/CollectionViewBinding/hooks/useCollectionInlineEditor.ts +2 -2
  141. package/src/components/CollectionViewBinding/hooks/useKanbanDragAndDrop.ts +2 -2
  142. package/src/components/CollectionViewBinding/useBoardDataController.tsx +9 -3
  143. package/src/components/CollectionViewBinding/usePreviewSlots.ts +1 -1
  144. package/src/components/DefaultAppBar.tsx +3 -3
  145. package/src/components/DefaultDrawer.tsx +3 -3
  146. package/src/components/DeleteEntityDialog.tsx +1 -1
  147. package/src/components/DetailViewBinding.tsx +7 -5
  148. package/src/components/DrawerNavigationGroup.tsx +2 -2
  149. package/src/components/EditFormActions.tsx +6 -6
  150. package/src/components/EditViewBinding.tsx +9 -8
  151. package/src/components/EntityPreviewBinding.tsx +5 -4
  152. package/src/components/EntityViewBinding.tsx +2 -2
  153. package/src/components/HomePage/ContentHomePage.tsx +6 -5
  154. package/src/components/HomePage/FavouritesView.tsx +2 -2
  155. package/src/components/HomePage/NavigationCardBinding.tsx +3 -3
  156. package/src/components/HomePage/NavigationGroup.tsx +1 -1
  157. package/src/components/HomePage/RenameGroupDialog.tsx +1 -1
  158. package/src/components/JsonPreviewBinding.tsx +1 -1
  159. package/src/components/{RebaseCMS.tsx → RebaseAdmin.tsx} +3 -3
  160. package/src/components/RebaseAuthGate.tsx +2 -2
  161. package/src/components/RebaseLayout.tsx +7 -13
  162. package/src/components/RebaseNavigation.tsx +18 -3
  163. package/src/components/RebaseRouteDefs.tsx +3 -3
  164. package/src/components/RebaseShell.tsx +2 -1
  165. package/src/components/ReferenceTable/SelectionTableBinding.tsx +7 -6
  166. package/src/components/ReferenceWidget.tsx +1 -1
  167. package/src/components/RelationSelector.tsx +1 -1
  168. package/src/components/SearchIconsView.tsx +2 -2
  169. package/src/components/SelectableTable/SelectableTable.tsx +2 -2
  170. package/src/components/SelectableTable/SelectableTableContext.tsx +1 -1
  171. package/src/components/SelectableTable/filters/BooleanFilterField.tsx +1 -1
  172. package/src/components/SelectableTable/filters/DateTimeFilterField.tsx +1 -1
  173. package/src/components/SelectableTable/filters/FilterFieldBinding.tsx +1 -1
  174. package/src/components/SelectableTable/filters/ReferenceFilterField.tsx +2 -2
  175. package/src/components/SelectableTable/filters/StringNumberFilterField.tsx +1 -1
  176. package/src/components/SideDialogs.tsx +1 -1
  177. package/src/components/SidePanelBinding.tsx +47 -9
  178. package/src/components/SidePanelProvider.tsx +15 -12
  179. package/src/components/UserSelector.tsx +1 -1
  180. package/src/components/admin/CreationResultDialog.tsx +6 -3
  181. package/src/components/app/Scaffold.tsx +6 -2
  182. package/src/components/common/default_entity_actions.tsx +123 -25
  183. package/src/components/field_configs.tsx +42 -25
  184. package/src/components/history/EntityHistoryEntry.tsx +1 -1
  185. package/src/components/history/EntityHistoryView.tsx +5 -5
  186. package/src/components/history/LastEditedByIndicator.tsx +2 -2
  187. package/src/components/index.ts +1 -1
  188. package/src/contexts/BreacrumbsContext.tsx +1 -1
  189. package/src/data_export/export/BasicExportAction.tsx +1 -1
  190. package/src/data_export/export/ExportCollectionAction.tsx +1 -1
  191. package/src/data_import/components/DataNewPropertiesMapping.tsx +1 -1
  192. package/src/data_import/components/ImportFileUpload.tsx +1 -1
  193. package/src/data_import/components/ImportNewPropertyFieldPreview.tsx +3 -5
  194. package/src/data_import/components/ImportSaveInProgress.tsx +1 -1
  195. package/src/data_import/import/ImportCollectionAction.tsx +8 -8
  196. package/src/data_import/utils/data.ts +2 -2
  197. package/src/data_import/utils/get_properties_mapping.ts +1 -1
  198. package/src/editor/components/image-bubble.tsx +1 -1
  199. package/src/editor/components/table-bubble.tsx +1 -1
  200. package/src/editor/editor.tsx +1 -1
  201. package/src/editor/selectors/color-selector.tsx +1 -1
  202. package/src/editor/selectors/link-selector.tsx +1 -1
  203. package/src/editor/selectors/node-selector.tsx +2 -2
  204. package/src/editor/selectors/text-buttons.tsx +1 -1
  205. package/src/form/EntityForm.tsx +8 -5
  206. package/src/form/EntityFormActions.tsx +1 -1
  207. package/src/form/EntityFormBinding.tsx +7 -5
  208. package/src/form/PropertyFieldBinding.tsx +3 -3
  209. package/src/form/components/ErrorFocus.tsx +1 -1
  210. package/src/form/components/LocalChangesMenu.tsx +3 -3
  211. package/src/form/components/StorageItemPreview.tsx +1 -1
  212. package/src/form/components/StorageUploadProgress.tsx +3 -3
  213. package/src/form/field_bindings/ArrayCustomShapedFieldBinding.tsx +3 -2
  214. package/src/form/field_bindings/ArrayOfReferencesFieldBinding.tsx +4 -3
  215. package/src/form/field_bindings/BlockFieldBinding.tsx +4 -3
  216. package/src/form/field_bindings/DateTimeFieldBinding.tsx +3 -2
  217. package/src/form/field_bindings/KeyValueFieldBinding.tsx +4 -3
  218. package/src/form/field_bindings/MapFieldBinding.tsx +3 -2
  219. package/src/form/field_bindings/MarkdownEditorFieldBinding.tsx +4 -3
  220. package/src/form/field_bindings/MultiSelectFieldBinding.tsx +2 -1
  221. package/src/form/field_bindings/MultipleRelationFieldBinding.tsx +3 -2
  222. package/src/form/field_bindings/ReadOnlyFieldBinding.tsx +2 -1
  223. package/src/form/field_bindings/ReferenceFieldBinding.tsx +5 -4
  224. package/src/form/field_bindings/RelationFieldBinding.tsx +3 -2
  225. package/src/form/field_bindings/RepeatFieldBinding.tsx +3 -2
  226. package/src/form/field_bindings/SelectFieldBinding.tsx +2 -1
  227. package/src/form/field_bindings/StorageUploadFieldBinding.tsx +5 -4
  228. package/src/form/field_bindings/SwitchFieldBinding.tsx +2 -1
  229. package/src/form/field_bindings/TextFieldBinding.tsx +2 -1
  230. package/src/form/field_bindings/UserSelectFieldBinding.tsx +2 -1
  231. package/src/form/field_bindings/VectorFieldBinding.tsx +2 -1
  232. package/src/form/form_utils.ts +1 -1
  233. package/src/hooks/navigation/useNavigationResolution.ts +19 -4
  234. package/src/hooks/useBuildSidePanel.tsx +10 -2
  235. package/src/hooks/useCMSContext.tsx +1 -1
  236. package/src/hooks/useHistory.ts +1 -1
  237. package/src/hooks/useResolvedNavigationFrom.tsx +4 -2
  238. package/src/hooks/useSelectionDialog.tsx +3 -3
  239. package/src/index.ts +3 -3
  240. package/src/preview/PropertyPreview.tsx +2 -2
  241. package/src/preview/components/DatePreview.tsx +1 -1
  242. package/src/preview/components/EnumValuesChip.tsx +1 -1
  243. package/src/preview/components/ImagePreview.tsx +2 -2
  244. package/src/preview/components/ReferencePreview.tsx +3 -3
  245. package/src/preview/components/RelationPreview.tsx +3 -3
  246. package/src/preview/components/StorageThumbnail.tsx +1 -1
  247. package/src/preview/components/UrlComponentPreview.tsx +2 -9
  248. package/src/preview/property_previews/ArrayOfStorageComponentsPreview.tsx +1 -1
  249. package/src/preview/property_previews/ArrayOfStringsPreview.tsx +1 -1
  250. package/src/preview/property_previews/ArrayOneOfPreview.tsx +1 -1
  251. package/src/preview/property_previews/ArrayPropertyPreview.tsx +1 -1
  252. package/src/preview/property_previews/NumberPropertyPreview.tsx +1 -1
  253. package/src/preview/util.ts +9 -0
  254. package/src/routes/CustomViewRoute.tsx +2 -1
  255. package/src/routes/RebaseRoute.tsx +21 -26
  256. package/src/types/components/formex.tsx +1 -1
  257. package/src/util/navigation_utils.ts +2 -5
  258. package/src/util/previews.ts +4 -2
  259. package/src/util/view_mode.ts +102 -0
  260. package/dist/CollectionEditorDialog-B-7uW3iJ.js.map +0 -1
  261. package/dist/PropertyEditView-7KMTcrqi.js.map +0 -1
  262. package/dist/RouterCollectionsStudioView-epqIbZrJ.js.map +0 -1
  263. package/dist/history-7X5bON_n.js.map +0 -1
  264. package/dist/src-sUZfe29F.js.map +0 -1
@@ -0,0 +1 @@
1
+ {"version":3,"file":"history-CtIPJxvQ.js","names":[],"sources":["../src/components/history/UserChip.tsx","../src/components/history/EntityHistoryEntry.tsx","../src/components/history/EntityHistoryView.tsx"],"sourcesContent":["import { User } from \"@rebasepro/types\";\nimport { Chip, Tooltip } from \"@rebasepro/ui\";\n\nexport function UserChip({ user }: { user: User }) {\n return (\n <Tooltip title={user.email ?? user.uid}>\n <Chip size={\"small\"} className={\"flex items-center\"}>\n {user.photoURL && <img\n className={\"rounded-full w-6 h-6 mr-2\"}\n src={user.photoURL} alt={user.displayName ?? \"User picture\"}/>}\n <span>{user.displayName ?? user.email ?? user.uid}</span>\n </Chip>\n </Tooltip>\n );\n}\n","import type { CollectionConfig } from \"@rebasepro/types\";\nimport type { Property } from \"@rebasepro/types\";\nimport * as React from \"react\";\n\nimport { ArrowLeftIcon, Chip, cls, defaultBorderMixin, iconSize, Tooltip, Typography } from \"@rebasepro/ui\";\nimport { PreviewSize } from \"../../types/components/PropertyPreviewProps\";\nimport { getPropertyInPath } from \"../../util/property_utils\";\nimport { PropertyPreview } from \"../../preview/PropertyPreview\";\nimport { SkeletonPropertyComponent } from \"../../preview/property_previews/SkeletonPropertyComponent\";\nimport { useAuthController } from \"@rebasepro/app\";\nimport { UserChip } from \"./UserChip\";\nimport { HistoryEntryData } from \"../../hooks\";\nimport { getValueInPath } from \"@rebasepro/utils\";\n\n/**\n * Recursive deep equality for primitives, arrays and plain objects.\n */\nfunction deepEqual(a: unknown, b: unknown): boolean {\n if (a === b) return true;\n if (a == null || b == null) return a === b;\n if (typeof a !== typeof b) return false;\n if (typeof a !== \"object\") return false;\n\n if (Array.isArray(a)) {\n if (!Array.isArray(b) || a.length !== (b as unknown[]).length) return false;\n return a.every((item, i) => deepEqual(item, (b as unknown[])[i]));\n }\n\n if (Array.isArray(b)) return false;\n\n const aObj = a as Record<string, unknown>;\n const bObj = b as Record<string, unknown>;\n const aKeys = Object.keys(aObj);\n const bKeys = Object.keys(bObj);\n if (aKeys.length !== bKeys.length) return false;\n return aKeys.every(key => key in bObj && deepEqual(aObj[key], bObj[key]));\n}\n\nexport type EntityHistoryEntryProps = {\n size: PreviewSize;\n actions?: React.ReactNode;\n collection?: CollectionConfig;\n hover?: boolean;\n entry: HistoryEntryData;\n onClick?: (e: React.SyntheticEvent) => void;\n};\n\nfunction PreviousValueView({\n previousValueInPath,\n childProperty,\n propertyKey\n}: {\n previousValueInPath: unknown;\n childProperty: Property;\n propertyKey: string;\n}) {\n if (typeof previousValueInPath === \"string\" || typeof previousValueInPath === \"number\") {\n return <Typography variant={\"caption\"} color={\"secondary\"} className=\"line-through\">\n {previousValueInPath}\n </Typography>;\n } else if (typeof previousValueInPath === \"boolean\") {\n return <Typography variant={\"caption\"} color={\"secondary\"} className=\"line-through\">\n {previousValueInPath ? \"true\" : \"false\"}\n </Typography>;\n } else {\n return <Tooltip\n side={\"left\"}\n title={<div className={\"flex flex-col gap-2\"}>\n <Typography variant={\"caption\"} color={\"secondary\"}>\n Previous value\n </Typography>\n <PropertyPreview\n propertyKey={propertyKey as string}\n value={previousValueInPath as never}\n property={childProperty as Property}\n size={\"small\"}/>\n </div>}>\n <ArrowLeftIcon size={iconSize.smallest} color={\"disabled\"} className={\"mb-1\"}/>\n </Tooltip>\n }\n}\n\n/**\n * Displays a single entity history revision entry.\n * Adapted from the entity_history plugin — now reads from backend API data.\n */\nexport function EntityHistoryEntry({\n actions,\n hover,\n collection,\n size,\n entry\n}: EntityHistoryEntryProps) {\n\n const authController = useAuthController();\n\n const changedFields = entry.changed_fields;\n const previousValues = entry.previous_values;\n const updatedOn = new Date(entry.updated_at);\n const updatedBy = entry.updated_by;\n\n // Resolve user display\n const currentUser = authController.user;\n const userDisplay = updatedBy === currentUser?.uid\n ? currentUser\n : undefined;\n\n return <div className={\"w-full flex flex-col gap-2 mt-4\"}>\n <div className={\"ml-4 flex items-center gap-4\"}>\n <Typography variant={\"body2\"} color={\"secondary\"}>\n {updatedOn.toLocaleString()}\n </Typography>\n <Chip size={\"small\"}>\n {entry.action}\n </Chip>\n {!userDisplay && updatedBy && <Chip size={\"small\"}>{updatedBy}</Chip>}\n {userDisplay && <UserChip user={userDisplay}/>}\n </div>\n <div\n className={cls(\n \"bg-white dark:bg-surface-900\",\n \"min-h-[44px]\",\n \"w-full\",\n \"items-center\",\n hover ? \"hover:bg-surface-accent-50 dark:hover:bg-surface-800\" : \"\",\n size === \"small\" ? \"p-1\" : \"px-2 py-1\",\n \"flex border rounded-lg\",\n defaultBorderMixin\n )}>\n\n {actions}\n\n <div className={\"flex flex-col grow w-full m-1 shrink min-w-0\"}>\n\n {changedFields && collection && changedFields.map((key: string) => {\n const childProperty = getPropertyInPath(collection.properties, key);\n const valueInPath = entry.values ? getValueInPath(entry.values, key) : undefined;\n const previousValueInPath = previousValues ? getValueInPath(previousValues, key) : undefined;\n\n const element = childProperty\n ? <PropertyPreview\n propertyKey={key}\n value={valueInPath as never}\n property={childProperty as Property}\n size={\"small\"}/>\n : <Typography variant={\"body2\"}>\n {typeof valueInPath === \"string\" ? valueInPath : JSON.stringify(valueInPath)}\n </Typography>;\n\n return (\n <div key={\"ref_prev_\" + key}\n className=\"flex w-full my-1 items-center\">\n <Typography variant={\"caption\"}\n color={\"secondary\"}\n className=\"min-w-[140px] md:min-w-[200px] w-1/5 pr-8 overflow-hidden text-ellipsis text-right\">\n {key}\n </Typography>\n <div className=\"w-4/5\">\n {previousValueInPath !== undefined && !deepEqual(previousValueInPath, valueInPath) &&\n <PreviousValueView previousValueInPath={previousValueInPath}\n childProperty={childProperty as Property}\n propertyKey={key}/>\n }\n {element}\n </div>\n </div>\n );\n })}\n\n {(!changedFields || changedFields.length === 0) && (\n <Typography variant={\"caption\"} color={\"secondary\"} className=\"ml-4\">\n {entry.action === \"create\" ? \"Entity created\" :\n entry.action === \"delete\" ? \"Entity deleted\" : \"No field changes recorded\"}\n </Typography>\n )}\n\n </div>\n\n </div>\n </div>;\n}\n","\nimport type { EntityCustomViewParams } from \"@rebasepro/types\";\nimport { useRef, useEffect } from \"react\";\nimport { cls, IconButton, Label, Tooltip, Typography } from \"@rebasepro/ui\";\nimport { ErrorBoundary, HistoryIcon } from \"@rebasepro/ui\";\nimport { EntityHistoryEntry } from \"./EntityHistoryEntry\";\nimport { useSnackbarController, useAuthController } from \"@rebasepro/app\";\nimport { ConfirmationDialog } from \"@rebasepro/app\";\nimport { useState } from \"react\";\nimport { useHistory } from \"../../hooks/useHistory\";\n\n/**\n * Entity history tab view. Shows a paginated list of entity revisions\n * fetched from the backend API. Supports infinite scroll and revert.\n */\nexport function EntityHistoryView<M extends Record<string, unknown>>({\n entity,\n collection,\n formContext\n}: EntityCustomViewParams<M>) {\n\n const snackbarController = useSnackbarController();\n const authController = useAuthController();\n const dirty = formContext?.formex.dirty;\n\n const slug = collection.slug;\n const entityId = entity?.id;\n\n const {\n entries,\n isLoading,\n hasMore,\n loadMore,\n revert\n } = useHistory({\n slug,\n entityId,\n enabled: !!entityId,\n pageSize: 10\n });\n\n const [revertHistoryId, setRevertHistoryId] = useState<string | undefined>();\n const [isReverting, setIsReverting] = useState(false);\n\n const containerRef = useRef<HTMLDivElement>(null);\n const loadMoreRef = useRef<HTMLDivElement>(null);\n\n // Intersection observer for infinite scroll\n useEffect(() => {\n const currentContainer = containerRef.current;\n const currentLoadMore = loadMoreRef.current;\n\n if (!currentContainer || !currentLoadMore || !hasMore || isLoading) return;\n\n const observer = new IntersectionObserver(\n (observerEntries) => {\n if (observerEntries[0].isIntersecting && hasMore && !isLoading) {\n loadMore();\n }\n },\n {\n root: currentContainer,\n rootMargin: \"0px 0px 200px 0px\",\n threshold: 0.01\n }\n );\n\n observer.observe(currentLoadMore);\n\n return () => observer.disconnect();\n }, [hasMore, isLoading, entries.length, loadMore]);\n\n if (!entity) {\n return <div className=\"flex items-center justify-center h-full\">\n <Label>History is only available for existing entities</Label>\n </div>;\n }\n\n async function doRevert(historyId: string) {\n setIsReverting(true);\n try {\n const revertedValues = await revert(historyId);\n setRevertHistoryId(undefined);\n\n // Reset the form with the reverted values so the UI updates\n // immediately without requiring a page refresh.\n if (formContext?.formex?.resetForm && revertedValues) {\n formContext.formex.resetForm({\n values: revertedValues as M,\n submitCount: 0,\n touched: {}\n });\n }\n\n snackbarController.open({\n message: \"Reverted to selected version\",\n type: \"info\"\n });\n } catch (error) {\n console.error(\"Error reverting entity:\", error);\n snackbarController.open({\n message: \"Error reverting entity\",\n type: \"error\"\n });\n } finally {\n setIsReverting(false);\n }\n }\n\n const revertEntry = revertHistoryId\n ? entries.find(e => e.id === revertHistoryId)\n : undefined;\n\n return <div\n ref={containerRef}\n className={cls(\"relative flex-1 h-full overflow-auto w-full flex flex-col gap-4 p-8\")}>\n <div className=\"flex flex-col gap-2 max-w-6xl mx-auto w-full\">\n\n <Typography variant={\"h5\"} className={\"mt-24 ml-4\"}>\n History\n </Typography>\n\n {isLoading && entries.length === 0 && (\n <div className=\"flex flex-col gap-4 mt-8 ml-4\">\n {[1, 2, 3].map(i => (\n <div key={i} className=\"flex flex-col gap-2 animate-pulse\">\n <div className=\"h-4 w-48 bg-surface-200 dark:bg-surface-700 rounded\"/>\n <div className=\"h-12 w-full bg-surface-100 dark:bg-surface-900 rounded-lg border border-surface-200 dark:border-surface-700\"/>\n </div>\n ))}\n </div>\n )}\n\n {!isLoading && entries.length === 0 && <>\n <Label className={\"ml-4 mt-8\"}>\n No history available\n </Label>\n <Typography variant={\"caption\"} className={\"ml-4\"}>\n When you save a entity, a new version is created and stored in the history.\n </Typography>\n </>}\n\n {entries.map((entry) => (\n <div key={entry.id} className=\"flex flex-cols gap-2 w-full\">\n <EntityHistoryEntry\n entry={entry}\n collection={collection}\n size={\"medium\"}\n actions={\n <Tooltip title={\"Revert to this version\"}\n className={\"m-2 grow-0 self-start\"}>\n <IconButton\n onClick={() => {\n if (dirty) {\n snackbarController.open({\n message: \"Please save or discard your changes before reverting\",\n type: \"warning\"\n });\n } else {\n setRevertHistoryId(entry.id);\n }\n }}>\n <HistoryIcon/>\n </IconButton>\n </Tooltip>\n }\n />\n </div>\n ))}\n\n {/* Load more sentinel */}\n {entries.length > 0 && (\n <div ref={loadMoreRef} className=\"py-4 text-center\">\n {isLoading && <Label>Loading more...</Label>}\n {!hasMore && entries.length > 10 && <Label>No more history available</Label>}\n </div>\n )}\n </div>\n\n <ErrorBoundary>\n <ConfirmationDialog\n open={Boolean(revertHistoryId)}\n onAccept={() => {\n if (revertHistoryId) doRevert(revertHistoryId);\n }}\n onCancel={() => setRevertHistoryId(undefined)}\n title={<Typography variant={\"subtitle2\"}>Revert data to this version?</Typography>}\n body={revertEntry\n ? <div className=\"p-4\">\n <Typography variant={\"caption\"} color={\"secondary\"}>\n This will save the entity with the values from{\" \"}\n {new Date(revertEntry.updated_at).toLocaleString()}.\n A new history entry will be created for the revert.\n </Typography>\n </div>\n : null\n }\n />\n </ErrorBoundary>\n </div>;\n}\n"],"mappings":"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"}
@@ -1,4 +1,4 @@
1
- import { SelectionProps } from "../components";
1
+ import { SelectionProps } from "../components/ReferenceTable/SelectionTableBinding";
2
2
  /**
3
3
  * This hook is used to open a side dialog that allows the selection
4
4
  * of entities under a given path.
@@ -0,0 +1,328 @@
1
+ import { t as __exportAll } from "./rolldown-runtime-D7D4PA-g.js";
2
+ import { Bn as getPropertiesWithPropertiesOrder, Dt as ImportSaveInProgress, Et as useImportConfig, Mt as PropertyConfigBadge, Nn as useCollectionRegistryController, O as getFieldConfig, Ot as ImportFileUpload, Qt as CollectionTableBinding, St as convertDataToEntity, Tt as getInferenceType, Vn as getPropertyInPath, Xt as useSelectionController, xt as DataNewPropertiesMapping } from "./util-XFwQ9FEc.js";
3
+ import React, { useCallback, useEffect } from "react";
4
+ import { Button, Dialog, DialogActions, DialogContent, DialogTitle, IconButton, Select, SelectItem, Tooltip, Typography, UploadIcon, cls, defaultBorderMixin, iconSize } from "@rebasepro/ui";
5
+ import { useAuthController, useCustomizationController, useSnackbarController } from "@rebasepro/app";
6
+ import { Fragment, jsx, jsxs } from "react/jsx-runtime";
7
+ import { slugify } from "@rebasepro/utils";
8
+ import { buildEntityPropertiesFromData } from "@rebasepro/inference";
9
+ //#region src/data_import/import/ImportCollectionAction.tsx
10
+ function ImportCollectionAction({ collection, path, onAnalyticsEvent }) {
11
+ const snackbarController = useSnackbarController();
12
+ const [open, setOpen] = React.useState(false);
13
+ const [step, setStep] = React.useState("initial");
14
+ const importConfig = useImportConfig();
15
+ const handleClickOpen = useCallback(() => {
16
+ setOpen(true);
17
+ onAnalyticsEvent?.("import_open");
18
+ setStep("initial");
19
+ }, [onAnalyticsEvent]);
20
+ const handleClose = useCallback(() => {
21
+ setOpen(false);
22
+ }, [setOpen]);
23
+ const onMappingComplete = useCallback(() => {
24
+ onAnalyticsEvent?.("import_mapping_complete");
25
+ setStep("preview");
26
+ }, [onAnalyticsEvent]);
27
+ const onPreviewComplete = useCallback(() => {
28
+ onAnalyticsEvent?.("import_data_save");
29
+ setStep("import_data_saving");
30
+ }, [onAnalyticsEvent]);
31
+ const onDataAdded = async (data) => {
32
+ importConfig.setImportData(data);
33
+ if (data.length > 0) {
34
+ const originProperties = await buildEntityPropertiesFromData(data, getInferenceType);
35
+ importConfig.setOriginProperties(originProperties);
36
+ const headersMapping = buildHeadersMappingFromData(data, collection?.properties);
37
+ importConfig.setHeadersMapping(headersMapping);
38
+ const firstKey = Object.keys(headersMapping)?.[0];
39
+ if (firstKey?.includes("id") || firstKey?.includes("key")) importConfig.setIdColumn(firstKey);
40
+ }
41
+ setTimeout(() => {
42
+ onAnalyticsEvent?.("import_data_added");
43
+ setStep("mapping");
44
+ }, 100);
45
+ };
46
+ const properties = getPropertiesWithPropertiesOrder(collection.properties, collection.propertiesOrder);
47
+ const propertiesAndLevel = Object.entries(properties).flatMap(([key, property]) => getPropertiesAndLevel(key, property, 0));
48
+ const propertiesOrder = collection.propertiesOrder ?? Object.keys(collection.properties);
49
+ return /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx(Tooltip, {
50
+ title: "Import",
51
+ asChild: true,
52
+ children: /* @__PURE__ */ jsx(IconButton, {
53
+ size: "small",
54
+ color: "primary",
55
+ onClick: handleClickOpen,
56
+ children: /* @__PURE__ */ jsx(UploadIcon, { size: iconSize.small })
57
+ })
58
+ }), /* @__PURE__ */ jsxs(Dialog, {
59
+ open,
60
+ fullWidth: step !== "initial",
61
+ fullHeight: step !== "initial",
62
+ maxWidth: step === "initial" ? "lg" : "7xl",
63
+ children: [
64
+ /* @__PURE__ */ jsx(DialogTitle, {
65
+ variant: "h6",
66
+ hidden: step === "preview",
67
+ children: "Import data"
68
+ }),
69
+ /* @__PURE__ */ jsxs(DialogContent, {
70
+ className: "h-full flex flex-col gap-4 my-4",
71
+ fullHeight: step === "preview",
72
+ children: [
73
+ step === "initial" && /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx(Typography, {
74
+ variant: "body2",
75
+ children: "Upload a CSV, Excel or JSON file and map it to your existing schema"
76
+ }), /* @__PURE__ */ jsx(ImportFileUpload, { onDataAdded })] }),
77
+ step === "mapping" && /* @__PURE__ */ jsx(Fragment, { children: /* @__PURE__ */ jsx(DataNewPropertiesMapping, {
78
+ importConfig,
79
+ destinationProperties: properties,
80
+ buildPropertyView: ({ isIdColumn, property, propertyKey, importKey }) => {
81
+ return /* @__PURE__ */ jsx(PropertyTreeSelect, {
82
+ selectedPropertyKey: propertyKey ?? "",
83
+ properties,
84
+ propertiesAndLevel,
85
+ isIdColumn,
86
+ onIdSelected: () => {
87
+ importConfig.setIdColumn(importKey);
88
+ },
89
+ onPropertySelected: (newPropertyKey) => {
90
+ onAnalyticsEvent?.("import_mapping_field_updated");
91
+ const newHeadersMapping = Object.entries(importConfig.headersMapping).map(([currentImportKey, currentPropertyKey]) => {
92
+ if (currentPropertyKey === newPropertyKey) return { [currentImportKey]: null };
93
+ if (currentImportKey === importKey) return { [currentImportKey]: newPropertyKey };
94
+ return { [currentImportKey]: currentPropertyKey };
95
+ }).reduce((acc, curr) => ({
96
+ ...acc,
97
+ ...curr
98
+ }), {});
99
+ importConfig.setHeadersMapping(newHeadersMapping);
100
+ if (newPropertyKey === importConfig.idColumn) importConfig.setIdColumn(void 0);
101
+ }
102
+ });
103
+ }
104
+ }) }),
105
+ step === "preview" && /* @__PURE__ */ jsx(ImportDataPreview, {
106
+ importConfig,
107
+ properties,
108
+ propertiesOrder
109
+ }),
110
+ step === "import_data_saving" && importConfig && /* @__PURE__ */ jsx(ImportSaveInProgress, {
111
+ importConfig,
112
+ collection,
113
+ path,
114
+ onImportSuccess: (importedCollection) => {
115
+ handleClose();
116
+ snackbarController.open({
117
+ type: "info",
118
+ message: "Data imported successfully"
119
+ });
120
+ }
121
+ })
122
+ ]
123
+ }),
124
+ /* @__PURE__ */ jsxs(DialogActions, { children: [
125
+ step === "mapping" && /* @__PURE__ */ jsx(Button, {
126
+ onClick: () => setStep("initial"),
127
+ variant: "text",
128
+ children: "Back"
129
+ }),
130
+ step === "preview" && /* @__PURE__ */ jsx(Button, {
131
+ onClick: () => setStep("mapping"),
132
+ variant: "text",
133
+ children: "Back"
134
+ }),
135
+ /* @__PURE__ */ jsx(Button, {
136
+ onClick: handleClose,
137
+ variant: "text",
138
+ children: "Cancel"
139
+ }),
140
+ step === "mapping" && /* @__PURE__ */ jsx(Button, {
141
+ variant: "filled",
142
+ color: "primary",
143
+ onClick: onMappingComplete,
144
+ children: "Next"
145
+ }),
146
+ step === "preview" && /* @__PURE__ */ jsx(Button, {
147
+ variant: "filled",
148
+ color: "primary",
149
+ onClick: onPreviewComplete,
150
+ children: "Save data"
151
+ })
152
+ ] })
153
+ ]
154
+ })] });
155
+ }
156
+ var internalIDValue = "__internal_id__";
157
+ function PropertyTreeSelect({ selectedPropertyKey, properties, onPropertySelected, onIdSelected, propertiesAndLevel, isIdColumn }) {
158
+ const selectedProperty = selectedPropertyKey ? getPropertyInPath(properties, selectedPropertyKey) : null;
159
+ const renderValue = useCallback((selectedPropertyKey) => {
160
+ if (selectedPropertyKey === internalIDValue) return /* @__PURE__ */ jsx(Typography, {
161
+ variant: "body2",
162
+ className: "p-4",
163
+ children: "Use this column as ID"
164
+ });
165
+ if (!selectedPropertyKey || !selectedProperty) return /* @__PURE__ */ jsx(Typography, {
166
+ variant: "body2",
167
+ color: "disabled",
168
+ className: "p-4",
169
+ children: "Do not import this property"
170
+ });
171
+ return /* @__PURE__ */ jsx(PropertySelectEntry, {
172
+ propertyKey: selectedPropertyKey,
173
+ property: selectedProperty
174
+ });
175
+ }, [selectedProperty]);
176
+ const onSelectValueChange = (value) => {
177
+ if (value === internalIDValue) {
178
+ onIdSelected();
179
+ onPropertySelected(null);
180
+ } else if (value === "__do_not_import") onPropertySelected(null);
181
+ else onPropertySelected(value);
182
+ };
183
+ return /* @__PURE__ */ jsxs(Select, {
184
+ value: isIdColumn ? internalIDValue : selectedPropertyKey ?? void 0,
185
+ fullWidth: true,
186
+ onValueChange: onSelectValueChange,
187
+ renderValue,
188
+ children: [
189
+ /* @__PURE__ */ jsx(SelectItem, {
190
+ value: "__do_not_import",
191
+ children: /* @__PURE__ */ jsx(Typography, {
192
+ variant: "body2",
193
+ color: "disabled",
194
+ className: "p-4",
195
+ children: "Do not import this property"
196
+ })
197
+ }),
198
+ /* @__PURE__ */ jsx(SelectItem, {
199
+ value: internalIDValue,
200
+ children: /* @__PURE__ */ jsx(Typography, {
201
+ variant: "body2",
202
+ className: "p-4",
203
+ children: "Use this column as ID"
204
+ })
205
+ }),
206
+ propertiesAndLevel.map(({ property, level, propertyKey }) => {
207
+ return /* @__PURE__ */ jsx(SelectItem, {
208
+ value: propertyKey,
209
+ disabled: property.type === "map",
210
+ children: /* @__PURE__ */ jsx(PropertySelectEntry, {
211
+ propertyKey,
212
+ property,
213
+ level
214
+ })
215
+ }, propertyKey);
216
+ })
217
+ ]
218
+ });
219
+ }
220
+ function getPropertiesAndLevel(key, property, level) {
221
+ const properties = [];
222
+ properties.push({
223
+ property,
224
+ level,
225
+ propertyKey: key
226
+ });
227
+ if (property.type === "map" && property.properties) Object.entries(property.properties).forEach(([childKey, value]) => {
228
+ properties.push(...getPropertiesAndLevel(`${key}.${childKey}`, value, level + 1));
229
+ });
230
+ return properties;
231
+ }
232
+ function PropertySelectEntry({ propertyKey, property, level = 0 }) {
233
+ const { propertyConfigs } = useCustomizationController();
234
+ const widget = getFieldConfig(property, propertyConfigs);
235
+ return /* @__PURE__ */ jsxs("div", {
236
+ className: "flex flex-row w-full text-start items-center h-full",
237
+ children: [
238
+ new Array(level).fill(0).map((_, index) => /* @__PURE__ */ jsx("div", { className: cls(defaultBorderMixin, "ml-8 border-l h-12") }, index)),
239
+ /* @__PURE__ */ jsx("div", {
240
+ className: "m-4",
241
+ children: /* @__PURE__ */ jsx(Tooltip, {
242
+ title: widget?.name,
243
+ children: /* @__PURE__ */ jsx(PropertyConfigBadge, { propertyConfig: widget })
244
+ })
245
+ }),
246
+ /* @__PURE__ */ jsxs("div", {
247
+ className: "flex flex-col grow p-2 pl-2",
248
+ children: [/* @__PURE__ */ jsx(Typography, {
249
+ variant: "body1",
250
+ component: "span",
251
+ className: "grow pr-2",
252
+ children: property.name ? property.name : "\xA0"
253
+ }), /* @__PURE__ */ jsx(Typography, {
254
+ className: " pr-2",
255
+ variant: "body2",
256
+ component: "span",
257
+ color: "secondary",
258
+ children: propertyKey
259
+ })]
260
+ })
261
+ ]
262
+ });
263
+ }
264
+ function ImportDataPreview({ importConfig, properties, propertiesOrder }) {
265
+ const authController = useAuthController();
266
+ const collectionRegistry = useCollectionRegistryController();
267
+ useEffect(() => {
268
+ const mappedData = importConfig.importData.map((d) => convertDataToEntity(authController, collectionRegistry, d, importConfig.idColumn, importConfig.headersMapping, properties, "TEMP_PATH", importConfig.defaultValues));
269
+ importConfig.setEntities(mappedData);
270
+ }, []);
271
+ const selectionController = useSelectionController();
272
+ return /* @__PURE__ */ jsx(CollectionTableBinding, {
273
+ title: /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx(Typography, {
274
+ variant: "subtitle2",
275
+ children: "Imported data preview"
276
+ }), /* @__PURE__ */ jsx(Typography, {
277
+ variant: "caption",
278
+ children: "Entities with the same id will be overwritten"
279
+ })] }),
280
+ tableController: {
281
+ data: importConfig.entities,
282
+ dataLoading: false,
283
+ noMoreToLoad: false
284
+ },
285
+ enablePopupIcon: false,
286
+ endAdornment: /* @__PURE__ */ jsx("div", { className: "h-12" }),
287
+ filterable: false,
288
+ sortable: false,
289
+ openEntityMode: "full_screen",
290
+ selectionController,
291
+ properties
292
+ });
293
+ }
294
+ function buildHeadersMappingFromData(objArr, properties) {
295
+ const headersMapping = {};
296
+ objArr.filter(Boolean).forEach((obj) => {
297
+ Object.keys(obj).forEach((key) => {
298
+ const child = obj[key];
299
+ if (child != null && typeof child === "object" && !Array.isArray(child)) {
300
+ const childProperty = properties?.[key];
301
+ const childProperties = childProperty && "properties" in childProperty ? childProperty.properties : void 0;
302
+ const childHeadersMapping = buildHeadersMappingFromData([child], childProperties);
303
+ Object.entries(childHeadersMapping).forEach(([subKey, mapping]) => {
304
+ headersMapping[`${key}.${subKey}`] = `${key}.${mapping}`;
305
+ });
306
+ }
307
+ if (!properties) headersMapping[key] = key;
308
+ else if (key in properties) headersMapping[key] = key;
309
+ else {
310
+ const slug = slugify(key);
311
+ if (slug in properties) headersMapping[key] = slug;
312
+ else headersMapping[key] = key;
313
+ }
314
+ });
315
+ });
316
+ return headersMapping;
317
+ }
318
+ //#endregion
319
+ //#region src/data_import/import/index.ts
320
+ var import_exports = /* @__PURE__ */ __exportAll({
321
+ ImportCollectionAction: () => ImportCollectionAction,
322
+ ImportDataPreview: () => ImportDataPreview,
323
+ PropertySelectEntry: () => PropertySelectEntry
324
+ });
325
+ //#endregion
326
+ export { PropertySelectEntry as i, ImportCollectionAction as n, ImportDataPreview as r, import_exports as t };
327
+
328
+ //# sourceMappingURL=import-DzQnT03v.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"import-DzQnT03v.js","names":[],"sources":["../src/data_import/import/ImportCollectionAction.tsx","../src/data_import/import/index.ts"],"sourcesContent":["import React, { useCallback, useEffect } from \"react\";\nimport {\n useAuthController,\n useCustomizationController,\n useSnackbarController\n} from \"@rebasepro/app\";\nimport { getPropertiesWithPropertiesOrder, getPropertyInPath } from \"../../util\";\nimport { CollectionActionsProps, Properties, Property, User, CollectionConfig } from \"@rebasepro/types\";\nimport { getFieldConfig } from \"../../components/field_configs\";\nimport { PropertyConfigBadge } from \"../../components/PropertyConfigBadge\";\nimport { useSelectionController } from \"../../components/CollectionViewBinding/useSelectionController\";\nimport { CollectionTableBinding } from \"../../components/CollectionTableBinding/CollectionTableBinding\";\nimport { useCollectionRegistryController } from \"../../hooks\";\nimport {\n Button,\n cls,\n defaultBorderMixin,\n Dialog,\n DialogActions,\n DialogContent,\n DialogTitle,\n IconButton,\n iconSize,\n Select,\n SelectItem,\n Tooltip,\n Typography,\n UploadIcon\n} from \"@rebasepro/ui\";\nimport { buildEntityPropertiesFromData } from \"@rebasepro/inference\";\nimport { useImportConfig } from \"../hooks\";\nimport { convertDataToEntity, getInferenceType } from \"../utils\";\nimport { DataNewPropertiesMapping } from \"../components/DataNewPropertiesMapping\";\nimport { ImportFileUpload } from \"../components/ImportFileUpload\";\nimport { ImportSaveInProgress } from \"../components/ImportSaveInProgress\";\nimport { ImportConfig } from \"../types\";\nimport { slugify } from \"@rebasepro/utils\";\n\ntype ImportState = \"initial\" | \"mapping\" | \"preview\" | \"import_data_saving\";\n\nexport function ImportCollectionAction<M extends Record<string, unknown>, USER extends User>({\n collection,\n path,\n onAnalyticsEvent\n}: CollectionActionsProps<M, USER> & {\n onAnalyticsEvent?: (event: string, params?: any) => void;\n}\n) {\n\n const snackbarController = useSnackbarController();\n\n const [open, setOpen] = React.useState(false);\n\n const [step, setStep] = React.useState<ImportState>(\"initial\");\n\n const importConfig = useImportConfig();\n\n const handleClickOpen = useCallback(() => {\n setOpen(true);\n onAnalyticsEvent?.(\"import_open\");\n setStep(\"initial\");\n }, [onAnalyticsEvent]);\n\n const handleClose = useCallback(() => {\n setOpen(false);\n }, [setOpen]);\n\n const onMappingComplete = useCallback(() => {\n onAnalyticsEvent?.(\"import_mapping_complete\");\n setStep(\"preview\");\n }, [onAnalyticsEvent]);\n\n const onPreviewComplete = useCallback(() => {\n onAnalyticsEvent?.(\"import_data_save\");\n setStep(\"import_data_saving\");\n }, [onAnalyticsEvent]);\n\n const onDataAdded = async (data: object[]) => {\n importConfig.setImportData(data);\n\n if (data.length > 0) {\n const originProperties = await buildEntityPropertiesFromData(data, getInferenceType);\n importConfig.setOriginProperties(originProperties as Properties);\n\n const headersMapping = buildHeadersMappingFromData(data, collection?.properties);\n importConfig.setHeadersMapping(headersMapping);\n const firstKey = Object.keys(headersMapping)?.[0];\n if (firstKey?.includes(\"id\") || firstKey?.includes(\"key\")) {\n importConfig.setIdColumn(firstKey);\n }\n }\n setTimeout(() => {\n onAnalyticsEvent?.(\"import_data_added\");\n setStep(\"mapping\");\n }, 100);\n };\n\n const properties = getPropertiesWithPropertiesOrder(collection.properties, collection.propertiesOrder as Extract<keyof M, string>[]);\n\n const propertiesAndLevel = Object.entries(properties)\n .flatMap(([key, property]) => getPropertiesAndLevel(key, property, 0));\n const propertiesOrder = (collection.propertiesOrder ?? Object.keys(collection.properties)) as Extract<keyof M, string>[];\n\n return <>\n\n <Tooltip title={\"Import\"}\n asChild={true}>\n <IconButton\n size={\"small\"}\n color={\"primary\"} onClick={handleClickOpen}>\n <UploadIcon size={iconSize.small}/>\n </IconButton>\n </Tooltip>\n\n <Dialog open={open}\n fullWidth={step !== \"initial\"}\n fullHeight={step !== \"initial\"}\n maxWidth={step === \"initial\" ? \"lg\" : \"7xl\"}>\n\n <DialogTitle variant={\"h6\"} hidden={step === \"preview\"}>Import data</DialogTitle>\n\n <DialogContent className={\"h-full flex flex-col gap-4 my-4\"} fullHeight={step === \"preview\"}>\n\n {step === \"initial\" && <>\n <Typography variant={\"body2\"}>Upload a CSV, Excel or JSON file and map it to your existing\n schema</Typography>\n <ImportFileUpload onDataAdded={onDataAdded}/>\n </>}\n\n {step === \"mapping\" && <>\n <DataNewPropertiesMapping importConfig={importConfig}\n destinationProperties={properties}\n buildPropertyView={({\n isIdColumn,\n property,\n propertyKey,\n importKey\n }) => {\n return <PropertyTreeSelect\n selectedPropertyKey={propertyKey ?? \"\"}\n properties={properties}\n propertiesAndLevel={propertiesAndLevel}\n isIdColumn={isIdColumn}\n onIdSelected={() => {\n importConfig.setIdColumn(importKey);\n }}\n onPropertySelected={(newPropertyKey) => {\n\n onAnalyticsEvent?.(\"import_mapping_field_updated\");\n const newHeadersMapping: Record<string, string | null> = Object.entries(importConfig.headersMapping)\n .map(([currentImportKey, currentPropertyKey]) => {\n if (currentPropertyKey === newPropertyKey) {\n return { [currentImportKey]: null };\n }\n if (currentImportKey === importKey) {\n return { [currentImportKey]: newPropertyKey };\n }\n return { [currentImportKey]: currentPropertyKey };\n })\n .reduce((acc, curr) => ({ ...acc,\n...curr }), {});\n importConfig.setHeadersMapping(newHeadersMapping as Record<string, string>);\n\n if (newPropertyKey === importConfig.idColumn) {\n importConfig.setIdColumn(undefined);\n }\n\n }}\n />;\n }}/>\n </>}\n\n {step === \"preview\" && <ImportDataPreview importConfig={importConfig}\n properties={properties}\n propertiesOrder={propertiesOrder}/>}\n\n {step === \"import_data_saving\" && importConfig &&\n <ImportSaveInProgress importConfig={importConfig}\n collection={collection as CollectionConfig}\n path={path}\n onImportSuccess={(importedCollection) => {\n handleClose();\n snackbarController.open({\n type: \"info\",\n message: \"Data imported successfully\"\n });\n }}\n />}\n\n </DialogContent>\n <DialogActions>\n\n {step === \"mapping\" && <Button\n onClick={() => setStep(\"initial\")}\n variant={\"text\"}>\n Back\n </Button>}\n\n {step === \"preview\" && <Button\n onClick={() => setStep(\"mapping\")}\n variant={\"text\"}>\n Back\n </Button>}\n\n <Button onClick={handleClose}\n variant={\"text\"}>\n Cancel\n </Button>\n\n {step === \"mapping\" && <Button variant=\"filled\"\n color={\"primary\"}\n onClick={onMappingComplete}>\n Next\n </Button>}\n\n {step === \"preview\" && <Button variant=\"filled\"\n color={\"primary\"}\n onClick={onPreviewComplete}>\n Save data\n </Button>}\n\n </DialogActions>\n </Dialog>\n\n </>;\n}\n\nconst internalIDValue = \"__internal_id__\";\n\nfunction PropertyTreeSelect({\n selectedPropertyKey,\n properties,\n onPropertySelected,\n onIdSelected,\n propertiesAndLevel,\n isIdColumn\n}: {\n selectedPropertyKey: string | null;\n properties: Record<string, Property>;\n onPropertySelected: (propertyKey: string | null) => void;\n onIdSelected: () => void;\n propertiesAndLevel: PropertyAndLevel[];\n isIdColumn?: boolean;\n}) {\n\n const selectedProperty = selectedPropertyKey ? getPropertyInPath(properties, selectedPropertyKey) : null;\n\n const renderValue = useCallback((selectedPropertyKey: string) => {\n\n if (selectedPropertyKey === internalIDValue) {\n return <Typography variant={\"body2\"} className={\"p-4\"}>Use this column as ID</Typography>;\n }\n\n if (!selectedPropertyKey || !selectedProperty) {\n return <Typography variant={\"body2\"} color=\"disabled\" className={\"p-4\"}>Do not import this\n property</Typography>;\n }\n\n return <PropertySelectEntry propertyKey={selectedPropertyKey}\n property={selectedProperty as Property}/>;\n }, [selectedProperty]);\n\n const onSelectValueChange = (value: string) => {\n if (value === internalIDValue) {\n onIdSelected();\n onPropertySelected(null);\n } else if (value === \"__do_not_import\") {\n onPropertySelected(null);\n } else {\n onPropertySelected(value);\n }\n };\n\n return <Select value={isIdColumn ? internalIDValue : (selectedPropertyKey ?? undefined)}\n fullWidth={true}\n onValueChange={onSelectValueChange}\n renderValue={renderValue}>\n\n <SelectItem value={\"__do_not_import\"}>\n <Typography variant={\"body2\"} color={\"disabled\"} className={\"p-4\"}>Do not import this property</Typography>\n </SelectItem>\n\n <SelectItem value={internalIDValue}>\n <Typography variant={\"body2\"} className={\"p-4\"}>Use this column as ID</Typography>\n </SelectItem>\n\n {propertiesAndLevel.map(({\n property,\n level,\n propertyKey\n }) => {\n return <SelectItem value={propertyKey}\n key={propertyKey}\n disabled={property.type === \"map\"}>\n <PropertySelectEntry propertyKey={propertyKey}\n property={property}\n level={level}/>\n </SelectItem>;\n })}\n\n </Select>;\n}\n\ntype PropertyAndLevel = {\n property: Property,\n level: number,\n propertyKey: string\n};\n\nfunction getPropertiesAndLevel(key: string, property: Property, level: number): PropertyAndLevel[] {\n const properties: PropertyAndLevel[] = [];\n properties.push({\n property,\n level,\n propertyKey: key\n });\n if (property.type === \"map\" && property.properties) {\n Object.entries(property.properties).forEach(([childKey, value]) => {\n properties.push(...getPropertiesAndLevel(`${key}.${childKey}`, value as Property, level + 1));\n });\n }\n return properties;\n}\n\nexport function PropertySelectEntry({\n propertyKey,\n property,\n level = 0\n}: {\n propertyKey: string;\n property: Property;\n level?: number;\n}) {\n\n const { propertyConfigs } = useCustomizationController();\n const widget = getFieldConfig(property, propertyConfigs);\n\n return <div\n className=\"flex flex-row w-full text-start items-center h-full\">\n\n {new Array(level).fill(0).map((_, index) =>\n <div className={cls(defaultBorderMixin, \"ml-8 border-l h-12\")} key={index}/>)}\n\n <div className={\"m-4\"}>\n <Tooltip title={widget?.name}>\n <PropertyConfigBadge propertyConfig={widget}/>\n </Tooltip>\n </div>\n\n <div className={\"flex flex-col grow p-2 pl-2\"}>\n <Typography variant=\"body1\"\n component=\"span\"\n className=\"grow pr-2\">\n {property.name\n ? property.name\n : \"\\u00a0\"\n }\n </Typography>\n\n <Typography className=\" pr-2\"\n variant={\"body2\"}\n component=\"span\"\n color=\"secondary\">\n {propertyKey}\n </Typography>\n </div>\n\n </div>;\n\n}\n\nexport function ImportDataPreview<M extends Record<string, unknown>>({\n importConfig,\n properties,\n propertiesOrder\n}: {\n importConfig: ImportConfig,\n properties: Properties,\n propertiesOrder: Extract<keyof M, string>[],\n}) {\n const authController = useAuthController();\n const collectionRegistry = useCollectionRegistryController();\n useEffect(() => {\n const mappedData = importConfig.importData.map(d => convertDataToEntity(\n authController,\n collectionRegistry,\n d,\n importConfig.idColumn,\n importConfig.headersMapping,\n properties,\n \"TEMP_PATH\",\n importConfig.defaultValues\n ));\n importConfig.setEntities(mappedData);\n }, []);\n\n const selectionController = useSelectionController();\n\n return <CollectionTableBinding\n title={<div>\n <Typography variant={\"subtitle2\"}>Imported data preview</Typography>\n <Typography variant={\"caption\"}>Entities with the same id will be overwritten</Typography>\n </div>}\n tableController={{\n data: importConfig.entities,\n dataLoading: false,\n noMoreToLoad: false\n }}\n enablePopupIcon={false}\n endAdornment={<div className={\"h-12\"}/>}\n filterable={false}\n sortable={false}\n openEntityMode={\"full_screen\"}\n selectionController={selectionController}\n properties={properties}/>\n\n}\n\nfunction buildHeadersMappingFromData(objArr: object[], properties?: Properties) {\n const headersMapping: Record<string, string> = {};\n objArr.filter(Boolean).forEach((obj) => {\n Object.keys(obj).forEach((key) => {\n const child = (obj as Record<string, unknown>)[key];\n if (child != null && typeof child === \"object\" && !Array.isArray(child)) {\n const childProperty = properties?.[key];\n const childProperties = childProperty && \"properties\" in childProperty ? childProperty.properties : undefined;\n const childHeadersMapping = buildHeadersMappingFromData([child as object], childProperties);\n Object.entries(childHeadersMapping).forEach(([subKey, mapping]) => {\n headersMapping[`${key}.${subKey}`] = `${key}.${mapping}`;\n });\n }\n\n if (!properties) {\n headersMapping[key] = key;\n } else if (key in properties) {\n headersMapping[key] = key;\n } else {\n const slug = slugify(key);\n if (slug in properties) {\n headersMapping[key] = slug;\n } else {\n headersMapping[key] = key;\n }\n }\n\n });\n });\n return headersMapping;\n}\n","export * from \"./ImportCollectionAction\";\n"],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -3,7 +3,7 @@ export type { RichTextEditorProps, RichTextEditorTextSize, JSONContent, EditorAI
3
3
  export * from "./form";
4
4
  export * from "./preview";
5
5
  export * from "./routes";
6
- export { EntityViewBinding, SelectionTableBinding, SelectableTable, SelectableTableContext, CollectionViewBinding, CollectionViewActions, CollectionCardViewBinding, EntityCardBinding, useSelectionController, PropertyConfigBadge, PropertyIdCopyTooltip, CollectionTableBinding, CollectionRowActions, VirtualTableInput, ArrayContainer, type ArrayEntryParams, ReferenceWidget, SearchIconsView, FieldCaption, EntityPreviewBinding, getFieldConfig, getFieldId, getDefaultFieldConfig, getDefaultFieldId, DEFAULT_FIELD_CONFIGS, editEntityAction, copyEntityAction, deleteEntityAction, resetPasswordAction, SidePanelProvider, Scaffold, AppBar, Drawer, DefaultDrawer, DrawerFooterActions, AdminModeSyncer, RebaseCMS, RebaseShell, RebaseAuthGate, RebaseNavigation, RebaseLayout, RebaseRouteDefs, SideDialogs, useApp, CollectionPanel } from "./components";
6
+ export { EntityViewBinding, SelectionTableBinding, SelectableTable, SelectableTableContext, CollectionViewBinding, CollectionViewActions, CollectionCardViewBinding, EntityCardBinding, useSelectionController, PropertyConfigBadge, PropertyIdCopyTooltip, CollectionTableBinding, CollectionRowActions, VirtualTableInput, ArrayContainer, type ArrayEntryParams, ReferenceWidget, SearchIconsView, FieldCaption, EntityPreviewBinding, getFieldConfig, getFieldId, getDefaultFieldConfig, getDefaultFieldId, DEFAULT_FIELD_CONFIGS, editEntityAction, copyEntityAction, deleteEntityAction, resetPasswordAction, SidePanelProvider, Scaffold, AppBar, Drawer, DefaultDrawer, DrawerFooterActions, AdminModeSyncer, RebaseAdmin, RebaseShell, RebaseAuthGate, RebaseNavigation, RebaseLayout, RebaseRouteDefs, SideDialogs, useApp, CollectionPanel } from "./components";
7
7
  export type { EntityViewBindingProps, SelectionProps, SelectableTableProps, CollectionPanelProps } from "./components";
8
8
  export * from "./hooks";
9
9
  export { addInitialSlash, removeInitialSlash, removeTrailingSlash, removeInitialAndTrailingSlashes, getLastSegment, getCollectionBySlugWithin, getCollectionPathsCombinations, resolveCollectionPathIds, mergeEntityActions, resolveEntityAction, resolveEntityView, isReferenceProperty, isRelationProperty, getIconForWidget, getIconForProperty, getPropertyInPath, getResolvedPropertyInPath, getBracketNotation, getPropertiesWithPropertiesOrder, getDefaultPropertiesOrder, getEntityPreviewKeys, getEntityTitlePropertyKey } from "./util";