@griddo/ax 11.15.7 → 11.15.8-rc.0

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 (88) hide show
  1. package/package.json +2 -2
  2. package/src/__tests__/components/Fields/Wysiwyg/Wysiwyg.atoms.test.tsx +409 -0
  3. package/src/__tests__/components/Fields/Wysiwyg/Wysiwyg.helpers.test.tsx +418 -0
  4. package/src/__tests__/components/Fields/Wysiwyg/Wysiwyg.test.tsx +776 -29
  5. package/src/__tests__/components/FieldsBehavior/FieldsBehavior.test.tsx +368 -11
  6. package/src/__tests__/modules/Users/UserList/UserList.test.tsx +6 -6
  7. package/src/components/Fields/IntegrationsField/IntegrationItem/atoms.tsx +14 -5
  8. package/src/components/Fields/IntegrationsField/IntegrationItem/index.tsx +1 -8
  9. package/src/components/Fields/UrlField/index.tsx +5 -4
  10. package/src/components/Fields/Wysiwyg/atoms.tsx +140 -0
  11. package/src/components/Fields/Wysiwyg/config.tsx +190 -9
  12. package/src/components/Fields/Wysiwyg/helpers.tsx +54 -1
  13. package/src/components/Fields/Wysiwyg/index.tsx +210 -61
  14. package/src/components/Fields/Wysiwyg/style.tsx +32 -1
  15. package/src/components/Fields/Wysiwyg/vendors.tsx +0 -1
  16. package/src/components/FieldsBehavior/index.tsx +66 -31
  17. package/src/components/Icon/components/Sync.js +16 -0
  18. package/src/components/Icon/svgs/Sync.svg +3 -0
  19. package/src/components/RestoreModal/index.tsx +1 -3
  20. package/src/components/ScheduleModal/index.tsx +3 -3
  21. package/src/components/TableList/index.tsx +5 -3
  22. package/src/containers/FileDrive/actions.tsx +5 -5
  23. package/src/containers/Forms/actions.tsx +40 -38
  24. package/src/containers/Gallery/actions.tsx +27 -27
  25. package/src/containers/Integrations/actions.tsx +2 -2
  26. package/src/containers/Navigation/Defaults/actions.tsx +1 -1
  27. package/src/containers/PageEditor/actions.tsx +3 -5
  28. package/src/containers/Redirects/actions.tsx +2 -2
  29. package/src/containers/Sites/actions.tsx +15 -8
  30. package/src/containers/StructuredData/actions.tsx +5 -5
  31. package/src/containers/Users/actions.tsx +2 -2
  32. package/src/modules/Categories/CategoriesList/CategoryItem/index.tsx +36 -43
  33. package/src/modules/Categories/CategoriesList/CategoryPanel/index.tsx +15 -11
  34. package/src/modules/Categories/CategoriesList/atoms.tsx +42 -12
  35. package/src/modules/Categories/CategoriesList/index.tsx +8 -30
  36. package/src/modules/Content/PageItem/index.tsx +6 -5
  37. package/src/modules/Content/atoms.tsx +7 -3
  38. package/src/modules/Content/index.tsx +8 -16
  39. package/src/modules/FileDrive/FileModal/DetailPanel/index.tsx +14 -14
  40. package/src/modules/FileDrive/FolderItem/index.tsx +46 -54
  41. package/src/modules/FileDrive/GridItem/index.tsx +32 -37
  42. package/src/modules/FileDrive/ListItem/index.tsx +31 -37
  43. package/src/modules/FileDrive/atoms.tsx +59 -12
  44. package/src/modules/FileDrive/index.tsx +88 -98
  45. package/src/modules/Forms/FormCategoriesList/CategoryItem/index.tsx +42 -34
  46. package/src/modules/Forms/FormCategoriesList/atoms.tsx +17 -6
  47. package/src/modules/Forms/FormCategoriesList/index.tsx +30 -34
  48. package/src/modules/Forms/FormEditor/index.tsx +14 -6
  49. package/src/modules/Forms/FormList/FormItem/index.tsx +5 -1
  50. package/src/modules/Forms/FormList/index.tsx +15 -9
  51. package/src/modules/Forms/atoms.tsx +7 -4
  52. package/src/modules/GlobalEditor/atoms.tsx +77 -0
  53. package/src/modules/GlobalEditor/index.tsx +24 -7
  54. package/src/modules/MediaGallery/FolderItem/index.tsx +36 -52
  55. package/src/modules/MediaGallery/GridItem/index.tsx +27 -38
  56. package/src/modules/MediaGallery/ImageModal/DetailPanel/index.tsx +13 -13
  57. package/src/modules/MediaGallery/ImageModal/index.tsx +2 -16
  58. package/src/modules/MediaGallery/ListItem/index.tsx +25 -37
  59. package/src/modules/MediaGallery/atoms.tsx +84 -15
  60. package/src/modules/MediaGallery/index.tsx +62 -122
  61. package/src/modules/Navigation/Defaults/Item/atoms.tsx +2 -4
  62. package/src/modules/Navigation/Defaults/Item/index.tsx +80 -94
  63. package/src/modules/Navigation/Defaults/atoms.tsx +179 -7
  64. package/src/modules/Navigation/Defaults/index.tsx +51 -18
  65. package/src/modules/Navigation/Defaults/style.tsx +10 -7
  66. package/src/modules/Navigation/Menus/List/Table/Item/atoms.tsx +33 -19
  67. package/src/modules/Navigation/Menus/List/Table/Item/index.tsx +18 -19
  68. package/src/modules/Navigation/Menus/List/Table/index.tsx +15 -13
  69. package/src/modules/Navigation/Menus/List/index.tsx +1 -1
  70. package/src/modules/PageEditor/atoms.tsx +14 -11
  71. package/src/modules/PageEditor/index.tsx +11 -16
  72. package/src/modules/Redirects/RedirectItem/index.tsx +37 -39
  73. package/src/modules/Redirects/atoms.tsx +58 -12
  74. package/src/modules/Redirects/index.tsx +30 -58
  75. package/src/modules/Settings/Integrations/IntegrationItem/CopyModal/index.tsx +1 -1
  76. package/src/modules/Settings/Integrations/IntegrationItem/index.tsx +57 -69
  77. package/src/modules/Settings/Integrations/atoms.tsx +72 -8
  78. package/src/modules/Settings/Integrations/index.tsx +34 -48
  79. package/src/modules/StructuredData/Form/index.tsx +25 -8
  80. package/src/modules/StructuredData/StructuredDataList/GlobalPageItem/atoms.tsx +26 -75
  81. package/src/modules/StructuredData/StructuredDataList/GlobalPageItem/index.tsx +15 -33
  82. package/src/modules/StructuredData/StructuredDataList/StructuredDataItem/index.tsx +63 -41
  83. package/src/modules/StructuredData/StructuredDataList/StructuredDataItem/style.tsx +13 -8
  84. package/src/modules/StructuredData/StructuredDataList/index.tsx +11 -16
  85. package/src/modules/StructuredData/{StructuredDataList/atoms.tsx → atoms.tsx} +25 -28
  86. package/src/modules/Users/UserList/UserItem/index.tsx +18 -35
  87. package/src/modules/Users/UserList/atoms.tsx +61 -0
  88. package/src/modules/Users/UserList/index.tsx +12 -32
