diff --git a/docs/docs/docs/01-core/admin/04-hooks/use-enterprise.mdx b/docs/docs/docs/01-core/admin/04-hooks/use-enterprise.mdx
index a8e0c49977..ca95abc1b8 100644
--- a/docs/docs/docs/01-core/admin/04-hooks/use-enterprise.mdx
+++ b/docs/docs/docs/01-core/admin/04-hooks/use-enterprise.mdx
@@ -54,3 +54,8 @@ if (!Component) {
return;
}
```
+
+### `enabled`
+
+Similar to react-query this boolean flag allows disabling the EE import, e.g. when more than one condition needs to be applied. If `enabled`
+is set to false, the first argument (CE_DATA) will be returned.
diff --git a/packages/core/admin/admin/src/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn.js b/packages/core/admin/admin/src/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn.js
deleted file mode 100644
index e19585b823..0000000000
--- a/packages/core/admin/admin/src/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn.js
+++ /dev/null
@@ -1,2 +0,0 @@
-// Overwritten in EE
-export default () => null;
diff --git a/packages/core/admin/admin/src/content-manager/pages/ListView/components/TableRows/index.js b/packages/core/admin/admin/src/content-manager/pages/ListView/components/TableRows/index.js
index f0da516370..b6e7e36e91 100644
--- a/packages/core/admin/admin/src/content-manager/pages/ListView/components/TableRows/index.js
+++ b/packages/core/admin/admin/src/content-manager/pages/ListView/components/TableRows/index.js
@@ -1,6 +1,16 @@
import React from 'react';
-import { BaseCheckbox, IconButton, Tbody, Td, Tr, Flex } from '@strapi/design-system';
+import {
+ BaseCheckbox,
+ IconButton,
+ Tbody,
+ Td,
+ Tr,
+ Flex,
+ lightTheme,
+ Status,
+ Typography,
+} from '@strapi/design-system';
import { useTracking, useFetchClient, useAPIErrorHandler } from '@strapi/helper-plugin';
import { Trash, Duplicate, Pencil } from '@strapi/icons';
import { AxiosError } from 'axios';
@@ -8,15 +18,19 @@ import PropTypes from 'prop-types';
import { useIntl } from 'react-intl';
import { Link, useHistory } from 'react-router-dom';
+import { useEnterprise } from '../../../../../hooks/useEnterprise';
import { getFullName } from '../../../../../utils';
import { usePluginsQueryParams } from '../../../../hooks';
import { getTrad } from '../../../../utils';
import CellContent from '../CellContent';
+const REVIEW_WORKFLOW_COLUMNS_CE = () => null;
+
export const TableRows = ({
canCreate,
canDelete,
contentType,
+ features: { hasDraftAndPublish, hasReviewWorkflows },
headers,
entriesToDelete,
onClickDelete,
@@ -33,6 +47,18 @@ export const TableRows = ({
const { trackUsage } = useTracking();
const pluginsQueryParams = usePluginsQueryParams();
const { formatAPIError } = useAPIErrorHandler(getTrad);
+ const ReviewWorkflowsStage = useEnterprise(
+ REVIEW_WORKFLOW_COLUMNS_CE,
+ async () =>
+ (
+ await import(
+ '../../../../../../../ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn'
+ )
+ ).ReviewWorkflowsStageEE,
+ {
+ enabled: hasReviewWorkflows,
+ }
+ );
/**
*
@@ -74,6 +100,11 @@ export const TableRows = ({
}
};
+ // block rendering until the review stage component is fully loaded in EE
+ if (!ReviewWorkflowsStage) {
+ return null;
+ }
+
/**
* Table Cells with actions e.g edit, delete, duplicate have `stopPropagation`
* to prevent the row from being selected.
@@ -113,20 +144,59 @@ export const TableRows = ({
/>
)}
+
{headers.map(({ key, cellFormatter, name, ...rest }) => {
+ if (hasDraftAndPublish && name === 'publishedAt') {
+ return (
+
+
+
+ {formatMessage({
+ id: getTrad(
+ `containers.List.${data.publishedAt ? 'published' : 'draft'}`
+ ),
+ defaultMessage: data.publishedAt ? 'Published' : 'Draft',
+ })}
+
+
+ |
+ );
+ }
+
+ if (hasReviewWorkflows && name === 'strapi_reviewWorkflows_stage') {
+ return (
+
+ {data.strapi_reviewWorkflows_stage ? (
+
+ ) : (
+ -
+ )}
+ |
+ );
+ }
+
return (
- {typeof cellFormatter === 'function' ? (
- cellFormatter(data, { key, name, ...rest })
- ) : (
-
- )}
+
|
);
})}
@@ -212,6 +282,10 @@ TableRows.propTypes = {
uid: PropTypes.string.isRequired,
}).isRequired,
entriesToDelete: PropTypes.array,
+ features: PropTypes.shape({
+ hasDraftAndPublish: PropTypes.bool.isRequired,
+ hasReviewWorkflows: PropTypes.bool.isRequired,
+ }).isRequired,
headers: PropTypes.array.isRequired,
onClickDelete: PropTypes.func,
onSelectRow: PropTypes.func,
diff --git a/packages/core/admin/admin/src/content-manager/pages/ListView/index.js b/packages/core/admin/admin/src/content-manager/pages/ListView/index.js
index 1eca5b378a..983b5c6ba9 100644
--- a/packages/core/admin/admin/src/content-manager/pages/ListView/index.js
+++ b/packages/core/admin/admin/src/content-manager/pages/ListView/index.js
@@ -10,8 +10,6 @@ import {
HeaderLayout,
useNotifyAT,
Flex,
- Typography,
- Status,
} from '@strapi/design-system';
import {
NoPermissions,
@@ -33,7 +31,6 @@ import {
} from '@strapi/helper-plugin';
import { ArrowLeft, Cog, Plus } from '@strapi/icons';
import axios from 'axios';
-import getReviewWorkflowsColumn from 'ee_else_ce/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn';
import isEqual from 'lodash/isEqual';
import PropTypes from 'prop-types';
import { stringify } from 'qs';
@@ -45,6 +42,7 @@ import { bindActionCreators, compose } from 'redux';
import styled from 'styled-components';
import { INJECT_COLUMN_IN_TABLE } from '../../../exposedHooks';
+import { useEnterprise } from '../../../hooks/useEnterprise';
import { selectAdminPermissions } from '../../../pages/App/selectors';
import { InjectionZone } from '../../../shared/components';
import AttributeFilter from '../../components/AttributeFilter';
@@ -67,6 +65,8 @@ const ConfigureLayoutBox = styled(Box)`
}
`;
+const REVIEW_WORKFLOW_COLUMNS_CE = null;
+
function ListView({
canCreate,
canDelete,
@@ -107,8 +107,24 @@ function ListView({
const { pathname } = useLocation();
const { push } = useHistory();
const { formatMessage } = useIntl();
- const hasDraftAndPublish = options?.draftAndPublish || false;
const fetchClient = useFetchClient();
+
+ const hasDraftAndPublish = options?.draftAndPublish ?? false;
+ const hasReviewWorkflows = options?.reviewWorkflows ?? false;
+
+ const reviewWorkflowColumns = useEnterprise(
+ REVIEW_WORKFLOW_COLUMNS_CE,
+ async () =>
+ (
+ await import(
+ '../../../../../ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/constants'
+ )
+ ).REVIEW_WORKFLOW_COLUMNS_EE,
+ {
+ enabled: !!options?.reviewWorkflows,
+ }
+ );
+
const { post, del } = fetchClient;
const bulkPublishMutation = useMutation(
@@ -388,24 +404,8 @@ function ListView({
};
});
- if (!hasDraftAndPublish) {
- return formattedHeaders;
- }
-
- // this should not exist. Ideally we would use registerHook() similar to what has been done
- // in the i18n plugin. In order to do that review-workflows should have been a plugin. In
- // a future iteration we need to find a better pattern.
-
- // In CE this will return null - in EE a column definition including the custom formatting component.
- const reviewWorkflowColumn = getReviewWorkflowsColumn(layout);
-
- if (reviewWorkflowColumn) {
- formattedHeaders.push(reviewWorkflowColumn);
- }
-
- return [
- ...formattedHeaders,
- {
+ if (hasDraftAndPublish) {
+ formattedHeaders.push({
key: '__published_at_temp_key__',
name: 'publishedAt',
fieldSchema: {
@@ -419,25 +419,29 @@ function ListView({
searchable: false,
sortable: true,
},
- // eslint-disable-next-line react/no-unstable-nested-components
- cellFormatter(cellData) {
- const isPublished = cellData.publishedAt;
- const variant = isPublished ? 'success' : 'secondary';
+ });
+ }
- return (
-
-
- {formatMessage({
- id: getTrad(`containers.List.${isPublished ? 'published' : 'draft'}`),
- defaultMessage: isPublished ? 'Published' : 'Draft',
- })}
-
-
- );
- },
- },
- ];
- }, [runHookWaterfall, displayedHeaders, layout, hasDraftAndPublish, formatMessage]);
+ if (reviewWorkflowColumns) {
+ // Make sure the column header label is translated
+ if (typeof reviewWorkflowColumns.metadatas.label !== 'string') {
+ reviewWorkflowColumns.metadatas.label = formatMessage(
+ reviewWorkflowColumns.metadatas.label
+ );
+ }
+
+ formattedHeaders.push(reviewWorkflowColumns);
+ }
+
+ return formattedHeaders;
+ }, [
+ runHookWaterfall,
+ displayedHeaders,
+ layout,
+ reviewWorkflowColumns,
+ hasDraftAndPublish,
+ formatMessage,
+ ]);
const subtitle = canRead
? formatMessage(
@@ -580,6 +584,10 @@ function ListView({
canCreate={canCreate}
canDelete={canDelete}
contentType={contentType}
+ features={{
+ hasDraftAndPublish,
+ hasReviewWorkflows,
+ }}
headers={tableHeaders}
rows={data}
withBulkActions
diff --git a/packages/core/admin/admin/src/hooks/useEnterprise/tests/useEnterprise.test.js b/packages/core/admin/admin/src/hooks/useEnterprise/tests/useEnterprise.test.js
index 47a8d20824..96b3a59e79 100644
--- a/packages/core/admin/admin/src/hooks/useEnterprise/tests/useEnterprise.test.js
+++ b/packages/core/admin/admin/src/hooks/useEnterprise/tests/useEnterprise.test.js
@@ -54,6 +54,14 @@ describe('useEnterprise (EE)', () => {
await waitFor(() => expect(result.current).toStrictEqual(EE_DATA_FIXTURE));
});
+ test('Returns CE data, when enabled is set to false', async () => {
+ const { result } = setup(CE_DATA_FIXTURE, async () => EE_DATA_FIXTURE, {
+ enabled: false,
+ });
+
+ await waitFor(() => expect(result.current).toStrictEqual(CE_DATA_FIXTURE));
+ });
+
test('Returns a custom defaultValue on first render followed by the EE data', async () => {
const { result } = setup(CE_DATA_FIXTURE, async () => EE_DATA_FIXTURE, {
defaultValue: false,
diff --git a/packages/core/admin/admin/src/hooks/useEnterprise/useEnterprise.js b/packages/core/admin/admin/src/hooks/useEnterprise/useEnterprise.js
index 97688cd872..03ab26c88f 100644
--- a/packages/core/admin/admin/src/hooks/useEnterprise/useEnterprise.js
+++ b/packages/core/admin/admin/src/hooks/useEnterprise/useEnterprise.js
@@ -9,7 +9,7 @@ function isEnterprise() {
export function useEnterprise(
ceData,
eeCallback,
- { defaultValue = null, combine = (ceData, eeData) => eeData } = {}
+ { defaultValue = null, combine = (ceData, eeData) => eeData, enabled = true } = {}
) {
const eeCallbackRef = useCallbackRef(eeCallback);
const combineCallbackRef = useCallbackRef(combine);
@@ -17,7 +17,7 @@ export function useEnterprise(
// We have to use a nested object here, because functions (e.g. Components)
// can not be stored as value directly
const [{ data }, setData] = React.useState({
- data: isEnterprise() ? defaultValue : ceData,
+ data: isEnterprise() && enabled ? defaultValue : ceData,
});
React.useEffect(() => {
@@ -27,10 +27,10 @@ export function useEnterprise(
setData({ data: combineCallbackRef(ceData, eeData) });
}
- if (isEnterprise()) {
+ if (isEnterprise() && enabled) {
importEE();
}
- }, [ceData, eeCallbackRef, combineCallbackRef]);
+ }, [ceData, eeCallbackRef, combineCallbackRef, enabled]);
return data;
}
diff --git a/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn.js b/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn.js
deleted file mode 100644
index c5afe6c8de..0000000000
--- a/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/getTableColumn.js
+++ /dev/null
@@ -1,58 +0,0 @@
-import React from 'react';
-
-import { Typography } from '@strapi/design-system';
-import { useIntl } from 'react-intl';
-
-import getTrad from '../../../../../../../admin/src/content-manager/utils/getTrad';
-import { STAGE_COLOR_DEFAULT } from '../../../../../pages/SettingsPage/pages/ReviewWorkflows/constants';
-
-import ReviewWorkflowsStage from '.';
-
-export default (layout) => {
- const { formatMessage } = useIntl();
-
- // TODO: As soon as the feature was enabled in EE mode, the BE currently does not have a way to send
- // `false` once a user is in CE mode again. We shouldn't have to perform the window.strapi.isEE check here
- // and it is meant to be in interim solution until we find a better one.
- const hasReviewWorkflows =
- (window.strapi.features.isEnabled(window.strapi.features.REVIEW_WORKFLOWS) &&
- layout.contentType.options?.reviewWorkflows) ??
- false;
-
- if (!hasReviewWorkflows) {
- return null;
- }
-
- return {
- key: '__strapi_reviewWorkflows_stage_temp_key__',
- name: 'strapi_reviewWorkflows_stage',
- fieldSchema: {
- type: 'relation',
- },
- metadatas: {
- label: formatMessage({
- id: getTrad(`containers.ListPage.table-headers.reviewWorkflows.stage`),
- defaultMessage: 'Review stage',
- }),
- searchable: false,
- sortable: true,
- mainField: {
- name: 'name',
- schema: {
- type: 'string',
- },
- },
- },
- cellFormatter({ strapi_reviewWorkflows_stage }) {
- // if entities are created e.g. through lifecycle methods
- // they may not have a stage assigned
- if (!strapi_reviewWorkflows_stage) {
- return -;
- }
-
- const { color, name } = strapi_reviewWorkflows_stage;
-
- return ;
- },
- };
-};
diff --git a/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/index.js b/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/index.js
deleted file mode 100644
index 9d18524090..0000000000
--- a/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/index.js
+++ /dev/null
@@ -1,3 +0,0 @@
-import { ReviewWorkflowsStageEE } from './ReviewWorkflowsStageEE';
-
-export default ReviewWorkflowsStageEE;
diff --git a/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/ReviewWorkflowsStageEE.js b/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/ReviewWorkflowsStageEE.js
similarity index 88%
rename from packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/ReviewWorkflowsStageEE.js
rename to packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/ReviewWorkflowsStageEE.js
index d10767b7f7..a3ac28b204 100644
--- a/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/ReviewWorkflowsStageEE.js
+++ b/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/ReviewWorkflowsStageEE.js
@@ -4,7 +4,7 @@ import { Box, Flex, Typography } from '@strapi/design-system';
import { pxToRem } from '@strapi/helper-plugin';
import PropTypes from 'prop-types';
-import { getStageColorByHex } from '../../../../../pages/SettingsPage/pages/ReviewWorkflows/utils/colors';
+import { getStageColorByHex } from '../../../../pages/SettingsPage/pages/ReviewWorkflows/utils/colors';
export function ReviewWorkflowsStageEE({ color, name }) {
const { themeColorName } = getStageColorByHex(color);
diff --git a/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/constants.js b/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/constants.js
new file mode 100644
index 0000000000..1ec56488b0
--- /dev/null
+++ b/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/constants.js
@@ -0,0 +1,24 @@
+import getTrad from '../../../../../../admin/src/content-manager/utils/getTrad';
+
+export const REVIEW_WORKFLOW_COLUMNS_EE = {
+ key: '__strapi_reviewWorkflows_stage_temp_key__',
+ name: 'strapi_reviewWorkflows_stage',
+ fieldSchema: {
+ type: 'relation',
+ },
+ metadatas: {
+ // formatMessage() will be applied when the column is rendered
+ label: {
+ id: getTrad(`containers.ListPage.table-headers.reviewWorkflows.stage`),
+ defaultMessage: 'Review stage',
+ },
+ searchable: false,
+ sortable: true,
+ mainField: {
+ name: 'name',
+ schema: {
+ type: 'string',
+ },
+ },
+ },
+};
diff --git a/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/index.js b/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/index.js
new file mode 100644
index 0000000000..354bfb6848
--- /dev/null
+++ b/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/index.js
@@ -0,0 +1 @@
+export * from './ReviewWorkflowsStageEE';
diff --git a/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/tests/ReviewWorkflowsStage.test.js b/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/tests/ReviewWorkflowsStage.test.js
similarity index 87%
rename from packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/tests/ReviewWorkflowsStage.test.js
rename to packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/tests/ReviewWorkflowsStage.test.js
index 76ec2a92a4..5d704a62a8 100644
--- a/packages/core/admin/ee/admin/content-manager/components/DynamicTable/CellContent/ReviewWorkflowsStage/tests/ReviewWorkflowsStage.test.js
+++ b/packages/core/admin/ee/admin/content-manager/pages/ListView/ReviewWorkflowsColumn/tests/ReviewWorkflowsStage.test.js
@@ -4,12 +4,12 @@ import { lightTheme, ThemeProvider } from '@strapi/design-system';
import { render } from '@testing-library/react';
import { IntlProvider } from 'react-intl';
-import ReviewWorkflowsStage from '..';
+import { ReviewWorkflowsStageEE } from '..';
const ComponentFixture = (props) => (
-
+
);