diff --git a/src/components/course/routes/CoursePageRoutes.jsx b/src/components/course/routes/CoursePageRoutes.jsx index 454b4e5e11..40538ce39e 100644 --- a/src/components/course/routes/CoursePageRoutes.jsx +++ b/src/components/course/routes/CoursePageRoutes.jsx @@ -1,10 +1,9 @@ import React from 'react'; import { Switch, useRouteMatch } from 'react-router-dom'; import { PageRoute } from '@edx/frontend-platform/react'; - -import CourseAbout from './CourseAbout'; import ExternalCourseEnrollment from './ExternalCourseEnrollment'; import ExternalCourseEnrollmentConfirmation from './ExternalCourseEnrollmentConfirmation'; +import CourseAbout from './CourseAbout'; import NotFoundPage from '../../NotFoundPage'; const CoursePageRoutes = () => { diff --git a/src/components/course/routes/ExternalCourseEnrollment.jsx b/src/components/course/routes/ExternalCourseEnrollment.jsx index 23887ff6c5..5f54cb605d 100644 --- a/src/components/course/routes/ExternalCourseEnrollment.jsx +++ b/src/components/course/routes/ExternalCourseEnrollment.jsx @@ -1,5 +1,5 @@ import React, { useContext, useEffect, useRef } from 'react'; -import { useHistory } from 'react-router-dom'; +import { generatePath, useHistory, useRouteMatch } from 'react-router-dom'; import { Alert, Button, Col, Container, Hyperlink, Row, } from '@edx/paragon'; @@ -20,6 +20,7 @@ import { features } from '../../../config'; const ExternalCourseEnrollment = () => { const config = getConfig(); const history = useHistory(); + const routeMatch = useRouteMatch(); const { state: { activeCourseRun, @@ -31,9 +32,13 @@ const ExternalCourseEnrollment = () => { externalCourseFormSubmissionError, } = useContext(CourseContext); const { - enterpriseConfig: { authOrgId }, + enterpriseConfig: { authOrgId, slug }, } = useContext(AppContext); const { redeemableLearnerCreditPolicies } = useContext(UserSubsidyContext); + const completeEnrollmentUrl = generatePath( + `${routeMatch.path}/complete`, + { enterpriseSlug: slug, courseType: course.courseType, courseKey: course.key }, + ); const isCourseAssigned = useIsCourseAssigned(redeemableLearnerCreditPolicies?.learnerContentAssignments, course?.key); const courseMetadata = useMinimalCourseMetadata(); @@ -62,15 +67,14 @@ const ExternalCourseEnrollment = () => { } }, [externalCourseFormSubmissionError, containerRef]); - const handleCheckoutSuccess = () => { - history.push('enroll/complete'); - }; - useEffect(() => { + // Once a redemption has successfully completed and the can-redeem query has been invalidated or + // a user attempts to navigate directly to :slug/:courseType/course/:courseKey/enroll, + // it will run this conditional and perform the redirect if (hasSuccessfulRedemption) { - history.push('enroll/complete'); + history.push(completeEnrollmentUrl); } - }, [hasSuccessfulRedemption, history]); + }, [completeEnrollmentUrl, course.key, hasSuccessfulRedemption, history, routeMatch.path, slug]); return (
@@ -120,7 +124,6 @@ const ExternalCourseEnrollment = () => { diff --git a/src/components/course/routes/tests/ExternalCourseEnrollment.test.jsx b/src/components/course/routes/tests/ExternalCourseEnrollment.test.jsx index 35eadde50f..097d6977cd 100644 --- a/src/components/course/routes/tests/ExternalCourseEnrollment.test.jsx +++ b/src/components/course/routes/tests/ExternalCourseEnrollment.test.jsx @@ -120,13 +120,9 @@ describe('ExternalCourseEnrollment', () => { expect(screen.getByTestId('user-enrollment-form')).toBeInTheDocument(); expect(UserEnrollmentForm.mock.calls[0][0]).toEqual( expect.objectContaining({ - onCheckoutSuccess: expect.any(Function), productSKU: 'test-sku', }), ); - UserEnrollmentForm.mock.calls[0][0].onCheckoutSuccess(); - expect(mockHistoryPush).toHaveBeenCalledTimes(1); - expect(mockHistoryPush).toHaveBeenCalledWith('enroll/complete'); }); it.each([ diff --git a/src/components/executive-education-2u/UserEnrollmentForm.jsx b/src/components/executive-education-2u/UserEnrollmentForm.jsx index 5181dd834d..379e8c8417 100644 --- a/src/components/executive-education-2u/UserEnrollmentForm.jsx +++ b/src/components/executive-education-2u/UserEnrollmentForm.jsx @@ -70,7 +70,9 @@ const UserEnrollmentForm = ({ await queryClient.invalidateQueries({ queryKey: enterpriseUserSubsidyQueryKeys.policy(), }); - onCheckoutSuccess(newTransaction); + if (onCheckoutSuccess) { + onCheckoutSuccess(newTransaction); + } }; const { redeem } = useStatefulEnroll({ @@ -394,7 +396,7 @@ const UserEnrollmentForm = ({ UserEnrollmentForm.propTypes = { className: PropTypes.string, productSKU: PropTypes.string.isRequired, - onCheckoutSuccess: PropTypes.func.isRequired, + onCheckoutSuccess: PropTypes.func, activeCourseRun: PropTypes.shape({ key: PropTypes.string.isRequired, }).isRequired, @@ -406,6 +408,7 @@ UserEnrollmentForm.propTypes = { UserEnrollmentForm.defaultProps = { className: undefined, userSubsidyApplicableToCourse: undefined, + onCheckoutSuccess: undefined, }; export default UserEnrollmentForm;