@@ -427,9 +427,9 @@ function deleteStructuredDataContent(
427
427
  };
428
428
 
429
429
  const callback = async () =>
430
- Array.isArray(id) ? structuredData.deleteDataContentBulk(id) : structuredData.deleteDataContent(id);
430
+ Array.isArray(id) ? await structuredData.deleteDataContentBulk(id) : await structuredData.deleteDataContent(id);
431
431
 
432
- return await handleRequest(callback, responseActions, [setIsLoading])(dispatch);
432
+ return await handleRequest(callback, responseActions, [setIsSaving])(dispatch);
433
433
  } catch (e) {
434
434
  console.log(e);
435
435
  return false;
@@ -662,7 +662,7 @@ function createCategoryGroup(
662
662
 
663
663
  const callback = async () => structuredData.createGroup(dataGroup);
664
664
 
665
- return await handleRequest(callback, responseActions, [appActions.setIsLoading])(dispatch);
665
+ return await handleRequest(callback, responseActions, [appActions.setIsSaving])(dispatch);
666
666
  } catch (e) {
667
667
  console.log(e);
668
668
  return false;
@@ -680,7 +680,7 @@ function updateCategoryGroup(groupID: number, data: ICategoryGroupParams): (disp
680
680
 
681
681
  const callback = async () => structuredData.updateGroup(groupID, data);
682
682
 
683
- return await handleRequest(callback, responseActions, [appActions.setIsLoading])(dispatch);
683
+ return await handleRequest(callback, responseActions, [appActions.setIsSaving])(dispatch);
684
684
  } catch (e) {
685
685
  console.log(e);
686
686
  return false;
@@ -723,7 +723,7 @@ function deleteCategoryGroup(
723
723
  ? structuredData.deleteGroupBulk(currentStructuredData.id, siteID, id, deleteChildren)
724
724
  : structuredData.deleteGroup(currentStructuredData.id, siteID, id, deleteChildren);
725
725
 
726
- return await handleRequest(callback, responseActions, [setIsLoading])(dispatch);
726
+ return await handleRequest(callback, responseActions, [setIsSaving])(dispatch);
727
727
  } catch (e) {
728
728
  console.log(e);
729
729
  return false;
@@ -219,7 +219,7 @@ function deleteUser(id: number | number[]): (dispatch: Dispatch, getState: () =>
219
219
 
220
220
  const callback = async () => (Array.isArray(id) ? users.deleteUserBulk(id) : users.deleteUser(id));
221
221
 
222
- return await handleRequest(callback, responseActions, [])(dispatch);
222
+ return await handleRequest(callback, responseActions, [appActions.setIsSaving])(dispatch);
223
223
  } catch (e) {
224
224
  console.log(e);
225
225
  return false;
@@ -255,7 +255,7 @@ function removeUserFromSite(userID: number, siteID: number): (dispatch: Dispatch
255
255
 
256
256
  const callback = async () => users.removeUserFromSite(userID, siteID);
257
257
 
258
- return await handleRequest(callback, responseActions, [])(dispatch);
258
+ return await handleRequest(callback, responseActions, [appActions.setIsSaving])(dispatch);
259
259
  } catch (e) {
260
260
  console.log(e);
261
261
  return false;
@@ -6,7 +6,7 @@ import { structuredData } from "@ax/api";
6
6
  import { CheckField, Flag, FloatingMenu, Icon, LanguageMenu, Tag, TruncatedTooltip } from "@ax/components";
7
7
  import { structuredDataActions } from "@ax/containers/StructuredData";
8
8
  import { isReqOk } from "@ax/helpers";
9
- import { useModal, usePermission } from "@ax/hooks";
9
+ import { useModals, usePermissions } from "@ax/hooks";
10
10
  import type { ICategoryGroup, ICheck, IDataLanguage, ILanguage, IRootState, IStructuredDataCategory } from "@ax/types";
11
11
 
12
12
  import { type AnimateLayoutChanges, useSortable } from "@dnd-kit/sortable";
@@ -34,12 +34,11 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
34
34
  depth,
35
35
  indentationWidth,
36
36
  collapsed,
37
+ isSaving,
37
38
  onCollapse,
38
39
  } = props;
39
40
 
40
- const { isOpen, toggleModal } = useModal();
41
- const { isOpen: isDeleteOpen, toggleModal: toggleDeleteModal } = useModal();
42
- const { isOpen: isGroupOpen, toggleModal: toggleGroupModal } = useModal();
41
+ const { isOpen, toggleModal } = useModals(["panel", "delete", "group"]);
43
42
  const [deleteGroupCategories, setDeleteGroupCategories] = useState(false);
44
43
  const [translation, setTranslation] = useState<{
45
44
  lang: { locale: string; id: number };
@@ -47,12 +46,14 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
47
46
  content: IStructuredDataCategory | ICategoryGroup | null;
48
47
  } | null>(null);
49
48
 
50
- const allowedToEditSiteCategory = usePermission("categories.editSiteTaxonomies");
51
- const allowedToEditGlobalCategory = usePermission("global.globalData.editTaxonomies");
52
- const allowedToDeleteSiteCategory = usePermission("categories.deleteSiteTaxonomies");
53
- const allowedToDeleteGlobalCategory = usePermission("global.globalData.deleteTaxonomies");
54
- const allowedToEditTaxonomy = currentSiteID ? allowedToEditSiteCategory : allowedToEditGlobalCategory;
55
- const allowedToDeleteTaxonomy = currentSiteID ? allowedToDeleteSiteCategory : allowedToDeleteGlobalCategory;
49
+ const isAllowedTo = usePermissions({
50
+ editSiteCategory: "categories.editSiteTaxonomies",
51
+ editGlobalCategory: "global.globalData.editTaxonomies",
52
+ deleteSiteCategory: "categories.deleteSiteTaxonomies",
53
+ deleteGlobalCategory: "global.globalData.deleteTaxonomies",
54
+ });
55
+ const allowedToEditTaxonomy = currentSiteID ? isAllowedTo.editSiteCategory : isAllowedTo.editGlobalCategory;
56
+ const allowedToDeleteTaxonomy = currentSiteID ? isAllowedTo.deleteSiteCategory : isAllowedTo.deleteGlobalCategory;
56
57
 
57
58
  const animateLayoutChanges: AnimateLayoutChanges = ({ isSorting, wasDragging }) => !(isSorting || wasDragging);
58
59
 
@@ -66,11 +67,11 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
66
67
  const { dataLanguages = [], content } = category;
67
68
  const isGroup = category.type === "group";
68
69
 
69
- const handleClick = () => !isDragging && toggleModal();
70
+ const handleClick = () => !isDragging && toggleModal("panel");
70
71
 
71
72
  const handleCloseModal = () => {
72
73
  setTranslation(null);
73
- toggleModal();
74
+ toggleModal("panel");
74
75
  };
75
76
 
76
77
  const handleOnChange = (value: ICheck) => onChange(value);
@@ -82,7 +83,7 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
82
83
  const deleted = await deleteStructuredDataContent(categoryIDs);
83
84
 
84
85
  if (deleted) {
85
- isDeleteOpen && toggleDeleteModal();
86
+ isOpen("delete") && toggleModal("delete");
86
87
  toggleToast("1 category deleted");
87
88
  }
88
89
  };
@@ -93,7 +94,7 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
93
94
  const deleted = await deleteCategoryGroup(categoryIDs, deleteGroupCategories);
94
95
 
95
96
  if (deleted) {
96
- isGroupOpen && toggleGroupModal();
97
+ isOpen("group") && toggleModal("group");
97
98
  toggleToast(
98
99
  deleteGroupCategories ? "1 grouping category and its categories deleted" : "1 grouping category deleted",
99
100
  );
@@ -105,7 +106,7 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
105
106
  {
106
107
  label: "delete",
107
108
  icon: "delete",
108
- action: isGroup ? toggleGroupModal : toggleDeleteModal,
109
+ action: isGroup ? () => toggleModal("group") : () => toggleModal("delete"),
109
110
  },
110
111
  ]
111
112
  : [];
@@ -154,7 +155,7 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
154
155
  content = await getDataTranslation(translationLang?.id || category.id, lang.id, category.type);
155
156
  }
156
157
  setTranslation({ lang, isNew, content });
157
- toggleModal();
158
+ toggleModal("panel");
158
159
  };
159
160
 
160
161
  const languageMenu = () => (
@@ -181,20 +182,6 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
181
182
  "Not translatable"
182
183
  );
183
184
 
184
- const mainDeleteModalAction = {
185
- title: "delete",
186
- onClick: removeCategory,
187
- };
188
-
189
- const secondaryDeleteModalAction = { title: "Cancel", onClick: toggleDeleteModal };
190
-
191
- const mainDeleteGroupModalAction = {
192
- title: "Delete",
193
- onClick: removeGroup,
194
- };
195
-
196
- const secondaryDeleteGroupModalAction = { title: "Cancel", onClick: toggleGroupModal };
197
-
198
185
  const selectable = !(isCategoryGroup(category) && category.selectable === false);
199
186
 
200
187
  return (
@@ -236,7 +223,11 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
236
223
  </TruncatedTooltip>
237
224
  </S.NameCell>
238
225
  <S.CodeCell role="cell" clickable={allowedToEditTaxonomy}>
239
- <TruncatedTooltip content={isCategory(category) && category.content ? category.content.code : ""} expanded top={-5}>
226
+ <TruncatedTooltip
227
+ content={isCategory(category) && category.content ? category.content.code : ""}
228
+ expanded
229
+ top={-5}
230
+ >
240
231
  <S.Code>{isCategory(category) && category.content ? category.content.code : ""}</S.Code>
241
232
  </TruncatedTooltip>
242
233
  </S.CodeCell>
@@ -254,9 +245,9 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
254
245
  </S.ActionsCell>
255
246
  </S.CategoryRow>
256
247
  </S.Wrapper>
257
- {isOpen && (
248
+ {isOpen("panel") && (
258
249
  <CategoryPanel
259
- isOpen={isOpen}
250
+ isOpen={isOpen("panel")}
260
251
  toggleModal={handleCloseModal}
261
252
  item={translation?.content || category}
262
253
  getContents={getContents}
@@ -264,22 +255,22 @@ const CategoryItem = (props: ICategoryItemProps): JSX.Element => {
264
255
  toggleToast={toggleToast}
265
256
  />
266
257
  )}
267
- {isDeleteOpen && (
258
+ {isOpen("delete") && (
268
259
  <DeleteModal
269
- isOpen={isDeleteOpen}
270
- toggleModal={toggleDeleteModal}
271
- mainModalAction={mainDeleteModalAction}
272
- secondaryModalAction={secondaryDeleteModalAction}
260
+ isOpen={isOpen("delete")}
261
+ toggleModal={() => toggleModal("delete")}
262
+ onDelete={removeCategory}
263
+ isLoading={isSaving}
273
264
  />
274
265
  )}
275
- {isGroupOpen && (
266
+ {isOpen("group") && (
276
267
  <DeleteGroupModal
277
- isOpen={isGroupOpen}
278
- toggleModal={toggleGroupModal}
279
- mainModalAction={mainDeleteGroupModalAction}
280
- secondaryModalAction={secondaryDeleteGroupModalAction}
268
+ isOpen={isOpen("group")}
269
+ toggleModal={() => toggleModal("group")}
270
+ onDelete={removeGroup}
281
271
  deleteGroupCategories={deleteGroupCategories}
282
272
  setDeleteGroupCategories={setDeleteGroupCategories}
273
+ isLoading={isSaving}
283
274
  />
284
275
  )}
285
276
  </>
@@ -300,6 +291,7 @@ interface IProps {
300
291
  depth: number;
301
292
  indentationWidth: number;
302
293
  collapsed: boolean;
294
+ isSaving: boolean;
303
295
  onCollapse?: () => void;
304
296
  }
305
297
 
@@ -312,6 +304,7 @@ type ICategoryItemProps = IProps & IDispatchProps;
312
304
 
313
305
  const mapStateToProps = (state: IRootState) => ({
314
306
  currentSiteID: state.sites.currentSiteInfo?.id ?? null,
307
+ isSaving: state.app.isSaving,
315
308
  });
316
309
 
317
310
  const mapDispatchToProps = {
@@ -1,17 +1,18 @@
1
- import React, { useState } from "react";
1
+ import { useState } from "react";
2
2
  import { connect } from "react-redux";
3
3
 
4
+ import { Button, Flag, FloatingPanel } from "@ax/components";
4
5
  import { structuredDataActions } from "@ax/containers/StructuredData";
5
- import {
6
+ import type {
7
+ ICategoryGroup,
8
+ ICategoryGroupParams,
9
+ ILanguage,
6
10
  IRootState,
7
11
  IStructuredData,
8
- IStructuredDataContent,
9
- ILanguage,
10
12
  IStructuredDataCategory,
11
- ICategoryGroup,
12
- ICategoryGroupParams,
13
+ IStructuredDataContent,
13
14
  } from "@ax/types";
14
- import { Button, Flag, FloatingPanel } from "@ax/components";
15
+
15
16
  import { isCategory, isCategoryGroup } from "../utils";
16
17
  import Form from "./Form";
17
18
 
@@ -31,6 +32,7 @@ const CategoryPanel = (props: IProps): JSX.Element => {
31
32
  currentStructuredData,
32
33
  languages,
33
34
  translation,
35
+ isSaving,
34
36
  } = props;
35
37
 
36
38
  const initState: IFormState = {
@@ -117,15 +119,15 @@ const CategoryPanel = (props: IProps): JSX.Element => {
117
119
  };
118
120
 
119
121
  const addButton = {
120
- label: "Add",
122
+ label: isSaving ? "Saving" : "Add",
121
123
  action: addItemAction,
122
- disabled: false,
124
+ disabled: isSaving,
123
125
  };
124
126
 
125
127
  const editButton = {
126
- label: "Update",
128
+ label: isSaving ? "Saving" : "Update",
127
129
  action: editItemAction,
128
- disabled: false,
130
+ disabled: isSaving,
129
131
  };
130
132
 
131
133
  const translateTitle = translation?.isNew ? "Translate" : "Edit";
@@ -172,6 +174,7 @@ const CategoryPanel = (props: IProps): JSX.Element => {
172
174
  interface IStateProps {
173
175
  currentStructuredData: IStructuredData | null;
174
176
  languages: ILanguage[];
177
+ isSaving: boolean;
175
178
  }
176
179
 
177
180
  interface ICategoryPanelProps {
@@ -193,6 +196,7 @@ export interface IFormState {
193
196
  const mapStateToProps = (state: IRootState) => ({
194
197
  currentStructuredData: state.structuredData.currentStructuredData,
195
198
  languages: state.app.globalLangs,
199
+ isSaving: state.app.isSaving,
196
200
  });
197
201
 
198
202
  const mapDispatchToProps = {
@@ -1,12 +1,29 @@
1
- import React from "react";
1
+ import type React from "react";
2
2
 
3
- import { IModal } from "@ax/types";
4
- import { Modal, FieldsBehavior } from "@ax/components";
3
+ import { FieldsBehavior, Modal } from "@ax/components";
5
4
 
6
5
  import * as S from "./style";
7
6
 
8
- const DeleteModal = (props: IModal): JSX.Element => {
9
- const { isOpen, toggleModal, mainModalAction, secondaryModalAction } = props;
7
+ interface IDeleteModal {
8
+ isOpen: boolean;
9
+ toggleModal: () => void;
10
+ onDelete: () => void;
11
+ isLoading?: boolean;
12
+ }
13
+
14
+ const DeleteModal = (props: IDeleteModal): JSX.Element => {
15
+ const { isOpen, toggleModal, onDelete, isLoading = false } = props;
16
+
17
+ const mainModalAction = {
18
+ title: isLoading ? "deleting" : "delete",
19
+ onClick: onDelete,
20
+ disabled: isLoading,
21
+ };
22
+
23
+ const secondaryModalAction = {
24
+ title: "Cancel",
25
+ onClick: toggleModal,
26
+ };
10
27
 
11
28
  return (
12
29
  <Modal
@@ -16,6 +33,7 @@ const DeleteModal = (props: IModal): JSX.Element => {
16
33
  secondaryAction={secondaryModalAction}
17
34
  mainAction={mainModalAction}
18
35
  size="S"
36
+ height="auto"
19
37
  >
20
38
  <S.ModalContent>
21
39
  <p>
@@ -29,16 +47,32 @@ const DeleteModal = (props: IModal): JSX.Element => {
29
47
  );
30
48
  };
31
49
 
50
+ interface IDeleteGroupModal extends IDeleteModal {
51
+ deleteGroupCategories: boolean;
52
+ setDeleteGroupCategories: React.Dispatch<React.SetStateAction<boolean>>;
53
+ }
54
+
32
55
  const DeleteGroupModal = (props: IDeleteGroupModal): JSX.Element => {
33
56
  const {
34
57
  isOpen,
35
58
  toggleModal,
36
- mainModalAction,
37
- secondaryModalAction,
59
+ onDelete,
60
+ isLoading = false,
38
61
  deleteGroupCategories,
39
62
  setDeleteGroupCategories,
40
63
  } = props;
41
64
 
65
+ const mainModalAction = {
66
+ title: isLoading ? "deleting" : "delete",
67
+ onClick: onDelete,
68
+ disabled: isLoading,
69
+ };
70
+
71
+ const secondaryModalAction = {
72
+ title: "Cancel",
73
+ onClick: toggleModal,
74
+ };
75
+
42
76
  const options = [
43
77
  {
44
78
  title: "Delete only the grouping category",
@@ -60,6 +94,7 @@ const DeleteGroupModal = (props: IDeleteGroupModal): JSX.Element => {
60
94
  secondaryAction={secondaryModalAction}
61
95
  mainAction={mainModalAction}
62
96
  size="S"
97
+ height="auto"
63
98
  >
64
99
  <S.ModalContent>
65
100
  <p>
@@ -78,9 +113,4 @@ const DeleteGroupModal = (props: IDeleteGroupModal): JSX.Element => {
78
113
  );
79
114
  };
80
115
 
81
- interface IDeleteGroupModal extends IModal {
82
- deleteGroupCategories: boolean;
83
- setDeleteGroupCategories: React.Dispatch<React.SetStateAction<boolean>>;
84
- }
85
-
86
116
  export { DeleteModal, DeleteGroupModal };
@@ -63,6 +63,7 @@ const CategoriesList = (props: IProps): JSX.Element => {
63
63
  setLanguage,
64
64
  totalItems,
65
65
  categories,
66
+ isSaving,
66
67
  setSelectedCategory,
67
68
  activatedDataPacks,
68
69
  deleteDataContent,
@@ -72,7 +73,6 @@ const CategoriesList = (props: IProps): JSX.Element => {
72
73
  } = props;
73
74
 
74
75
  const [isScrolling, setIsScrolling] = useState(false);
75
- const [isBulkLoading, setIsBulkLoading] = useState(false);
76
76
  const [deleteGroupCategories, setDeleteGroupCategories] = useState(false);
77
77
  const [searchQuery, setSearchQuery] = useState<string>("");
78
78
  const [items, setItems] = useState<TreeItem[]>(currentDataContent);
@@ -197,7 +197,6 @@ const CategoriesList = (props: IProps): JSX.Element => {
197
197
  : undefined;
198
198
 
199
199
  const bulkDelete = async () => {
200
- setIsBulkLoading(true);
201
200
  const { groups, categories } = filterCategoriesAndGroups(currentDataContent);
202
201
  const idsCatsToBeDeleted = getAllLangCategoriesIds(categories, selectedItems);
203
202
  const idsGroupsToBeDeleted = getAllLangCategoriesIds(groups, selectedItems);
@@ -211,7 +210,6 @@ const CategoriesList = (props: IProps): JSX.Element => {
211
210
  isOpen("delete") && toggleModal("delete");
212
211
  isOpen("group") && toggleModal("group");
213
212
  }
214
- setIsBulkLoading(false);
215
213
  };
216
214
 
217
215
  const handleToggleDeleteModal = () => {
@@ -259,7 +257,7 @@ const CategoriesList = (props: IProps): JSX.Element => {
259
257
  filterItems={filterItems}
260
258
  setHoverCheck={setHoverCheck}
261
259
  selectedItems={selectedItems}
262
- isLoading={isBulkLoading}
260
+ isLoading={isSaving}
263
261
  />
264
262
  );
265
263
 
@@ -341,28 +339,6 @@ const CategoriesList = (props: IProps): JSX.Element => {
341
339
  action: hasCategories ? () => toggleModal("panel") : () => setHistoryPush("/sites/settings/content-types"),
342
340
  };
343
341
 
344
- const mainDeleteModalAction = {
345
- title: isBulkLoading ? "deleting" : "delete",
346
- onClick: bulkDelete,
347
- disabled: isBulkLoading,
348
- };
349
-
350
- const secondaryDeleteModalAction = {
351
- title: "Cancel",
352
- onClick: () => toggleModal("delete"),
353
- };
354
-
355
- const mainDeleteGroupModalAction = {
356
- title: isBulkLoading ? "deleting" : "delete",
357
- disabled: isBulkLoading,
358
- onClick: bulkDelete,
359
- };
360
-
361
- const secondaryDeleteGroupModalAction = {
362
- title: "cancel",
363
- onClick: () => toggleModal("group"),
364
- };
365
-
366
342
  return (
367
343
  <MainWrapper
368
344
  title={toTitleCase(LOCALE.entityLabel.category.other)}
@@ -456,16 +432,16 @@ const CategoriesList = (props: IProps): JSX.Element => {
456
432
  <DeleteModal
457
433
  isOpen={isOpen("delete")}
458
434
  toggleModal={() => toggleModal("delete")}
459
- mainModalAction={mainDeleteModalAction}
460
- secondaryModalAction={secondaryDeleteModalAction}
435
+ onDelete={bulkDelete}
436
+ isLoading={isSaving}
461
437
  />
462
438
  )}
463
439
  {isOpen("group") && (
464
440
  <DeleteGroupModal
465
441
  isOpen={isOpen("group")}
466
442
  toggleModal={() => toggleModal("group")}
467
- mainModalAction={mainDeleteGroupModalAction}
468
- secondaryModalAction={secondaryDeleteGroupModalAction}
443
+ onDelete={bulkDelete}
444
+ isLoading={isSaving}
469
445
  deleteGroupCategories={deleteGroupCategories}
470
446
  setDeleteGroupCategories={setDeleteGroupCategories}
471
447
  />
@@ -485,6 +461,7 @@ const mapStateToProps = (state: IRootState) => ({
485
461
  lang: state.app.lang,
486
462
  totalItems: state.sites.totalItems,
487
463
  activatedDataPacks: state.dataPacks.activated,
464
+ isSaving: state.app.isSaving,
488
465
  });
489
466
 
490
467
  interface IDispatchProps {
@@ -507,6 +484,7 @@ interface ICategoriesProps {
507
484
  totalItems: number;
508
485
  categories: { global: IStructuredData[]; site: IStructuredData[] };
509
486
  activatedDataPacks: IDataPack[];
487
+ isSaving: boolean;
510
488
  }
511
489
 
512
490
  type IProps = ICategoriesProps & IDispatchProps;
@@ -200,7 +200,7 @@ const PageItem = (props: IPageItemProps): JSX.Element => {
200
200
 
201
201
  const handleDeleteItem = async () => {
202
202
  const allPageVersions = pageLanguages.map((lang: IPageLanguage) => lang.pageId);
203
- deleteAllVersions ? deleteBulk(allPageVersions) : deletePage();
203
+ deleteAllVersions ? await deleteBulk(allPageVersions) : await deletePage();
204
204
  toggleModal("delete");
205
205
  };
206
206
 
@@ -333,7 +333,7 @@ const PageItem = (props: IPageItemProps): JSX.Element => {
333
333
 
334
334
  if (isAllowedToDelete) {
335
335
  menuOptions.push({
336
- label: isGlobal ? "Remove" : "delete",
336
+ label: isGlobal ? "remove" : "delete",
337
337
  icon: "delete",
338
338
  action: () => toggleModal(isGlobal ? "remove" : "delete"),
339
339
  disabled: deleteDisabled,
@@ -538,13 +538,14 @@ const PageItem = (props: IPageItemProps): JSX.Element => {
538
538
  toggleModal={() => toggleModal("remove")}
539
539
  pageTitle={page.title}
540
540
  onRemove={handleRemoveItemFromSite}
541
+ isRemoving={isSaving}
541
542
  />
542
543
  <UnpublishPageModal isOpen={isOpen("unpublish")} toggleModal={() => toggleModal("unpublish")} />
543
544
  <DeleteModal
544
545
  isOpen={isOpen("delete")}
545
546
  toggleModal={() => toggleModal("delete")}
546
547
  onDelete={handleDeleteItem}
547
- {...{ isTranslated, deleteAllVersions, setDeleteAllVersions, title: page.title }}
548
+ {...{ isTranslated, deleteAllVersions, setDeleteAllVersions, title: page.title, isDeleting: isSaving }}
548
549
  />
549
550
  </>
550
551
  );
@@ -571,14 +572,14 @@ interface IPageItemProps {
571
572
  functions: {
572
573
  onClick: (e: any) => void;
573
574
  onCheck: (e: any) => void;
574
- deletePage(params?: ISavePageParams, currentLanguage?: string): void;
575
+ deletePage(params?: ISavePageParams, currentLanguage?: string): Promise<boolean>;
575
576
  getSiteContent(): any;
576
577
  setHistoryPush(path: string, isEditor: boolean): void;
577
578
  updatePageStatus(ids: number[], status: string, updatedFromList: boolean): Promise<boolean>;
578
579
  setCurrentPageID(currentPageID: number | null): ISetCurrentPageIDAction;
579
580
  duplicatePage(pageID: number, data: any, siteID?: number): Promise<boolean>;
580
581
  removePageFromSite(pageID: number): Promise<boolean>;
581
- deleteBulk(ids: number[]): void;
582
+ deleteBulk(ids: number[]): Promise<boolean>;
582
583
  setTemplateInstanceError(error: any): void;
583
584
  getDataPack: (id: string) => Promise<void>;
584
585
  toggleCopiedToast(): void;
@@ -6,7 +6,8 @@ import type { IModal, ISite } from "@ax/types";
6
6
  import * as S from "./style";
7
7
 
8
8
  const DeleteModal = (props: IDeleteModal): JSX.Element => {
9
- const { isOpen, toggleModal, isTranslated, deleteAllVersions, setDeleteAllVersions, title, onDelete, isDeleting } = props;
9
+ const { isOpen, toggleModal, isTranslated, deleteAllVersions, setDeleteAllVersions, title, onDelete, isDeleting } =
10
+ props;
10
11
 
11
12
  const options = [
12
13
  {
@@ -39,6 +40,7 @@ const DeleteModal = (props: IDeleteModal): JSX.Element => {
39
40
  secondaryAction={secondaryAction}
40
41
  mainAction={mainAction}
41
42
  size="S"
43
+ height="auto"
42
44
  >
43
45
  {isTranslated ? (
44
46
  <>
@@ -167,11 +169,12 @@ const DuplicatePageModal = (props: IDuplicatePageModal): JSX.Element => {
167
169
  };
168
170
 
169
171
  const RemovePageModal = (props: IRemovePageModal): JSX.Element => {
170
- const { isOpen, toggleModal, pageTitle, onRemove } = props;
172
+ const { isOpen, toggleModal, pageTitle, onRemove, isRemoving } = props;
171
173
 
172
174
  const mainAction = {
173
- title: "Remove",
175
+ title: isRemoving ? "Removing" : "Remove",
174
176
  onClick: onRemove,
177
+ disabled: isRemoving,
175
178
  };
176
179
 
177
180
  const secondaryAction = { title: "Cancel", onClick: toggleModal };
@@ -250,6 +253,7 @@ interface IDuplicatePageModal extends IModal {
250
253
  interface IRemovePageModal extends IModal {
251
254
  pageTitle: string;
252
255
  onRemove: () => void;
256
+ isRemoving?: boolean;
253
257
  }
254
258
 
255
259
  interface IUnpublishPageModal extends IModal {}