@firecms/core 3.0.0-canary.17 → 3.0.0-canary.170

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 (364) hide show
  1. package/README.md +3 -3
  2. package/dist/app/AppBar.d.ts +12 -0
  3. package/dist/app/Drawer.d.ts +16 -0
  4. package/dist/app/Scaffold.d.ts +30 -0
  5. package/dist/app/index.d.ts +4 -0
  6. package/dist/app/useApp.d.ts +16 -0
  7. package/dist/components/ArrayContainer.d.ts +23 -6
  8. package/dist/components/CircularProgressCenter.d.ts +1 -1
  9. package/dist/components/ClearFilterSortButton.d.ts +5 -0
  10. package/dist/components/{DeleteConfirmationDialog.d.ts → ConfirmationDialog.d.ts} +1 -1
  11. package/dist/components/EntityCollectionTable/EntityCollectionRowActions.d.ts +13 -13
  12. package/dist/components/EntityCollectionTable/EntityCollectionTable.d.ts +2 -2
  13. package/dist/components/EntityCollectionTable/EntityCollectionTableProps.d.ts +22 -6
  14. package/dist/components/EntityCollectionTable/PropertyTableCell.d.ts +1 -0
  15. package/dist/components/EntityCollectionTable/column_utils.d.ts +1 -2
  16. package/dist/components/EntityCollectionTable/fields/TableReferenceField.d.ts +3 -1
  17. package/dist/components/EntityCollectionTable/index.d.ts +1 -1
  18. package/dist/components/EntityCollectionTable/internal/CollectionTableToolbar.d.ts +1 -4
  19. package/dist/components/EntityCollectionTable/internal/EntityTableCell.d.ts +2 -2
  20. package/dist/components/EntityCollectionTable/internal/popup_field/PopupFormField.d.ts +7 -4
  21. package/dist/components/EntityCollectionView/EntityCollectionView.d.ts +16 -2
  22. package/dist/components/EntityCollectionView/EntityCollectionViewStartActions.d.ts +11 -0
  23. package/dist/components/EntityCollectionView/utils.d.ts +3 -0
  24. package/dist/components/EntityPreview.d.ts +7 -6
  25. package/dist/components/ErrorView.d.ts +1 -1
  26. package/dist/components/HomePage/DefaultHomePage.d.ts +1 -1
  27. package/dist/components/HomePage/NavigationCardBinding.d.ts +1 -1
  28. package/dist/components/PropertyConfigBadge.d.ts +2 -1
  29. package/dist/components/PropertyIdCopyTooltip.d.ts +8 -0
  30. package/dist/components/ReferenceWidget.d.ts +3 -1
  31. package/dist/components/SelectableTable/SelectableTable.d.ts +13 -3
  32. package/dist/components/SelectableTable/filters/ReferenceFilterField.d.ts +2 -1
  33. package/dist/components/UnsavedChangesDialog.d.ts +8 -0
  34. package/dist/components/VirtualTable/VirtualTableProps.d.ts +28 -12
  35. package/dist/components/VirtualTable/types.d.ts +3 -3
  36. package/dist/components/{EntityCollectionTable/internal → common}/default_entity_actions.d.ts +1 -3
  37. package/dist/components/common/index.d.ts +2 -1
  38. package/dist/components/common/table_height.d.ts +5 -0
  39. package/dist/components/common/types.d.ts +4 -6
  40. package/dist/components/common/useColumnsIds.d.ts +3 -1
  41. package/dist/components/common/{useDataSourceEntityCollectionTableController.d.ts → useDataSourceTableController.d.ts} +13 -2
  42. package/dist/components/common/useDebouncedCallback.d.ts +1 -0
  43. package/dist/components/common/useScrollRestoration.d.ts +14 -0
  44. package/dist/components/index.d.ts +4 -2
  45. package/dist/contexts/BreacrumbsContext.d.ts +8 -0
  46. package/dist/{components/FireCMSAppBar.d.ts → core/DefaultAppBar.d.ts} +6 -9
  47. package/dist/core/DefaultDrawer.d.ts +19 -0
  48. package/dist/core/DrawerNavigationItem.d.ts +10 -0
  49. package/dist/core/EntityEditView.d.ts +41 -9
  50. package/dist/core/FireCMS.d.ts +2 -2
  51. package/dist/core/FireCMSRouter.d.ts +4 -0
  52. package/dist/core/NavigationRoutes.d.ts +2 -3
  53. package/dist/core/index.d.ts +4 -4
  54. package/dist/form/PropertyFieldBinding.d.ts +1 -1
  55. package/dist/form/components/ErrorFocus.d.ts +1 -1
  56. package/dist/form/components/FieldHelperText.d.ts +3 -3
  57. package/dist/form/components/LabelWithIcon.d.ts +1 -1
  58. package/dist/form/components/LabelWithIconAndTooltip.d.ts +15 -0
  59. package/dist/form/components/StorageItemPreview.d.ts +4 -4
  60. package/dist/form/components/index.d.ts +1 -1
  61. package/dist/form/field_bindings/ArrayCustomShapedFieldBinding.d.ts +1 -1
  62. package/dist/form/field_bindings/ArrayOfReferencesFieldBinding.d.ts +1 -1
  63. package/dist/form/field_bindings/BlockFieldBinding.d.ts +1 -1
  64. package/dist/form/field_bindings/KeyValueFieldBinding.d.ts +1 -1
  65. package/dist/form/field_bindings/MapFieldBinding.d.ts +1 -1
  66. package/dist/form/field_bindings/MarkdownEditorFieldBinding.d.ts +11 -0
  67. package/dist/form/field_bindings/{MultiSelectBinding.d.ts → MultiSelectFieldBinding.d.ts} +1 -1
  68. package/dist/form/field_bindings/ReadOnlyFieldBinding.d.ts +1 -1
  69. package/dist/form/field_bindings/ReferenceFieldBinding.d.ts +2 -2
  70. package/dist/form/field_bindings/RepeatFieldBinding.d.ts +1 -1
  71. package/dist/form/field_bindings/SelectFieldBinding.d.ts +1 -1
  72. package/dist/form/field_bindings/StorageUploadFieldBinding.d.ts +3 -5
  73. package/dist/form/field_bindings/SwitchFieldBinding.d.ts +1 -2
  74. package/dist/form/field_bindings/TextFieldBinding.d.ts +1 -1
  75. package/dist/form/index.d.ts +3 -5
  76. package/dist/form/useClearRestoreValue.d.ts +2 -2
  77. package/dist/hooks/data/delete.d.ts +4 -4
  78. package/dist/hooks/data/save.d.ts +4 -5
  79. package/dist/hooks/data/useCollectionFetch.d.ts +1 -1
  80. package/dist/hooks/data/useEntityFetch.d.ts +4 -3
  81. package/dist/hooks/index.d.ts +1 -0
  82. package/dist/hooks/useAuthController.d.ts +1 -1
  83. package/dist/hooks/useBreadcrumbsController.d.ts +26 -0
  84. package/dist/hooks/useBuildNavigationController.d.ts +3 -5
  85. package/dist/hooks/useFireCMSContext.d.ts +1 -1
  86. package/dist/hooks/useProjectLog.d.ts +8 -2
  87. package/dist/hooks/useResolvedNavigationFrom.d.ts +3 -3
  88. package/dist/hooks/useValidateAuthenticator.d.ts +5 -9
  89. package/dist/index.d.ts +1 -0
  90. package/dist/index.es.js +21352 -14215
  91. package/dist/index.es.js.map +1 -1
  92. package/dist/index.umd.js +23817 -588
  93. package/dist/index.umd.js.map +1 -1
  94. package/dist/internal/useBuildDataSource.d.ts +1 -16
  95. package/dist/internal/useUnsavedChangesDialog.d.ts +7 -9
  96. package/dist/preview/PropertyPreviewProps.d.ts +6 -1
  97. package/dist/preview/components/EnumValuesChip.d.ts +1 -1
  98. package/dist/preview/components/ReferencePreview.d.ts +3 -2
  99. package/dist/preview/components/StorageThumbnail.d.ts +2 -1
  100. package/dist/preview/components/UrlComponentPreview.d.ts +2 -1
  101. package/dist/preview/util.d.ts +3 -3
  102. package/dist/routes/CustomCMSRoute.d.ts +4 -0
  103. package/dist/routes/FireCMSRoute.d.ts +1 -0
  104. package/dist/routes/HomePageRoute.d.ts +3 -0
  105. package/dist/types/auth.d.ts +8 -10
  106. package/dist/types/collections.d.ts +69 -22
  107. package/dist/types/datasource.d.ts +52 -36
  108. package/dist/types/dialogs_controller.d.ts +7 -3
  109. package/dist/types/entities.d.ts +7 -2
  110. package/dist/types/entity_actions.d.ts +28 -4
  111. package/dist/types/entity_callbacks.d.ts +16 -16
  112. package/dist/types/entity_overrides.d.ts +2 -2
  113. package/dist/types/export_import.d.ts +4 -4
  114. package/dist/types/fields.d.ts +63 -41
  115. package/dist/types/firecms.d.ts +6 -2
  116. package/dist/types/firecms_context.d.ts +1 -1
  117. package/dist/types/index.d.ts +0 -1
  118. package/dist/types/navigation.d.ts +34 -17
  119. package/dist/types/permissions.d.ts +4 -4
  120. package/dist/types/plugins.d.ts +23 -12
  121. package/dist/types/properties.d.ts +34 -21
  122. package/dist/types/property_config.d.ts +0 -2
  123. package/dist/types/side_dialogs_controller.d.ts +10 -0
  124. package/dist/types/side_entity_controller.d.ts +1 -1
  125. package/dist/types/storage.d.ts +86 -3
  126. package/dist/types/user.d.ts +1 -0
  127. package/dist/util/builders.d.ts +2 -2
  128. package/dist/util/entities.d.ts +3 -3
  129. package/dist/util/entity_actions.d.ts +2 -0
  130. package/dist/util/entity_cache.d.ts +23 -0
  131. package/dist/util/icon_list.d.ts +5 -1
  132. package/dist/util/icon_synonyms.d.ts +1 -98
  133. package/dist/util/icons.d.ts +6 -3
  134. package/dist/util/index.d.ts +2 -0
  135. package/dist/util/navigation_from_path.d.ts +5 -1
  136. package/dist/util/navigation_utils.d.ts +14 -3
  137. package/dist/util/objects.d.ts +2 -1
  138. package/dist/util/permissions.d.ts +4 -4
  139. package/dist/util/plurals.d.ts +0 -2
  140. package/dist/util/property_utils.d.ts +3 -3
  141. package/dist/util/resolutions.d.ts +30 -16
  142. package/dist/util/storage.d.ts +23 -2
  143. package/dist/util/useStorageUploadController.d.ts +3 -3
  144. package/package.json +58 -45
  145. package/src/app/AppBar.tsx +18 -0
  146. package/src/app/Drawer.tsx +24 -0
  147. package/src/app/Scaffold.tsx +243 -0
  148. package/src/app/index.ts +4 -0
  149. package/src/app/useApp.tsx +32 -0
  150. package/src/components/ArrayContainer.tsx +126 -40
  151. package/src/components/CircularProgressCenter.tsx +2 -2
  152. package/src/components/ClearFilterSortButton.tsx +41 -0
  153. package/src/components/{DeleteConfirmationDialog.tsx → ConfirmationDialog.tsx} +3 -3
  154. package/src/components/DeleteEntityDialog.tsx +10 -19
  155. package/src/components/EntityCollectionTable/EntityCollectionRowActions.tsx +54 -37
  156. package/src/components/EntityCollectionTable/EntityCollectionTable.tsx +38 -31
  157. package/src/components/EntityCollectionTable/EntityCollectionTableProps.tsx +30 -9
  158. package/src/components/EntityCollectionTable/PropertyTableCell.tsx +47 -39
  159. package/src/components/EntityCollectionTable/column_utils.tsx +3 -3
  160. package/src/components/EntityCollectionTable/fields/TableReferenceField.tsx +31 -17
  161. package/src/components/EntityCollectionTable/fields/TableStorageUpload.tsx +19 -17
  162. package/src/components/EntityCollectionTable/index.tsx +1 -1
  163. package/src/components/EntityCollectionTable/internal/CollectionTableToolbar.tsx +31 -36
  164. package/src/components/EntityCollectionTable/internal/EntityTableCell.tsx +36 -34
  165. package/src/components/EntityCollectionTable/internal/EntityTableCellActions.tsx +20 -8
  166. package/src/components/EntityCollectionTable/internal/popup_field/PopupFormField.tsx +84 -77
  167. package/src/components/EntityCollectionView/EntityCollectionView.tsx +206 -112
  168. package/src/components/EntityCollectionView/EntityCollectionViewStartActions.tsx +68 -0
  169. package/src/components/EntityCollectionView/useSelectionController.tsx +20 -7
  170. package/src/components/EntityCollectionView/utils.ts +19 -0
  171. package/src/components/EntityPreview.tsx +66 -53
  172. package/src/components/EntityView.tsx +10 -10
  173. package/src/components/ErrorView.tsx +4 -4
  174. package/src/components/HomePage/DefaultHomePage.tsx +26 -19
  175. package/src/components/HomePage/FavouritesView.tsx +6 -11
  176. package/src/components/HomePage/NavigationCard.tsx +4 -4
  177. package/src/components/HomePage/NavigationCardBinding.tsx +5 -10
  178. package/src/components/HomePage/NavigationGroup.tsx +2 -2
  179. package/src/components/HomePage/SmallNavigationCard.tsx +5 -6
  180. package/src/components/NotFoundPage.tsx +2 -2
  181. package/src/components/PropertyConfigBadge.tsx +9 -3
  182. package/src/components/PropertyIdCopyTooltip.tsx +48 -0
  183. package/src/components/ReferenceTable/ReferenceSelectionTable.tsx +17 -12
  184. package/src/components/ReferenceWidget.tsx +22 -12
  185. package/src/components/SearchIconsView.tsx +10 -7
  186. package/src/components/SelectableTable/SelectableTable.tsx +27 -12
  187. package/src/components/SelectableTable/filters/BooleanFilterField.tsx +2 -3
  188. package/src/components/SelectableTable/filters/DateTimeFilterField.tsx +25 -8
  189. package/src/components/SelectableTable/filters/ReferenceFilterField.tsx +30 -6
  190. package/src/components/SelectableTable/filters/StringNumberFilterField.tsx +92 -23
  191. package/src/components/UnsavedChangesDialog.tsx +42 -0
  192. package/src/components/VirtualTable/VirtualTable.tsx +96 -48
  193. package/src/components/VirtualTable/VirtualTableCell.tsx +1 -9
  194. package/src/components/VirtualTable/VirtualTableHeader.tsx +10 -10
  195. package/src/components/VirtualTable/VirtualTableHeaderRow.tsx +2 -2
  196. package/src/components/VirtualTable/VirtualTableProps.tsx +33 -14
  197. package/src/components/VirtualTable/VirtualTableRow.tsx +5 -6
  198. package/src/components/VirtualTable/fields/VirtualTableDateField.tsx +5 -5
  199. package/src/components/VirtualTable/fields/VirtualTableInput.tsx +3 -2
  200. package/src/components/VirtualTable/fields/VirtualTableNumberInput.tsx +2 -1
  201. package/src/components/VirtualTable/fields/VirtualTableSelect.tsx +16 -28
  202. package/src/components/VirtualTable/types.tsx +2 -3
  203. package/src/components/{EntityCollectionTable/internal → common}/default_entity_actions.tsx +33 -40
  204. package/src/components/common/index.ts +2 -1
  205. package/src/components/{VirtualTable/common.tsx → common/table_height.tsx} +5 -2
  206. package/src/components/common/types.tsx +4 -6
  207. package/src/components/common/useColumnsIds.tsx +24 -3
  208. package/src/components/common/{useDataSourceEntityCollectionTableController.tsx → useDataSourceTableController.tsx} +142 -22
  209. package/src/components/common/useDebouncedCallback.tsx +20 -0
  210. package/src/components/common/useScrollRestoration.tsx +68 -0
  211. package/src/components/common/useTableSearchHelper.ts +53 -12
  212. package/src/components/index.tsx +4 -2
  213. package/src/contexts/BreacrumbsContext.tsx +38 -0
  214. package/src/contexts/DialogsProvider.tsx +5 -4
  215. package/src/contexts/SnackbarProvider.tsx +2 -0
  216. package/src/core/DefaultAppBar.tsx +201 -0
  217. package/src/core/DefaultDrawer.tsx +185 -0
  218. package/src/core/DrawerNavigationItem.tsx +66 -0
  219. package/src/core/EntityEditView.tsx +933 -204
  220. package/src/core/EntitySidePanel.tsx +73 -8
  221. package/src/core/FireCMS.tsx +56 -49
  222. package/src/core/FireCMSRouter.tsx +17 -0
  223. package/src/core/NavigationRoutes.tsx +20 -34
  224. package/src/core/SideDialogs.tsx +12 -6
  225. package/src/core/field_configs.tsx +11 -12
  226. package/src/core/index.tsx +6 -5
  227. package/src/form/PropertyFieldBinding.tsx +74 -35
  228. package/src/form/components/CustomIdField.tsx +6 -2
  229. package/src/form/components/FieldHelperText.tsx +4 -4
  230. package/src/form/components/LabelWithIcon.tsx +27 -19
  231. package/src/form/components/LabelWithIconAndTooltip.tsx +28 -0
  232. package/src/form/components/StorageItemPreview.tsx +22 -12
  233. package/src/form/components/StorageUploadProgress.tsx +3 -4
  234. package/src/form/components/index.tsx +1 -1
  235. package/src/form/field_bindings/ArrayCustomShapedFieldBinding.tsx +29 -17
  236. package/src/form/field_bindings/ArrayOfReferencesFieldBinding.tsx +45 -35
  237. package/src/form/field_bindings/BlockFieldBinding.tsx +53 -33
  238. package/src/form/field_bindings/DateTimeFieldBinding.tsx +17 -14
  239. package/src/form/field_bindings/KeyValueFieldBinding.tsx +60 -51
  240. package/src/form/field_bindings/MapFieldBinding.tsx +67 -48
  241. package/src/form/field_bindings/MarkdownEditorFieldBinding.tsx +150 -0
  242. package/src/form/field_bindings/{MultiSelectBinding.tsx → MultiSelectFieldBinding.tsx} +25 -20
  243. package/src/form/field_bindings/ReadOnlyFieldBinding.tsx +11 -16
  244. package/src/form/field_bindings/ReferenceFieldBinding.tsx +42 -31
  245. package/src/form/field_bindings/RepeatFieldBinding.tsx +52 -34
  246. package/src/form/field_bindings/SelectFieldBinding.tsx +22 -14
  247. package/src/form/field_bindings/StorageUploadFieldBinding.tsx +37 -47
  248. package/src/form/field_bindings/SwitchFieldBinding.tsx +28 -24
  249. package/src/form/field_bindings/TextFieldBinding.tsx +27 -24
  250. package/src/form/index.tsx +4 -9
  251. package/src/form/useClearRestoreValue.tsx +2 -2
  252. package/src/form/validation.ts +1 -17
  253. package/src/hooks/data/delete.ts +6 -5
  254. package/src/hooks/data/save.ts +13 -9
  255. package/src/hooks/data/useCollectionFetch.tsx +3 -3
  256. package/src/hooks/data/useDataSource.tsx +11 -3
  257. package/src/hooks/data/useEntityFetch.tsx +10 -6
  258. package/src/hooks/index.tsx +1 -0
  259. package/src/hooks/useAuthController.tsx +1 -1
  260. package/src/hooks/useBreadcrumbsController.tsx +31 -0
  261. package/src/hooks/useBuildLocalConfigurationPersistence.tsx +8 -10
  262. package/src/hooks/useBuildModeController.tsx +11 -5
  263. package/src/hooks/useBuildNavigationController.tsx +153 -55
  264. package/src/hooks/useFireCMSContext.tsx +5 -5
  265. package/src/hooks/useLargeLayout.tsx +0 -35
  266. package/src/hooks/useProjectLog.tsx +32 -10
  267. package/src/hooks/useResolvedNavigationFrom.tsx +10 -12
  268. package/src/hooks/useValidateAuthenticator.tsx +21 -41
  269. package/src/index.ts +1 -0
  270. package/src/internal/useBuildDataSource.ts +72 -82
  271. package/src/internal/useBuildSideDialogsController.tsx +4 -2
  272. package/src/internal/useBuildSideEntityController.tsx +230 -70
  273. package/src/internal/useUnsavedChangesDialog.tsx +127 -91
  274. package/src/preview/PropertyPreview.tsx +13 -20
  275. package/src/preview/PropertyPreviewProps.tsx +7 -1
  276. package/src/preview/components/BooleanPreview.tsx +2 -2
  277. package/src/preview/components/EmptyValue.tsx +1 -1
  278. package/src/preview/components/EnumValuesChip.tsx +2 -2
  279. package/src/preview/components/ImagePreview.tsx +25 -36
  280. package/src/preview/components/ReferencePreview.tsx +23 -34
  281. package/src/preview/components/StorageThumbnail.tsx +5 -1
  282. package/src/preview/components/UrlComponentPreview.tsx +44 -11
  283. package/src/preview/property_previews/ArrayOfMapsPreview.tsx +2 -3
  284. package/src/preview/property_previews/ArrayOfReferencesPreview.tsx +4 -3
  285. package/src/preview/property_previews/ArrayOfStorageComponentsPreview.tsx +2 -3
  286. package/src/preview/property_previews/ArrayOfStringsPreview.tsx +1 -2
  287. package/src/preview/property_previews/ArrayOneOfPreview.tsx +4 -5
  288. package/src/preview/property_previews/ArrayPropertyPreview.tsx +4 -5
  289. package/src/preview/property_previews/MapPropertyPreview.tsx +9 -9
  290. package/src/preview/property_previews/SkeletonPropertyComponent.tsx +12 -12
  291. package/src/preview/property_previews/StringPropertyPreview.tsx +3 -3
  292. package/src/preview/util.ts +10 -10
  293. package/src/routes/CustomCMSRoute.tsx +21 -0
  294. package/src/routes/FireCMSRoute.tsx +230 -0
  295. package/src/routes/HomePageRoute.tsx +17 -0
  296. package/src/types/auth.tsx +9 -13
  297. package/src/types/collections.ts +79 -24
  298. package/src/types/customization_controller.tsx +0 -1
  299. package/src/types/datasource.ts +61 -43
  300. package/src/types/dialogs_controller.tsx +7 -3
  301. package/src/types/entities.ts +12 -2
  302. package/src/types/entity_actions.tsx +32 -7
  303. package/src/types/entity_callbacks.ts +18 -18
  304. package/src/types/entity_overrides.tsx +2 -2
  305. package/src/types/export_import.ts +4 -4
  306. package/src/types/fields.tsx +69 -45
  307. package/src/types/firecms.tsx +7 -2
  308. package/src/types/firecms_context.tsx +1 -1
  309. package/src/types/index.ts +0 -1
  310. package/src/types/navigation.ts +40 -21
  311. package/src/types/permissions.ts +5 -5
  312. package/src/types/plugins.tsx +25 -14
  313. package/src/types/properties.ts +39 -22
  314. package/src/types/property_config.tsx +0 -2
  315. package/src/types/side_dialogs_controller.tsx +13 -0
  316. package/src/types/side_entity_controller.tsx +1 -1
  317. package/src/types/storage.ts +94 -3
  318. package/src/types/user.ts +2 -0
  319. package/src/util/builders.ts +6 -6
  320. package/src/util/entities.ts +9 -6
  321. package/src/util/entity_actions.ts +28 -0
  322. package/src/util/entity_cache.ts +196 -0
  323. package/src/util/enums.ts +1 -1
  324. package/src/util/icon_list.ts +16 -10
  325. package/src/util/icon_synonyms.ts +3 -100
  326. package/src/util/icons.tsx +17 -7
  327. package/src/util/index.ts +2 -0
  328. package/src/util/make_properties_editable.ts +13 -5
  329. package/src/util/navigation_from_path.ts +10 -2
  330. package/src/util/navigation_utils.ts +59 -7
  331. package/src/util/objects.ts +45 -28
  332. package/src/util/parent_references_from_path.ts +3 -3
  333. package/src/util/permissions.ts +9 -8
  334. package/src/util/plurals.ts +0 -2
  335. package/src/util/property_utils.tsx +11 -4
  336. package/src/util/references.ts +11 -2
  337. package/src/util/resolutions.ts +79 -46
  338. package/src/util/storage.ts +79 -21
  339. package/src/util/strings.ts +2 -2
  340. package/src/util/useStorageUploadController.tsx +34 -8
  341. package/src/util/useTraceUpdate.tsx +1 -0
  342. package/dist/components/PropertyIdCopyTooltipContent.d.ts +0 -3
  343. package/dist/components/VirtualTable/common.d.ts +0 -2
  344. package/dist/core/Drawer.d.ts +0 -23
  345. package/dist/core/Scaffold.d.ts +0 -55
  346. package/dist/core/SideEntityView.d.ts +0 -7
  347. package/dist/form/EntityForm.d.ts +0 -77
  348. package/dist/form/components/FormikArrayContainer.d.ts +0 -18
  349. package/dist/form/field_bindings/MarkdownFieldBinding.d.ts +0 -9
  350. package/dist/internal/useBuildCustomizationController.d.ts +0 -2
  351. package/dist/internal/useLocaleConfig.d.ts +0 -1
  352. package/dist/types/appcheck.d.ts +0 -26
  353. package/src/components/FireCMSAppBar.tsx +0 -165
  354. package/src/components/PropertyIdCopyTooltipContent.tsx +0 -28
  355. package/src/core/Drawer.tsx +0 -191
  356. package/src/core/Scaffold.tsx +0 -281
  357. package/src/core/SideEntityView.tsx +0 -38
  358. package/src/form/EntityForm.tsx +0 -728
  359. package/src/form/components/FormikArrayContainer.tsx +0 -44
  360. package/src/form/field_bindings/MarkdownFieldBinding.tsx +0 -695
  361. package/src/internal/useBuildCustomizationController.tsx +0 -5
  362. package/src/internal/useLocaleConfig.tsx +0 -18
  363. package/src/types/appcheck.ts +0 -29
  364. /package/src/util/{common.tsx → common.ts} +0 -0
