diff --git a/src/grading-settings/grading-sidebar/GradingSidebar.test.jsx b/src/grading-settings/grading-sidebar/GradingSidebar.test.jsx
index 33da030b5b..64e8df482d 100644
--- a/src/grading-settings/grading-sidebar/GradingSidebar.test.jsx
+++ b/src/grading-settings/grading-sidebar/GradingSidebar.test.jsx
@@ -1,11 +1,14 @@
-import React from 'react';
import { IntlProvider, injectIntl } from '@edx/frontend-platform/i18n';
import { render } from '@testing-library/react';
+import { initializeMockApp } from '@edx/frontend-platform';
+import { AppProvider } from '@edx/frontend-platform/react';
+import initializeStore from '../../store';
import messages from './messages';
import GradingSidebar from '.';
const mockPathname = '/foo-bar';
+let store;
jest.mock('react-router-dom', () => ({
...jest.requireActual('react-router-dom'),
@@ -16,11 +19,31 @@ jest.mock('react-router-dom', () => ({
const RootWrapper = () => (
-
+
+
+
);
describe('', () => {
+ beforeEach(async () => {
+ initializeMockApp({
+ authenticatedUser: {
+ userId: 3,
+ username: 'abc123',
+ administrator: false,
+ roles: [],
+ },
+ });
+
+ store = initializeStore({
+ courseDetail: {
+ courseId: 'id',
+ status: 'sucessful',
+ },
+ });
+ });
+
it('renders sidebar text content correctly', () => {
const { getByText } = render();
expect(getByText(messages.gradingSidebarTitle.defaultMessage)).toBeInTheDocument();
diff --git a/src/group-configurations/experiment-configurations-section/ExperimentConfigurationsSection.test.jsx b/src/group-configurations/experiment-configurations-section/ExperimentConfigurationsSection.test.jsx
index 580258006f..6fcd756567 100644
--- a/src/group-configurations/experiment-configurations-section/ExperimentConfigurationsSection.test.jsx
+++ b/src/group-configurations/experiment-configurations-section/ExperimentConfigurationsSection.test.jsx
@@ -8,12 +8,20 @@ import ExperimentConfigurationsSection from '.';
const handleCreateMock = jest.fn();
const handleDeleteMock = jest.fn();
const handleEditMock = jest.fn();
+const mockPathname = '/foo-bar';
const experimentConfigurationActions = {
handleCreate: handleCreateMock,
handleDelete: handleDeleteMock,
handleEdit: handleEditMock,
};
+jest.mock('react-router-dom', () => ({
+ ...jest.requireActual('react-router-dom'),
+ useLocation: () => ({
+ pathname: mockPathname,
+ }),
+}));
+
const renderComponent = (props) => render(
{
expect(screen.queryByRole('heading', { name: 'Content permissions' })).not.toBeInTheDocument();
});
+
it('show content permissions section if Learning Assistant app is enabled', async () => {
const initialState = {
models: {
diff --git a/src/pages-and-resources/pages/PageCard.test.jsx b/src/pages-and-resources/pages/PageCard.test.jsx
index 33ecf5f4b4..376ef757cf 100644
--- a/src/pages-and-resources/pages/PageCard.test.jsx
+++ b/src/pages-and-resources/pages/PageCard.test.jsx
@@ -3,7 +3,7 @@ import {
queryAllByRole,
} from '@testing-library/react';
-import { initializeMockApp } from '@edx/frontend-platform';
+import { initializeMockApp, getConfig } from '@edx/frontend-platform';
import { AppProvider } from '@edx/frontend-platform/react';
import { IntlProvider } from '@edx/frontend-platform/i18n';
@@ -14,24 +14,33 @@ import PagesAndResourcesProvider from '../PagesAndResourcesProvider';
let container;
let store;
+const mockPageConfig = [
+ {
+ id: '1',
+ legacyLink: `${getConfig().STUDIO_BASE_URL}/tabs/course-v1:OpenedX+DemoX+DemoCourse`,
+ name: 'Custom pages',
+ },
+ {
+ id: '2',
+ legacyLink: `${getConfig().STUDIO_BASE_URL}/textbooks/course-v1:OpenedX+DemoX+DemoCourse`,
+ name: 'Textbook',
+ enabled: true,
+ },
+ {
+ name: 'Page',
+ allowedOperations: {
+ enable: true,
+ },
+ id: '3',
+ },
+];
const renderComponent = () => {
const wrapper = render(
-
+
,
@@ -61,9 +70,11 @@ describe('LiveSettings', () => {
renderComponent();
expect(queryAllByRole(container, 'button')).toHaveLength(3);
});
+
it('should navigate to legacyLink', async () => {
renderComponent();
+ const textbookPagePath = mockPageConfig[0][1];
const textbookSettingsButton = queryAllByRole(container, 'link')[1];
- expect(textbookSettingsButton).toHaveAttribute('href', 'SomeUrl');
+ expect(textbookSettingsButton).toHaveAttribute('href', textbookPagePath);
});
});
diff --git a/src/pages-and-resources/pages/PageSettingButton.jsx b/src/pages-and-resources/pages/PageSettingButton.jsx
index 803bcc6886..63f6f8521e 100644
--- a/src/pages-and-resources/pages/PageSettingButton.jsx
+++ b/src/pages-and-resources/pages/PageSettingButton.jsx
@@ -20,25 +20,25 @@ const PageSettingButton = ({
const { formatMessage } = useIntl();
const { path: pagesAndResourcesPath } = useContext(PagesAndResourcesContext);
const navigate = useNavigate();
- const { waffleFlags } = useSelector(getStudioHomeData);
+ const studioHomeData = useSelector(getStudioHomeData);
const linkTo = useMemo(() => {
if (!legacyLink) { return null; }
if (legacyLink.includes('textbooks')) {
- return waffleFlags?.ENABLE_NEW_TEXTBOOKS_PAGE
+ return studioHomeData?.waffleFlags?.ENABLE_NEW_TEXTBOOKS_PAGE
? `/course/${courseId}/${id.replace('_', '-')}`
: legacyLink;
}
if (legacyLink.includes('tabs')) {
- return waffleFlags?.ENABLE_NEW_CUSTOM_PAGES
+ return studioHomeData?.waffleFlags?.ENABLE_NEW_CUSTOM_PAGES
? `/course/${courseId}/${id.replace('_', '-')}`
: legacyLink;
}
return null;
- }, [legacyLink, waffleFlags, id]);
+ }, [legacyLink, studioHomeData?.waffleFlags, id]);
const canConfigureOrEnable = allowedOperations?.configure || allowedOperations?.enable;
diff --git a/src/studio-home/card-item/CardItem.test.tsx b/src/studio-home/card-item/CardItem.test.tsx
index e2cd393459..986cb40997 100644
--- a/src/studio-home/card-item/CardItem.test.tsx
+++ b/src/studio-home/card-item/CardItem.test.tsx
@@ -43,7 +43,7 @@ describe('', () => {
const dropDownMenu = screen.getByTestId('toggle-dropdown');
fireEvent.click(dropDownMenu);
const btnReRunCourse = screen.getByText(messages.btnReRunText.defaultMessage);
- expect(btnReRunCourse).toHaveAttribute('href', trimSlashes(props.rerunLink));
+ expect(btnReRunCourse).toHaveAttribute('href', `/${trimSlashes(props.rerunLink)}`);
const viewLiveLink = screen.getByText(messages.viewLiveBtnText.defaultMessage);
expect(viewLiveLink).toHaveAttribute('href', props.lmsLink);
});
diff --git a/src/studio-home/data/api.js b/src/studio-home/data/api.js
index 6602a4e370..5e80bc6182 100644
--- a/src/studio-home/data/api.js
+++ b/src/studio-home/data/api.js
@@ -2,6 +2,8 @@
import { camelCaseObject, snakeCaseObject, getConfig } from '@edx/frontend-platform';
import { getAuthenticatedHttpClient } from '@edx/frontend-platform/auth';
+import { getWaffleFlagsConfig } from './utils';
+
export const getApiBaseUrl = () => getConfig().STUDIO_BASE_URL;
export const getStudioHomeApiUrl = () => new URL('api/contentstore/v1/home', getApiBaseUrl()).href;
export const getRequestCourseCreatorUrl = () => new URL('request_course_creator', getApiBaseUrl()).href;
@@ -14,30 +16,11 @@ export const getCourseNotificationUrl = (url) => new URL(url, getApiBaseUrl()).h
export async function getStudioHomeData() {
const { data } = await getAuthenticatedHttpClient().get(getStudioHomeApiUrl());
- const result = camelCaseObject(data);
-
- const waffleFlagsConfig = {
- ENABLE_NEW_SCHEDULE_AND_DETAILS_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewScheduleDetailsPage,
- ENABLE_NEW_GRADING_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewGradingPage,
- ENABLE_NEW_COURSE_TEAM_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewCourseTeamPage,
- ENABLE_NEW_GROUP_CONFIGURATIONS_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewGroupConfigurationsPage,
- ENABLE_NEW_ADVANCED_SETTINGS_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewAdvancedSettingsPage,
- ENABLE_NEW_COURSE_OUTLINE_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewCourseOutlinePage,
- ENABLE_NEW_COURSE_UPDATES_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewUpdatesPage,
- ENABLE_NEW_FILE_UPLOAD_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewFilesUploadsPage,
- ENABLE_NEW_PAGES_AND_RESOURCES_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewCustomPages,
- ENABLE_NEW_IMPORT_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewImportPage,
- ENABLE_NEW_EXPORT_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewExportPage,
- ENABLE_NEW_HOME_PAGE: result?.waffleFlags?.newStudioMfeUseNewHomePage,
- ENABLE_NEW_TEXTBOOKS_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewTextbooksPage,
- ENABLE_NEW_CUSTOM_PAGES: result?.waffleFlags?.contentstoreNewStudioMfeUseNewCustomPages,
- ENABLE_NEW_VIDEO_UPLOAD_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewVideoUploadsPage,
- ENABLE_NEW_CERTIFICATES_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewCertificatesPage,
- ENABLE_NEW_UNIT_PAGE: result?.waffleFlags?.contentstoreNewStudioMfeUseNewUnitPage,
+ const result = {
+ ...camelCaseObject(data),
+ waffleFlags: getWaffleFlagsConfig(camelCaseObject(data)),
};
- result.waffleFlags = waffleFlagsConfig;
-
return result;
}
diff --git a/src/studio-home/data/selectors.js b/src/studio-home/data/selectors.js
index 5487ca42b6..97e525fb5b 100644
--- a/src/studio-home/data/selectors.js
+++ b/src/studio-home/data/selectors.js
@@ -1,4 +1,4 @@
-export const getStudioHomeData = (state) => state.studioHome.studioHomeData;
+export const getStudioHomeData = (state) => state.studioHome?.studioHomeData;
export const getLoadingStatuses = (state) => state.studioHome.loadingStatuses;
export const getSavingStatuses = (state) => state.studioHome.savingStatuses;
export const getStudioHomeCoursesParams = (state) => state.studioHome.studioHomeCoursesRequestParams;
diff --git a/src/studio-home/data/utils.js b/src/studio-home/data/utils.js
new file mode 100644
index 0000000000..81d6d885f5
--- /dev/null
+++ b/src/studio-home/data/utils.js
@@ -0,0 +1,27 @@
+/**
+ * Retrieves the waffle flag configuration based on the provided result object.
+ *
+ * @param {Object} result - The result object containing waffle flags.
+ * @param {Object} result.waffleFlags - The waffle flags for feature toggling.
+ * @returns {Object} The configuration object with feature toggles.
+ */
+// eslint-disable-next-line import/prefer-default-export
+export const getWaffleFlagsConfig = ({ waffleFlags = {} }) => ({
+ ENABLE_NEW_SCHEDULE_AND_DETAILS_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewScheduleDetailsPage ?? false,
+ ENABLE_NEW_GRADING_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewGradingPage ?? false,
+ ENABLE_NEW_COURSE_TEAM_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewCourseTeamPage ?? false,
+ ENABLE_NEW_GROUP_CONFIGURATIONS_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewGroupConfigurationsPage ?? false,
+ ENABLE_NEW_ADVANCED_SETTINGS_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewAdvancedSettingsPage ?? false,
+ ENABLE_NEW_COURSE_OUTLINE_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewCourseOutlinePage ?? false,
+ ENABLE_NEW_COURSE_UPDATES_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewUpdatesPage ?? false,
+ ENABLE_NEW_FILE_UPLOAD_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewFilesUploadsPage ?? false,
+ ENABLE_NEW_PAGES_AND_RESOURCES_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewCustomPages ?? false,
+ ENABLE_NEW_IMPORT_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewImportPage ?? false,
+ ENABLE_NEW_EXPORT_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewExportPage ?? false,
+ ENABLE_NEW_HOME_PAGE: waffleFlags.newStudioMfeUseNewHomePage ?? false,
+ ENABLE_NEW_TEXTBOOKS_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewTextbooksPage ?? false,
+ ENABLE_NEW_CUSTOM_PAGES: waffleFlags.contentstoreNewStudioMfeUseNewCustomPages ?? false,
+ ENABLE_NEW_VIDEO_UPLOAD_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewVideoUploadsPage ?? false,
+ ENABLE_NEW_CERTIFICATES_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewCertificatesPage ?? false,
+ ENABLE_NEW_UNIT_PAGE: waffleFlags.contentstoreNewStudioMfeUseNewUnitPage ?? false,
+});
diff --git a/src/studio-home/factories/mockApiResponses.jsx b/src/studio-home/factories/mockApiResponses.jsx
index 8d86e22d4a..ce5fdf90e2 100644
--- a/src/studio-home/factories/mockApiResponses.jsx
+++ b/src/studio-home/factories/mockApiResponses.jsx
@@ -45,6 +45,25 @@ export const generateGetStudioHomeDataApiResponse = () => ({
platformName: 'Your Platform Name Here',
userIsActive: true,
allowToCreateNewOrg: false,
+ waffleFlags: {
+ ENABLE_NEW_ADVANCED_SETTINGS_PAGE: false,
+ ENABLE_NEW_CERTIFICATES_PAGE: false,
+ ENABLE_NEW_COURSE_OUTLINE_PAGE: false,
+ ENABLE_NEW_COURSE_TEAM_PAGE: false,
+ ENABLE_NEW_COURSE_UPDATES_PAGE: false,
+ ENABLE_NEW_CUSTOM_PAGES: false,
+ ENABLE_NEW_EXPORT_PAGE: false,
+ ENABLE_NEW_FILE_UPLOAD_PAGE: false,
+ ENABLE_NEW_GRADING_PAGE: false,
+ ENABLE_NEW_GROUP_CONFIGURATIONS_PAGE: false,
+ ENABLE_NEW_HOME_PAGE: false,
+ ENABLE_NEW_IMPORT_PAGE: false,
+ ENABLE_NEW_PAGES_AND_RESOURCES_PAGE: false,
+ ENABLE_NEW_SCHEDULE_AND_DETAILS_PAGE: false,
+ ENABLE_NEW_TEXTBOOKS_PAGE: false,
+ ENABLE_NEW_UNIT_PAGE: false,
+ ENABLE_NEW_VIDEO_UPLOAD_PAGE: false,
+ },
});
/** Mock for the deprecated /api/contentstore/v1/home/courses endpoint. Note this endpoint is NOT paginated. */
diff --git a/src/studio-home/verify-email-layout/VerifyEmailLayout.test.jsx b/src/studio-home/verify-email-layout/VerifyEmailLayout.test.jsx
index ed5f507831..785fb484f0 100644
--- a/src/studio-home/verify-email-layout/VerifyEmailLayout.test.jsx
+++ b/src/studio-home/verify-email-layout/VerifyEmailLayout.test.jsx
@@ -1,11 +1,15 @@
-import React from 'react';
import { render } from '@testing-library/react';
import { getAuthenticatedUser } from '@edx/frontend-platform/auth';
import { IntlProvider } from '@edx/frontend-platform/i18n';
+import { initializeMockApp } from '@edx/frontend-platform';
+import { AppProvider } from '@edx/frontend-platform/react';
+import initializeStore from '../../store';
import messages from './messages';
import VerifyEmailLayout from '.';
+let store;
+
const mockPathname = '/foo-bar';
const fakeAuthenticatedUser = {
email: 'email@fake.com',
@@ -18,28 +22,52 @@ jest.mock('react-router-dom', () => ({
pathname: mockPathname,
}),
}));
+
jest.mock('@edx/frontend-platform/auth');
+
getAuthenticatedUser.mockImplementation(() => fakeAuthenticatedUser);
const RootWrapper = () => (
-
+
+
+
);
describe('', () => {
+ beforeEach(async () => {
+ initializeMockApp({
+ authenticatedUser: {
+ userId: 3,
+ username: 'abc123',
+ administrator: false,
+ roles: [],
+ },
+ });
+
+ store = initializeStore({
+ courseDetail: {
+ courseId: 'id',
+ status: 'sucessful',
+ },
+ });
+ });
+
it('renders successfully', () => {
const { getByText } = render();
+
expect(
getByText(`Thanks for signing up, ${fakeAuthenticatedUser.username}!`, {
exact: false,
}),
).toBeInTheDocument();
- expect(getByText(messages.bannerTitle.defaultMessage)).toBeInTheDocument();
+
expect(getByText(
`Almost there! In order to complete your sign up we need you to verify your email address (${fakeAuthenticatedUser.email}). An activation message and next steps should be waiting for you there.`,
{ exact: false },
)).toBeInTheDocument();
+
expect(getByText(messages.sidebarTitle.defaultMessage)).toBeInTheDocument();
expect(getByText(messages.sidebarDescription.defaultMessage)).toBeInTheDocument();
});
diff --git a/src/utils.test.js b/src/utils.test.js
index e4aada849f..05e07ddc1a 100644
--- a/src/utils.test.js
+++ b/src/utils.test.js
@@ -71,7 +71,7 @@ describe('FilesAndUploads utils', () => {
getConfig.mockReturnValue({ PUBLIC_PATH: 'example.com/' });
getPath.mockReturnValue('/course-authoring/');
- const checkPath = '/some/path';
+ const checkPath = '/course-authoring/some/path';
const result = createCorrectInternalRoute(checkPath);
expect(result).toBe('/course-authoring/some/path');