@strapi/admin 4.10.0-beta.0 → 4.10.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 (229) hide show
  1. package/.eslintignore +4 -0
  2. package/.eslintrc.js +14 -0
  3. package/admin/src/components/LanguageProvider/index.js +1 -1
  4. package/admin/src/components/LocalesProvider/__mocks__/useLocalesProvider.js +7 -0
  5. package/admin/src/components/LocalesProvider/index.js +2 -3
  6. package/admin/src/content-manager/components/CollectionTypeFormWrapper/index.js +3 -6
  7. package/admin/src/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn.js +2 -0
  8. package/admin/src/content-manager/components/DynamicTable/index.js +11 -29
  9. package/admin/src/content-manager/components/EditViewDataManagerProvider/reducer.js +12 -6
  10. package/admin/src/content-manager/components/EditViewDataManagerProvider/utils/findAllAndReplace.js +10 -3
  11. package/admin/src/content-manager/components/InputUID/endActionStyle.js +4 -13
  12. package/admin/src/content-manager/components/InputUID/index.js +95 -72
  13. package/admin/src/content-manager/components/RepeatableComponent/components/Component.js +8 -2
  14. package/admin/src/content-manager/components/SingleTypeFormWrapper/index.js +4 -8
  15. package/admin/src/content-manager/pages/App/LeftMenu/index.js +56 -35
  16. package/admin/src/content-manager/pages/App/actions.js +19 -7
  17. package/admin/src/content-manager/pages/App/constants.js +3 -3
  18. package/admin/src/content-manager/pages/App/index.js +5 -4
  19. package/admin/src/content-manager/pages/App/reducer.js +7 -6
  20. package/admin/src/content-manager/pages/App/selectors.js +3 -0
  21. package/admin/src/content-manager/pages/App/{useModels.js → useContentManagerInitData.js} +29 -28
  22. package/admin/src/content-manager/pages/App/utils/generateModelsLinks.js +2 -2
  23. package/admin/src/content-manager/pages/App/utils/getContentTypeLinks.js +17 -15
  24. package/admin/src/content-manager/pages/EditSettingsView/components/ModalForm.js +6 -5
  25. package/admin/src/content-manager/pages/EditSettingsView/index.js +4 -0
  26. package/admin/src/content-manager/pages/EditSettingsView/reducer.js +12 -7
  27. package/admin/src/content-manager/pages/EditSettingsView/utils/layout.js +1 -30
  28. package/admin/src/content-manager/pages/EditView/DeleteLink/index.js +5 -11
  29. package/admin/src/content-manager/pages/EditView/index.js +2 -7
  30. package/admin/src/content-manager/pages/EditViewLayoutManager/reducer.js +4 -4
  31. package/admin/src/content-manager/pages/ListSettingsView/index.js +1 -0
  32. package/admin/src/hooks/useConfigurations/__mocks__/index.js +7 -0
  33. package/admin/src/hooks/useFetchMarketplacePlugins/utils/api.js +7 -8
  34. package/admin/src/hooks/useFetchMarketplaceProviders/utils/api.js +5 -0
  35. package/admin/src/hooks/useFetchPermissionsLayout/index.js +24 -15
  36. package/admin/src/hooks/useFetchRole/index.js +37 -30
  37. package/admin/src/hooks/useModels/index.js +22 -12
  38. package/admin/src/hooks/useRegenerate/index.js +12 -7
  39. package/admin/src/hooks/useSettingsForm/index.js +14 -6
  40. package/admin/src/pages/App/index.js +19 -24
  41. package/admin/src/pages/AuthPage/components/Register/index.js +46 -38
  42. package/admin/src/pages/HomePage/SocialLinks.js +1 -1
  43. package/admin/src/pages/MarketplacePage/components/EmptyNpmPackageSearch/index.js +3 -3
  44. package/admin/src/pages/MarketplacePage/components/NpmPackagesGrid/index.js +42 -9
  45. package/admin/src/pages/MarketplacePage/components/NpmPackagesPagination/index.js +26 -0
  46. package/admin/src/pages/MarketplacePage/components/OfflineLayout/index.js +45 -0
  47. package/admin/src/pages/MarketplacePage/index.js +80 -175
  48. package/admin/src/pages/MarketplacePage/utils/useMarketplaceData.js +85 -0
  49. package/admin/src/pages/SettingsPage/components/Tokens/FormHead/index.js +4 -0
  50. package/admin/src/pages/SettingsPage/components/Tokens/Regenerate/index.js +5 -3
  51. package/admin/src/pages/SettingsPage/components/Tokens/TokenTypeSelect/index.js +7 -5
  52. package/admin/src/pages/SettingsPage/pages/ApplicationInfosPage/components/LogoModalStepper/PendingLogoDialog.js +1 -3
  53. package/admin/src/pages/SettingsPage/pages/Roles/CreatePage/index.js +6 -12
  54. package/admin/src/pages/SettingsPage/pages/Roles/EditPage/index.js +6 -10
  55. package/admin/src/pages/SettingsPage/pages/Roles/ListPage/components/RoleRow/index.js +12 -4
  56. package/admin/src/pages/SettingsPage/pages/Roles/ListPage/index.js +21 -2
  57. package/admin/src/pages/SettingsPage/pages/TransferTokens/EditView/components/FormTransferTokenContainer/index.js +41 -0
  58. package/admin/src/pages/SettingsPage/pages/TransferTokens/EditView/index.js +53 -9
  59. package/admin/src/pages/SettingsPage/pages/TransferTokens/EditView/utils/schema.js +1 -0
  60. package/admin/src/pages/SettingsPage/pages/TransferTokens/ListView/index.js +27 -5
  61. package/admin/src/pages/SettingsPage/pages/Webhooks/EditView/index.js +18 -33
  62. package/admin/src/pages/SettingsPage/pages/Webhooks/ListView/index.js +41 -41
  63. package/admin/src/translations/en.json +52 -50
  64. package/admin/src/translations/fr.json +89 -1
  65. package/admin/src/translations/ru.json +51 -19
  66. package/build/1387.84b454d3.chunk.js +1 -0
  67. package/build/1657.45231968.chunk.js +168 -0
  68. package/build/3081.bcf9a12f.chunk.js +108 -0
  69. package/build/462.8fff7f3b.chunk.js +71 -0
  70. package/build/4628.20631dd1.chunk.js +1 -0
  71. package/build/5542.b8240e3f.chunk.js +70 -0
  72. package/build/5563.905daa13.chunk.js +79 -0
  73. package/build/6404.68405699.chunk.js +100 -0
  74. package/build/7259.b7d00cea.chunk.js +1 -0
  75. package/build/8694.6522968d.chunk.js +247 -0
  76. package/build/Admin-authenticatedApp.b036fe95.chunk.js +79 -0
  77. package/build/Admin_InternalErrorPage.15c6bf07.chunk.js +1 -0
  78. package/build/Admin_homePage.f9309c6d.chunk.js +73 -0
  79. package/build/Admin_marketplace.56bc1008.chunk.js +31 -0
  80. package/build/Admin_pluginsPage.f6b52ee9.chunk.js +6 -0
  81. package/build/Admin_profilePage.9112cffc.chunk.js +15 -0
  82. package/build/Admin_settingsPage.4604a16c.chunk.js +79 -0
  83. package/build/Upload_ConfigureTheView.eaaec495.chunk.js +1 -0
  84. package/build/admin-app.014adc27.chunk.js +110 -0
  85. package/build/admin-edit-roles-page.8a4063f7.chunk.js +280 -0
  86. package/build/admin-edit-users.7e14d85f.chunk.js +10 -0
  87. package/build/admin-roles-list.329c1f63.chunk.js +31 -0
  88. package/build/admin-users.d02de059.chunk.js +34 -0
  89. package/build/api-tokens-create-page.97595e12.chunk.js +1 -0
  90. package/build/api-tokens-edit-page.cd36e30e.chunk.js +1 -0
  91. package/build/api-tokens-list-page.6757c7b9.chunk.js +16 -0
  92. package/build/audit-logs-settings-page.19d90bda.chunk.js +76 -0
  93. package/build/content-manager.84f81966.chunk.js +1130 -0
  94. package/build/content-type-builder-list-view.9c2c020c.chunk.js +214 -0
  95. package/build/{content-type-builder-translation-de-json.0979cccb.chunk.js → content-type-builder-translation-de-json.393a76c0.chunk.js} +1 -1
  96. package/build/{content-type-builder-translation-dk-json.e05583e9.chunk.js → content-type-builder-translation-dk-json.fbd39bb7.chunk.js} +1 -1
  97. package/build/content-type-builder-translation-en-json.446b611d.chunk.js +1 -0
  98. package/build/{content-type-builder-translation-es-json.fe4daad8.chunk.js → content-type-builder-translation-es-json.9288474b.chunk.js} +1 -1
  99. package/build/{content-type-builder-translation-fr-json.b1eb52f6.chunk.js → content-type-builder-translation-fr-json.d35e269c.chunk.js} +1 -1
  100. package/build/{content-type-builder-translation-id-json.ee3b36bb.chunk.js → content-type-builder-translation-id-json.f0513929.chunk.js} +1 -1
  101. package/build/{content-type-builder-translation-it-json.13b3c26a.chunk.js → content-type-builder-translation-it-json.aaf16753.chunk.js} +1 -1
  102. package/build/{content-type-builder-translation-ko-json.8a274be5.chunk.js → content-type-builder-translation-ko-json.8fe21a7f.chunk.js} +1 -1
  103. package/build/{content-type-builder-translation-ms-json.2d29c1e0.chunk.js → content-type-builder-translation-ms-json.3b5d2d3e.chunk.js} +1 -1
  104. package/build/{content-type-builder-translation-nl-json.40bbc562.chunk.js → content-type-builder-translation-nl-json.225ef5d3.chunk.js} +1 -1
  105. package/build/{content-type-builder-translation-pl-json.24a34349.chunk.js → content-type-builder-translation-pl-json.92f36be2.chunk.js} +1 -1
  106. package/build/{content-type-builder-translation-pt-BR-json.97f71a9d.chunk.js → content-type-builder-translation-pt-BR-json.3bd10f89.chunk.js} +1 -1
  107. package/build/{content-type-builder-translation-ru-json.54d11230.chunk.js → content-type-builder-translation-ru-json.9bfe47ce.chunk.js} +1 -1
  108. package/build/{content-type-builder-translation-sk-json.626c9493.chunk.js → content-type-builder-translation-sk-json.d03cc18a.chunk.js} +1 -1
  109. package/build/{content-type-builder-translation-sv-json.59f5e1e5.chunk.js → content-type-builder-translation-sv-json.d23dcd32.chunk.js} +1 -1
  110. package/build/{content-type-builder-translation-th-json.6fe3ed55.chunk.js → content-type-builder-translation-th-json.7ad256e2.chunk.js} +1 -1
  111. package/build/{content-type-builder-translation-tr-json.cea4d226.chunk.js → content-type-builder-translation-tr-json.926f6191.chunk.js} +1 -1
  112. package/build/{content-type-builder-translation-uk-json.c4524247.chunk.js → content-type-builder-translation-uk-json.7bf19546.chunk.js} +1 -1
  113. package/build/{content-type-builder-translation-zh-json.faedd610.chunk.js → content-type-builder-translation-zh-json.ad24dbeb.chunk.js} +1 -1
  114. package/build/content-type-builder.68af11d2.chunk.js +126 -0
  115. package/build/email-settings-page.1095e1ab.chunk.js +10 -0
  116. package/build/en-json.c7fc79af.chunk.js +1 -0
  117. package/build/fr-json.5947cf63.chunk.js +1 -0
  118. package/build/{highlight.js.26ef649f.chunk.js → highlight.js.28a1547e.chunk.js} +2 -2
  119. package/build/i18n-settings-page.d95b32df.chunk.js +60 -0
  120. package/build/index.html +1 -1
  121. package/build/main.841e0dcb.js +2280 -0
  122. package/build/review-workflows-settings.f7890c40.chunk.js +106 -0
  123. package/build/ru-json.e0662702.chunk.js +1 -0
  124. package/build/{runtime~main.5a95bee6.js → runtime~main.965f8af8.js} +1 -1
  125. package/build/sso-settings-page.1dd4886e.chunk.js +1 -0
  126. package/build/transfer-tokens-create-page.ec2ca215.chunk.js +1 -0
  127. package/build/transfer-tokens-edit-page.22bf28e5.chunk.js +1 -0
  128. package/build/transfer-tokens-list-page.cf8c77f2.chunk.js +16 -0
  129. package/build/upload-settings.945fdcfa.chunk.js +13 -0
  130. package/build/{upload-translation-th-json.3847dae0.chunk.js → upload-translation-th-json.98d35574.chunk.js} +1 -1
  131. package/build/upload.a86b1054.chunk.js +33 -0
  132. package/build/users-advanced-settings-page.5b5a9baa.chunk.js +8 -0
  133. package/build/users-email-settings-page.e5506eb4.chunk.js +23 -0
  134. package/build/users-providers-settings-page.e32089c2.chunk.js +28 -0
  135. package/build/users-roles-settings-page.20656f92.chunk.js +30 -0
  136. package/build/webhook-edit-page.a3b62049.chunk.js +75 -0
  137. package/build/webhook-list-page.ca38eeef.chunk.js +71 -0
  138. package/{admin/src/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/ReviewWorkflowsStage.js → ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/ReviewWorkflowsStageEE.js} +2 -2
  139. package/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn.js +47 -0
  140. package/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/index.js +3 -0
  141. package/ee/admin/content-manager/pages/EditView/InformationBox/InformationBoxEE.js +64 -18
  142. package/ee/admin/hooks/useAuthProviders/index.js +28 -29
  143. package/ee/admin/hooks/useLicenseLimitNotification/index.js +1 -1
  144. package/ee/admin/pages/AuthResponse/index.js +7 -3
  145. package/ee/admin/pages/SettingsPage/pages/AuditLogs/ListView/hooks/useAuditLogsData.js +6 -3
  146. package/ee/admin/pages/SettingsPage/pages/AuditLogs/ListView/index.js +15 -5
  147. package/ee/admin/pages/SettingsPage/pages/AuditLogs/ListView/utils/getDisplayedFilters.js +52 -45
  148. package/ee/admin/pages/SettingsPage/pages/ReviewWorkflows/ReviewWorkflows.js +9 -5
  149. package/ee/admin/pages/SettingsPage/pages/ReviewWorkflows/components/Stages/Stage/Stage.js +2 -2
  150. package/ee/admin/pages/SettingsPage/pages/ReviewWorkflows/hooks/useReviewWorkflows.js +2 -2
  151. package/ee/admin/pages/SettingsPage/pages/ReviewWorkflows/reducer/index.js +2 -1
  152. package/ee/server/content-types/workflow/index.js +0 -3
  153. package/ee/server/content-types/workflow-stage/index.js +0 -5
  154. package/ee/server/controllers/authentication/middlewares.js +2 -1
  155. package/ee/server/controllers/workflows/stages/index.js +8 -1
  156. package/ee/server/register.js +3 -1
  157. package/ee/server/services/audit-logs.js +75 -16
  158. package/ee/server/services/index.js +1 -0
  159. package/ee/server/services/review-workflows/entity-service-decorator.js +17 -5
  160. package/ee/server/services/review-workflows/metrics.js +24 -0
  161. package/ee/server/services/review-workflows/review-workflows.js +44 -94
  162. package/ee/server/services/review-workflows/stages.js +136 -17
  163. package/ee/server/utils/persisted-tables.js +116 -22
  164. package/ee/server/utils/review-workflows.js +9 -0
  165. package/jest.config.front.js +1 -6
  166. package/package.json +25 -23
  167. package/server/controllers/transfer/runner.js +4 -2
  168. package/server/middlewares/data-transfer.js +4 -1
  169. package/server/routes/transfer.js +13 -4
  170. package/server/services/constants.js +4 -0
  171. package/server/services/transfer/permission.js +1 -1
  172. package/server/services/transfer/token.js +33 -31
  173. package/server/strategies/api-token.js +8 -1
  174. package/server/validation/transfer/token.js +10 -2
  175. package/webpack.config.js +6 -2
  176. package/admin/src/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/index.js +0 -1
  177. package/admin/src/content-manager/pages/App/LeftMenu/utils/index.js +0 -1
  178. package/admin/src/content-manager/pages/App/LeftMenu/utils/matchByTitle.js +0 -24
  179. package/build/2263.4c5916f9.chunk.js +0 -98
  180. package/build/4049.64715f20.chunk.js +0 -1
  181. package/build/4649.213b8a3b.chunk.js +0 -30
  182. package/build/6985.66cca29c.chunk.js +0 -1
  183. package/build/7259.aefb51e8.chunk.js +0 -1
  184. package/build/8469.853c822b.chunk.js +0 -1
  185. package/build/9505.dbe702ab.chunk.js +0 -14
  186. package/build/9816.01ee964f.chunk.js +0 -2
  187. package/build/Admin-authenticatedApp.f50ad423.chunk.js +0 -79
  188. package/build/Admin_InternalErrorPage.4ad8b0df.chunk.js +0 -1
  189. package/build/Admin_homePage.1411fb7c.chunk.js +0 -68
  190. package/build/Admin_marketplace.02608d56.chunk.js +0 -22
  191. package/build/Admin_pluginsPage.15e3b0fd.chunk.js +0 -1
  192. package/build/Admin_profilePage.76afeca0.chunk.js +0 -15
  193. package/build/Admin_settingsPage.147755cd.chunk.js +0 -9
  194. package/build/Upload_ConfigureTheView.34dde278.chunk.js +0 -1
  195. package/build/admin-app.55dd7921.chunk.js +0 -112
  196. package/build/admin-edit-roles-page.cf543488.chunk.js +0 -216
  197. package/build/admin-edit-users.31c20712.chunk.js +0 -10
  198. package/build/admin-roles-list.489c501f.chunk.js +0 -2
  199. package/build/admin-users.3e111a7d.chunk.js +0 -11
  200. package/build/api-tokens-create-page.4328b852.chunk.js +0 -1
  201. package/build/api-tokens-edit-page.bce5050f.chunk.js +0 -1
  202. package/build/api-tokens-list-page.93f24348.chunk.js +0 -16
  203. package/build/audit-logs-settings-page.7be97e82.chunk.js +0 -1
  204. package/build/content-manager.4480ae88.chunk.js +0 -1137
  205. package/build/content-type-builder-list-view.cf38fe2f.chunk.js +0 -191
  206. package/build/content-type-builder-translation-en-json.7961593e.chunk.js +0 -1
  207. package/build/content-type-builder.af9abf1e.chunk.js +0 -126
  208. package/build/email-settings-page.4bdbef9a.chunk.js +0 -3
  209. package/build/en-json.697b4bcf.chunk.js +0 -1
  210. package/build/fr-json.f66c3211.chunk.js +0 -1
  211. package/build/i18n-settings-page.2bb5be96.chunk.js +0 -1
  212. package/build/main.af8c0f31.js +0 -3790
  213. package/build/review-workflows-settings.7a7dc773.chunk.js +0 -57
  214. package/build/ru-json.6a01cea6.chunk.js +0 -1
  215. package/build/sso-settings-page.272b87c8.chunk.js +0 -1
  216. package/build/transfer-tokens-create-page.a1f14bb1.chunk.js +0 -1
  217. package/build/transfer-tokens-edit-page.00ee1c74.chunk.js +0 -1
  218. package/build/transfer-tokens-list-page.ce37354b.chunk.js +0 -16
  219. package/build/upload-settings.0875e973.chunk.js +0 -1
  220. package/build/upload.c7da1611.chunk.js +0 -13
  221. package/build/users-advanced-settings-page.1d3c14c7.chunk.js +0 -1
  222. package/build/users-email-settings-page.e8db68c4.chunk.js +0 -1
  223. package/build/users-providers-settings-page.14cac425.chunk.js +0 -1
  224. package/build/users-roles-settings-page.2ea4de84.chunk.js +0 -30
  225. package/build/webhook-edit-page.329141a5.chunk.js +0 -23
  226. package/build/webhook-list-page.029957a4.chunk.js +0 -1
  227. package/ee/server/migrations/review-workflows.js +0 -39
  228. package/ee/server/utils/test.js +0 -11
  229. /package/admin/src/{content-manager/components/InputUID/useDebounce.js → hooks/useDebounce/index.js} +0 -0
