Пример #1
0
    def test_course_goal_updates(self):
        """
        Ensure that the following five use cases work as expected.

        1) Unenrolled users are not shown the update goal selection field.
        2) Enrolled users are not shown the update goal selection field if they have not yet set a course goal.
        3) Enrolled users are shown the update goal selection field if they have set a course goal.
        4) Enrolled users in the verified track are shown the update goal selection field.
        """
        # Create a course with a verified track.
        verifiable_course = CourseFactory.create()
        add_course_mode(verifiable_course, upgrade_deadline_expired=False)

        # Verify that unenrolled users are not shown the update goal selection field.
        user = self.create_user_for_course(verifiable_course, CourseUserType.UNENROLLED)
        response = self.client.get(course_home_url(verifiable_course))
        self.assertNotContains(response, TEST_COURSE_GOAL_UPDATE_FIELD)

        # Verify that enrolled users that have not set a course goal are shown a hidden update goal selection field.
        enrollment = CourseEnrollment.enroll(user, verifiable_course.id)
        response = self.client.get(course_home_url(verifiable_course))
        self.assertContains(response, TEST_COURSE_GOAL_UPDATE_FIELD_HIDDEN)

        # Verify that enrolled users that have set a course goal are shown a visible update goal selection field.
        add_course_goal(user, verifiable_course.id, COURSE_GOAL_DISMISS_OPTION)
        response = self.client.get(course_home_url(verifiable_course))
        self.assertContains(response, TEST_COURSE_GOAL_UPDATE_FIELD)
        self.assertNotContains(response, TEST_COURSE_GOAL_UPDATE_FIELD_HIDDEN)

        # Verify that enrolled and verified users are shown the update goal selection
        CourseEnrollment.update_enrollment(enrollment, is_active=True, mode=CourseMode.VERIFIED)
        response = self.client.get(course_home_url(verifiable_course))
        self.assertContains(response, TEST_COURSE_GOAL_UPDATE_FIELD)
        self.assertNotContains(response, TEST_COURSE_GOAL_UPDATE_FIELD_HIDDEN)
Пример #2
0
    def setUp(self):
        super(CourseExpirationTestCase, self).setUp()
        self.course = CourseFactory(start=now() - timedelta(weeks=10), )
        self.user = UserFactory()

        # Make this a verified course so we can test expiration date
        add_course_mode(self.course, upgrade_deadline_expired=False)
Пример #3
0
    def test_content_gating_course_card_changes(self):
        """
        When a course is expired, the links on the course card should be removed.
        Links will be removed from the course title, course image and button (View Course/Resume Course).
        The course card should have an access expired message.
        """
        CourseDurationLimitConfig.objects.create(enabled=True, enabled_as_of=datetime(2018, 1, 1))
        self.override_waffle_switch(True)

        course = CourseFactory.create(start=self.THREE_YEARS_AGO)
        add_course_mode(course, upgrade_deadline_expired=False)
        enrollment = CourseEnrollmentFactory.create(
            user=self.user,
            course_id=course.id
        )

        # pylint: disable=unused-variable
        schedule = ScheduleFactory(start_date=self.THREE_YEARS_AGO + timedelta(days=1), enrollment=enrollment)

        response = self.client.get(reverse('dashboard'))
        dashboard_html = self._remove_whitespace_from_response(response)
        access_expired_substring = 'Accessexpired'
        course_link_class = 'course-target-link'

        self.assertNotIn(
            course_link_class,
            dashboard_html
        )

        self.assertIn(
            access_expired_substring,
            dashboard_html
        )
    def test_content_availability_date(self, mock_get_course_run_details):
        """
        Content availability date is course start date or enrollment date, whichever is later.
        """
        access_duration = timedelta(weeks=7)
        mock_get_course_run_details.return_value = {'weeks_to_complete': 7}

        # Content availability date is enrollment date
        start_date = now() - timedelta(weeks=10)
        past_course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, past_course.id,
                                             CourseMode.AUDIT)
        result = get_user_course_expiration_date(self.user, past_course)
        self.assertEqual(result, None)

        add_course_mode(past_course, upgrade_deadline_expired=False)
        result = get_user_course_expiration_date(self.user, past_course)
        content_availability_date = enrollment.created
        self.assertEqual(result, content_availability_date + access_duration)

        # Content availability date is course start date
        start_date = now() + timedelta(weeks=10)
        future_course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, future_course.id,
                                             CourseMode.AUDIT)
        result = get_user_course_expiration_date(self.user, future_course)
        self.assertEqual(result, None)

        add_course_mode(future_course, upgrade_deadline_expired=False)
        result = get_user_course_expiration_date(self.user, future_course)
        content_availability_date = start_date
        self.assertEqual(result, content_availability_date + access_duration)
