@strapi/admin 4.14.5 → 4.15.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.
- package/admin/src/StrapiApp.js +13 -12
- package/admin/src/components/AuthenticatedApp.tsx +187 -0
- package/admin/src/components/ConfigurationProvider.tsx +2 -1
- package/admin/src/components/GuidedTour/Homepage.tsx +111 -0
- package/admin/src/components/GuidedTour/Modal.tsx +303 -0
- package/admin/src/components/GuidedTour/Ornaments.tsx +74 -0
- package/admin/src/components/GuidedTour/Provider.tsx +253 -0
- package/admin/src/components/GuidedTour/{layout.js → constants.ts} +13 -3
- package/admin/src/components/LanguageProvider.tsx +1 -0
- package/admin/src/components/Providers.tsx +125 -0
- package/admin/src/components/RBACProvider.tsx +124 -0
- package/admin/src/components/Theme.tsx +4 -2
- package/admin/src/components/ThemeToggleProvider.tsx +23 -9
- package/admin/src/components/__mocks__/{LanguageProvider.js → LanguageProvider.ts} +2 -0
- package/admin/src/{constants.js → constants.ts} +48 -0
- package/admin/src/content-manager/components/BlocksEditor/Toolbar/index.js +75 -51
- package/admin/src/content-manager/components/BlocksEditor/hooks/useBlocksStore.js +72 -14
- package/admin/src/content-manager/pages/App/selectors.js +1 -1
- package/admin/src/content-manager/pages/App/useContentManagerInitData.js +3 -1
- package/admin/src/content-manager/pages/EditView/selectors.js +1 -1
- package/admin/src/content-manager/pages/EditViewLayoutManager/index.js +3 -1
- package/admin/src/content-manager/pages/ListView/components/Body/index.js +53 -56
- package/admin/src/content-manager/pages/ListView/components/BulkActionButtons/SelectedEntriesModal/index.js +5 -3
- package/admin/src/content-manager/pages/ListView/components/TableRows/index.js +1 -1
- package/admin/src/content-manager/pages/ListView/index.js +33 -50
- package/admin/src/content-manager/pages/ListView/selectors.js +1 -1
- package/admin/src/contexts/admin.ts +1 -0
- package/admin/src/contexts/apiTokenPermissions.tsx +64 -0
- package/admin/src/contexts/themeToggle.ts +3 -1
- package/admin/src/core/store/configure.ts +91 -0
- package/admin/src/core/store/hooks.ts +15 -0
- package/admin/src/hooks/index.js +0 -1
- package/admin/src/hooks/{useContentTypes/useContentTypes.js → useContentTypes.ts} +39 -16
- package/admin/src/hooks/useSettingsForm/index.js +14 -2
- package/admin/src/hooks/useSettingsMenu/constants.js +39 -0
- package/admin/src/index.js +2 -4
- package/admin/src/layouts/{AppLayout/index.js → AppLayout.tsx} +7 -10
- package/admin/src/layouts/UnauthenticatedLayout.tsx +77 -0
- package/admin/src/pages/Admin/index.js +11 -5
- package/admin/src/pages/App/index.js +7 -4
- package/admin/src/pages/App/selectors.js +1 -1
- package/admin/src/pages/AuthPage/components/ForgotPassword/index.js +2 -1
- package/admin/src/pages/AuthPage/components/ForgotPasswordSuccess/index.js +2 -1
- package/admin/src/pages/AuthPage/components/Login/index.js +1 -1
- package/admin/src/pages/AuthPage/components/Oops/index.js +2 -1
- package/admin/src/pages/AuthPage/components/Register/index.js +1 -1
- package/admin/src/pages/AuthPage/components/ResetPassword/index.js +2 -1
- package/admin/src/pages/AuthPage/index.js +2 -3
- package/admin/src/pages/HomePage/index.js +6 -3
- package/admin/src/pages/{InternalErrorPage/index.js → InternalErrorPage.tsx} +10 -6
- package/admin/src/pages/{NotFoundPage/index.js → NotFoundPage.tsx} +9 -7
- package/admin/src/pages/ProfilePage/components/Preferences/index.js +23 -9
- package/admin/src/pages/ProfilePage/index.js +1 -1
- package/admin/src/pages/SettingsPage/components/SettingsNav/index.js +20 -0
- package/admin/src/pages/SettingsPage/constants.js +33 -0
- package/admin/src/pages/SettingsPage/index.js +2 -2
- package/admin/src/pages/SettingsPage/pages/ApiTokens/EditView/components/ActionBoundRoutes/index.js +1 -1
- package/admin/src/pages/SettingsPage/pages/ApiTokens/EditView/components/CollapsableContentType/index.js +1 -1
- package/admin/src/pages/SettingsPage/pages/ApiTokens/EditView/components/Permissions/index.js +1 -1
- package/admin/src/pages/SettingsPage/pages/ApiTokens/EditView/index.js +2 -2
- package/admin/src/pages/SettingsPage/pages/AuditLogs/SalesPage.js +50 -0
- package/admin/src/pages/SettingsPage/pages/ReviewWorkflows/SalesPage.js +53 -0
- package/admin/src/pages/SettingsPage/pages/SingleSignOn/SalesPage.js +53 -0
- package/admin/src/pages/SettingsPage/pages/TransferTokens/EditView/index.js +1 -1
- package/admin/src/pages/SettingsPage/pages/Users/EditPage/index.js +2 -1
- package/admin/src/pages/SettingsPage/pages/Users/ListPage/DynamicTable/TableRows/index.js +1 -1
- package/admin/src/pages/{UseCasePage/index.js → UseCasePage.tsx} +10 -12
- package/admin/src/translations/en.json +5 -0
- package/admin/src/utils/createRoute.tsx +54 -0
- package/admin/src/utils/formatAPIErrors.ts +18 -0
- package/admin/src/utils/getFullName.ts +3 -0
- package/admin/src/utils/{uniqueAdminHash.js → hashAdminUserEmail.ts} +6 -3
- package/admin/src/utils/makeUniqueRoutes.ts +11 -0
- package/build/{1049.9236e785.chunk.js → 1049.ecc10c97.chunk.js} +1 -1
- package/build/1217.96155682.chunk.js +35 -0
- package/build/{1227.e0f7447b.chunk.js → 1227.947ceaf9.chunk.js} +1 -1
- package/build/1306.2699df52.chunk.js +79 -0
- package/build/{1386.07f2bbb3.chunk.js → 1386.eabd8a1e.chunk.js} +1 -1
- package/build/{2379.b0bc4013.chunk.js → 2379.7ce8e110.chunk.js} +1 -1
- package/build/{2395.d37b1025.chunk.js → 2395.acb961a8.chunk.js} +3 -3
- package/build/{2801.12522720.chunk.js → 2801.4711ea5a.chunk.js} +1 -1
- package/build/{3019.0d74d080.chunk.js → 3019.fde2e1be.chunk.js} +2 -2
- package/build/3460.8644e608.chunk.js +146 -0
- package/build/{3483.8f1b25f8.chunk.js → 3483.db8c1520.chunk.js} +1 -1
- package/build/{4174.2c4f958e.chunk.js → 4174.49cedb6a.chunk.js} +1 -1
- package/build/4732.149f5f8f.chunk.js +1 -0
- package/build/{502.b845473a.chunk.js → 502.f536f78b.chunk.js} +1 -1
- package/build/{7464.91341b4f.chunk.js → 7464.579564ac.chunk.js} +1 -1
- package/build/7811.fdbe09af.chunk.js +103 -0
- package/build/{7897.dffa5ad5.chunk.js → 7897.63ba0a00.chunk.js} +1 -1
- package/build/{8276.e9698944.chunk.js → 8276.9abe4679.chunk.js} +3 -3
- package/build/8773.ee67141c.chunk.js +48 -0
- package/build/9077.2cc01ac8.chunk.js +105 -0
- package/build/{9218.306ad178.chunk.js → 9218.b2d367f8.chunk.js} +1 -1
- package/build/Admin-authenticatedApp.059dc48f.chunk.js +79 -0
- package/build/Admin_InternalErrorPage.06eeef20.chunk.js +1 -0
- package/build/Admin_homePage.56b9eb3f.chunk.js +81 -0
- package/build/{Admin_marketplace.0db78604.chunk.js → Admin_marketplace.d693a435.chunk.js} +1 -1
- package/build/{Admin_pluginsPage.1083f7f0.chunk.js → Admin_pluginsPage.ae2c872a.chunk.js} +1 -1
- package/build/Admin_profilePage.89099d5b.chunk.js +13 -0
- package/build/Admin_settingsPage.88c45586.chunk.js +12 -0
- package/build/{Upload_ConfigureTheView.3cfeb108.chunk.js → Upload_ConfigureTheView.44f28145.chunk.js} +1 -1
- package/build/admin-app.990e112f.chunk.js +69 -0
- package/build/{admin-edit-roles-page.556fac52.chunk.js → admin-edit-roles-page.4e1eb4a9.chunk.js} +3 -3
- package/build/admin-edit-users.5b91404e.chunk.js +10 -0
- package/build/{admin-roles-list.15918328.chunk.js → admin-roles-list.89dd94fe.chunk.js} +1 -1
- package/build/{admin-users.74fddc87.chunk.js → admin-users.7be4fc5f.chunk.js} +2 -2
- package/build/{api-tokens-create-page.c08ae118.chunk.js → api-tokens-create-page.571920e5.chunk.js} +1 -1
- package/build/{api-tokens-edit-page.ce18efdc.chunk.js → api-tokens-edit-page.cbdc81b1.chunk.js} +1 -1
- package/build/{api-tokens-list-page.783b7569.chunk.js → api-tokens-list-page.de0c49e8.chunk.js} +2 -2
- package/build/audit-logs-sales-page.2955db88.chunk.js +1 -0
- package/build/{audit-logs-settings-page.12aeea8c.chunk.js → audit-logs-settings-page.b0cb5164.chunk.js} +1 -1
- package/build/content-manager.de7ae330.chunk.js +1241 -0
- package/build/{content-type-builder-list-view.38ed3935.chunk.js → content-type-builder-list-view.6c8d3213.chunk.js} +1 -1
- package/build/{content-type-builder-translation-en-json.43f9d7bc.chunk.js → content-type-builder-translation-en-json.74d80f18.chunk.js} +1 -1
- package/build/{content-type-builder.758a9d23.chunk.js → content-type-builder.0bc97051.chunk.js} +13 -23
- package/build/{email-settings-page.e08a587e.chunk.js → email-settings-page.07712efc.chunk.js} +1 -1
- package/build/en-json.5b907f67.chunk.js +1 -0
- package/build/{i18n-settings-page.3186e3e9.chunk.js → i18n-settings-page.5c34f012.chunk.js} +1 -1
- package/build/index.html +1 -1
- package/build/main.f84563f1.js +2665 -0
- package/build/review-workflows-sales-page.f46a8f00.chunk.js +1 -0
- package/build/{review-workflows-settings-create-view.5cdc4d64.chunk.js → review-workflows-settings-create-view.d0544fb0.chunk.js} +1 -1
- package/build/{review-workflows-settings-edit-view.53bf7865.chunk.js → review-workflows-settings-edit-view.aabf49ef.chunk.js} +1 -1
- package/build/review-workflows-settings-list-view.8b0525ab.chunk.js +56 -0
- package/build/runtime~main.270fd45f.js +2 -0
- package/build/sso-sales-page.ef22e469.chunk.js +1 -0
- package/build/sso-settings-page.21e16ae4.chunk.js +1 -0
- package/build/{transfer-tokens-create-page.2662d519.chunk.js → transfer-tokens-create-page.3366204d.chunk.js} +1 -1
- package/build/{transfer-tokens-edit-page.f64d8d8c.chunk.js → transfer-tokens-edit-page.15cf0f73.chunk.js} +1 -1
- package/build/{transfer-tokens-list-page.e6fd5f87.chunk.js → transfer-tokens-list-page.0bc0e682.chunk.js} +2 -2
- package/build/{upload-settings.450a1de0.chunk.js → upload-settings.1319dca0.chunk.js} +1 -1
- package/build/{upload.0d53e7a3.chunk.js → upload.1ced11be.chunk.js} +1 -1
- package/build/{users-advanced-settings-page.4a1f1f6d.chunk.js → users-advanced-settings-page.8e657084.chunk.js} +1 -1
- package/build/{users-email-settings-page.ea81fe82.chunk.js → users-email-settings-page.e57745e5.chunk.js} +1 -1
- package/build/{users-providers-settings-page.10280cdb.chunk.js → users-providers-settings-page.55796d13.chunk.js} +1 -1
- package/build/{users-roles-settings-page.4a7158be.chunk.js → users-roles-settings-page.57079245.chunk.js} +1 -1
- package/build/webhook-edit-page.3a28b2e7.chunk.js +33 -0
- package/build/{webhook-list-page.f57285ca.chunk.js → webhook-list-page.ee80767b.chunk.js} +1 -1
- package/ee/admin/pages/AuthPage/components/Login/index.js +1 -1
- package/ee/admin/pages/AuthPage/components/Providers/index.js +2 -1
- package/ee/admin/pages/SettingsPage/pages/ReviewWorkflows/selectors.js +1 -1
- package/ee/server/bootstrap.js +1 -1
- package/ee/server/controllers/admin.js +1 -1
- package/ee/server/controllers/user.js +1 -1
- package/ee/server/destroy.js +1 -1
- package/ee/server/register.js +1 -1
- package/ee/server/routes/utils.js +1 -1
- package/ee/server/services/audit-logs.js +1 -1
- package/ee/server/services/passport/sso.js +1 -1
- package/ee/server/services/passport.js +1 -1
- package/ee/server/services/seat-enforcement.js +1 -1
- package/ee/server/utils/sso-lock.js +1 -1
- package/ee/server/validation/role.js +1 -1
- package/ee/server/validation/user.js +1 -1
- package/package.json +15 -16
- package/server/controllers/admin.js +1 -1
- package/shared/entities.ts +1 -1
- package/shared/permissions.ts +35 -35
- package/shared/schema.ts +9 -0
- package/admin/src/components/AuthenticatedApp/index.js +0 -116
- package/admin/src/components/AuthenticatedApp/utils/api.js +0 -47
- package/admin/src/components/AuthenticatedApp/utils/checkLatestStrapiVersion.ts +0 -13
- package/admin/src/components/AuthenticatedApp/utils/fetchStrapiLatestRelease.ts +0 -19
- package/admin/src/components/GuidedTour/Homepage/components/Step.js +0 -61
- package/admin/src/components/GuidedTour/Homepage/components/Stepper.js +0 -61
- package/admin/src/components/GuidedTour/Homepage/index.js +0 -71
- package/admin/src/components/GuidedTour/Modal/components/Content.js +0 -66
- package/admin/src/components/GuidedTour/Modal/components/Modal.js +0 -72
- package/admin/src/components/GuidedTour/Modal/components/StepNumberWithPadding.js +0 -26
- package/admin/src/components/GuidedTour/Modal/components/Stepper.js +0 -118
- package/admin/src/components/GuidedTour/Modal/index.js +0 -94
- package/admin/src/components/GuidedTour/Modal/reducer.js +0 -29
- package/admin/src/components/GuidedTour/Stepper/StepLine.js +0 -29
- package/admin/src/components/GuidedTour/Stepper/StepNumber.js +0 -71
- package/admin/src/components/GuidedTour/constants.js +0 -3
- package/admin/src/components/GuidedTour/index.js +0 -102
- package/admin/src/components/GuidedTour/init.js +0 -37
- package/admin/src/components/GuidedTour/reducer.js +0 -50
- package/admin/src/components/GuidedTour/utils/arePreviousSectionsDone.js +0 -13
- package/admin/src/components/GuidedTour/utils/arePreviousStepsDone.js +0 -12
- package/admin/src/components/GuidedTour/utils/isGuidedTourCompleted.js +0 -6
- package/admin/src/components/GuidedTour/utils/persistStateToLocaleStorage.js +0 -34
- package/admin/src/components/Providers/index.js +0 -156
- package/admin/src/components/RBACProvider/actions.js +0 -10
- package/admin/src/components/RBACProvider/constants.js +0 -2
- package/admin/src/components/RBACProvider/index.js +0 -39
- package/admin/src/components/RBACProvider/reducer.js +0 -51
- package/admin/src/contexts/ApiTokenPermissions/index.js +0 -25
- package/admin/src/core/store/configureStore.js +0 -47
- package/admin/src/exposedHooks.js +0 -27
- package/admin/src/hooks/useContentTypes/index.js +0 -1
- package/admin/src/injectionZones.js +0 -25
- package/admin/src/layouts/UnauthenticatedLayout/LocaleToggle/index.js +0 -29
- package/admin/src/layouts/UnauthenticatedLayout/index.js +0 -55
- package/admin/src/reducers.js +0 -23
- package/admin/src/utils/checkFormValidity.js +0 -15
- package/admin/src/utils/createRoute.js +0 -50
- package/admin/src/utils/formatAPIErrors.js +0 -17
- package/admin/src/utils/getAttributesToDisplay.js +0 -19
- package/admin/src/utils/getExistingActions.js +0 -32
- package/admin/src/utils/getFullName.js +0 -9
- package/admin/src/utils/index.js +0 -9
- package/admin/src/utils/makeUniqueRoutes.js +0 -6
- package/admin/src/utils/sortLinks.js +0 -5
- package/build/1222.fe92c653.chunk.js +0 -35
- package/build/2225.a2147b8f.chunk.js +0 -79
- package/build/3021.33ad47fb.chunk.js +0 -103
- package/build/6373.1a21d665.chunk.js +0 -105
- package/build/8894.5ca4852a.chunk.js +0 -26
- package/build/9302.550cf5b7.chunk.js +0 -146
- package/build/Admin-authenticatedApp.e897fccb.chunk.js +0 -79
- package/build/Admin_InternalErrorPage.e2431a95.chunk.js +0 -1
- package/build/Admin_homePage.71ef8d06.chunk.js +0 -81
- package/build/Admin_profilePage.61704b7d.chunk.js +0 -13
- package/build/Admin_settingsPage.39cb9fca.chunk.js +0 -111
- package/build/admin-app.06f5e70a.chunk.js +0 -69
- package/build/admin-edit-users.64fd1318.chunk.js +0 -10
- package/build/content-manager.2e3f660b.chunk.js +0 -1220
- package/build/en-json.bd611a8e.chunk.js +0 -1
- package/build/main.00ea6f5a.js +0 -2665
- package/build/review-workflows-settings-list-view.b4a8aefb.chunk.js +0 -56
- package/build/runtime~main.e3bf3980.js +0 -2
- package/build/sso-settings-page.6a35d473.chunk.js +0 -1
- package/build/webhook-edit-page.65ac30ee.chunk.js +0 -33
- /package/admin/src/hooks/{useContentTypes/__mocks__/index.js → __mocks__/useContentTypes.ts} +0 -0
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
2
|
|
|
3
|
+
import { bindActionCreators } from '@reduxjs/toolkit';
|
|
3
4
|
import {
|
|
4
5
|
Main,
|
|
5
6
|
ActionLayout,
|
|
@@ -39,11 +40,11 @@ import PropTypes from 'prop-types';
|
|
|
39
40
|
import { stringify } from 'qs';
|
|
40
41
|
import { useIntl } from 'react-intl';
|
|
41
42
|
import { useMutation } from 'react-query';
|
|
42
|
-
import {
|
|
43
|
+
import { useDispatch } from 'react-redux';
|
|
43
44
|
import { useHistory, useLocation, Link as ReactRouterLink } from 'react-router-dom';
|
|
44
|
-
import { bindActionCreators, compose } from 'redux';
|
|
45
45
|
|
|
46
|
-
import {
|
|
46
|
+
import { HOOKS } from '../../../constants';
|
|
47
|
+
import { useTypedSelector } from '../../../core/store/hooks';
|
|
47
48
|
import { useAdminUsers } from '../../../hooks/useAdminUsers';
|
|
48
49
|
import { useEnterprise } from '../../../hooks/useEnterprise';
|
|
49
50
|
import { InjectionZone } from '../../../shared/components';
|
|
@@ -53,7 +54,7 @@ import { CREATOR_FIELDS } from '../../constants/attributes';
|
|
|
53
54
|
import { useAllowedAttributes } from '../../hooks/useAllowedAttributes';
|
|
54
55
|
import { getTrad, getDisplayName } from '../../utils';
|
|
55
56
|
|
|
56
|
-
import
|
|
57
|
+
import * as Actions from './actions';
|
|
57
58
|
import { Body } from './components/Body';
|
|
58
59
|
import BulkActionButtons from './components/BulkActionButtons';
|
|
59
60
|
import CellContent from './components/CellContent';
|
|
@@ -61,24 +62,23 @@ import { ViewSettingsMenu } from './components/ViewSettingsMenu';
|
|
|
61
62
|
import makeSelectListView, { selectDisplayedHeaders } from './selectors';
|
|
62
63
|
import { buildValidGetParams } from './utils';
|
|
63
64
|
|
|
65
|
+
const { INJECT_COLUMN_IN_TABLE } = HOOKS;
|
|
64
66
|
const REVIEW_WORKFLOW_COLUMNS_CE = null;
|
|
65
67
|
const REVIEW_WORKFLOW_COLUMNS_CELL_CE = () => null;
|
|
66
68
|
const REVIEW_WORKFLOW_FILTER_CE = [];
|
|
67
69
|
const USER_FILTER_ATTRIBUTES = [...CREATOR_FIELDS, 'strapi_assignee'];
|
|
68
70
|
|
|
69
|
-
function ListView({
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
pagination,
|
|
80
|
-
slug,
|
|
81
|
-
}) {
|
|
71
|
+
function ListView({ canCreate, canDelete, canRead, canPublish, layout, slug }) {
|
|
72
|
+
const dispatch = useDispatch();
|
|
73
|
+
const { getData, getDataSucceeded } = React.useMemo(
|
|
74
|
+
() =>
|
|
75
|
+
bindActionCreators(
|
|
76
|
+
{ getData: Actions.getData, getDataSucceeded: Actions.getDataSucceeded },
|
|
77
|
+
dispatch
|
|
78
|
+
),
|
|
79
|
+
[dispatch]
|
|
80
|
+
);
|
|
81
|
+
const { pagination, isLoading, data } = useTypedSelector(makeSelectListView());
|
|
82
82
|
const { total } = pagination;
|
|
83
83
|
const { contentType } = layout;
|
|
84
84
|
const {
|
|
@@ -468,7 +468,7 @@ function ListView({
|
|
|
468
468
|
});
|
|
469
469
|
|
|
470
470
|
const { runHookWaterfall } = useStrapiApp();
|
|
471
|
-
const displayedHeaders =
|
|
471
|
+
const displayedHeaders = useTypedSelector(selectDisplayedHeaders);
|
|
472
472
|
|
|
473
473
|
const tableHeaders = React.useMemo(() => {
|
|
474
474
|
const headers = runHookWaterfall(INJECT_COLUMN_IN_TABLE, {
|
|
@@ -731,9 +731,11 @@ function ListView({
|
|
|
731
731
|
>
|
|
732
732
|
{data.map((rowData, index) => {
|
|
733
733
|
return (
|
|
734
|
-
<Tr cursor="pointer" key={
|
|
734
|
+
<Tr cursor="pointer" key={rowData.id} onClick={handleRowClick(rowData.id)}>
|
|
735
735
|
{/* Bulk action row checkbox */}
|
|
736
|
-
<
|
|
736
|
+
<Td>
|
|
737
|
+
<Body.CheckboxDataCell rowId={rowData.id} index={index} />
|
|
738
|
+
</Td>
|
|
737
739
|
{/* Field data */}
|
|
738
740
|
{tableHeaders.map(({ key, name, cellFormatter, ...rest }) => {
|
|
739
741
|
if (hasDraftAndPublish && name === 'publishedAt') {
|
|
@@ -832,14 +834,16 @@ function ListView({
|
|
|
832
834
|
})}
|
|
833
835
|
{/* Actions: edit, duplicate, delete */}
|
|
834
836
|
{(canDelete || canPublish) && isBulkable && (
|
|
835
|
-
<
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
837
|
+
<Td>
|
|
838
|
+
<Body.EntityActionsDataCell
|
|
839
|
+
rowId={rowData.id}
|
|
840
|
+
index={index}
|
|
841
|
+
setIsConfirmDeleteRowOpen={setIsConfirmDeleteRowOpen}
|
|
842
|
+
canCreate={canCreate}
|
|
843
|
+
canDelete={canDelete}
|
|
844
|
+
handleCloneClick={handleCloneClick}
|
|
845
|
+
/>
|
|
846
|
+
</Td>
|
|
843
847
|
)}
|
|
844
848
|
</Tr>
|
|
845
849
|
);
|
|
@@ -865,7 +869,6 @@ ListView.propTypes = {
|
|
|
865
869
|
canDelete: PropTypes.bool.isRequired,
|
|
866
870
|
canRead: PropTypes.bool.isRequired,
|
|
867
871
|
canPublish: PropTypes.bool.isRequired,
|
|
868
|
-
data: PropTypes.array.isRequired,
|
|
869
872
|
layout: PropTypes.exact({
|
|
870
873
|
components: PropTypes.object.isRequired,
|
|
871
874
|
contentType: PropTypes.shape({
|
|
@@ -880,27 +883,7 @@ ListView.propTypes = {
|
|
|
880
883
|
settings: PropTypes.object.isRequired,
|
|
881
884
|
}).isRequired,
|
|
882
885
|
}).isRequired,
|
|
883
|
-
isLoading: PropTypes.bool.isRequired,
|
|
884
|
-
getData: PropTypes.func.isRequired,
|
|
885
|
-
getDataSucceeded: PropTypes.func.isRequired,
|
|
886
|
-
pagination: PropTypes.shape({ total: PropTypes.number.isRequired, pageCount: PropTypes.number })
|
|
887
|
-
.isRequired,
|
|
888
886
|
slug: PropTypes.string.isRequired,
|
|
889
887
|
};
|
|
890
888
|
|
|
891
|
-
|
|
892
|
-
|
|
893
|
-
export function mapDispatchToProps(dispatch) {
|
|
894
|
-
return bindActionCreators(
|
|
895
|
-
{
|
|
896
|
-
getData,
|
|
897
|
-
getDataSucceeded,
|
|
898
|
-
onChangeListHeaders,
|
|
899
|
-
onResetListHeaders,
|
|
900
|
-
},
|
|
901
|
-
dispatch
|
|
902
|
-
);
|
|
903
|
-
}
|
|
904
|
-
const withConnect = connect(mapStateToProps, mapDispatchToProps);
|
|
905
|
-
|
|
906
|
-
export default compose(withConnect)(React.memo(ListView, isEqual));
|
|
889
|
+
export default React.memo(ListView, isEqual);
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
/* eslint-disable check-file/filename-naming-convention */
|
|
2
|
+
|
|
3
|
+
import * as React from 'react';
|
|
4
|
+
|
|
5
|
+
import { Entity } from '@strapi/types';
|
|
6
|
+
|
|
7
|
+
interface PseudoEvent {
|
|
8
|
+
target: { value: string };
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
interface ApiTokenPermissionsContextValue {
|
|
12
|
+
selectedAction: string[] | null;
|
|
13
|
+
routes: string[];
|
|
14
|
+
selectedActions: string[];
|
|
15
|
+
data: {
|
|
16
|
+
allActionsIds: Entity.ID[];
|
|
17
|
+
permissions: {
|
|
18
|
+
apiId: string;
|
|
19
|
+
label: string;
|
|
20
|
+
controllers: { controller: string; actions: { actionId: string; action: string } }[];
|
|
21
|
+
}[];
|
|
22
|
+
};
|
|
23
|
+
onChange: ({ target: { value } }: PseudoEvent) => void;
|
|
24
|
+
onChangeSelectAll: ({ target: { value } }: PseudoEvent) => void;
|
|
25
|
+
setSelectedAction: ({ target: { value } }: PseudoEvent) => void;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
interface ApiTokenPermissionsContextProviderProps extends ApiTokenPermissionsContextValue {
|
|
29
|
+
children: React.ReactNode[];
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
const ApiTokenPermissionsContext = React.createContext<ApiTokenPermissionsContextValue>({
|
|
33
|
+
selectedAction: null,
|
|
34
|
+
routes: [],
|
|
35
|
+
selectedActions: [],
|
|
36
|
+
data: {
|
|
37
|
+
allActionsIds: [],
|
|
38
|
+
permissions: [],
|
|
39
|
+
},
|
|
40
|
+
onChange: () => {},
|
|
41
|
+
onChangeSelectAll: () => {},
|
|
42
|
+
setSelectedAction: () => {},
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
const ApiTokenPermissionsContextProvider = ({
|
|
46
|
+
children,
|
|
47
|
+
...rest
|
|
48
|
+
}: ApiTokenPermissionsContextProviderProps) => {
|
|
49
|
+
return (
|
|
50
|
+
<ApiTokenPermissionsContext.Provider value={rest}>
|
|
51
|
+
{children}
|
|
52
|
+
</ApiTokenPermissionsContext.Provider>
|
|
53
|
+
);
|
|
54
|
+
};
|
|
55
|
+
|
|
56
|
+
const useApiTokenPermissionsContext = () => React.useContext(ApiTokenPermissionsContext);
|
|
57
|
+
|
|
58
|
+
export {
|
|
59
|
+
ApiTokenPermissionsContext,
|
|
60
|
+
ApiTokenPermissionsContextProvider,
|
|
61
|
+
useApiTokenPermissionsContext,
|
|
62
|
+
};
|
|
63
|
+
|
|
64
|
+
export type { ApiTokenPermissionsContextValue, ApiTokenPermissionsContextProviderProps };
|
|
@@ -2,7 +2,8 @@ import { createContext } from 'react';
|
|
|
2
2
|
|
|
3
3
|
import { DefaultTheme } from 'styled-components';
|
|
4
4
|
|
|
5
|
-
export type ThemeName = 'light' | 'dark';
|
|
5
|
+
export type ThemeName = 'light' | 'dark' | 'system';
|
|
6
|
+
export type NonSystemThemeName = Exclude<ThemeName, 'system'>;
|
|
6
7
|
|
|
7
8
|
interface ThemeToggleContextContextValue {
|
|
8
9
|
currentTheme?: ThemeName;
|
|
@@ -11,6 +12,7 @@ interface ThemeToggleContextContextValue {
|
|
|
11
12
|
dark: DefaultTheme;
|
|
12
13
|
light: DefaultTheme;
|
|
13
14
|
};
|
|
15
|
+
systemTheme?: NonSystemThemeName;
|
|
14
16
|
}
|
|
15
17
|
|
|
16
18
|
export const ThemeToggleContext = createContext<ThemeToggleContextContextValue>({});
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
import {
|
|
2
|
+
configureStore,
|
|
3
|
+
StoreEnhancer,
|
|
4
|
+
Middleware,
|
|
5
|
+
Reducer,
|
|
6
|
+
combineReducers,
|
|
7
|
+
} from '@reduxjs/toolkit';
|
|
8
|
+
|
|
9
|
+
import { RBACReducer } from '../../components/RBACProvider';
|
|
10
|
+
// @ts-expect-error no types, yet.
|
|
11
|
+
import rbacManagerReducer from '../../content-manager/hooks/useSyncRbac/reducer';
|
|
12
|
+
// @ts-expect-error no types, yet.
|
|
13
|
+
import cmAppReducer from '../../content-manager/pages/App/reducer';
|
|
14
|
+
// @ts-expect-error no types, yet.
|
|
15
|
+
import editViewLayoutManagerReducer from '../../content-manager/pages/EditViewLayoutManager/reducer';
|
|
16
|
+
// @ts-expect-error no types, yet.
|
|
17
|
+
import listViewReducer from '../../content-manager/pages/ListView/reducer';
|
|
18
|
+
// @ts-expect-error no types, yet.
|
|
19
|
+
import editViewCrudReducer from '../../content-manager/sharedReducers/crudReducer/reducer';
|
|
20
|
+
// @ts-expect-error no types, yet.
|
|
21
|
+
import appReducer from '../../pages/App/reducer';
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* @description Static reducers are ones we know, they live in the admin package.
|
|
25
|
+
*/
|
|
26
|
+
const staticReducers = {
|
|
27
|
+
admin_app: appReducer,
|
|
28
|
+
rbacProvider: RBACReducer,
|
|
29
|
+
'content-manager_app': cmAppReducer,
|
|
30
|
+
'content-manager_listView': listViewReducer,
|
|
31
|
+
'content-manager_rbacManager': rbacManagerReducer,
|
|
32
|
+
'content-manager_editViewLayoutManager': editViewLayoutManagerReducer,
|
|
33
|
+
'content-manager_editViewCrudReducer': editViewCrudReducer,
|
|
34
|
+
} as const;
|
|
35
|
+
|
|
36
|
+
const injectReducerStoreEnhancer: (appReducers: Record<string, Reducer>) => StoreEnhancer =
|
|
37
|
+
(appReducers) =>
|
|
38
|
+
(next) =>
|
|
39
|
+
(...args) => {
|
|
40
|
+
const store = next(...args);
|
|
41
|
+
|
|
42
|
+
const asyncReducers: Record<string, Reducer> = {};
|
|
43
|
+
|
|
44
|
+
return {
|
|
45
|
+
...store,
|
|
46
|
+
asyncReducers,
|
|
47
|
+
injectReducer: (key: string, asyncReducer: Reducer) => {
|
|
48
|
+
asyncReducers[key] = asyncReducer;
|
|
49
|
+
store.replaceReducer(
|
|
50
|
+
// @ts-expect-error we dynamically add reducers which makes the types uncomfortable.
|
|
51
|
+
combineReducers({
|
|
52
|
+
...appReducers,
|
|
53
|
+
...asyncReducers,
|
|
54
|
+
})
|
|
55
|
+
);
|
|
56
|
+
},
|
|
57
|
+
};
|
|
58
|
+
};
|
|
59
|
+
|
|
60
|
+
/**
|
|
61
|
+
* @description This is the main store configuration function, injected Reducers use our legacy app.addReducer API,
|
|
62
|
+
* which we're trying to phase out. App Middlewares could potentially be improved...?
|
|
63
|
+
*/
|
|
64
|
+
const configureStoreImpl = (
|
|
65
|
+
appMiddlewares: Array<() => Middleware> = [],
|
|
66
|
+
injectedReducers: Record<string, Reducer> = {}
|
|
67
|
+
) => {
|
|
68
|
+
const coreReducers = { ...staticReducers, ...injectedReducers } as const;
|
|
69
|
+
|
|
70
|
+
const store = configureStore({
|
|
71
|
+
reducer: coreReducers,
|
|
72
|
+
devTools: process.env.NODE_ENV !== 'production',
|
|
73
|
+
middleware: (getDefaultMiddleware) => [
|
|
74
|
+
...getDefaultMiddleware(),
|
|
75
|
+
...appMiddlewares.map((m) => m()),
|
|
76
|
+
],
|
|
77
|
+
enhancers: [injectReducerStoreEnhancer(coreReducers)],
|
|
78
|
+
});
|
|
79
|
+
|
|
80
|
+
return store;
|
|
81
|
+
};
|
|
82
|
+
|
|
83
|
+
type Store = ReturnType<typeof configureStoreImpl> & {
|
|
84
|
+
asyncReducers: Record<string, Reducer>;
|
|
85
|
+
injectReducer: (key: string, asyncReducer: Reducer) => void;
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
type RootState = ReturnType<Store['getState']>;
|
|
89
|
+
|
|
90
|
+
export { configureStoreImpl as configureStore };
|
|
91
|
+
export type { RootState, Store };
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { createSelector, Selector } from '@reduxjs/toolkit';
|
|
2
|
+
import { useDispatch, useStore, TypedUseSelectorHook, useSelector } from 'react-redux';
|
|
3
|
+
|
|
4
|
+
import type { RootState, Store } from './configure';
|
|
5
|
+
|
|
6
|
+
type AppDispatch = Store['dispatch'];
|
|
7
|
+
|
|
8
|
+
const useTypedDispatch: () => AppDispatch = useDispatch;
|
|
9
|
+
const useTypedStore = useStore as () => Store;
|
|
10
|
+
const useTypedSelector: TypedUseSelectorHook<RootState> = useSelector;
|
|
11
|
+
|
|
12
|
+
const createTypedSelector = <TResult>(selector: Selector<RootState, TResult>) =>
|
|
13
|
+
createSelector((state: RootState) => state, selector);
|
|
14
|
+
|
|
15
|
+
export { useTypedDispatch, useTypedStore, useTypedSelector, createTypedSelector };
|
package/admin/src/hooks/index.js
CHANGED
|
@@ -1,32 +1,55 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
2
|
|
|
3
3
|
import { useAPIErrorHandler, useFetchClient, useNotification } from '@strapi/helper-plugin';
|
|
4
|
+
import { AxiosError } from 'axios';
|
|
4
5
|
import { useQueries } from 'react-query';
|
|
5
6
|
|
|
7
|
+
import { Component, ContentType } from '../../../shared/schema';
|
|
8
|
+
import { APIResponse } from '../types/adminAPI';
|
|
9
|
+
|
|
6
10
|
export function useContentTypes() {
|
|
7
11
|
const { get } = useFetchClient();
|
|
8
12
|
const { formatAPIError } = useAPIErrorHandler();
|
|
9
13
|
const toggleNotification = useNotification();
|
|
10
|
-
const queries = useQueries(
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
14
|
+
const queries = useQueries([
|
|
15
|
+
{
|
|
16
|
+
queryKey: ['content-manager', 'components'],
|
|
17
|
+
async queryFn() {
|
|
18
|
+
const {
|
|
19
|
+
data: { data },
|
|
20
|
+
} = await get<APIResponse<Component[]>>(`/content-manager/components`);
|
|
21
|
+
|
|
22
|
+
return data;
|
|
23
|
+
},
|
|
24
|
+
onError(error: unknown) {
|
|
25
|
+
if (error instanceof AxiosError) {
|
|
26
|
+
toggleNotification({
|
|
27
|
+
type: 'warning',
|
|
28
|
+
message: formatAPIError(error),
|
|
29
|
+
});
|
|
30
|
+
}
|
|
31
|
+
},
|
|
32
|
+
},
|
|
33
|
+
|
|
34
|
+
{
|
|
35
|
+
queryKey: ['content-manager', 'content-types'],
|
|
36
|
+
async queryFn() {
|
|
37
|
+
const {
|
|
38
|
+
data: { data },
|
|
39
|
+
} = await get<APIResponse<ContentType[]>>(`/content-manager/content-types`);
|
|
40
|
+
|
|
41
|
+
return data;
|
|
42
|
+
},
|
|
43
|
+
onError(error: unknown) {
|
|
44
|
+
if (error instanceof AxiosError) {
|
|
22
45
|
toggleNotification({
|
|
23
46
|
type: 'warning',
|
|
24
47
|
message: formatAPIError(error),
|
|
25
48
|
});
|
|
26
|
-
}
|
|
27
|
-
}
|
|
28
|
-
}
|
|
29
|
-
);
|
|
49
|
+
}
|
|
50
|
+
},
|
|
51
|
+
},
|
|
52
|
+
]);
|
|
30
53
|
|
|
31
54
|
const [components, contentTypes] = queries;
|
|
32
55
|
const isLoading = components.isLoading || contentTypes.isLoading;
|
|
@@ -1,13 +1,25 @@
|
|
|
1
1
|
import { useEffect, useReducer } from 'react';
|
|
2
2
|
|
|
3
|
-
import { useFetchClient, useNotification, useOverlayBlocker } from '@strapi/helper-plugin';
|
|
3
|
+
import { getYupInnerErrors, useFetchClient, useNotification, useOverlayBlocker } from '@strapi/helper-plugin';
|
|
4
4
|
import omit from 'lodash/omit';
|
|
5
5
|
|
|
6
|
-
import {
|
|
6
|
+
import { formatAPIErrors } from '../../utils/formatAPIErrors';
|
|
7
7
|
|
|
8
8
|
import init from './init';
|
|
9
9
|
import { initialState, reducer } from './reducer';
|
|
10
10
|
|
|
11
|
+
const checkFormValidity = async (data, schema) => {
|
|
12
|
+
let errors = null;
|
|
13
|
+
|
|
14
|
+
try {
|
|
15
|
+
await schema.validate(data, { abortEarly: false });
|
|
16
|
+
} catch (err) {
|
|
17
|
+
errors = getYupInnerErrors(err);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
return errors;
|
|
21
|
+
};
|
|
22
|
+
|
|
11
23
|
/**
|
|
12
24
|
* TODO: refactor this, it's confusing and hard to read.
|
|
13
25
|
* It's also only used in `Settings/pages/SingleSignOn` so it can
|
|
@@ -21,6 +21,34 @@ export const LINKS_CE = {
|
|
|
21
21
|
to: '/settings/transfer-tokens?sort=name:ASC',
|
|
22
22
|
id: 'transfer-tokens',
|
|
23
23
|
},
|
|
24
|
+
// If the Enterprise feature is not enabled and if the config doesn't disable it, we promote the Enterprise feature by displaying them in the settings menu.
|
|
25
|
+
// Disable this by adding "promoteEE: false" to your `./config/admin.js` file
|
|
26
|
+
...(!window.strapi.features.isEnabled(window.strapi.features.SSO) &&
|
|
27
|
+
window.strapi?.flags?.promoteEE
|
|
28
|
+
? [
|
|
29
|
+
{
|
|
30
|
+
intlLabel: { id: 'Settings.sso.title', defaultMessage: 'Single Sign-On' },
|
|
31
|
+
to: '/settings/purchase-single-sign-on',
|
|
32
|
+
id: 'sso',
|
|
33
|
+
lockIcon: true,
|
|
34
|
+
},
|
|
35
|
+
]
|
|
36
|
+
: []),
|
|
37
|
+
|
|
38
|
+
...(!window.strapi.features.isEnabled(window.strapi.features.REVIEW_WORKFLOWS) &&
|
|
39
|
+
window.strapi?.flags?.promoteEE
|
|
40
|
+
? [
|
|
41
|
+
{
|
|
42
|
+
intlLabel: {
|
|
43
|
+
id: 'Settings.review-workflows.page.title',
|
|
44
|
+
defaultMessage: 'Review Workflows',
|
|
45
|
+
},
|
|
46
|
+
to: '/settings/purchase-review-workflows',
|
|
47
|
+
id: 'review-workflows',
|
|
48
|
+
lockIcon: true,
|
|
49
|
+
},
|
|
50
|
+
]
|
|
51
|
+
: []),
|
|
24
52
|
],
|
|
25
53
|
|
|
26
54
|
admin: [
|
|
@@ -35,5 +63,16 @@ export const LINKS_CE = {
|
|
|
35
63
|
to: '/settings/users?pageSize=10&page=1&sort=firstname',
|
|
36
64
|
id: 'users',
|
|
37
65
|
},
|
|
66
|
+
...(!window.strapi.features.isEnabled(window.strapi.features.AUDIT_LOGS) &&
|
|
67
|
+
window.strapi?.flags?.promoteEE
|
|
68
|
+
? [
|
|
69
|
+
{
|
|
70
|
+
intlLabel: { id: 'global.auditLogs', defaultMessage: 'Audit Logs' },
|
|
71
|
+
to: '/settings/purchase-audit-logs',
|
|
72
|
+
id: 'auditLogs',
|
|
73
|
+
lockIcon: true,
|
|
74
|
+
},
|
|
75
|
+
]
|
|
76
|
+
: []),
|
|
38
77
|
],
|
|
39
78
|
};
|
package/admin/src/index.js
CHANGED
|
@@ -2,10 +2,9 @@ import { getFetchClient } from '@strapi/helper-plugin';
|
|
|
2
2
|
import { createRoot } from 'react-dom/client';
|
|
3
3
|
|
|
4
4
|
import appCustomisations from './app';
|
|
5
|
-
import { Components, Fields, Middlewares
|
|
5
|
+
import { Components, Fields, Middlewares } from './core/apis';
|
|
6
6
|
// eslint-disable-next-line import/extensions
|
|
7
7
|
import plugins from './plugins';
|
|
8
|
-
import appReducers from './reducers';
|
|
9
8
|
|
|
10
9
|
window.strapi = {
|
|
11
10
|
/**
|
|
@@ -25,6 +24,7 @@ window.strapi = {
|
|
|
25
24
|
projectType: 'Community',
|
|
26
25
|
flags: {
|
|
27
26
|
nps: false,
|
|
27
|
+
promoteEE: true,
|
|
28
28
|
},
|
|
29
29
|
};
|
|
30
30
|
|
|
@@ -35,7 +35,6 @@ const library = {
|
|
|
35
35
|
fields: Fields(),
|
|
36
36
|
};
|
|
37
37
|
const middlewares = Middlewares();
|
|
38
|
-
const reducers = Reducers({ appReducers });
|
|
39
38
|
|
|
40
39
|
const MOUNT_NODE = document.getElementById('app');
|
|
41
40
|
|
|
@@ -69,7 +68,6 @@ const run = async () => {
|
|
|
69
68
|
adminConfig: customConfig,
|
|
70
69
|
bootstrap: customConfig,
|
|
71
70
|
middlewares,
|
|
72
|
-
reducers,
|
|
73
71
|
});
|
|
74
72
|
|
|
75
73
|
await app.bootstrapAdmin();
|
|
@@ -1,7 +1,6 @@
|
|
|
1
|
-
import React from 'react';
|
|
1
|
+
import * as React from 'react';
|
|
2
2
|
|
|
3
3
|
import { Box, Flex, SkipToContent } from '@strapi/design-system';
|
|
4
|
-
import PropTypes from 'prop-types';
|
|
5
4
|
import { useIntl } from 'react-intl';
|
|
6
5
|
import styled from 'styled-components';
|
|
7
6
|
|
|
@@ -9,7 +8,12 @@ const FlexBox = styled(Box)`
|
|
|
9
8
|
flex: 1;
|
|
10
9
|
`;
|
|
11
10
|
|
|
12
|
-
|
|
11
|
+
interface AppLayoutProps {
|
|
12
|
+
children: React.ReactNode;
|
|
13
|
+
sideNav: React.ReactNode;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export const AppLayout = ({ children, sideNav }: AppLayoutProps) => {
|
|
13
17
|
const { formatMessage } = useIntl();
|
|
14
18
|
|
|
15
19
|
return (
|
|
@@ -24,10 +28,3 @@ const AppLayout = ({ children, sideNav }) => {
|
|
|
24
28
|
</Box>
|
|
25
29
|
);
|
|
26
30
|
};
|
|
27
|
-
|
|
28
|
-
AppLayout.propTypes = {
|
|
29
|
-
children: PropTypes.node.isRequired,
|
|
30
|
-
sideNav: PropTypes.node.isRequired,
|
|
31
|
-
};
|
|
32
|
-
|
|
33
|
-
export default AppLayout;
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import * as React from 'react';
|
|
2
|
+
|
|
3
|
+
import { Box, Flex, SingleSelect, SingleSelectOption } from '@strapi/design-system';
|
|
4
|
+
import { useIntl } from 'react-intl';
|
|
5
|
+
import styled from 'styled-components';
|
|
6
|
+
|
|
7
|
+
import { useLocales } from '../components/LanguageProvider';
|
|
8
|
+
|
|
9
|
+
const Wrapper = styled(Box)`
|
|
10
|
+
margin: 0 auto;
|
|
11
|
+
width: 552px;
|
|
12
|
+
`;
|
|
13
|
+
|
|
14
|
+
export const Column = styled(Flex)`
|
|
15
|
+
flex-direction: column;
|
|
16
|
+
`;
|
|
17
|
+
|
|
18
|
+
const LocaleToggle = () => {
|
|
19
|
+
const { changeLocale, localeNames } = useLocales();
|
|
20
|
+
const { formatMessage, locale } = useIntl();
|
|
21
|
+
|
|
22
|
+
return (
|
|
23
|
+
<SingleSelect
|
|
24
|
+
aria-label={formatMessage({
|
|
25
|
+
id: 'global.localeToggle.label',
|
|
26
|
+
defaultMessage: 'Select interface language',
|
|
27
|
+
})}
|
|
28
|
+
value={locale}
|
|
29
|
+
onChange={(language) => {
|
|
30
|
+
changeLocale(language as string);
|
|
31
|
+
}}
|
|
32
|
+
>
|
|
33
|
+
{Object.entries(localeNames).map(([language, name]) => (
|
|
34
|
+
<SingleSelectOption key={language} value={language}>
|
|
35
|
+
{name}
|
|
36
|
+
</SingleSelectOption>
|
|
37
|
+
))}
|
|
38
|
+
</SingleSelect>
|
|
39
|
+
);
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
interface LayoutContentProps {
|
|
43
|
+
children: React.ReactNode;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
export const LayoutContent = ({ children }: LayoutContentProps) => (
|
|
47
|
+
<Wrapper
|
|
48
|
+
shadow="tableShadow"
|
|
49
|
+
hasRadius
|
|
50
|
+
paddingTop={9}
|
|
51
|
+
paddingBottom={9}
|
|
52
|
+
paddingLeft={10}
|
|
53
|
+
paddingRight={10}
|
|
54
|
+
background="neutral0"
|
|
55
|
+
>
|
|
56
|
+
{children}
|
|
57
|
+
</Wrapper>
|
|
58
|
+
);
|
|
59
|
+
|
|
60
|
+
interface UnauthenticatedLayoutProps {
|
|
61
|
+
children: React.ReactNode;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
export const UnauthenticatedLayout = ({ children }: UnauthenticatedLayoutProps) => {
|
|
65
|
+
return (
|
|
66
|
+
<div>
|
|
67
|
+
<Flex as="header" justifyContent="flex-end">
|
|
68
|
+
<Box paddingTop={6} paddingRight={8}>
|
|
69
|
+
<LocaleToggle />
|
|
70
|
+
</Box>
|
|
71
|
+
</Flex>
|
|
72
|
+
<Box paddingTop={2} paddingBottom={11}>
|
|
73
|
+
{children}
|
|
74
|
+
</Box>
|
|
75
|
+
</div>
|
|
76
|
+
);
|
|
77
|
+
};
|