Skip to content

Commit

Permalink
refactor: fixed tests
Browse files Browse the repository at this point in the history
  • Loading branch information
PKulkoRaccoonGang committed Oct 20, 2024
1 parent 6187a96 commit 0146c70
Show file tree
Hide file tree
Showing 12 changed files with 148 additions and 48 deletions.
27 changes: 25 additions & 2 deletions src/grading-settings/grading-sidebar/GradingSidebar.test.jsx
Original file line number Diff line number Diff line change
@@ -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'),
Expand All @@ -16,11 +19,31 @@ jest.mock('react-router-dom', () => ({

const RootWrapper = () => (
<IntlProvider locale="en" messages={{}}>
<GradingSidebar intl={injectIntl} courseId="123" />
<AppProvider store={store}>
<GradingSidebar intl={injectIntl} courseId="123" />
</AppProvider>
</IntlProvider>
);

describe('<GradingSidebar />', () => {
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(<RootWrapper />);
expect(getByText(messages.gradingSidebarTitle.defaultMessage)).toBeInTheDocument();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -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(
<IntlProvider locale="en">
<ExperimentConfigurationsSection
Expand Down
1 change: 1 addition & 0 deletions src/pages-and-resources/PagesAndResources.test.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ describe('PagesAndResources', () => {

expect(screen.queryByRole('heading', { name: 'Content permissions' })).not.toBeInTheDocument();
});

it('show content permissions section if Learning Assistant app is enabled', async () => {
const initialState = {
models: {
Expand Down
39 changes: 25 additions & 14 deletions src/pages-and-resources/pages/PageCard.test.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -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';

Expand All @@ -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(
<IntlProvider locale="en">
<AppProvider store={store}>
<PagesAndResourcesProvider courseId="id">
<PageGrid
pages={[
{ legacyLink: 'SomeUrl', name: 'Custom pages', id: '1' },
{
legacyLink: 'SomeUrl',
name: 'Textbook',
id: '2',
enabled: true,
},
{ name: 'Page', allowedOperations: { enable: true }, id: '3' },
]}
/>
<PageGrid pages={mockPageConfig} />
</PagesAndResourcesProvider>
</AppProvider>
</IntlProvider>,
Expand Down Expand Up @@ -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);
});
});
8 changes: 4 additions & 4 deletions src/pages-and-resources/pages/PageSettingButton.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -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;

Expand Down
2 changes: 1 addition & 1 deletion src/studio-home/card-item/CardItem.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ describe('<CardItem />', () => {
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);
});
Expand Down
27 changes: 5 additions & 22 deletions src/studio-home/data/api.js
Original file line number Diff line number Diff line change
Expand Up @@ -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;
Expand All @@ -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;
}

Expand Down
2 changes: 1 addition & 1 deletion src/studio-home/data/selectors.js
Original file line number Diff line number Diff line change
@@ -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;
27 changes: 27 additions & 0 deletions src/studio-home/data/utils.js
Original file line number Diff line number Diff line change
@@ -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,
});
19 changes: 19 additions & 0 deletions src/studio-home/factories/mockApiResponses.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -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. */
Expand Down
34 changes: 31 additions & 3 deletions src/studio-home/verify-email-layout/VerifyEmailLayout.test.jsx
Original file line number Diff line number Diff line change
@@ -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 protected]',
Expand All @@ -18,28 +22,52 @@ jest.mock('react-router-dom', () => ({
pathname: mockPathname,
}),
}));

jest.mock('@edx/frontend-platform/auth');

getAuthenticatedUser.mockImplementation(() => fakeAuthenticatedUser);

const RootWrapper = () => (
<IntlProvider locale="en" messages={{}}>
<VerifyEmailLayout />
<AppProvider store={store}>
<VerifyEmailLayout />
</AppProvider>
</IntlProvider>
);

describe('<VerifyEmailLayout />', () => {
beforeEach(async () => {
initializeMockApp({
authenticatedUser: {
userId: 3,
username: 'abc123',
administrator: false,
roles: [],
},
});

store = initializeStore({
courseDetail: {
courseId: 'id',
status: 'sucessful',
},
});
});

it('renders successfully', () => {
const { getByText } = render(<RootWrapper />);

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();
});
Expand Down
2 changes: 1 addition & 1 deletion src/utils.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -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');
Expand Down

0 comments on commit 0146c70

Please sign in to comment.