Пример #5
0
    def test_masters_course_message(self):
        enroll_button_html = "<button class=\"enroll-btn btn-link\">Enroll now</button>"

        # Verify that unenrolled users visiting a course with a Master's track
        # that is not the only track are shown an enroll call to action message
        add_course_mode(self.course,
                        CourseMode.MASTERS,
                        'Master\'s Mode',
                        upgrade_deadline_expired=False)
        remove_course_mode(self.course, CourseMode.AUDIT)

        self.create_user_for_course(self.course, CourseUserType.UNENROLLED)
        url = course_home_url(self.course)
        response = self.client.get(url)

        self.assertContains(response, TEST_COURSE_HOME_MESSAGE)
        self.assertContains(response, TEST_COURSE_HOME_MESSAGE_UNENROLLED)
        self.assertContains(response, enroll_button_html)

        # Verify that unenrolled users visiting a course that contains only a Master's track
        # are not shown an enroll call to action message
        remove_course_mode(self.course, CourseMode.VERIFIED)

        response = self.client.get(url)

        expected_message = (
            'You must be enrolled in the course to see course content. '
            'Please contact your degree administrator or edX Support if you have questions.'
        )
        self.assertContains(response, TEST_COURSE_HOME_MESSAGE)
        self.assertContains(response, expected_message)
        self.assertNotContains(response, enroll_button_html)
Пример #6
0
    def test_content_gating_course_card_changes(self):
        """
        When a course is expired, the links on the course card should be removed.
        Links will be removed from the course title, course image and button (View Course/Resume Course).
        The course card should have an access expired message.
        """
        CourseDurationLimitConfig.objects.create(
            enabled=True, enabled_as_of=THREE_YEARS_AGO - timedelta(days=30))
        self.override_waffle_switch(True)

        course = CourseFactory.create(start=THREE_YEARS_AGO)
        add_course_mode(course, mode_slug=CourseMode.AUDIT)
        add_course_mode(course)
        enrollment = CourseEnrollmentFactory.create(user=self.user,
                                                    course_id=course.id)
        enrollment.created = THREE_YEARS_AGO + timedelta(days=1)
        enrollment.save()

        response = self.client.get(reverse('dashboard'))
        dashboard_html = self._remove_whitespace_from_response(response)
        access_expired_substring = 'Accessexpired'
        course_link_class = 'course-target-link'

        assert course_link_class not in dashboard_html

        assert access_expired_substring in dashboard_html
Пример #7
0
    def test_content_availability_date(self, mock_get_course_run_details):
        """
        Content availability date is course start date or enrollment date, whichever is later.
        """
        access_duration = timedelta(weeks=7)
        mock_get_course_run_details.return_value = {'weeks_to_complete': 7}

        # Content availability date is enrollment date
        start_date = now() - timedelta(weeks=10)
        past_course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, past_course.id, CourseMode.AUDIT)
        result = get_user_course_expiration_date(self.user, past_course)
        self.assertEqual(result, None)

        add_course_mode(past_course, upgrade_deadline_expired=False)
        result = get_user_course_expiration_date(self.user, past_course)
        content_availability_date = enrollment.created
        self.assertEqual(result, content_availability_date + access_duration)

        # Content availability date is course start date
        start_date = now() + timedelta(weeks=10)
        future_course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, future_course.id, CourseMode.AUDIT)
        result = get_user_course_expiration_date(self.user, future_course)
        self.assertEqual(result, None)

        add_course_mode(future_course, upgrade_deadline_expired=False)
        result = get_user_course_expiration_date(self.user, future_course)
        content_availability_date = start_date
        self.assertEqual(result, content_availability_date + access_duration)