@@ -9,13 +9,15 @@ import {
9
9
  FilterValues,
10
10
  FireCMSContext,
11
11
  SelectedCellProps,
12
- User
12
+ User,
13
+ WhereFilterOp
13
14
  } from "../../types";
14
15
  import { useDebouncedData } from "./useDebouncedData";
16
+ import { ScrollRestorationController } from "./useScrollRestoration";
15
17
 
16
18
  const DEFAULT_PAGE_SIZE = 50;
17
19
 
18
- export type DataSourceEntityCollectionTableControllerProps<M extends Record<string, any> = any> = {
20
+ export type DataSourceTableControllerProps<M extends Record<string, any> = any> = {
19
21
  /**
20
22
  * Full path where the data of this table is located
21
23
  */
@@ -31,7 +33,19 @@ export type DataSourceEntityCollectionTableControllerProps<M extends Record<stri
31
33
  entitiesDisplayedFirst?: Entity<M>[];
32
34
 
33
35
  lastDeleteTimestamp?: number;
36
+
37
+ /**
38
+ * Force filter to be applied to the table.
39
+ */
34
40
  forceFilter?: FilterValues<string>;
41
+
42
+ scrollRestoration?: ScrollRestorationController;
43
+
44
+ /**
45
+ * When set to true the filters and sort will be updated in the URL
46
+ */
47
+ updateUrl?: boolean;
48
+
35
49
  }
36
50
 
37
51
  /**
@@ -43,18 +57,22 @@ export type DataSourceEntityCollectionTableControllerProps<M extends Record<stri
43
57
  *
44
58
  * @param fullPath
45
59
  * @param collection
60
+ * @param scrollRestoration
46
61
  * @param entitiesDisplayedFirst
47
62
  * @param lastDeleteTimestamp
48
63
  * @param forceFilterFromProps
64
+ * @param updateUrl
49
65
  */
50
- export function useDataSourceEntityCollectionTableController<M extends Record<string, any> = any, UserType extends User = User>(
66
+ export function useDataSourceTableController<M extends Record<string, any> = any, USER extends User = User>(
51
67
  {
52
68
  fullPath,
53
69
  collection,
70
+ scrollRestoration,
54
71
  entitiesDisplayedFirst,
55
72
  lastDeleteTimestamp,
56
73
  forceFilter: forceFilterFromProps,
57
- }: DataSourceEntityCollectionTableControllerProps<M>)
74
+ updateUrl
75
+ }: DataSourceTableControllerProps<M>)
58
76
  : EntityTableController<M> {
59
77
 
60
78
  const {
@@ -66,14 +84,40 @@ export function useDataSourceEntityCollectionTableController<M extends Record<st
66
84
  const [popupCell, setPopupCell] = React.useState<SelectedCellProps<M> | undefined>(undefined);
67
85
  const navigation = useNavigationController();
68
86
  const dataSource = useDataSource(collection);
69
- const resolvedPath = useMemo(() => navigation.resolveAliasesFrom(fullPath), [fullPath, navigation.resolveAliasesFrom]);
87
+ const resolvedPath = useMemo(() => navigation.resolveIdsFrom(fullPath), [fullPath, navigation.resolveIdsFrom]);
70
88
 
71
89
  const forceFilter = forceFilterFromProps ?? forceFilterFromCollection;
72
90
  const paginationEnabled = collection.pagination === undefined || Boolean(collection.pagination);
73
91
  const pageSize = typeof collection.pagination === "number" ? collection.pagination : DEFAULT_PAGE_SIZE;
74
92
 
75
93
  const [searchString, setSearchString] = React.useState<string | undefined>();
76
- const [itemCount, setItemCount] = React.useState<number | undefined>(paginationEnabled ? pageSize : undefined);
94
+
95
+ const checkFilterCombination = useCallback((filterValues: FilterValues<any>,
96
+ sortBy?: [string, "asc" | "desc"]) => {
97
+ if (!dataSource.isFilterCombinationValid)
98
+ return true;
99
+ return dataSource.isFilterCombinationValid({
100
+ path: resolvedPath,
101
+ collection,
102
+ filterValues,
103
+ sortBy
104
+ })
105
+ }, []);
106
+
107
+ const onScroll = ({
108
+ scrollOffset
109
+ }: {
110
+ scrollOffset: number
111
+ }) => {
112
+ if (scrollRestoration) {
113
+ scrollRestoration.updateCollectionScroll({
114
+ fullPath: resolvedPath,
115
+ scrollOffset,
116
+ data: rawData,
117
+ filters: filterValues
118
+ });
119
+ }
120
+ }
77
121
 
78
122
  const initialSortInternal = useMemo(() => {
79
123
  if (initialSort && forceFilter && !checkFilterCombination(forceFilter, initialSort)) {
@@ -83,32 +127,43 @@ export function useDataSourceEntityCollectionTableController<M extends Record<st
83
127
  return initialSort;
84
128
  }, [initialSort, forceFilter]);
85
129
 
86
- const [filterValues, setFilterValues] = React.useState<FilterValues<Extract<keyof M, string>> | undefined>(forceFilter ?? initialFilter ?? undefined);
87
- const [sortBy, setSortBy] = React.useState<[Extract<keyof M, string>, "asc" | "desc"] | undefined>(initialSortInternal);
130
+ const {
131
+ filterValues: initialFilteUrl,
132
+ sortBy: initialSortUrl,
133
+ } = parseFilterAndSort(window.location.search);
134
+
135
+ const [filterValues, setFilterValues] = React.useState<FilterValues<Extract<keyof M, string>> | undefined>(forceFilter ?? initialFilteUrl ?? initialFilter ?? undefined);
136
+ const [sortBy, setSortBy] = React.useState<[Extract<keyof M, string>, "asc" | "desc"] | undefined>(initialSortUrl ?? initialSortInternal);
137
+
138
+ useUpdateUrl(filterValues, sortBy, searchString, updateUrl);
139
+
140
+ const collectionScroll = scrollRestoration?.getCollectionScroll(fullPath, filterValues);
141
+ const initialItemCount = collectionScroll?.data.length ?? pageSize;
142
+
143
+ useEffect(() => {
144
+ if (scrollRestoration) {
145
+ scrollRestoration.updateCollectionScroll({
146
+ fullPath: resolvedPath,
147
+ scrollOffset: collectionScroll?.scrollOffset ?? 0,
148
+ data: rawData,
149
+ filters: filterValues
150
+ });
151
+ }
152
+ }, []);
153
+
154
+ const [itemCount, setItemCount] = React.useState<number | undefined>(paginationEnabled ? initialItemCount : undefined);
88
155
 
89
156
  const sortByProperty = sortBy ? sortBy[0] : undefined;
90
157
  const currentSort = sortBy ? sortBy[1] : undefined;
91
158
 
92
- const context: FireCMSContext<UserType> = useFireCMSContext();
159
+ const context: FireCMSContext<USER> = useFireCMSContext();
93
160
 
94
- const [rawData, setRawData] = useState<Entity<M>[]>([]);
161
+ const [rawData, setRawData] = useState<Entity<M>[]>(collectionScroll?.data ?? []);
95
162
 
96
163
  const [dataLoading, setDataLoading] = useState<boolean>(false);
97
164
  const [dataLoadingError, setDataLoadingError] = useState<Error | undefined>();
98
165
  const [noMoreToLoad, setNoMoreToLoad] = useState<boolean>(false);
99
166
 
100
- const checkFilterCombination = useCallback((filterValues: FilterValues<any>,
101
- sortBy?: [string, "asc" | "desc"]) => {
102
- if (!dataSource.isFilterCombinationValid)
103
- return true;
104
- return dataSource.isFilterCombinationValid({
105
- path: resolvedPath,
106
- collection,
107
- filterValues,
108
- sortBy
109
- })
110
- }, []);
111
-
112
167
  const clearFilter = useCallback(() => setFilterValues(forceFilter ?? undefined), [forceFilter]);
113
168
 
114
169
  const updateFilterValues = useCallback((updatedFilter: FilterValues<Extract<keyof M, string>> | undefined) => {
@@ -216,6 +271,8 @@ export function useDataSourceEntityCollectionTableController<M extends Record<st
216
271
  clearFilter,
217
272
  itemCount,
218
273
  setItemCount,
274
+ initialScroll: collectionScroll?.scrollOffset,
275
+ onScroll,
219
276
  paginationEnabled,
220
277
  pageSize,
221
278
  checkFilterCombination,
@@ -223,3 +280,66 @@ export function useDataSourceEntityCollectionTableController<M extends Record<st
223
280
  setPopupCell
224
281
  }
225
282
  }
283
+
284
+ function useUpdateUrl<M extends Record<string, any> = any>(
285
+ filterValues: FilterValues<Extract<keyof M, string>> | undefined,
286
+ sortBy: [Extract<keyof M, string>, "asc" | "desc"] | undefined,
287
+ searchString: string | undefined,
288
+ updateUrl: boolean | undefined
289
+ ) {
290
+
291
+ useEffect(() => {
292
+ if (updateUrl) {
293
+ const newUrl = encodeFilterAndSort(filterValues, sortBy);
294
+ const search = searchString ? `&search=${encodeURIComponent(searchString)}` : "";
295
+ const state = `${newUrl}${search}`;
296
+ const hash = window.location.hash;
297
+ if (state === "")
298
+ window.history.replaceState({}, "", `${window.location.pathname}${hash}`);
299
+ else
300
+ window.history.replaceState({}, "", `?${state}${hash}`);
301
+ }
302
+ }, [filterValues, sortBy, searchString, updateUrl]);
303
+ }
304
+
305
+ function encodeFilterAndSort(filterValues?: FilterValues<string> | undefined, sortBy?: [string, "asc" | "desc"] | undefined) {
306
+ const entries: Record<string, string> = {};
307
+ if (sortBy) {
308
+ entries["__sort"] = encodeURIComponent(sortBy[0]);
309
+ entries["__sort_order"] = encodeURIComponent(sortBy[1]);
310
+ }
311
+ if (filterValues) {
312
+ Object.entries(filterValues).forEach(([key, value]) => {
313
+ if (value) {
314
+ entries[encodeURIComponent(`${key}_op`)] = encodeURIComponent(value[0]);
315
+ entries[encodeURIComponent(`${key}_value`)] = encodeURIComponent(value[1]);
316
+ }
317
+ });
318
+ }
319
+ if (!Object.keys(entries).length) {
320
+ return "";
321
+ }
322
+ return Object.entries(entries).map(([key, value]) => `${key}=${value}`).join("&");
323
+ }
324
+
325
+ function parseFilterAndSort<M>(search: string): {
326
+ filterValues: FilterValues<string> | undefined,
327
+ sortBy?: [Extract<keyof M, string>, "asc" | "desc"]
328
+ } {
329
+ const entries = new URLSearchParams(search);
330
+ const filterValues: FilterValues<string> = {};
331
+ let sortBy: [string, "asc" | "desc"] | undefined = undefined;
332
+ entries.forEach((value, key) => {
333
+ if (key === "__sort") {
334
+ sortBy = [value, entries.get("__sort_order") as "asc" | "desc"];
335
+ } else if (key.endsWith("_op")) {
336
+ const filterValue = entries.get(`${key.replace("_op", "_value")}`);
337
+ filterValues[key.replace("_op", "")] = [value as WhereFilterOp, filterValue as string];
338
+ }
339
+ });
340
+
341
+ return {
342
+ filterValues: Object.keys(filterValues).length ? filterValues : undefined,
343
+ sortBy
344
+ }
345
+ }
@@ -0,0 +1,20 @@
1
+ import { useCallback, useRef } from "react";
2
+
3
+ export function useDebounceCallback<T extends (...args: any[]) => any>(
4
+ callback?: T,
5
+ delay?: number
6
+ ): T {
7
+ const timeoutRef = useRef<number | null>(null);
8
+
9
+ const debouncedCallback = useCallback((...args: Parameters<T>) => {
10
+ if (timeoutRef.current !== null) {
11
+ clearTimeout(timeoutRef.current);
12
+ }
13
+
14
+ timeoutRef.current = window.setTimeout(() => {
15
+ callback?.(...args);
16
+ }, delay ?? 200);
17
+ }, [callback, delay]);
18
+
19
+ return debouncedCallback as T;
20
+ }
@@ -0,0 +1,68 @@
1
+ import { Entity, FilterValues } from "../../types";
2
+
3
+ const collectionScrollCache = new Map<string, { scrollOffset: number, data: Entity<any>[] }>();
4
+
5
+ export type ScrollRestorationController = {
6
+
7
+ getCollectionScroll: (fullPath: string,
8
+ filters?: FilterValues<any>) => {
9
+ scrollOffset: number,
10
+ data: Entity<any>[]
11
+ } | undefined;
12
+
13
+ updateCollectionScroll: (props: {
14
+ fullPath: string,
15
+ scrollOffset: number,
16
+ filters?: FilterValues<any>;
17
+ data: Entity<any>[]
18
+ }) => void;
19
+
20
+ }
21
+
22
+ export function useScrollRestoration(): ScrollRestorationController {
23
+
24
+ const updateCollectionScroll = ({
25
+ fullPath,
26
+ filters,
27
+ scrollOffset,
28
+ data
29
+ }: {
30
+ fullPath: string;
31
+ filters?: FilterValues<any>;
32
+ sort?: [string, "asc" | "desc"];
33
+ scrollOffset: number;
34
+ data: Entity<any>[]
35
+ }) => {
36
+ collectionScrollCache.set(
37
+ createCacheKey(fullPath, filters),
38
+ {
39
+ scrollOffset,
40
+ data
41
+ })
42
+ }
43
+
44
+ const getCollectionScroll = (fullPath: string,
45
+ filters?: FilterValues<any>) => {
46
+ return collectionScrollCache.get(createCacheKey(fullPath, filters));
47
+ }
48
+
49
+ return {
50
+ getCollectionScroll,
51
+ updateCollectionScroll
52
+ }
53
+ }
54
+
55
+ function createCacheKey(fullPath: string, filters?: FilterValues<any>) {
56
+
57
+ if (!filters) {
58
+ return fullPath;
59
+ }
60
+
61
+ // codify the filters into a url friendly string
62
+ const filtersString = filters ? Object.keys(filters).map(key => {
63
+ const value = JSON.stringify(filters[key]);
64
+ return `${key}=${value}`;
65
+ }).join("&") : "";
66
+
67
+ return `${fullPath}?${filtersString}`;
68
+ }
@@ -1,7 +1,7 @@
1
1
  import { useState } from "react";
2
2
 
3
3
  import { EntityCollection } from "../../types";
4
- import { useCustomizationController, useFireCMSContext } from "../../hooks";
4
+ import { useCustomizationController, useDataSource, useFireCMSContext } from "../../hooks";
5
5
 
6
6
  export interface UseTableSearchHelperParams<M extends Record<string, any>> {
7
7
  collection: EntityCollection<M>;
@@ -9,27 +9,58 @@ export interface UseTableSearchHelperParams<M extends Record<string, any>> {
9
9
  parentCollectionIds?: string[];
10
10
  }
11
11
 
12
- export function useTableSearchHelper<M extends Record<string, any>>({ collection, fullPath, parentCollectionIds }: UseTableSearchHelperParams<M>) {
12
+ export function useTableSearchHelper<M extends Record<string, any>>({
13
+ collection,
14
+ fullPath,
15
+ parentCollectionIds
16
+ }: UseTableSearchHelperParams<M>) {
13
17
 
14
18
  const context = useFireCMSContext();
15
19
  const customizationController = useCustomizationController();
20
+ const dataSource = useDataSource();
16
21
 
17
22
  const [textSearchLoading, setTextSearchLoading] = useState<boolean>(false);
18
23
  const [textSearchInitialised, setTextSearchInitialised] = useState<boolean>(false);
24
+
19
25
  let onTextSearchClick: (() => void) | undefined;
20
26
  let textSearchEnabled = Boolean(collection.textSearchEnabled);
21
- if (customizationController?.plugins) {
22
- const addTextSearchClickListener = customizationController.plugins?.find(p => Boolean(p.collectionView?.onTextSearchClick));
27
+
28
+ const props = {
29
+ context,
30
+ path: fullPath,
31
+ databaseId: collection.databaseId,
32
+ collection,
33
+ parentCollectionIds
34
+ };
35
+
36
+ const searchBlocked = customizationController.plugins?.find(p => {
37
+ return p.collectionView?.blockSearch?.(props);
38
+ });
39
+
40
+ const addTextSearchClickListener = Boolean(dataSource?.initTextSearch) || customizationController.plugins?.find(p => Boolean(p.collectionView?.onTextSearchClick));
41
+
42
+ if (addTextSearchClickListener) {
23
43
 
24
44
  onTextSearchClick = addTextSearchClickListener
25
45
  ? () => {
26
46
  setTextSearchLoading(true);
27
- Promise.all(customizationController.plugins?.map(p => {
28
- if (p.collectionView?.onTextSearchClick)
29
- return p.collectionView.onTextSearchClick({ context, path: fullPath, collection, parentCollectionIds });
30
- return Promise.resolve(true);
31
- }) as Promise<boolean>[])
32
- .then((res) => {
47
+ const promises: Promise<boolean>[] = [];
48
+ if (dataSource?.initTextSearch && !searchBlocked) {
49
+ promises.push(dataSource.initTextSearch(props));
50
+ }
51
+ if (searchBlocked) {
52
+ customizationController.plugins?.forEach(p => {
53
+ if (p.collectionView?.onTextSearchClick)
54
+ promises.push(p.collectionView.onTextSearchClick({
55
+ context,
56
+ path: fullPath,
57
+ collection,
58
+ parentCollectionIds
59
+ }));
60
+ })
61
+ }
62
+ return Promise.all(promises)
63
+ .then((res: boolean[]) => {
33
64
  if (res.every(Boolean)) setTextSearchInitialised(true);
34
65
  })
35
66
  .finally(() => setTextSearchLoading(false));
@@ -39,9 +70,19 @@ export function useTableSearchHelper<M extends Record<string, any>>({ collection
39
70
  customizationController.plugins?.forEach(p => {
40
71
  if (!textSearchEnabled)
41
72
  if (p.collectionView?.showTextSearchBar) {
42
- textSearchEnabled = p.collectionView.showTextSearchBar({ context, path: fullPath, collection, parentCollectionIds });
73
+ textSearchEnabled = p.collectionView.showTextSearchBar({
74
+ context,
75
+ path: fullPath,
76
+ collection,
77
+ parentCollectionIds
78
+ });
43
79
  }
44
80
  })
45
81
  }
46
- return { textSearchLoading, textSearchInitialised, onTextSearchClick, textSearchEnabled };
82
+ return {
83
+ textSearchLoading,
84
+ textSearchInitialised,
85
+ onTextSearchClick,
86
+ textSearchEnabled
87
+ };
47
88
  }
@@ -13,22 +13,24 @@ export * from "./common";
13
13
 
14
14
  export * from "./HomePage";
15
15
  export * from "./SelectableTable/SelectableTable";
16
+ export * from "./SelectableTable/SelectableTableContext";
16
17
  export * from "./EntityCollectionView/EntityCollectionView";
17
18
  export * from "./EntityCollectionView/EntityCollectionViewActions";
18
19
  export * from "./EntityCollectionView/useSelectionController";
19
20
 
20
21
  export * from "./PropertyConfigBadge";
22
+ export * from "./PropertyIdCopyTooltip";
21
23
 
22
24
  export * from "./EntityCollectionTable";
23
25
  export * from "./NotFoundPage";
24
26
 
25
27
  export * from "./VirtualTable";
26
28
  export * from "./ErrorBoundary";
27
- export * from "./DeleteConfirmationDialog";
29
+ export * from "./ConfirmationDialog";
28
30
 
29
31
  export * from "./FireCMSLogo";
30
32
 
31
- export * from "./FireCMSAppBar";
33
+ export * from "../core/DefaultAppBar";
32
34
 
33
35
  export * from "./ArrayContainer";
34
36
  export * from "./ReferenceWidget";
@@ -0,0 +1,38 @@
1
+ import React, { useState } from "react";
2
+ import { BreadcrumbEntry, BreadcrumbsController } from "../hooks/useBreadcrumbsController";
3
+
4
+ const DEFAULT_BREADCRUMBS_CONTROLLER = {
5
+ breadcrumbs: [],
6
+ set: (props: {
7
+ breadcrumbs: BreadcrumbEntry[];
8
+ }) => {
9
+ }
10
+ };
11
+
12
+ export const BreadcrumbContext = React.createContext<BreadcrumbsController>(DEFAULT_BREADCRUMBS_CONTROLLER);
13
+
14
+ interface BreadcrumbsProviderProps {
15
+ children: React.ReactNode;
16
+ }
17
+
18
+ export const BreadcrumbsProvider: React.FC<BreadcrumbsProviderProps> = ({ children }) => {
19
+
20
+ const [breadcrumbs, setBreadcrumbs] = useState<BreadcrumbEntry[]>([]);
21
+
22
+ const set = (props: {
23
+ breadcrumbs: BreadcrumbEntry[];
24
+ }) => {
25
+ setBreadcrumbs(props.breadcrumbs);
26
+ };
27
+
28
+ return (
29
+ <BreadcrumbContext.Provider
30
+ value={{
31
+ breadcrumbs,
32
+ set
33
+ }}
34
+ >
35
+ {children}
36
+ </BreadcrumbContext.Provider>
37
+ );
38
+ };
@@ -8,7 +8,7 @@ export const DialogsProvider: React.FC<PropsWithChildren<{}>> = ({ children }) =
8
8
  const [dialogEntries, setDialogEntries] = useState<DialogControllerEntryProps[]>([]);
9
9
  const dialogEntriesRef = useRef<DialogControllerEntryProps[]>(dialogEntries);
10
10
 
11
- const updateDialogEntries = (newPanels: DialogControllerEntryProps[]) => {
11
+ const updateDialogEntries = (newPanels: DialogControllerEntryProps<any>[]) => {
12
12
  dialogEntriesRef.current = newPanels;
13
13
  setDialogEntries(newPanels);
14
14
  };
@@ -18,14 +18,14 @@ export const DialogsProvider: React.FC<PropsWithChildren<{}>> = ({ children }) =
18
18
  if (dialogEntries.length === 0)
19
19
  return;
20
20
 
21
- const updatedPanels = [...dialogEntries.slice(0, -1)];
21
+ const updatedPanels = [...dialogEntriesRef.current.slice(0, -1)];
22
22
  updateDialogEntries(updatedPanels);
23
23
 
24
24
  }, [dialogEntries]);
25
25
 
26
- const open = useCallback((dialogEntry: DialogControllerEntryProps) => {
26
+ const open = useCallback(<T extends object = object>(dialogEntry: DialogControllerEntryProps<T>) => {
27
27
 
28
- const updatedPanels = [...dialogEntries, dialogEntry];
28
+ const updatedPanels = [...dialogEntriesRef.current, dialogEntry];
29
29
  updateDialogEntries(updatedPanels);
30
30
 
31
31
  return {
@@ -46,6 +46,7 @@ export const DialogsProvider: React.FC<PropsWithChildren<{}>> = ({ children }) =
46
46
  key={`dialog_${i}`}
47
47
  open={true}
48
48
  closeDialog={close}
49
+ {...entry.props}
49
50
  />)}
50
51
  </DialogsControllerContext.Provider>
51
52
  );
@@ -1,3 +1,5 @@
1
+ "use client";
2
+
1
3
  import React, { PropsWithChildren } from "react";
2
4
  import { SnackbarProvider as NotistackSnackbarProvider } from "notistack";
3
5