diff --git a/plugins/course-apps/proctoring/Settings.test.jsx b/plugins/course-apps/proctoring/Settings.test.jsx index a2148e89e2..6a07c7143c 100644 --- a/plugins/course-apps/proctoring/Settings.test.jsx +++ b/plugins/course-apps/proctoring/Settings.test.jsx @@ -471,9 +471,8 @@ describe('ProctoredExamSettings', () => { screen.getByDisplayValue('mockproc'); }); // (1) for studio settings - // (2) waffle flags - // (3) for course details - expect(axiosMock.history.get.length).toBe(3); + // (2) for course details + expect(axiosMock.history.get.length).toBe(2); expect(axiosMock.history.get[0].url.includes('proctored_exam_settings')).toEqual(true); }); diff --git a/src/CourseAuthoringContext.tsx b/src/CourseAuthoringContext.tsx index a3101eb5f1..c980e11829 100644 --- a/src/CourseAuthoringContext.tsx +++ b/src/CourseAuthoringContext.tsx @@ -1,4 +1,3 @@ -import { getConfig } from '@edx/frontend-platform'; import { createContext, useContext, @@ -10,7 +9,7 @@ import { useNavigate } from 'react-router'; import { useToggleWithValue } from '@src/hooks'; import { type UnitXBlock, type XBlock } from '@src/data/types'; import { CourseDetailsData } from './data/api'; -import { useCourseDetails, useWaffleFlags } from './data/apiHooks'; +import { useCourseDetails } from './data/apiHooks'; import { RequestStatusType } from './data/constants'; import { getOutlineIndexData } from './course-outline/data/selectors'; @@ -53,7 +52,6 @@ export const CourseAuthoringProvider = ({ courseId, }: CourseAuthoringProviderProps) => { const navigate = useNavigate(); - const waffleFlags = useWaffleFlags(); const { data: courseDetails, status: courseDetailStatus } = useCourseDetails(courseId); const canChangeProviders = getAuthenticatedUser().administrator || new Date(courseDetails?.start ?? 0) > new Date(); const { courseStructure } = useSelector(getOutlineIndexData); @@ -65,25 +63,13 @@ export const CourseAuthoringProvider = ({ closeUnlinkModal, ] = useToggleWithValue(); - const getUnitUrl = (locator: string) => { - if (getConfig().ENABLE_UNIT_PAGE === 'true' && waffleFlags.useNewUnitPage) { - // instanbul ignore next - return `/course/${courseId}/container/${locator}`; - } - return `${getConfig().STUDIO_BASE_URL}/container/${locator}`; - }; + const getUnitUrl = (locator: string) => `/course/${courseId}/container/${locator}`; /** * Open the unit page for a given locator. */ const openUnitPage = async (locator: string) => { - const url = getUnitUrl(locator); - if (getConfig().ENABLE_UNIT_PAGE === 'true' && waffleFlags.useNewUnitPage) { - // instanbul ignore next - navigate(url); - } else { - window.location.assign(url); - } + navigate(getUnitUrl(locator)); }; const context = useMemo(() => ({ diff --git a/src/course-checklist/ChecklistSection/ChecklistItemBody.jsx b/src/course-checklist/ChecklistSection/ChecklistItemBody.jsx index 8fc0c1643a..79cde9a4ea 100644 --- a/src/course-checklist/ChecklistSection/ChecklistItemBody.jsx +++ b/src/course-checklist/ChecklistSection/ChecklistItemBody.jsx @@ -5,13 +5,10 @@ import { ActionRow, Button, Icon } from '@openedx/paragon'; import { CheckCircle, RadioButtonUnchecked } from '@openedx/paragon/icons'; import { getConfig } from '@edx/frontend-platform'; -import { useWaffleFlags } from '@src/data/apiHooks'; - import messages from './messages'; -const getUpdateLinks = (courseId, waffleFlags) => { +const getUpdateLinks = (courseId) => { const baseUrl = getConfig().STUDIO_BASE_URL; - const isLegacyOutlineUrl = !waffleFlags.useNewCourseOutlinePage; return { welcomeMessage: `/course/${courseId}/course_info`, @@ -19,7 +16,7 @@ const getUpdateLinks = (courseId, waffleFlags) => { certificate: `/course/${courseId}/certificates`, courseDates: `/course/${courseId}/settings/details/#schedule`, proctoringEmail: `${baseUrl}/pages-and-resources/proctoring/settings`, - outline: isLegacyOutlineUrl ? `${baseUrl}/course/${courseId}` : `/course/${courseId}`, + outline: `/course/${courseId}`, }; }; @@ -29,8 +26,7 @@ const ChecklistItemBody = ({ isCompleted, }) => { const intl = useIntl(); - const waffleFlags = useWaffleFlags(courseId); - const updateLinks = getUpdateLinks(courseId, waffleFlags); + const updateLinks = getUpdateLinks(courseId); return ( diff --git a/src/course-checklist/ChecklistSection/ChecklistItemComment.jsx b/src/course-checklist/ChecklistSection/ChecklistItemComment.jsx index aa0e3f3010..b2c8ec234a 100644 --- a/src/course-checklist/ChecklistSection/ChecklistItemComment.jsx +++ b/src/course-checklist/ChecklistSection/ChecklistItemComment.jsx @@ -3,8 +3,6 @@ import { FormattedMessage, FormattedNumber } from '@edx/frontend-platform/i18n'; import { Icon } from '@openedx/paragon'; import { Link } from 'react-router-dom'; import { ModeComment } from '@openedx/paragon/icons'; -import { getConfig } from '@edx/frontend-platform'; -import { useWaffleFlags } from '../../data/apiHooks'; import messages from './messages'; const ChecklistItemComment = ({ @@ -12,11 +10,7 @@ const ChecklistItemComment = ({ checkId, data, }) => { - const waffleFlags = useWaffleFlags(courseId); - - const getPathToCourseOutlinePage = (assignmentId) => (waffleFlags.useNewCourseOutlinePage - ? `/course/${courseId}#${assignmentId}` : - `${getConfig().STUDIO_BASE_URL}/course/${courseId}#${assignmentId}`); + const getPathToCourseOutlinePage = (assignmentId) => `/course/${courseId}#${assignmentId}`; const commentWrapper = (comment) => (
diff --git a/src/course-checklist/ChecklistSection/ChecklistSection.test.jsx b/src/course-checklist/ChecklistSection/ChecklistSection.test.jsx index 6eda1f059d..8b35de0da6 100644 --- a/src/course-checklist/ChecklistSection/ChecklistSection.test.jsx +++ b/src/course-checklist/ChecklistSection/ChecklistSection.test.jsx @@ -39,9 +39,7 @@ describe('ChecklistSection', () => { const { axiosMock } = initializeMocks(); axiosMock .onGet(getApiWaffleFlagsUrl(courseId)) - .reply(200, { - useNewCourseOutlinePage: true, - }); + .reply(200, {}); }); it('a heading using the dataHeading prop', () => { diff --git a/src/course-unit/breadcrumbs/Breadcrumbs.test.tsx b/src/course-unit/breadcrumbs/Breadcrumbs.test.tsx index 5f47f25251..6ffa9bf23c 100644 --- a/src/course-unit/breadcrumbs/Breadcrumbs.test.tsx +++ b/src/course-unit/breadcrumbs/Breadcrumbs.test.tsx @@ -1,5 +1,4 @@ import userEvent from '@testing-library/user-event'; -import { getConfig } from '@edx/frontend-platform'; import { initializeMocks, waitFor, @@ -54,7 +53,7 @@ describe('', () => { await executeThunk(fetchCourseSectionVerticalData(courseId), reduxStore.dispatch); axiosMock .onGet(getApiWaffleFlagsUrl(courseId)) - .reply(200, { useNewCourseOutlinePage: true }); + .reply(200, {}); }); it('render Breadcrumbs component correctly', async () => { @@ -150,24 +149,4 @@ describe('', () => { await user.click(dropdownItem); expect(dropdownItem).toHaveAttribute('href', url); }); - - it('falls back to window.location.href when the waffle flag is disabled', async () => { - const user = userEvent.setup(); - // eslint-disable-next-line @typescript-eslint/naming-convention - const { ancestor_xblocks: [{ children: [{ display_name, url }] }] } = courseSectionVerticalMock; - axiosMock - .onGet(getApiWaffleFlagsUrl(courseId)) - .reply(200, { useNewCourseOutlinePage: false }); - - const { getByText, getByRole } = renderComponent(); - - const dropdownBtn = getByText(breadcrumbsExpected.section.displayName); - await user.click(dropdownBtn); - - const dropdownItem = getByRole('link', { name: display_name }); - // We need waitFor here because the waffle flag defaults to true but asynchronously loads false from our axiosMock - await waitFor(() => { - expect(dropdownItem).toHaveAttribute('href', `${getConfig().STUDIO_BASE_URL}${url}`); - }); - }); }); diff --git a/src/course-unit/breadcrumbs/Breadcrumbs.tsx b/src/course-unit/breadcrumbs/Breadcrumbs.tsx index 1790ff1917..ed45cbddd2 100644 --- a/src/course-unit/breadcrumbs/Breadcrumbs.tsx +++ b/src/course-unit/breadcrumbs/Breadcrumbs.tsx @@ -5,23 +5,13 @@ import { ArrowDropDown as ArrowDropDownIcon, ChevronRight as ChevronRightIcon, } from '@openedx/paragon/icons'; -import { getConfig } from '@edx/frontend-platform'; - -import { useWaffleFlags } from '../../data/apiHooks'; import { getCourseSectionVertical } from '../data/selectors'; import { adoptCourseSectionUrl, subsectionFirstUnitEditUrl } from '../utils'; const Breadcrumbs = ({ courseId, parentUnitId }: { courseId: string; parentUnitId: string; }) => { const { ancestorXblocks = [] } = useSelector(getCourseSectionVertical); - const waffleFlags = useWaffleFlags(courseId); - - const getPathToCourseOutlinePage = (url) => (waffleFlags.useNewCourseOutlinePage - ? url : - `${getConfig().STUDIO_BASE_URL}${url}`); - const getPathToCourseUnitPage = (url) => (waffleFlags.useNewUnitPage - ? adoptCourseSectionUrl({ url, courseId, parentUnitId }) - : `${getConfig().STUDIO_BASE_URL}${url}`); + const getPathToCourseUnitPage = (url) => adoptCourseSectionUrl({ url, courseId, parentUnitId }); // based on the level of breadcrumbs the url will differ // at the subsection level it should navigate to the first unit if available @@ -29,7 +19,7 @@ const Breadcrumbs = ({ courseId, parentUnitId }: { courseId: string; parentUnitI function getPathToCoursePage(index, url, usageKey: string) { let navUrl: string; if (index === 0) { - navUrl = getPathToCourseOutlinePage(url); + navUrl = url; } else if (index === 1) { navUrl = subsectionFirstUnitEditUrl({ courseId, subsectionId: usageKey }); } else { diff --git a/src/custom-pages/CustomPages.test.tsx b/src/custom-pages/CustomPages.test.tsx index 2a7ca571a8..46ef3a59e2 100644 --- a/src/custom-pages/CustomPages.test.tsx +++ b/src/custom-pages/CustomPages.test.tsx @@ -61,9 +61,7 @@ describe('CustomPages', () => { axiosMock = mocks.axiosMock; axiosMock .onGet(getApiWaffleFlagsUrl(courseId)) - .reply(200, { - useNewCourseOutlinePage: true, - }); + .reply(200, {}); }); it('should ', async () => { renderComponent(); diff --git a/src/custom-pages/CustomPages.tsx b/src/custom-pages/CustomPages.tsx index dddb9091eb..3f12009ed2 100644 --- a/src/custom-pages/CustomPages.tsx +++ b/src/custom-pages/CustomPages.tsx @@ -28,7 +28,6 @@ import DraggableList, { SortableItem } from '@src/generic/DraggableList'; import ErrorAlert from '@src/editors/sharedComponents/ErrorAlerts/ErrorAlert'; import { RequestStatus } from '@src/data/constants'; import { useModels } from '@src/generic/model-store'; -import { useWaffleFlags } from '@src/data/apiHooks'; import getPageHeadTitle from '@src/generic/utils'; import { getPagePath } from '@src/utils'; import { DeprecatedReduxState } from '@src/store'; @@ -70,8 +69,6 @@ const CustomPages = () => { const deletePageStatus = useSelector((state: DeprecatedReduxState) => state.customPages.deletingStatus); const savingStatus = useSelector(getSavingStatus); const loadingStatus = useSelector(getLoadingStatus); - const waffleFlags = useWaffleFlags(courseId); - const pages = useModels('customPages', customPagesIds); const handleAddPage = () => { @@ -128,9 +125,7 @@ const CustomPages = () => { links={[ { label: 'Content', - to: waffleFlags.useNewCourseOutlinePage - ? `/course/${courseId}` - : `${config.STUDIO_BASE_URL}/course/${courseId}`, + to: `/course/${courseId}`, }, { label: 'Pages and Resources', to: getPagePath(courseId, 'true', 'tabs') }, ]} diff --git a/src/data/api.ts b/src/data/api.ts index 817817bee1..2c5b12f2a0 100644 --- a/src/data/api.ts +++ b/src/data/api.ts @@ -79,16 +79,7 @@ export const waffleFlagDefaults = { enableCourseOptimizer: false, enableNotifications: false, enableCourseOptimizerCheckPrevRunLinks: false, - useNewHomePage: true, - useNewCustomPages: true, - useNewUpdatesPage: true, - useNewImportPage: false, - useNewExportPage: true, - useNewFilesUploadsPage: true, useNewVideoUploadsPage: true, - useNewCourseOutlinePage: true, - useNewUnitPage: false, - useNewTextbooksPage: true, useNewPdfEditor: true, useReactMarkdownEditor: true, useVideoGalleryFlow: false, diff --git a/src/data/apiHooks.mock.ts b/src/data/apiHooks.mock.ts index bf922f9cf1..7f70594859 100644 --- a/src/data/apiHooks.mock.ts +++ b/src/data/apiHooks.mock.ts @@ -7,7 +7,7 @@ import * as apiHooks from './apiHooks'; * loading; if you need more realistic handling, use: * axiosMock * .onGet(getApiWaffleFlagsUrl(courseId)) - * .reply(200, { useNewCourseOutlinePage: true }); // etc + * .reply(200, { enableCourseOptimizer: true }); // etc */ export function mockWaffleFlags(overrides: Partial> = {}) { return jest.spyOn(apiHooks, 'useWaffleFlags').mockImplementation(() => ({ diff --git a/src/data/apiHooks.test.tsx b/src/data/apiHooks.test.tsx index 9b3f90e4b2..996a62daf1 100644 --- a/src/data/apiHooks.test.tsx +++ b/src/data/apiHooks.test.tsx @@ -15,7 +15,7 @@ const FlagComponent = ({ courseId }: { courseId?: string; }) => {
  • {waffleFlags.isLoading ? 'loading' : 'false'}
  • {waffleFlags.isError ? 'error' : 'false'}
  • -
  • {waffleFlags.useNewCourseOutlinePage ? 'enabled' : 'disabled'}
  • +
  • {waffleFlags.useReactMarkdownEditor ? 'enabled' : 'disabled'}
); }; @@ -34,17 +34,17 @@ describe('useWaffleFlags', () => { expect(await screen.findByLabelText('isLoading')).toHaveTextContent('loading'); expect(await screen.findByLabelText('isError')).toHaveTextContent('false'); // The default should be enabled, even before we hear back from the server: - expect(await screen.findByLabelText('useNewCourseOutlinePage')).toHaveTextContent('enabled'); + expect(await screen.findByLabelText('useReactMarkdownEditor')).toHaveTextContent('enabled'); // Then, the server responds with a new value: - resolveResponse([200, { useNewCourseOutlinePage: false }]); + resolveResponse([200, { useReactMarkdownEditor: false }]); // Now, we're no longer loading and we have the new value: await waitFor(async () => { expect(await screen.findByLabelText('isLoading')).toHaveTextContent('false'); }); expect(await screen.findByLabelText('isError')).toHaveTextContent('false'); - expect(await screen.findByLabelText('useNewCourseOutlinePage')).toHaveTextContent('disabled'); + expect(await screen.findByLabelText('useReactMarkdownEditor')).toHaveTextContent('disabled'); }); it('uses the default values if there\'s an error', async () => { @@ -60,7 +60,7 @@ describe('useWaffleFlags', () => { expect(await screen.findByLabelText('isLoading')).toHaveTextContent('loading'); expect(await screen.findByLabelText('isError')).toHaveTextContent('false'); // The default should be enabled, even before we hear back from the server: - expect(await screen.findByLabelText('useNewCourseOutlinePage')).toHaveTextContent('enabled'); + expect(await screen.findByLabelText('useReactMarkdownEditor')).toHaveTextContent('enabled'); // Then, the server responds with an error resolveResponse([500, {}]); @@ -70,14 +70,14 @@ describe('useWaffleFlags', () => { expect(await screen.findByLabelText('isLoading')).toHaveTextContent('false'); }); expect(await screen.findByLabelText('isError')).toHaveTextContent('error'); - expect(await screen.findByLabelText('useNewCourseOutlinePage')).toHaveTextContent('enabled'); + expect(await screen.findByLabelText('useReactMarkdownEditor')).toHaveTextContent('enabled'); }); it('uses the global flag values while loading the course-specific flags', async () => { const { axiosMock } = initializeMocks(); const courseId = 'course-v1:A+b+C'; // Set the global flag OFF: - axiosMock.onGet(getApiWaffleFlagsUrl()).reply(200, { useNewCourseOutlinePage: false }); + axiosMock.onGet(getApiWaffleFlagsUrl()).reply(200, { useReactMarkdownEditor: false }); // Control when we respond with the course-specific flag value: let resolveResponse; const promise = new Promise<[number, unknown]>(resolve => { @@ -89,7 +89,7 @@ describe('useWaffleFlags', () => { render(); await waitFor(async () => { // Once it loads the flags from the server, the global 'false' value will override the default 'true': - expect(await screen.findByLabelText('useNewCourseOutlinePage')).toHaveTextContent('disabled'); + expect(await screen.findByLabelText('useReactMarkdownEditor')).toHaveTextContent('disabled'); }); // Now check the course-specific flag: @@ -99,14 +99,14 @@ describe('useWaffleFlags', () => { // Now, the course-specific value is loading but in the meantime we use the global default: expect(await screen.findByLabelText('isLoading')).toHaveTextContent('loading'); expect(await screen.findByLabelText('isError')).toHaveTextContent('false'); - expect(await screen.findByLabelText('useNewCourseOutlinePage')).toHaveTextContent('disabled'); + expect(await screen.findByLabelText('useReactMarkdownEditor')).toHaveTextContent('disabled'); // Now the server responds: the course-specific flag is ON: - resolveResponse([200, { useNewCourseOutlinePage: true }]); + resolveResponse([200, { useReactMarkdownEditor: true }]); await waitFor(async () => { expect(await screen.findByLabelText('isLoading')).toHaveTextContent('false'); }); expect(await screen.findByLabelText('isError')).toHaveTextContent('false'); - expect(await screen.findByLabelText('useNewCourseOutlinePage')).toHaveTextContent('enabled'); + expect(await screen.findByLabelText('useReactMarkdownEditor')).toHaveTextContent('enabled'); }); }); diff --git a/src/header/Header.tsx b/src/header/Header.tsx index 2f2e307cf4..461c09247c 100644 --- a/src/header/Header.tsx +++ b/src/header/Header.tsx @@ -3,7 +3,6 @@ import { getConfig } from '@edx/frontend-platform'; import { useIntl } from '@edx/frontend-platform/i18n'; import { type Container, useToggle } from '@openedx/paragon'; -import { useWaffleFlags } from '../data/apiHooks'; import { SearchModal } from '../search-modal'; import { useContentMenuItems, @@ -38,11 +37,9 @@ const Header = ({ readOnly = false, }: HeaderProps) => { const intl = useIntl(); - const waffleFlags = useWaffleFlags(); const [isShowSearchModalOpen, openSearchModal, closeSearchModal] = useToggle(false); - const studioBaseUrl = getConfig().STUDIO_BASE_URL; const meiliSearchEnabled = [true, 'true'].includes(getConfig().MEILISEARCH_ENABLED); const contentMenuItems = useContentMenuItems(contextId); @@ -90,7 +87,7 @@ const Header = ({ if (isLibrary) { return `/library/${contextId}`; } - return waffleFlags.useNewCourseOutlinePage ? `/course/${contextId}` : `${studioBaseUrl}/course/${contextId}`; + return `/course/${contextId}`; }; return ( @@ -104,7 +101,8 @@ const Header = ({ outlineLink={getOutlineLink()} searchButtonAction={meiliSearchEnabled ? openSearchModal : undefined} containerProps={containerProps} - isNewHomePage={waffleFlags.useNewHomePage} + // TODO: remove isNewHomePage prop once StudioHeader drops support for it (https://github.com/openedx/frontend-app-authoring/issues/3086) + isNewHomePage={true} /> {meiliSearchEnabled && ( { const actualItemsTitle = actualItems.map((item) => item.title); expect(actualItemsTitle).toContain(messages['header.links.updates'].defaultMessage); }); - it('when useNewUpdatesPage is false should use legacy studio URL for updates', () => { - mockWaffleFlags({ enableAuthzCourseAuthoring: false, useNewUpdatesPage: false }); + it('should always use MFE URL for updates', () => { + mockWaffleFlags({ enableAuthzCourseAuthoring: false }); jest.mocked(useCourseUserPermissions).mockReturnValue({ isLoading: false, isAuthzEnabled: false, @@ -201,7 +201,7 @@ describe('header utils', () => { const actualItems = renderHook(() => useContentMenuItems('course-123'), { wrapper: createWrapper() }).result.current; const updatesItem = actualItems.find((item) => item.title === messages['header.links.updates'].defaultMessage); - expect(updatesItem?.href).toContain('/course_info/course-123'); + expect(updatesItem?.href).toContain('/course/course-123/course_info'); }); it('when authz enabled and user has canViewPagesAndResources should include pages and resources option', async () => { mockWaffleFlags({ enableAuthzCourseAuthoring: true }); diff --git a/src/header/hooks.tsx b/src/header/hooks.tsx index fd67ce1e08..17341428ee 100644 --- a/src/header/hooks.tsx +++ b/src/header/hooks.tsx @@ -23,7 +23,6 @@ import { getCourseUpdatesPermissions } from '@src/authz/permissionHelpers'; export const useContentMenuItems = (courseId: string) => { const intl = useIntl(); - const studioBaseUrl = getConfig().STUDIO_BASE_URL; const waffleFlags = useWaffleFlags(courseId); const { librariesV2Enabled } = useSelector(getStudioHomeData); @@ -38,14 +37,12 @@ export const useContentMenuItems = (courseId: string) => { const items = [ { - href: waffleFlags.useNewCourseOutlinePage ? `/course/${courseId}` : `${studioBaseUrl}/course/${courseId}`, + href: `/course/${courseId}`, title: intl.formatMessage(messages['header.links.outline']), }, ...(canViewCourseUpdates ? [{ - href: waffleFlags.useNewUpdatesPage - ? `/course/${courseId}/course_info` - : `${studioBaseUrl}/course_info/${courseId}`, + href: `/course/${courseId}/course_info`, title: intl.formatMessage(messages['header.links.updates']), }] : []), @@ -57,11 +54,12 @@ export const useContentMenuItems = (courseId: string) => { : []), ...(canViewFiles ? [{ - href: waffleFlags.useNewFilesUploadsPage ? `/course/${courseId}/assets` : `${studioBaseUrl}/assets/${courseId}`, + href: `/course/${courseId}/assets`, title: intl.formatMessage(messages['header.links.filesAndUploads']), }] : []), ]; + if (getConfig().ENABLE_VIDEO_UPLOAD_PAGE_LINK_IN_CONTENT_DROPDOWN === 'true' || waffleFlags.useNewVideoUploadsPage) { items.push({ href: `/course/${courseId}/videos`, @@ -152,11 +150,11 @@ export const useToolsMenuItems = (courseId: string) => { const items = [ { - href: waffleFlags.useNewImportPage ? `/course/${courseId}/import` : `${studioBaseUrl}/import/${courseId}`, + href: `/course/${courseId}/import`, title: intl.formatMessage(messages['header.links.import']), }, { - href: waffleFlags.useNewExportPage ? `/course/${courseId}/export` : `${studioBaseUrl}/export/${courseId}`, + href: `/course/${courseId}/export`, title: intl.formatMessage(messages['header.links.exportCourse']), }, ...(getConfig().ENABLE_TAGGING_TAXONOMY_PAGES === 'true' diff --git a/src/pages-and-resources/pages/PageCard.test.jsx b/src/pages-and-resources/pages/PageCard.test.jsx index 4423ede0f5..3ce3dfe290 100644 --- a/src/pages-and-resources/pages/PageCard.test.jsx +++ b/src/pages-and-resources/pages/PageCard.test.jsx @@ -50,9 +50,7 @@ describe('LiveSettings', () => { axiosMock = mocks.axiosMock; axiosMock .onGet(getApiWaffleFlagsUrl(courseId)) - .reply(200, { - useNewCourseOutlinePage: true, - }); + .reply(200, {}); }); it('should render three cards', async () => { diff --git a/src/pages-and-resources/pages/PageSettingButton.jsx b/src/pages-and-resources/pages/PageSettingButton.jsx index b0850e7af3..eefb3bff10 100644 --- a/src/pages-and-resources/pages/PageSettingButton.jsx +++ b/src/pages-and-resources/pages/PageSettingButton.jsx @@ -6,7 +6,6 @@ import { Icon, IconButton } from '@openedx/paragon'; import { ArrowForward, Settings } from '@openedx/paragon/icons'; import { useNavigate, Link } from 'react-router-dom'; -import { useWaffleFlags } from '../../data/apiHooks'; import { useCourseUserPermissions } from '../../authz/hooks'; import { getAdvancedSettingsPermissions } from '../../authz/permissionHelpers'; import messages from '../messages'; @@ -22,25 +21,12 @@ const PageSettingButton = ({ const { path: pagesAndResourcesPath, isEditable } = useContext(PagesAndResourcesContext); const { canManageAdvancedSettings } = useCourseUserPermissions(courseId, getAdvancedSettingsPermissions(courseId)); const navigate = useNavigate(); - const waffleFlags = useWaffleFlags(courseId); - const determineLinkDestination = useMemo(() => { - if (!legacyLink) { return null; } - - if (legacyLink.includes('textbooks')) { - return waffleFlags.useNewTextbooksPage - ? `/course/${courseId}/${id.replace('_', '-')}` - : legacyLink; - } - - if (legacyLink.includes('tabs')) { - return waffleFlags.useNewCustomPages - ? `/course/${courseId}/${id.replace('_', '-')}` - : legacyLink; - } - - return null; - }, [legacyLink, waffleFlags, id]); + const determineLinkDestination = useMemo(() => ( + legacyLink?.includes('textbooks') || legacyLink?.includes('tabs') + ? `/course/${courseId}/${id.replace('_', '-')}` + : null + ), [legacyLink, courseId, id]); const canConfigureOrEnable = allowedOperations?.configure || allowedOperations?.enable; diff --git a/src/pages-and-resources/pages/PageSettingButton.test.jsx b/src/pages-and-resources/pages/PageSettingButton.test.jsx index ade2350ca0..cab3cca3f2 100644 --- a/src/pages-and-resources/pages/PageSettingButton.test.jsx +++ b/src/pages-and-resources/pages/PageSettingButton.test.jsx @@ -1,7 +1,6 @@ // @ts-check import { screen, render, initializeMocks, fireEvent } from '../../testUtils'; import PageSettingButton from './PageSettingButton'; -import { mockWaffleFlags } from '../../data/apiHooks.mock'; import { useCourseUserPermissions } from '../../authz/hooks'; import PagesAndResourcesProvider from '../PagesAndResourcesProvider'; @@ -30,14 +29,12 @@ const renderComponent = (props = {}, { isEditable = true, canManageAdvancedSetti ); }; -mockWaffleFlags(); - describe('PageSettingButton', () => { beforeEach(() => { initializeMocks(); }); - it('renders the settings button with the new textbooks page link when useNewTextbooksPage is true', () => { + it('renders the settings button with the new textbooks page link', () => { renderComponent({ legacyLink: 'http://legacylink.com/textbooks' }); const linkElement = screen.getByRole('link'); @@ -50,31 +47,13 @@ describe('PageSettingButton', () => { expect(screen.queryByRole('link')).toBeNull(); }); - it('renders the settings button with the legacy link when useNewTextbooksPage is false', () => { - mockWaffleFlags({ useNewTextbooksPage: false }); - - renderComponent({ legacyLink: 'http://legacylink.com/textbooks' }); - - const linkElement = screen.getByRole('link'); - expect(linkElement).toHaveAttribute('href', 'http://legacylink.com/textbooks'); - }); - - it('renders the settings button with the new custom pages link when useNewCustomPages is true', () => { + it('renders the settings button with the new custom pages link', () => { renderComponent(); const linkElement = screen.getByRole('link'); expect(linkElement).toHaveAttribute('href', `/course/${defaultProps.courseId}/page-id`); }); - it('renders the settings button with the legacy link when useNewCustomPages is false', () => { - mockWaffleFlags({ useNewCustomPages: false }); - - renderComponent(); - - const linkElement = screen.getByRole('link'); - expect(linkElement).toHaveAttribute('href', defaultProps.legacyLink); - }); - it('renders disabled icon button in read-only mode with legacy link', () => { renderComponent({ legacyLink: 'http://legacylink.com/textbooks' }, { isEditable: false }); diff --git a/src/studio-home/card-item/index.tsx b/src/studio-home/card-item/index.tsx index c076792de4..317631d455 100644 --- a/src/studio-home/card-item/index.tsx +++ b/src/studio-home/card-item/index.tsx @@ -18,7 +18,6 @@ import { FormattedMessage, useIntl } from '@edx/frontend-platform/i18n'; import { getConfig } from '@edx/frontend-platform'; import { Link } from 'react-router-dom'; -import { useWaffleFlags } from '@src/data/apiHooks'; import { COURSE_CREATOR_STATES } from '@src/constants'; import classNames from 'classnames'; import { getStudioHomeData } from '../data/selectors'; @@ -248,11 +247,10 @@ export const CardItem: React.FC = ({ courseCreatorStatus, rerunCreatorStatus, } = useSelector(getStudioHomeData); - const waffleFlags = useWaffleFlags(); const cardRef = useRef(null); const destinationUrl: string = path ?? ( - waffleFlags.useNewCourseOutlinePage && !isLibraries + !isLibraries ? url : new URL(url, getConfig().STUDIO_BASE_URL).toString() ); diff --git a/src/textbooks/hooks.tsx b/src/textbooks/hooks.tsx index 1f71c0b961..442c9b1b84 100644 --- a/src/textbooks/hooks.tsx +++ b/src/textbooks/hooks.tsx @@ -3,10 +3,8 @@ import { AxiosError } from 'axios'; import { useState } from 'react'; import { useIntl } from '@edx/frontend-platform/i18n'; import { useToggle } from '@openedx/paragon'; -import { getConfig } from '@edx/frontend-platform'; import { useCourseAuthoringContext } from '@src/CourseAuthoringContext'; -import { useWaffleFlags } from '@src/data/apiHooks'; import { getMessageFromAxiosError } from '@src/generic/saving-error-alert/utils'; import messages from './messages'; import { @@ -22,7 +20,6 @@ export type OnErrorCallbackFunc = (error: AxiosError) => void; export const useTextbooksFeatures = () => { const intl = useIntl(); const { courseId } = useCourseAuthoringContext(); - const waffleFlags = useWaffleFlags(courseId); const { data: textbooksData, @@ -49,9 +46,7 @@ export const useTextbooksFeatures = () => { const breadcrumbs = [ { label: intl.formatMessage(messages.breadcrumbContent), - to: waffleFlags.useNewCourseOutlinePage - ? `/course/${courseId}` - : `${getConfig().STUDIO_BASE_URL}/course/${courseId}`, + to: `/course/${courseId}`, }, { label: intl.formatMessage(messages.breadcrumbPagesAndResources),