Пример #8
0
    def test_content_gating_course_card_changes(self):
        """
        When a course is expired, the links on the course card should be removed.
        Links will be removed from the course title, course image and button (View Course/Resume Course).
        The course card should have an access expired message.
        """
        CourseDurationLimitConfig.objects.create(enabled=True, enabled_as_of=datetime(2018, 1, 1))
        self.override_waffle_switch(True)

        course = CourseFactory.create(start=self.THREE_YEARS_AGO)
        add_course_mode(course, upgrade_deadline_expired=False)
        enrollment = CourseEnrollmentFactory.create(
            user=self.user,
            course_id=course.id
        )
        schedule = ScheduleFactory(start=self.THREE_YEARS_AGO + timedelta(days=1), enrollment=enrollment)

        response = self.client.get(reverse('dashboard'))
        dashboard_html = self._remove_whitespace_from_html_string(response.content)
        access_expired_substring = 'Accessexpired'
        course_link_class = 'course-target-link'

        self.assertNotIn(
            course_link_class,
            dashboard_html
        )

        self.assertIn(
            access_expired_substring,
            dashboard_html
        )
Пример #9
0
    def setUp(self):
        super(CourseExpirationTestCase, self).setUp()
        self.course = CourseFactory(start=now() - timedelta(weeks=10), )
        self.user = UserFactory()
        self.THREE_YEARS_AGO = now() - timedelta(days=(365 * 3))

        # Make this a verified course so we can test expiration date
        add_course_mode(self.course, mode_slug=CourseMode.AUDIT)
        add_course_mode(self.course)
Пример #10
0
    def setUp(self):
        super(CourseExpirationTestCase, self).setUp()
        self.course = CourseFactory(
            start=now() - timedelta(weeks=10),
        )
        self.user = UserFactory()

        # Make this a verified course so we can test expiration date
        add_course_mode(self.course, upgrade_deadline_expired=False)
Пример #11
0
    def setUp(self):
        super().setUp()  # lint-amnesty, pylint: disable=super-with-arguments
        self.course = CourseFactory(start=now() - timedelta(weeks=10), )
        self.user = UserFactory()
        self.THREE_YEARS_AGO = now() - timedelta(days=(365 * 3))

        # Make this a verified course so we can test expiration date
        add_course_mode(self.course, mode_slug=CourseMode.AUDIT)
        add_course_mode(self.course)
Пример #12
0
    def setUp(self):
        super().setUp()
        self.client.logout()  # start with least access and add access back in the various test cases

        # Make this a verified course so that an upgrade message might be shown
        add_course_mode(self.course, mode_slug=CourseMode.AUDIT)
        add_course_mode(self.course)

        # Add a welcome message
        self.create_course_update(TEST_WELCOME_MESSAGE)
    def test_expired_upgrade_deadline(self, mock_get_course_run_details):
        """
        The expiration date still exists if the upgrade deadline has passed
        """
        access_duration = timedelta(weeks=7)
        mock_get_course_run_details.return_value = {'weeks_to_complete': 7}

        start_date = now() - timedelta(weeks=10)
        course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, course.id,
                                             CourseMode.AUDIT)
        add_course_mode(course, upgrade_deadline_expired=True)
        result = get_user_course_expiration_date(self.user, course)
        content_availability_date = enrollment.created
        self.assertEqual(result, content_availability_date + access_duration)
Пример #14
0
    def create_enrollment(self, expired):
        """
        Create an enrollment
        """
        if expired:
            course = CourseFactory.create(start=self.THREE_YEARS_AGO,
                                          mobile_available=True)
            enrollment = CourseEnrollmentFactory.create(user=self.user,
                                                        course_id=course.id)
            ScheduleFactory(start=self.THREE_YEARS_AGO, enrollment=enrollment)
        else:
            course = CourseFactory.create(start=self.LAST_WEEK,
                                          mobile_available=True)
            self.enroll(course.id)

        add_course_mode(course, upgrade_deadline_expired=False)