@@ -12,18 +12,18 @@ export const initialState = {
12
12
 
13
13
  const editViewManagerReducer = (state = initialState, action) =>
14
14
  // eslint-disable-next-line consistent-return
15
- produce(state, (drafState) => {
15
+ produce(state, (draftState) => {
16
16
  switch (action.type) {
17
17
  case RESET_PROPS: {
18
- drafState.currentLayout = null;
18
+ draftState.currentLayout = null;
19
19
  break;
20
20
  }
21
21
  case SET_LAYOUT: {
22
- drafState.currentLayout = action.layout;
22
+ draftState.currentLayout = action.layout;
23
23
  break;
24
24
  }
25
25
  default:
26
- return drafState;
26
+ return draftState;
27
27
  }
28
28
  });
29
29
 
@@ -127,6 +127,7 @@ const ListSettingsView = ({ layout, slug }) => {
127
127
  dispatch({
128
128
  type: 'SUBMIT_FIELD_FORM',
129
129
  });
130
+ handleCloseModal();
130
131
  };
131
132
 
132
133
  const submitMutation = useMutation((body) => putCMSettingsLV(body, slug), {
@@ -0,0 +1,7 @@
1
+ export default function () {
2
+ return {
3
+ logos: {
4
+ auth: { custom: 'customAuthLogo.png', default: 'defaultAuthLogo.png' },
5
+ },
6
+ };
7
+ }
@@ -1,19 +1,18 @@
1
1
  import axios from 'axios';
2
+ import qs from 'qs';
2
3
 
3
4
  const MARKETPLACE_API_URL = 'https://market-api.strapi.io';
4
5
 
5
6
  const fetchMarketplacePlugins = async (params = {}) => {
6
- const { data: response } = await axios.get(`${MARKETPLACE_API_URL}/plugins`, {
7
+ const { data } = await axios.get(`${MARKETPLACE_API_URL}/plugins`, {
7
8
  params,
9
+ paramsSerializer: {
10
+ encode: qs.parse,
11
+ serialize: qs.stringify,
12
+ },
8
13
  });
9
14
 
10
- // Only keep v4 plugins
11
- const filteredResponse = {
12
- ...response,
13
- data: response.data.filter((plugin) => plugin.attributes.strapiCompatibility === 'v4'),
14
- };
15
-
16
- return filteredResponse;
15
+ return data;
17
16
  };
18
17
 
19
18
  export { fetchMarketplacePlugins };
@@ -1,10 +1,15 @@
1
1
  import axios from 'axios';
2
+ import qs from 'qs';
2
3
 
3
4
  const MARKETPLACE_API_URL = 'https://market-api.strapi.io';
4
5
 
5
6
  const fetchMarketplaceProviders = async (params = {}) => {
6
7
  const { data } = await axios.get(`${MARKETPLACE_API_URL}/providers`, {
7
8
  params,
9
+ paramsSerializer: {
10
+ encode: qs.parse,
11
+ serialize: qs.stringify,
12
+ },
8
13
  });
9
14
 
10
15
  return data;
@@ -1,30 +1,39 @@
1
1
  import { useEffect, useReducer } from 'react';
2
- import { request } from '@strapi/helper-plugin';
2
+ import { useFetchClient } from '@strapi/helper-plugin';
3
3
 
4
4
  import reducer, { initialState } from './reducer';
5
5
 
6
+ /**
7
+ * TODO: refactor this to use react-query and move it to the `Roles` SettingsPage
8
+ */
6
9
  const useFetchPermissionsLayout = (id) => {
7
10
  const [{ data, error, isLoading }, dispatch] = useReducer(reducer, initialState);
11
+ const { get } = useFetchClient();
8
12
 
9
13
  useEffect(() => {
10
14
  const getData = async () => {
11
- dispatch({
12
- type: 'GET_DATA',
13
- });
14
-
15
- const { data } = await request('/admin/permissions', {
16
- method: 'GET',
17
- params: { role: id },
18
- });
19
-
20
- dispatch({
21
- type: 'GET_DATA_SUCCEEDED',
22
- data,
23
- });
15
+ try {
16
+ dispatch({
17
+ type: 'GET_DATA',
18
+ });
19
+
20
+ const {
21
+ data: { data },
22
+ } = await get('/admin/permissions', {
23
+ params: { role: id },
24
+ });
25
+
26
+ dispatch({
27
+ type: 'GET_DATA_SUCCEEDED',
28
+ data,
29
+ });
30
+ } catch (err) {
31
+ // silence is golden
32
+ }
24
33
  };
25
34
 
26
35
  getData();
27
- }, [id]);
36
+ }, [id, get]);
28
37
 
29
38
  return { data, error, isLoading };
30
39
  };
@@ -1,13 +1,48 @@
1
1
  import { useCallback, useReducer, useEffect } from 'react';
2
- import { request, useNotification } from '@strapi/helper-plugin';
2
+ import { useFetchClient, useNotification } from '@strapi/helper-plugin';
3
3
  import reducer, { initialState } from './reducer';
4
4
 
5
5
  const useFetchRole = (id) => {
6
6
  const toggleNotification = useNotification();
7
7
  const [state, dispatch] = useReducer(reducer, initialState);
8
8
 
9
+ const { get } = useFetchClient();
10
+
9
11
  useEffect(() => {
10
12
  if (id) {
13
+ const fetchRole = async (roleId) => {
14
+ try {
15
+ const [
16
+ {
17
+ data: { data: role },
18
+ },
19
+ {
20
+ data: { data: permissions },
21
+ },
22
+ ] = await Promise.all(
23
+ [`roles/${roleId}`, `roles/${roleId}/permissions`].map((endPoint) =>
24
+ get(`/admin/${endPoint}`)
25
+ )
26
+ );
27
+
28
+ dispatch({
29
+ type: 'GET_DATA_SUCCEEDED',
30
+ role,
31
+ permissions,
32
+ });
33
+ } catch (err) {
34
+ console.error(err);
35
+
36
+ dispatch({
37
+ type: 'GET_DATA_ERROR',
38
+ });
39
+ toggleNotification({
40
+ type: 'warning',
41
+ message: { id: 'notification.error' },
42
+ });
43
+ }
44
+ };
45
+
11
46
  fetchRole(id);
12
47
  } else {
13
48
  dispatch({
@@ -16,35 +51,7 @@ const useFetchRole = (id) => {
16
51
  permissions: [],
17
52
  });
18
53
  }
19
-
20
- // eslint-disable-next-line react-hooks/exhaustive-deps
21
- }, [id]);
22
-
23
- const fetchRole = async (roleId) => {
24
- try {
25
- const [{ data: role }, { data: permissions }] = await Promise.all(
26
- [`roles/${roleId}`, `roles/${roleId}/permissions`].map((endPoint) =>
27
- request(`/admin/${endPoint}`, { method: 'GET' })
28
- )
29
- );
30
-
31
- dispatch({
32
- type: 'GET_DATA_SUCCEEDED',
33
- role,
34
- permissions,
35
- });
36
- } catch (err) {
37
- console.error(err);
38
-
39
- dispatch({
40
- type: 'GET_DATA_ERROR',
41
- });
42
- toggleNotification({
43
- type: 'warning',
44
- message: { id: 'notification.error' },
45
- });
46
- }
47
- };
54
+ }, [get, id, toggleNotification]);
48
55
 
49
56
  const handleSubmitSucceeded = useCallback((data) => {
50
57
  dispatch({
@@ -1,26 +1,32 @@
1
- import { useReducer, useEffect } from 'react';
2
- import { request, useNotification } from '@strapi/helper-plugin';
1
+ import { useReducer, useEffect, useCallback } from 'react';
2
+ import { useFetchClient, useNotification } from '@strapi/helper-plugin';
3
3
  import reducer, { initialState } from './reducer';
4
4
 
5
+ /**
6
+ * TODO: refactor this to not use the `useReducer` hook,
7
+ * it's not really necessary. Also use `useQuery`?
8
+ */
5
9
  const useModels = () => {
6
10
  const toggleNotification = useNotification();
7
11
  const [state, dispatch] = useReducer(reducer, initialState);
8
12
 
9
- useEffect(() => {
10
- fetchModels();
11
- // eslint-disable-next-line react-hooks/exhaustive-deps
12
- }, []);
13
+ const { get } = useFetchClient();
13
14
 
14
- const fetchModels = async () => {
15
+ const fetchModels = useCallback(async () => {
15
16
  dispatch({
16
17
  type: 'GET_MODELS',
17
18
  });
18
19
 
19
20
  try {
20
- const [{ data: components }, { data: contentTypes }] = await Promise.all(
21
- ['components', 'content-types'].map((endPoint) =>
22
- request(`/content-manager/${endPoint}`, { method: 'GET' })
23
- )
21
+ const [
22
+ {
23
+ data: { data: components },
24
+ },
25
+ {
26
+ data: { data: contentTypes },
27
+ },
28
+ ] = await Promise.all(
29
+ ['components', 'content-types'].map((endPoint) => get(`/content-manager/${endPoint}`))
24
30
  );
25
31
 
26
32
  dispatch({
@@ -37,7 +43,11 @@ const useModels = () => {
37
43
  message: { id: 'notification.error' },
38
44
  });
39
45
  }
40
- };
46
+ }, [toggleNotification, get]);
47
+
48
+ useEffect(() => {
49
+ fetchModels();
50
+ }, [fetchModels]);
41
51
 
42
52
  return {
43
53
  ...state,
@@ -1,11 +1,11 @@
1
1
  import { useState } from 'react';
2
- import get from 'lodash/get';
3
- import { useFetchClient, useNotification } from '@strapi/helper-plugin';
2
+ import { useFetchClient, useNotification, useAPIErrorHandler } from '@strapi/helper-plugin';
4
3
 
5
- const useRegenerate = (url, id, onRegenerate) => {
4
+ const useRegenerate = (url, id, onRegenerate, onError) => {
6
5
  const [isLoadingConfirmation, setIsLoadingConfirmation] = useState(false);
7
6
  const toggleNotification = useNotification();
8
7
  const { post } = useFetchClient();
8
+ const { formatAPIError } = useAPIErrorHandler();
9
9
 
10
10
  const regenerateData = async () => {
11
11
  try {
@@ -18,10 +18,15 @@ const useRegenerate = (url, id, onRegenerate) => {
18
18
  onRegenerate(accessKey);
19
19
  } catch (error) {
20
20
  setIsLoadingConfirmation(false);
21
- toggleNotification({
22
- type: 'warning',
23
- message: get(error, 'response.data.message', 'notification.error'),
24
- });
21
+
22
+ if (onError) {
23
+ onError(error);
24
+ } else {
25
+ toggleNotification({
26
+ type: 'warning',
27
+ message: formatAPIError(error),
28
+ });
29
+ }
25
30
  }
26
31
  };
27
32
 
@@ -1,10 +1,15 @@
1
1
  import { useEffect, useReducer } from 'react';
2
- import { request, useNotification, useOverlayBlocker } from '@strapi/helper-plugin';
2
+ import { useFetchClient, useNotification, useOverlayBlocker } from '@strapi/helper-plugin';
3
3
  import omit from 'lodash/omit';
4
4
  import { checkFormValidity, formatAPIErrors } from '../../utils';
5
5
  import { initialState, reducer } from './reducer';
6
6
  import init from './init';
7
7
 
8
+ /**
9
+ * TODO: refactor this, it's confusing and hard to read.
10
+ * It's also only used in `Settings/pages/SingleSignOn` so it can
11
+ * probably be deleted and everything written there...
12
+ */
8
13
  const useSettingsForm = (endPoint, schema, cbSuccess, fieldsToPick) => {
9
14
  const [
10
15
  { formErrors, initialData, isLoading, modifiedData, showHeaderButtonLoader, showHeaderLoader },
@@ -13,10 +18,14 @@ const useSettingsForm = (endPoint, schema, cbSuccess, fieldsToPick) => {
13
18
  const toggleNotification = useNotification();
14
19
  const { lockApp, unlockApp } = useOverlayBlocker();
15
20
 
21
+ const { get, put } = useFetchClient();
22
+
16
23
  useEffect(() => {
17
24
  const getData = async () => {
18
25
  try {
19
- const { data } = await request(endPoint, { method: 'GET' });
26
+ const {
27
+ data: { data },
28
+ } = await get(endPoint);
20
29
 
21
30
  dispatch({
22
31
  type: 'GET_DATA_SUCCEEDED',
@@ -85,10 +94,9 @@ const useSettingsForm = (endPoint, schema, cbSuccess, fieldsToPick) => {
85
94
  cleanedData.roles = cleanedData.roles.map((role) => role.id);
86
95
  }
87
96
 
88
- const { data } = await request(endPoint, {
89
- method: 'PUT',
90
- body: cleanedData,
91
- });
97
+ const {
98
+ data: { data },
99
+ } = await put(endPoint, cleanedData);
92
100
 
93
101
  cbSuccess(data);
94
102
 
@@ -6,17 +6,16 @@
6
6
 
7
7
  import React, { useEffect, useState, useMemo, lazy, Suspense } from 'react';
8
8
  import { Switch, Route } from 'react-router-dom';
9
+ import axios from 'axios';
9
10
  import {
10
11
  LoadingIndicatorPage,
11
12
  auth,
12
- request,
13
13
  useNotification,
14
14
  TrackingProvider,
15
15
  prefixFileUrlWithBackendUrl,
16
16
  useAppInfos,
17
17
  useFetchClient,
18
18
  } from '@strapi/helper-plugin';
19
- import axios from 'axios';
20
19
  import { SkipToContent } from '@strapi/design-system';
21
20
  import { useIntl } from 'react-intl';
22
21
  import PrivateRoute from '../../components/PrivateRoute';
@@ -41,7 +40,7 @@ function App() {
41
40
  hasAdmin: false,
42
41
  });
43
42
  const appInfo = useAppInfos();
44
- const { get } = useFetchClient();
43
+ const { get, post } = useFetchClient();
45
44
 
46
45
  const authRoutes = useMemo(() => {
47
46
  return makeUniqueRoutes(
@@ -57,11 +56,10 @@ function App() {
57
56
  const renewToken = async () => {
58
57
  try {
59
58
  const {
60
- data: { token },
61
- } = await request('/admin/renew-token', {
62
- method: 'POST',
63
- body: { token: currentToken },
64
- });
59
+ data: {
60
+ data: { token },
61
+ },
62
+ } = await post('/admin/renew-token', { token: currentToken });
65
63
  auth.updateToken(token);
66
64
  } catch (err) {
67
65
  // Refresh app
@@ -73,7 +71,7 @@ function App() {
73
71
  if (currentToken) {
74
72
  renewToken();
75
73
  }
76
- }, []);
74
+ }, [post]);
77
75
 
78
76
  useEffect(() => {
79
77
  const getData = async () => {
@@ -82,7 +80,7 @@ function App() {
82
80
  data: {
83
81
  data: { hasAdmin, uuid, menuLogo, authLogo },
84
82
  },
85
- } = await axios.get(`${strapi.backendURL}/admin/init`);
83
+ } = await get(`/admin/init`);
86
84
 
87
85
  updateProjectSettings({
88
86
  menuLogo: prefixFileUrlWithBackendUrl(menuLogo),
@@ -102,20 +100,17 @@ function App() {
102
100
  setTelemetryProperties(properties);
103
101
 
104
102
  try {
105
- await fetch('https://analytics.strapi.io/api/v2/track', {
106
- method: 'POST',
107
- body: JSON.stringify({
108
- // This event is anonymous
109
- event: 'didInitializeAdministration',
110
- userId: '',
111
- deviceId,
112
- eventPropeties: {},
113
- userProperties: { environment: appInfo.currentEnvironment },
114
- groupProperties: { ...properties, projectId: uuid },
115
- }),
116
- headers: {
117
- 'Content-Type': 'application/json',
118
- },
103
+ /**
104
+ * TODO: remove this call to `axios`
105
+ */
106
+ await axios.post('https://analytics.strapi.io/api/v2/track', {
107
+ // This event is anonymous
108
+ event: 'didInitializeAdministration',
109
+ userId: '',
110
+ deviceId,
111
+ eventPropeties: {},
112
+ userProperties: { environment: appInfo.currentEnvironment },
113
+ groupProperties: { ...properties, projectId: uuid },
119
114
  });
120
115
  } catch (e) {
121
116
  // Silent.
@@ -1,7 +1,6 @@
1
1
  import React, { useState, useEffect } from 'react';
2
2
  import { useIntl } from 'react-intl';
3
3
  import styled from 'styled-components';
4
- import get from 'lodash/get';
5
4
  import omit from 'lodash/omit';
6
5
  import { useHistory } from 'react-router-dom';
7
6
  import PropTypes from 'prop-types';
@@ -14,6 +13,7 @@ import {
14
13
  useTracking,
15
14
  getYupInnerErrors,
16
15
  Link,
16
+ useAPIErrorHandler,
17
17
  } from '@strapi/helper-plugin';
18
18
  import {
19
19
  Box,
@@ -27,17 +27,10 @@ import {
27
27
  Typography,
28
28
  } from '@strapi/design-system';
29
29
  import { EyeStriked, Eye } from '@strapi/icons';
30
- import UnauthenticatedLayout, {
31
- Column,
32
- LayoutContent,
33
- } from '../../../../layouts/UnauthenticatedLayout';
30
+ import UnauthenticatedLayout, { LayoutContent } from '../../../../layouts/UnauthenticatedLayout';
34
31
  import Logo from '../../../../components/UnauthenticatedLogo';
35
32
  import FieldActionWrapper from '../FieldActionWrapper';
36
33
 
37
- const CenteredBox = styled(Box)`
38
- text-align: center;
39
- `;
40
-
41
34
  const A = styled.a`
42
35
  color: ${({ theme }) => theme.colors.primary600};
43
36
  `;
@@ -58,6 +51,8 @@ const Register = ({ authType, fieldsToDisable, noSignin, onSubmit, schema }) =>
58
51
  const { trackUsage } = useTracking();
59
52
  const { formatMessage } = useIntl();
60
53
  const query = useQuery();
54
+ const { formatAPIError } = useAPIErrorHandler();
55
+
61
56
  const registrationToken = query.get('registrationToken');
62
57
 
63
58
  useEffect(() => {
@@ -73,17 +68,17 @@ const Register = ({ authType, fieldsToDisable, noSignin, onSubmit, schema }) =>
73
68
  if (data) {
74
69
  setUserInfo(data);
75
70
  }
76
- } catch (err) {
77
- const errorMessage = get(err, ['response', 'data', 'message'], 'An error occurred');
71
+ } catch (error) {
72
+ const message = formatAPIError(error);
78
73
 
79
74
  toggleNotification({
80
75
  type: 'warning',
81
- message: errorMessage,
76
+ message,
82
77
  });
83
78
 
84
79
  // Redirect to the oops page in case of an invalid token
85
80
  // @alexandrebodin @JAB I am not sure it is the wanted behavior
86
- push(`/auth/oops?info=${encodeURIComponent(errorMessage)}`);
81
+ push(`/auth/oops?info=${encodeURIComponent(message)}`);
87
82
  }
88
83
  };
89
84
 
@@ -92,6 +87,20 @@ const Register = ({ authType, fieldsToDisable, noSignin, onSubmit, schema }) =>
92
87
  // eslint-disable-next-line react-hooks/exhaustive-deps
93
88
  }, [registrationToken]);
94
89
 
90
+ function normalizeData(data) {
91
+ return Object.entries(data).reduce((acc, [key, value]) => {
92
+ let normalizedvalue = value;
93
+
94
+ if (!['password', 'confirmPassword'].includes(key) && typeof value === 'string') {
95
+ normalizedvalue = normalizedvalue.trim();
96
+ }
97
+
98
+ acc[key] = normalizedvalue;
99
+
100
+ return acc;
101
+ }, {});
102
+ }
103
+
95
104
  return (
96
105
  <UnauthenticatedLayout>
97
106
  <LayoutContent>
@@ -107,8 +116,10 @@ const Register = ({ authType, fieldsToDisable, noSignin, onSubmit, schema }) =>
107
116
  news: false,
108
117
  }}
109
118
  onSubmit={async (data, formik) => {
119
+ const normalizedData = normalizeData(data);
120
+
110
121
  try {
111
- await schema.validate(data, { abortEarly: false });
122
+ await schema.validate(normalizedData, { abortEarly: false });
112
123
 
113
124
  if (submitCount > 0 && authType === 'register-admin') {
114
125
  trackUsage('didSubmitWithErrorsFirstAdmin', { count: submitCount.toString() });
@@ -117,11 +128,11 @@ const Register = ({ authType, fieldsToDisable, noSignin, onSubmit, schema }) =>
117
128
  if (registrationToken) {
118
129
  // We need to pass the registration token in the url param to the api in order to submit another admin user
119
130
  onSubmit(
120
- { userInfo: omit(data, ['registrationToken']), registrationToken },
131
+ { userInfo: omit(normalizedData, ['registrationToken']), registrationToken },
121
132
  formik
122
133
  );
123
134
  } else {
124
- onSubmit(data, formik);
135
+ onSubmit(normalizedData, formik);
125
136
  }
126
137
  } catch (err) {
127
138
  const errors = getYupInnerErrors(err);
@@ -138,27 +149,26 @@ const Register = ({ authType, fieldsToDisable, noSignin, onSubmit, schema }) =>
138
149
  return (
139
150
  <Form noValidate>
140
151
  <Main>
141
- <Column>
152
+ <Flex direction="column" alignItems="stretch" gap={3}>
142
153
  <Logo />
143
- <Box paddingTop={6} paddingBottom={1}>
144
- <Typography as="h1" variant="alpha">
145
- {formatMessage({
146
- id: 'Auth.form.welcome.title',
147
- defaultMessage: 'Welcome to Strapi!',
148
- })}
149
- </Typography>
150
- </Box>
151
- <CenteredBox paddingBottom={7}>
152
- <Typography variant="epsilon" textColor="neutral600">
153
- {formatMessage({
154
- id: 'Auth.form.register.subtitle',
155
- defaultMessage:
156
- 'Credentials are only used to authenticate in Strapi. All saved data will be stored in your database.',
157
- })}
158
- </Typography>
159
- </CenteredBox>
160
- </Column>
161
- <Flex direction="column" alignItems="stretch" gap={6}>
154
+
155
+ <Typography as="h1" variant="alpha" textAlign="center">
156
+ {formatMessage({
157
+ id: 'Auth.form.welcome.title',
158
+ defaultMessage: 'Welcome to Strapi!',
159
+ })}
160
+ </Typography>
161
+
162
+ <Typography variant="epsilon" textColor="neutral600" textAlign="center">
163
+ {formatMessage({
164
+ id: 'Auth.form.register.subtitle',
165
+ defaultMessage:
166
+ 'Credentials are only used to authenticate in Strapi. All saved data will be stored in your database.',
167
+ })}
168
+ </Typography>
169
+ </Flex>
170
+
171
+ <Flex direction="column" alignItems="stretch" gap={6} marginTop={7}>
162
172
  <Grid gap={4}>
163
173
  <GridItem col={6}>
164
174
  <TextInput
@@ -204,7 +214,6 @@ const Register = ({ authType, fieldsToDisable, noSignin, onSubmit, schema }) =>
204
214
  value={values.password}
205
215
  error={errors.password ? formatMessage(errors.password) : undefined}
206
216
  endAction={
207
- // eslint-disable-next-line react/jsx-wrap-multilines
208
217
  <FieldActionWrapper
209
218
  onClick={(e) => {
210
219
  e.preventDefault();
@@ -245,7 +254,6 @@ const Register = ({ authType, fieldsToDisable, noSignin, onSubmit, schema }) =>
245
254
  errors.confirmPassword ? formatMessage(errors.confirmPassword) : undefined
246
255
  }
247
256
  endAction={
248
- // eslint-disable-next-line react/jsx-wrap-multilines
249
257
  <FieldActionWrapper
250
258
  onClick={(e) => {
251
259
  e.preventDefault();
@@ -187,7 +187,7 @@ const SocialLinks = () => {
187
187
  <GridGap>
188
188
  {socialLinksExtended.map(({ icon, link, name }) => {
189
189
  return (
190
- <GridItem col={6} s={12} key={name}>
190
+ <GridItem col={6} s={12} key={name.id}>
191
191
  <LinkCustom size="L" startIcon={icon} variant="tertiary" href={link} isExternal>
192
192
  {formatMessage(name)}
193
193
  </LinkCustom>
@@ -1,16 +1,16 @@
1
1
  import React from 'react';
2
2
  import PropTypes from 'prop-types';
3
3
  import { Typography, Box, Flex, Icon } from '@strapi/design-system';
4
- import { EmptyStateDocument } from '@strapi/icons';
4
+ import { EmptyDocuments } from '@strapi/icons';
5
5
  import { EmptyNpmPackageGrid } from './EmptyNpmPackageGrid';
6
6
 
7
7
  const EmptyNpmPackageSearch = ({ content }) => {
8
8
  return (
9
- <Box position="relative">
9
+ <Box position="relative" data-testid="marketplace-results">
10
10
  <EmptyNpmPackageGrid />
11
11
  <Box position="absolute" top={11} width="100%">
12
12
  <Flex alignItems="center" justifyContent="center" direction="column">
13
- <Icon as={EmptyStateDocument} color="" width="160px" height="88px" />
13
+ <Icon as={EmptyDocuments} color="" width="160px" height="88px" />
14
14
  <Box paddingTop={6}>
15
15
  <Typography variant="delta" as="p" textColor="neutral600">
16
16
  {content}