def test_post_program_enrollment_view_redirect_to_program_dashboard( self, course_catalog_api_client_mock, program_data_extender_mock, *args): # pylint: disable=unused-argument,invalid-name """ The user is redirected to the program dashboard on POST if already certificate eligible for the program. """ program_data_extender_mock = self._setup_program_data_extender( program_data_extender_mock) for course in program_data_extender_mock.return_value.extend.return_value[ 'courses']: course['course_runs'][0].update({ "is_enrolled": True, "upgrade_url": None, }) setup_course_catalog_api_client_mock(course_catalog_api_client_mock) enterprise_customer = EnterpriseCustomerFactory() program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.post(program_enrollment_page_url) assert response.status_code == 302 self.assertRedirects( response, 'http://lms.example.com/dashboard/programs/52ad909b-c57d-4ff1-bab3-999813a2479b', fetch_redirect_response=False)
def test_post_program_enrollment_view_redirect_to_dsc( self, program_data_extender_mock, course_catalog_api_client_mock, get_dsc_mock, *args): # pylint: disable=unused-argument """ The user is redirected to the DSC page when DSC is needed. """ self._setup_program_data_extender(program_data_extender_mock) setup_course_catalog_api_client_mock(course_catalog_api_client_mock) self._setup_get_data_sharing_consent(get_dsc_mock, required=True) enterprise_customer = EnterpriseCustomerFactory() program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.post(program_enrollment_page_url) assert response.status_code == 302 self.assertRedirects( response, '/enterprise/grant_data_sharing_permissions?{}'.format( urlencode({ 'next': 'http://localhost:18130/basket/add/?sku=sku1&sku=sku2' '&bundle=52ad909b-c57d-4ff1-bab3-999813a2479b', 'failure_url': program_enrollment_page_url, 'enterprise_customer_uuid': enterprise_customer.uuid, 'program_uuid': self.dummy_program_uuid, })), fetch_redirect_response=False)
def test_get_program_enrollment_page_program_unenrollable( self, enrollable, program_data_extender_mock, course_catalog_api_client_mock, embargo_api_mock, *args): # pylint: disable=unused-argument,invalid-name """ The message about the program being unenrollable is displayed. """ self._setup_embargo_api(embargo_api_mock) program_data_extender_mock = self._setup_program_data_extender( program_data_extender_mock).return_value program_data_extender_mock.extend.return_value[ 'is_learner_eligible_for_one_click_purchase'] = enrollable setup_course_catalog_api_client_mock(course_catalog_api_client_mock) enterprise_customer = EnterpriseCustomerFactory( name='Starfleet Academy') program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.get(program_enrollment_page_url) messages = self._get_messages_from_response_cookies(response) if enrollable: assert not messages else: assert messages self._assert_request_message( messages[0], 'info', ('<strong>Something happened.</strong> ' '<span>This program is not currently open to new learners. ' 'Please start over and select a different program.</span>'))
def test_get_program_enrollment_page_for_certificate_eligible_user( self, program_data_extender_mock, course_catalog_api_client_mock, *args): # pylint: disable=unused-argument,invalid-name """ The user will be redirected to the program's dashboard when already certificate-eligible for the program. """ program_data_extender_mock = self._setup_program_data_extender( program_data_extender_mock) for course in program_data_extender_mock.return_value.extend.return_value[ 'courses']: course['course_runs'][0].update({ "is_enrolled": True, "upgrade_url": None, }) setup_course_catalog_api_client_mock(course_catalog_api_client_mock) enterprise_customer = EnterpriseCustomerFactory() program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.get(program_enrollment_page_url) self.assertRedirects( response, 'http://lms.example.com/dashboard/programs/{program_uuid}'.format( program_uuid=self.dummy_program_uuid), fetch_redirect_response=False, )
def test_embargo_restriction(self, program_data_extender_mock, course_catalog_api_client_mock_1, course_catalog_api_client_mock_2, embargo_api_mock, *args): # pylint: disable=unused-argument,invalid-name """ The Enterprise Program landing page is rendered appropriately given some context. """ self._setup_embargo_api(embargo_api_mock, redirect_url=self.EMBARGO_REDIRECT_URL) self._setup_program_data_extender(program_data_extender_mock) setup_course_catalog_api_client_mock(course_catalog_api_client_mock_1) setup_course_catalog_api_client_mock(course_catalog_api_client_mock_2) enterprise_customer = EnterpriseCustomerFactory( name='Starfleet Academy') program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.get(program_enrollment_page_url) assert response.status_code == 302 self.assertRedirects(response, self.EMBARGO_REDIRECT_URL, fetch_redirect_response=False)
def test_get_program_enrollment_page_no_price_info_found_message( self, program_data_extender_mock, course_catalog_api_client_mock, embargo_api_mock, *args): # pylint: disable=unused-argument,invalid-name """ The message about no price information found is rendered if the program extender fails to get price info. """ self._setup_embargo_api(embargo_api_mock) program_data_extender_mock = self._setup_program_data_extender( program_data_extender_mock) program_data_extender_mock.return_value.extend.return_value[ 'discount_data'] = {} setup_course_catalog_api_client_mock(course_catalog_api_client_mock) enterprise_customer = EnterpriseCustomerFactory( name='Starfleet Academy') program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.get(program_enrollment_page_url) messages = self._get_messages_from_response_cookies(response) assert messages self._assert_request_message(messages[0], 'warning', ( '<strong>We could not gather price information for <em>Program Title 1</em>.</strong> ' '<span>If you continue to have these issues, please contact ' '<a href="{enterprise_support_link}" target="_blank">{platform_name} support</a>.</span>' ).format( enterprise_support_link=settings.ENTERPRISE_SUPPORT_URL, platform_name=settings.PLATFORM_NAME, ))
def test_post_program_enrollment_view_redirect_to_basket( self, program_data_extender_mock, course_catalog_api_client_mock, get_dsc_mock, *args ): # pylint: disable=unused-argument """ The user is redirected to the basket page when something needs to be bought. """ self._setup_program_data_extender(program_data_extender_mock) setup_course_catalog_api_client_mock(course_catalog_api_client_mock) self._setup_get_data_sharing_consent(get_dsc_mock, required=False) enterprise_customer = EnterpriseCustomerFactory() program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.post(program_enrollment_page_url) assert response.status_code == 302 self.assertRedirects( response, 'http://localhost:18130/basket/add/?sku=sku1&sku=sku2&bundle=52ad909b-c57d-4ff1-bab3-999813a2479b', fetch_redirect_response=False )
def setUp(self): self.user = factories.UserFactory() self.other_user = factories.UserFactory() self.staff_user = factories.UserFactory(is_staff=True, is_active=True) self.subdomain = 'fake-subdomain' self.session_token = 'fake-session-token' self.callback_url = '/services/x/content-online-content-api/v1' self.user_guid = "fake-guid" self.course_id = 'course-v1:edX+DemoX+DemoCourse' self.course_key = 'edX+DemoX' self.enterprise_customer = factories.EnterpriseCustomerFactory( enable_audit_enrollment=True, enable_audit_data_reporting=True, ) self.config = factories.CornerstoneEnterpriseCustomerConfigurationFactory( enterprise_customer=self.enterprise_customer, active=True, ) self.global_config = factories.CornerstoneGlobalConfigurationFactory( key='test_key', secret='test_secret') self.enterprise_course_enrollment = self._setup_enterprise_enrollment( self.user, self.course_id, self.course_key) course_catalog_api_client_mock = mock.patch( 'enterprise.api_client.discovery.CourseCatalogApiServiceClient') course_catalog_client = course_catalog_api_client_mock.start() setup_course_catalog_api_client_mock(course_catalog_client) self.addCleanup(course_catalog_api_client_mock.stop) super(TestCornerstoneLearnerExporter, self).setUp()
def setUp(self): self.user = factories.UserFactory(username='******', id=1, email='*****@*****.**') self.course_id = 'course-v1:edX+DemoX+DemoCourse' self.course_key = 'edX+DemoX' self.enterprise_customer = factories.EnterpriseCustomerFactory() self.enterprise_customer_user = factories.EnterpriseCustomerUserFactory( user_id=self.user.id, enterprise_customer=self.enterprise_customer, ) self.data_sharing_consent = factories.DataSharingConsentFactory( username=self.user.username, course_id=self.course_id, enterprise_customer=self.enterprise_customer, granted=True, ) self.config = factories.DegreedEnterpriseCustomerConfigurationFactory( enterprise_customer=self.enterprise_customer, active=True, ) self.idp = factories.EnterpriseCustomerIdentityProviderFactory( enterprise_customer=self.enterprise_customer) tpa_client_mock = mock.patch( 'enterprise.models.ThirdPartyAuthApiClient') self.tpa_client = tpa_client_mock.start() self.tpa_client.return_value.get_remote_id.return_value = 'fake-remote-id' self.addCleanup(tpa_client_mock.stop) course_catalog_api_client_mock = mock.patch( 'enterprise.api_client.discovery.CourseCatalogApiServiceClient') self.course_catalog_client = course_catalog_api_client_mock.start() setup_course_catalog_api_client_mock(self.course_catalog_client) self.addCleanup(course_catalog_api_client_mock.stop) super(TestDegreedLearnerExporter, self).setUp()
def test_get_raises_404_with_bad_course_key(self, catalog_api_mock): """ ``get`` raises a 404 when a course run cannot be found given the provided course key. """ fake_catalog_api.setup_course_catalog_api_client_mock( catalog_api_mock, course_overrides={'course_runs': []}) kwargs = { 'enterprise_uuid': str(self.enterprise_customer.uuid), 'course_key': 'fake_course_key' } with self.assertRaises(Http404): views.RouterView().get(self.request, **kwargs)
def test_get_program_enrollment_page_consent_message( self, consent_granted, program_data_extender_mock, course_catalog_api_client_mock, embargo_api_mock, *args ): # pylint: disable=unused-argument,invalid-name """ The DSC-declined message is rendered if DSC is not given. """ self._setup_embargo_api(embargo_api_mock) self._setup_program_data_extender(program_data_extender_mock) setup_course_catalog_api_client_mock(course_catalog_api_client_mock) enterprise_customer = EnterpriseCustomerFactory(name='Starfleet Academy') enterprise_customer_user = EnterpriseCustomerUserFactory( enterprise_customer=enterprise_customer, user_id=self.user.id ) for dummy_course_id in self.demo_course_ids: DataSharingConsentFactory( course_id=dummy_course_id, granted=consent_granted, enterprise_customer=enterprise_customer, username=enterprise_customer_user.username, ) program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.get(program_enrollment_page_url) messages = self._get_messages_from_response_cookies(response) if consent_granted: assert not messages else: assert messages self._assert_request_message( messages[0], 'warning', ( '<strong>We could not enroll you in <em>Program Title 1</em>.</strong> ' '<span>If you have questions or concerns about sharing your data, please ' 'contact your learning manager at Starfleet Academy, or contact ' '<a href="{enterprise_support_link}" target="_blank">{platform_name} support</a>.</span>' ).format( enterprise_support_link=settings.ENTERPRISE_SUPPORT_URL, platform_name=settings.PLATFORM_NAME, ) )
def test_get_redirects_with_course_key(self, router_view_mock, catalog_api_mock): """ ``get`` performs a redirect with a course key in the request path. """ fake_catalog_api.setup_course_catalog_api_client_mock(catalog_api_mock) router_view_mock.eligible_for_direct_audit_enrollment = mock.MagicMock( return_value=False) router_view_mock.redirect = mock.MagicMock(return_value=None) kwargs = { 'enterprise_uuid': str(self.enterprise_customer.uuid), 'course_key': 'fake_course_key' } router_view_mock.get(self.request, **kwargs) router_view_mock.redirect.assert_called_once()
def test_get_raises_404_with_bad_course_key(self, catalog_api_mock, mock_global_context): """ ``get`` responds with a 404 when a course run cannot be found given the provided course key. """ mock_global_context.return_value = {} fake_catalog_api.setup_course_catalog_api_client_mock( catalog_api_mock, course_overrides={'course_runs': []}) kwargs = { 'enterprise_uuid': str(self.enterprise_customer.uuid), 'course_key': 'fake_course_key' } with mock.patch('enterprise.views.render') as mock_render: mock_render.return_value = HttpResponse( ) # Must return response to keep view happy views.RouterView().get(self.request, **kwargs) assert mock_render.call_args_list[0][1]['status'] == 404
def test_get_program_enrollment_page_enrolled_in_program( self, program_data_extender_mock, course_catalog_api_client_mock, embargo_api_mock, *args): # pylint: disable=unused-argument,invalid-name """ The Enterprise Program landing page is rendered appropriately given that the user is enrolled in the program. """ self._setup_embargo_api(embargo_api_mock) program_data_extender_mock = self._setup_program_data_extender( program_data_extender_mock) program_data_extender_mock.return_value.extend.return_value['courses'][ 0]['course_runs'][0].update({ "is_enrolled": True, "upgrade_url": None, }) setup_course_catalog_api_client_mock(course_catalog_api_client_mock) enterprise_customer = EnterpriseCustomerFactory( name='Starfleet Academy') expected_context = { 'page_title': 'Confirm your enrollment', 'purchase_text': 'Purchase all unenrolled courses for', 'courses': [ { "key": 'course-v1:edX+DemoX+Demo_Course', "uuid": "a312ec52-74ef-434b-b848-f110eb90b672", "title": "edX Demonstration Course", 'course_title': 'edX Demonstration Course', 'course_short_description': 'This course demonstrates many features of the edX platform.', 'course_full_description': 'Lorem ipsum dolor sit amet, consectetur adipiscing elit.', 'course_image_uri': 'http://edx.devstack.lms:18000/asset-v1:edX+DemoX+Demo_Course+type' '@asset+block@images_course_image.jpg', 'course_level_type': 'Type 1', 'course_effort': '5-6 hours per week', 'weeks_to_complete': '10 weeks', 'staff': [{ 'uuid': '51df1077-1b8d-4f86-8305-8adbc82b72e9', 'given_name': 'Anant', 'family_name': 'Agarwal', 'bio': "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", 'profile_image_url': 'https://www.edx.org/sites/default/files/executive/photo/' 'anant-agarwal.jpg', 'slug': 'anant-agarwal', 'position': { 'title': 'CEO', 'organization_name': 'edX' }, 'profile_image': {}, 'works': [], 'urls': { 'twitter': None, 'facebook': None, 'blog': None }, 'email': None }], 'expected_learning_items': [ 'XBlocks', 'Peer Assessment', ], "course_runs": [ { "key": 'course-v1:edX+DemoX+Demo_Course', "uuid": "a276c25f-c640-4943-98dd-6c9ad8c71bb9", "title": "edX Demonstration Course", "short_description": "", "marketing_url": "course/edxdemo?utm_medium=affiliate_partner&utm_source=staff", "seats": [], "start": "2016-01-01T00:00:00Z", "end": "2018-01-01T00:00:00Z", "enrollment_start": None, "enrollment_end": None, "pacing_type": "self_paced", "type": None, "status": "published", "is_enrolled": True, "upgrade_url": None, }, ], }, { "key": 'course-v1:edX+DemoX+Demo_Course2', "uuid": "b312ec52-74ef-434b-b848-f110eb90b672", "title": "edX Demonstration Course 2", 'course_title': 'edX Demonstration Course', 'course_short_description': 'This course demonstrates many features of the edX platform.', 'course_full_description': 'Lorem ipsum dolor sit amet, consectetur adipiscing elit.', 'course_image_uri': 'http://edx.devstack.lms:18000/asset-v1:edX+DemoX+Demo_Course+type' '@asset+block@images_course_image.jpg', 'course_level_type': 'Type 1', 'course_effort': '5-6 hours per week', 'weeks_to_complete': '10 weeks', 'staff': [{ 'uuid': '51df1077-1b8d-4f86-8305-8adbc82b72e9', 'given_name': 'Anant', 'family_name': 'Agarwal', 'bio': "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", 'profile_image_url': 'https://www.edx.org/sites/default/files/executive/photo/' 'anant-agarwal.jpg', 'slug': 'anant-agarwal', 'position': { 'title': 'CEO', 'organization_name': 'edX' }, 'profile_image': {}, 'works': [], 'urls': { 'twitter': None, 'facebook': None, 'blog': None }, 'email': None }], 'expected_learning_items': [ 'XBlocks', 'Peer Assessment', ], "course_runs": [ { "key": 'course-v1:edX+DemoX+Demo_Course2', "uuid": "b276c25f-c640-4943-98dd-6c9ad8c71bb9", "title": "edX Demonstration Course 2", "short_description": "", "marketing_url": "course/edxdemo?utm_medium=affiliate_partner&utm_source=staff", "seats": [], "start": "2016-01-01T00:00:00Z", "end": "2018-01-01T00:00:00Z", "enrollment_start": None, "enrollment_end": None, "pacing_type": "self_paced", "type": None, "status": "published", "is_enrolled": False, "upgrade_url": None, }, ], }, ], } program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.get(program_enrollment_page_url) self._check_expected_enrollment_page(response, expected_context)
def test_get_program_enrollment_page(self, program_data_extender_mock, course_catalog_api_client_mock, embargo_api_mock, *args): # pylint: disable=unused-argument,invalid-name """ The Enterprise Program landing page is rendered appropriately given some context. """ self._setup_embargo_api(embargo_api_mock) self._setup_program_data_extender(program_data_extender_mock) setup_course_catalog_api_client_mock(course_catalog_api_client_mock) enterprise_customer = EnterpriseCustomerFactory( name='Starfleet Academy') expected_context = { 'LMS_SEGMENT_KEY': settings.LMS_SEGMENT_KEY, 'LMS_ROOT_URL': 'http://lms.example.com', 'enterprise_customer': enterprise_customer, 'platform_name': 'Test platform', 'program_type_logo': 'http://*****:*****@asset+block@images_course_image.jpg', 'course_level_type': 'Type 1', 'weeks_to_complete': '10 weeks', 'course_effort': '5-6 hours per week', 'staff': [{ 'uuid': '51df1077-1b8d-4f86-8305-8adbc82b72e9', 'given_name': 'Anant', 'family_name': 'Agarwal', 'bio': "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", 'profile_image_url': 'https://www.edx.org/sites/default/files/executive/photo/' 'anant-agarwal.jpg', 'slug': 'anant-agarwal', 'position': { 'title': 'CEO', 'organization_name': 'edX' }, 'profile_image': {}, 'works': [], 'urls': { 'twitter': None, 'facebook': None, 'blog': None }, 'email': None }], 'expected_learning_items': [ 'XBlocks', 'Peer Assessment', ], "course_runs": [ { "key": 'course-v1:edX+DemoX+Demo_Course', "uuid": "a276c25f-c640-4943-98dd-6c9ad8c71bb9", "title": "edX Demonstration Course", "short_description": "", "marketing_url": "course/edxdemo?utm_medium=affiliate_partner&utm_source=staff", "seats": [], "start": "2016-01-01T00:00:00Z", "end": "2018-01-01T00:00:00Z", "enrollment_start": None, "enrollment_end": None, "pacing_type": "self_paced", "type": None, "status": "published", "is_enrolled": False, "upgrade_url": None, }, ], }, { "key": 'course-v1:edX+DemoX+Demo_Course2', "uuid": "b312ec52-74ef-434b-b848-f110eb90b672", "title": "edX Demonstration Course 2", 'course_title': 'edX Demonstration Course', 'course_short_description': 'This course demonstrates many features of the edX platform.', 'course_full_description': 'Lorem ipsum dolor sit amet, consectetur adipiscing elit.', 'course_image_uri': 'http://edx.devstack.lms:18000/asset-v1:edX+DemoX+Demo_Course+type' '@asset+block@images_course_image.jpg', 'course_level_type': 'Type 1', 'course_effort': '5-6 hours per week', 'weeks_to_complete': '10 weeks', 'staff': [{ 'uuid': '51df1077-1b8d-4f86-8305-8adbc82b72e9', 'given_name': 'Anant', 'family_name': 'Agarwal', 'bio': "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", 'profile_image_url': 'https://www.edx.org/sites/default/files/executive/photo/' 'anant-agarwal.jpg', 'slug': 'anant-agarwal', 'position': { 'title': 'CEO', 'organization_name': 'edX' }, 'profile_image': {}, 'works': [], 'urls': { 'twitter': None, 'facebook': None, 'blog': None }, 'email': None }], 'expected_learning_items': [ 'XBlocks', 'Peer Assessment', ], "course_runs": [ { "key": 'course-v1:edX+DemoX+Demo_Course2', "uuid": "b276c25f-c640-4943-98dd-6c9ad8c71bb9", "title": "edX Demonstration Course 2", "short_description": "", "marketing_url": "course/edxdemo?utm_medium=affiliate_partner&utm_source=staff", "seats": [], "start": "2016-01-01T00:00:00Z", "end": "2018-01-01T00:00:00Z", "enrollment_start": None, "enrollment_end": None, "pacing_type": "self_paced", "type": None, "status": "published", "is_enrolled": False, "upgrade_url": None, }, ], }, ], 'purchase_text': 'Pursue the program for', 'course_count_text': '2 Courses', 'item_bullet_points': [ 'Credit- and Certificate-eligible', 'Self-paced; courses can be taken in any order', ], 'enrolled_in_course_and_paid_text': 'enrolled', 'enrolled_in_course_and_unpaid_text': 'already enrolled, must pay for certificate', 'expected_learning_items_text': "What you'll learn", 'expected_learning_items': ["Blocks", "XBlocks", "Peer Assessment"], 'expected_learning_items_show_count': 2, 'corporate_endorsements_text': 'Real Career Impact', 'corporate_endorsements': [{ "corporation_name": "Bob's Company", "statement": "", "image": { "src": "http://evonexus.org/wp-content/uploads/2016/01/IBM-logo-1024x576.jpg", "description": None, "height": None, "width": None, }, "individual_endorsements": [{ "endorser": { "uuid": "789aa881-e44b-4675-9377-fa103c12bbfc", "given_name": "Bob", "family_name": "the Builder", "bio": "Working hard on a daily basis!", "profile_image_url": None, "slug": "bob-the-builder", "position": { "title": "Engineer", "organization_name": "Bob's Company", "organization_id": 1 }, "profile_image": {}, "works": [], "urls": { "facebook": None, "twitter": None, "blog": None, }, "email": None }, "quote": "Life is hard for us engineers. Period." }] }], 'corporate_endorsements_show_count': 1, 'see_more_text': 'See More', 'see_less_text': 'See Less', 'confirm_button_text': 'Confirm Program', 'summary_header': 'Program Summary', 'price_text': 'Price', 'length_text': 'Length', 'length_info_text': '4-6 weeks per course', 'effort_text': 'Effort', 'effort_info_text': '5-10 hours per week, per course', 'program_not_eligible_for_one_click_purchase_text': 'Program not eligible for one-click purchase.', 'level_text': 'Level', 'course_full_description_text': 'About This Course', 'staff_text': 'Course Staff', 'close_modal_button_text': 'Close', 'is_learner_eligible_for_one_click_purchase': True, } program_enrollment_page_url = reverse( 'enterprise_program_enrollment_page', args=[enterprise_customer.uuid, self.dummy_program_uuid], ) self._login() response = self.client.get(program_enrollment_page_url) self._check_expected_enrollment_page(response, expected_context)