Пример #15
0
    def create_enrollment(self, expired):
        """
        Create an enrollment
        """
        if expired:
            course = CourseFactory.create(start=self.THREE_YEARS_AGO, mobile_available=True)
            enrollment = CourseEnrollmentFactory.create(
                user=self.user,
                course_id=course.id
            )
            ScheduleFactory(start=self.THREE_YEARS_AGO, enrollment=enrollment)
        else:
            course = CourseFactory.create(start=self.LAST_WEEK, mobile_available=True)
            self.enroll(course.id)

        add_course_mode(course, upgrade_deadline_expired=False)
    def test_content_availability_date(self, mock_get_course_run_details):
        """
        Content availability date is course start date or enrollment date, whichever is later.
        """
        access_duration = timedelta(weeks=7)
        mock_get_course_run_details.return_value = {'weeks_to_complete': 7}

        # Content availability date is enrollment date
        start_date = now() - timedelta(weeks=10)
        past_course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, past_course.id,
                                             CourseMode.AUDIT)
        CourseDurationLimitConfig.objects.create(
            enabled=True,
            course=CourseOverview.get_from_id(past_course.id),
            enabled_as_of=past_course.start,
        )
        result = get_user_course_expiration_date(
            self.user,
            CourseOverview.get_from_id(past_course.id),
        )
        assert result is None

        add_course_mode(past_course, mode_slug=CourseMode.AUDIT)
        add_course_mode(past_course, upgrade_deadline_expired=False)
        result = get_user_course_expiration_date(
            self.user,
            CourseOverview.get_from_id(past_course.id),
        )
        content_availability_date = enrollment.created
        assert result == (content_availability_date + access_duration)

        # Content availability date is course start date
        start_date = now() + timedelta(weeks=10)
        future_course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, future_course.id,
                                             CourseMode.AUDIT)
        CourseDurationLimitConfig.objects.create(
            enabled=True,
            course=CourseOverview.get_from_id(future_course.id),
            enabled_as_of=past_course.start,
        )
        result = get_user_course_expiration_date(
            self.user,
            CourseOverview.get_from_id(future_course.id),
        )
        assert result is None

        add_course_mode(future_course, mode_slug=CourseMode.AUDIT)
        add_course_mode(future_course, upgrade_deadline_expired=False)
        result = get_user_course_expiration_date(
            self.user,
            CourseOverview.get_from_id(future_course.id),
        ).replace(microsecond=0)
        content_availability_date = start_date.replace(microsecond=0)
        assert result == (content_availability_date + access_duration)
    def test_expired_upgrade_deadline(self, mock_get_course_run_details):
        """
        The expiration date still exists if the upgrade deadline has passed
        """
        access_duration = timedelta(weeks=7)
        mock_get_course_run_details.return_value = {'weeks_to_complete': 7}

        start_date = now() - timedelta(weeks=10)
        course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, course.id, CourseMode.AUDIT)
        add_course_mode(course, upgrade_deadline_expired=True)
        result = get_user_course_expiration_date(
            self.user,
            CourseOverview.get_from_id(course.id),
        )
        content_availability_date = enrollment.created
        self.assertEqual(result, content_availability_date + access_duration)
Пример #18
0
    def create_enrollment(self, expired):
        """
        Create an enrollment
        """
        if expired:
            course = CourseFactory.create(start=self.THREE_YEARS_AGO, mobile_available=True)
            enrollment = CourseEnrollmentFactory.create(
                user=self.user,
                course_id=course.id
            )
            enrollment.created = self.THREE_YEARS_AGO + datetime.timedelta(days=1)
            enrollment.save()
        else:
            course = CourseFactory.create(start=self.LAST_WEEK, mobile_available=True)
            self.enroll(course.id)

        add_course_mode(course, mode_slug=CourseMode.AUDIT)
        add_course_mode(course)
    def setUp(self):
        super().setUp()  # lint-amnesty, pylint: disable=super-with-arguments
        self.course = CourseFactory(start=now() - timedelta(weeks=10), )
        self.chapter = ItemFactory.create(category='chapter',
                                          parent_location=self.course.location,
                                          display_name='Test Chapter')
        self.sequential = ItemFactory.create(
            category='sequential',
            parent_location=self.chapter.location,
            display_name='Test Sequential')
        ItemFactory.create(category='vertical',
                           parent_location=self.sequential.location,
                           display_name='Test Vertical')
        self.user = UserFactory()
        self.THREE_YEARS_AGO = now() - timedelta(days=(365 * 3))

        # Make this a verified course so we can test expiration date
        add_course_mode(self.course, mode_slug=CourseMode.AUDIT)
        add_course_mode(self.course)
Пример #20
0
    def test_course_goals(self):
        """
        Ensure that the following five use cases work as expected.

        1) Unenrolled users are not shown the set course goal message.
        2) Enrolled users are shown the set course goal message if they have not yet set a course goal.
        3) Enrolled users are not shown the set course goal message if they have set a course goal.
        4) Enrolled and verified users are not shown the set course goal message.
        5) Enrolled users are not shown the set course goal message in a course that cannot be verified.
        """
        # Create a course with a verified track.
        verifiable_course = CourseFactory.create()
        add_course_mode(verifiable_course, upgrade_deadline_expired=False)

        # Verify that unenrolled users are not shown the set course goal message.
        user = self.create_user_for_course(verifiable_course,
                                           CourseUserType.UNENROLLED)
        response = self.client.get(course_home_url(verifiable_course))
        self.assertNotContains(response, TEST_COURSE_GOAL_OPTIONS)

        # Verify that enrolled users are shown the set course goal message in a verified course.
        CourseEnrollment.enroll(user, verifiable_course.id)
        response = self.client.get(course_home_url(verifiable_course))
        self.assertContains(response, TEST_COURSE_GOAL_OPTIONS)

        # Verify that enrolled users that have set a course goal are not shown the set course goal message.
        add_course_goal_deprecated(user, verifiable_course.id,
                                   COURSE_GOAL_DISMISS_OPTION)
        response = self.client.get(course_home_url(verifiable_course))
        self.assertNotContains(response, TEST_COURSE_GOAL_OPTIONS)

        # Verify that enrolled and verified users are not shown the set course goal message.
        get_course_goal(user, verifiable_course.id).delete()
        CourseEnrollment.enroll(user, verifiable_course.id,
                                CourseMode.VERIFIED)
        response = self.client.get(course_home_url(verifiable_course))
        self.assertNotContains(response, TEST_COURSE_GOAL_OPTIONS)

        # Verify that enrolled users are not shown the set course goal message in an audit only course.
        audit_only_course = CourseFactory.create()
        CourseEnrollment.enroll(user, audit_only_course.id)
        response = self.client.get(course_home_url(audit_only_course))
        self.assertNotContains(response, TEST_COURSE_GOAL_OPTIONS)
Пример #21
0
    def create_enrollment(self, expired):
        """
        Create an enrollment
        """
        if expired:
            course = CourseFactory.create(start=self.THREE_YEARS_AGO,
                                          mobile_available=True)
            enrollment = CourseEnrollmentFactory.create(user=self.user,
                                                        course_id=course.id)
            ScheduleFactory(
                # TODO replace 'start' field with 'start_date' after data migration,
                #  in removing writes from old field step in column renaming release
                start=self.THREE_YEARS_AGO + datetime.timedelta(days=1),
                enrollment=enrollment)
        else:
            course = CourseFactory.create(start=self.LAST_WEEK,
                                          mobile_available=True)
            self.enroll(course.id)

        add_course_mode(course, upgrade_deadline_expired=False)
    def test_expired_upgrade_deadline(self, mock_get_course_run_details):
        """
        The expiration date still exists if the upgrade deadline has passed
        """
        access_duration = timedelta(weeks=7)
        mock_get_course_run_details.return_value = {'weeks_to_complete': 7}

        start_date = now() - timedelta(weeks=10)
        course = CourseFactory(start=start_date)
        enrollment = CourseEnrollment.enroll(self.user, course.id, CourseMode.AUDIT)
        CourseDurationLimitConfig.objects.create(
            enabled=True,
            course=CourseOverview.get_from_id(course.id),
            enabled_as_of=course.start,
        )
        add_course_mode(course, mode_slug=CourseMode.AUDIT)
        add_course_mode(course, upgrade_deadline_expired=True)
        result = get_user_course_expiration_date(
            self.user,
            CourseOverview.get_from_id(course.id),
        )
        content_availability_date = enrollment.created
        assert result == (content_availability_date + access_duration)