Example #1
0
    def test_user_customized_lang_code_as_settings_language_code(self):
        with override_settings(USE_I18N=True,
                               LANGUAGES=self.LANGUAGES_CONF2,
                               LANGUAGE_CODE='user_customized_lang_code'):
            with self.assertRaises(IOError):
                # because there's no file named "user_customized_lang_code.mo"
                get_course_specific_language_choices()

            with mock.patch(REAL_TRANSLATION_FUNCTION_TO_MOCK) as mock_gettext:
                mock_gettext.side_effect = real_trans_side_effect
                choices = get_course_specific_language_choices()

                # The language description is the language_code, because it can't
                # be found in django.conf.locale.LANG_INFO
                self.assertEqual(choices[1][1], "user_customized_lang_code")

        with override_settings(USE_I18N=False,
                               LANGUAGES=self.LANGUAGES_CONF2,
                               LANGUAGE_CODE='user_customized_lang_code'):
            with mock.patch(REAL_TRANSLATION_FUNCTION_TO_MOCK) as mock_gettext:
                mock_gettext.side_effect = real_trans_side_effect
                choices = get_course_specific_language_choices()

                # The language description is the language_code, because it can't
                # be found in django.conf.locale.LANG_INFO
                self.assertIn("user_customized_lang_code", choices[0][1])
Example #2
0
    def test_set_up_new_course_failed_to_delete_repo(self):
        resp = self.get_set_up_new_course()
        self.assertTrue(resp.status_code, 403)

        def force_remove_path_side_effect(path):
            # we need to delete the path, or tests followed will fail
            force_remove_path(path)
            raise OSError("my os error")

        data = SINGLE_COURSE_SETUP_LIST[0]["course"]

        with mock.patch(
                "dulwich.client.GitClient.fetch") as mock_fetch, mock.patch(
                    'relate.utils.force_remove_path'
                ) as mock_force_remove_path:
            mock_fetch.side_effect = RuntimeError("my fetch error")
            mock_force_remove_path.side_effect = force_remove_path_side_effect
            resp = self.post_create_course(data, raise_error=False)
            self.assertTrue(resp.status_code, 200)
            self.assertEqual(Course.objects.count(), 0)

            self.assertAddMessageCallCount(2)

            self.assertAddMessageCalledWith(
                "Failed to delete unused repository directory", reset=False)
            self.assertAddMessageCalledWith(
                "Course creation failed: RuntimeError: my fetch error")
Example #3
0
    def test_purge_page_view_superuser(self):
        with self.temporarily_switch_to_user(self.superuser):
            resp = self.get_purget_page_view()
            self.assertEqual(resp.status_code, 200)
            self.assertEqual(
                resp.context.get("form").fields["course"].queryset.count(), 2)

            with mock.patch("celery.app.task.Task.delay") \
                    as mocked_delay,\
                    mock.patch("course.views.monitor_task"):
                # post without "submit"
                resp = self.post_purget_page_view(self.course1.pk,
                                                  add_submit=False)

                # Nothing happened
                self.assertEqual(resp.status_code, 200)
                self.assertEqual(mocked_delay.call_count, 0)

                # post with "submit"
                # Manually fake an async result id
                faked_async_result_id = "64907302-3166-43d8-b822"
                mocked_delay.return_value.id = faked_async_result_id

                resp = self.post_purget_page_view(self.course1.pk)
                self.assertRedirects(resp,
                                     reverse("relate-monitor_task",
                                             args=[faked_async_result_id]),
                                     fetch_redirect_response=False)

                self.assertEqual(mocked_delay.call_count, 1)
                self.assertTrue(self.course1.id in mocked_delay.call_args[0])
Example #4
0
    def test_set_up_new_course_failed_to_delete_repo(self):
        resp = self.get_set_up_new_course()
        self.assertTrue(resp.status_code, 403)

        def force_remove_path_side_effect(path):
            # we need to delete the path, or tests followed will fail
            force_remove_path(path)
            raise OSError("my os error")

        data = SINGLE_COURSE_SETUP_LIST[0]["course"]

        with mock.patch(
                "dulwich.client.GitClient.fetch"
        ) as mock_fetch, mock.patch(
                'relate.utils.force_remove_path'
        )as mock_force_remove_path:
            mock_fetch.side_effect = RuntimeError("my fetch error")
            mock_force_remove_path.side_effect = force_remove_path_side_effect
            resp = self.post_create_course(data, raise_error=False)
            self.assertTrue(resp.status_code, 200)
            self.assertEqual(Course.objects.count(), 0)

            self.assertAddMessageCallCount(2)

            self.assertAddMessageCalledWith(
                "Failed to delete unused repository directory", reset=False)
            self.assertAddMessageCalledWith(
                "Course creation failed: RuntimeError: my fetch error")
Example #5
0
    def test_markup_body_for_title_not_implemented(self):
        with mock.patch("course.page.static.Page.markup_body_for_title")\
                as mock_markup_body_for_title,\
                mock.patch("warnings.warn") as mock_warn:
            mock_markup_body_for_title.side_effect = NotImplementedError
            mock_warn.side_effect = [None, None, None]

            markdown = (
                    PAGE_WITH_TITLE_MARKDOWN_PATTERN
                    % {"attr_title": "",
                       "content_title": ""})

            resp = self.get_page_sandbox_preview_response(markdown)
            self.assertEqual(resp.status_code, 200)
            self.assertSandboxNotHasValidPage(resp)
            self.assertResponseContextContains(
                resp, PAGE_ERRORS,
                "no title found in body or title attribute")

            # There are other warnings besides this expected warning
            self.assertTrue(mock_warn.call_count >= 1)
            warned_with_expected_msg = False
            expected_warn_msg = ("PageBaseWithTitle subclass 'Page' does not "
                                 "implement markup_body_for_title()")
            for args in mock_warn.call_args_list:
                if expected_warn_msg in args[0]:
                    warned_with_expected_msg = True
                    break

            if not warned_with_expected_msg:
                self.fail("%s is not warned as expected" % expected_warn_msg)
Example #6
0
    def test_set_up_new_course(self):
        # In this test, we use client instead of request factory to simplify
        # the logic.

        with self.temporarily_switch_to_user(self.instructor):
            # the permission is cached, need to repopulated from db
            resp = self.get_set_up_new_course()
            self.assertTrue(resp.status_code, 200)

            with mock.patch("dulwich.client.GitClient.fetch",
                            return_value={b"HEAD": b"some_commit_sha"}), \
                  mock.patch("course.versioning.transfer_remote_refs",
                            return_value=None), \
                      mock.patch("course.validation.validate_course_content",
                               return_value=None):
                data = self.get_set_up_new_course_form_data()

                resp = self.post_create_course(data,
                                               raise_error=False,
                                               login_superuser=False)
                self.assertTrue(resp.status_code, 200)
                self.assertEqual(Course.objects.count(), 1)
                self.assertEqual(Participation.objects.count(), 1)
                self.assertEqual(Participation.objects.first().user.username,
                                 "test_instructor")
                self.assertAddMessageCalledWith(
                    "Course content validated, creation succeeded.")

                from course.enrollment import get_participation_role_identifiers

                # the user who setup the course has role instructor
                self.assertTrue(
                    get_participation_role_identifiers(
                        Course.objects.first(), Participation.objects.first()),
                    "instructor")
Example #7
0
    def test_validate_point_count_called(self):
        import random
        with mock.patch("course.page.base.validate_point_count") \
                as mock_validate_point_count, \
                mock.patch("course.page.base.get_auto_feedback") \
                        as mock_get_auto_feedback:
            mock_validate_point_count.side_effect = lambda x: x

            mock_get_auto_feedback.side_effect = lambda x: x
            for i in range(10):
                correctness = random.uniform(0, 15)
                feedback = "some feedback"
                AnswerFeedback(correctness, feedback)
                mock_validate_point_count.assert_called_once_with(correctness)

                # because feedback is not None
                self.assertEqual(mock_get_auto_feedback.call_count, 0)
                mock_validate_point_count.reset_mock()

            for i in range(10):
                correctness = random.uniform(0, 15)
                AnswerFeedback(correctness)

                # because get_auto_feedback is mocked, the call_count of
                # mock_validate_point_count is only once
                mock_validate_point_count.assert_called_once_with(correctness)
                mock_validate_point_count.reset_mock()

                # because feedback is None
                self.assertEqual(mock_get_auto_feedback.call_count, 1)
                mock_get_auto_feedback.reset_mock()

            AnswerFeedback(correctness=None)
            mock_validate_point_count.assert_called_once_with(None)
Example #8
0
    def test_post_form_deprecated(self):
        page_id = "half"

        with mock.patch(
                "course.page.text.TextQuestionBase.process_form_post",
                autospec=True
        ) as mock_process_form_post, mock.patch(
                "course.page.text.TextQuestionBase.post_form",
                autospec=True) as mock_post_form, mock.patch(
                "warnings.warn") as mock_warn:

            mock_process_form_post.side_effect = process_form_post_side_effect_super
            mock_post_form.side_effect = post_form_side_effect

            self.post_answer_by_page_id(
                page_id, answer_data={"answer": "1/2"})

            self.assertTrue(mock_warn.call_count >= 1)

            expected_warn_msg = (
                "TextQuestion is using the post_form compatiblity hook, "
                "which is deprecated.")

            warned_with_expected_msg = False

            for args in mock_warn.call_args_list:
                if expected_warn_msg in args[0]:
                    warned_with_expected_msg = True
                    break

            if not warned_with_expected_msg:
                self.fail("'%s' is not warned as expected" % expected_warn_msg)

        self.assertEqual(self.end_flow().status_code, 200)
        self.assertSessionScoreEqual(5)
Example #9
0
    def test_markup_body_for_title_not_implemented(self):
        with mock.patch("course.page.static.Page.markup_body_for_title")\
                as mock_markup_body_for_title,\
                mock.patch("warnings.warn") as mock_warn:
            mock_markup_body_for_title.side_effect = NotImplementedError
            mock_warn.side_effect = [None, None, None]

            markdown = (
                    PAGE_WITH_TITLE_MARKDOWN_PATTERN
                    % {"attr_title": "",
                       "content_title": ""})

            resp = self.get_page_sandbox_preview_response(markdown)
            self.assertEqual(resp.status_code, 200)
            self.assertSandboxNotHasValidPage(resp)
            self.assertResponseContextContains(
                resp, PAGE_ERRORS,
                "no title found in body or title attribute")

            # There are other warnings besides this expected warning
            self.assertTrue(mock_warn.call_count >= 1)
            warned_with_expected_msg = False
            expected_warn_msg = ("PageBaseWithTitle subclass 'Page' does not "
                                 "implement markup_body_for_title()")
            for args in mock_warn.call_args_list:
                if expected_warn_msg in args[0]:
                    warned_with_expected_msg = True
                    break

            if not warned_with_expected_msg:
                self.fail("%s is not warned as expected" % expected_warn_msg)
Example #10
0
    def setUp(self):
        super(FlowRuleExceptionTest, self).setUp()
        user = factories.UserFactory()
        self.participation = factories.ParticipationFactory(course=self.course,
                                                            user=user)
        fake_get_course_repo = mock.patch("course.content.get_course_repo")
        self.mock_get_course_repo = fake_get_course_repo.start()
        self.mock_get_course_repo.return_value = mock.MagicMock()
        self.addCleanup(fake_get_course_repo.stop)

        fake_get_flow_desc = mock.patch("course.content.get_flow_desc")
        self.mock_get_flow_desc = fake_get_flow_desc.start()
        self.addCleanup(fake_get_flow_desc.stop)

        fake_validate_session_start_rule = mock.patch(
            "course.validation.validate_session_start_rule")
        self.mock_validate_session_start_rule = (
            fake_validate_session_start_rule.start())
        self.addCleanup(fake_validate_session_start_rule.stop)

        fake_validate_session_access_rule = mock.patch(
            "course.validation.validate_session_access_rule")
        self.mock_validate_session_access_rule = (
            fake_validate_session_access_rule.start())
        self.addCleanup(fake_validate_session_access_rule.stop)

        fake_validate_session_grading_rule = mock.patch(
            "course.validation.validate_session_grading_rule")
        self.mock_validate_session_grading_rule = (
            fake_validate_session_grading_rule.start())
        self.addCleanup(fake_validate_session_grading_rule.stop)
Example #11
0
    def test_deprecated_make_page_data_has_warning(self):
        with mock.patch("course.page.text.TextQuestionBase.make_page_data",
                        autospec=True) as mock_make_page_data, mock.patch(
                "warnings.warn") as mock_warn:

            mock_make_page_data.side_effect = make_page_data_side_effect_has_data
            resp = self.get_page_sandbox_preview_response(TEXT_QUESTION_MARKDOWN)
            self.assertEqual(resp.status_code, 200)
            self.assertSandboxHasValidPage(resp)
            self.assertSandboxWarningTextContain(resp, None)

            # There are other warnings besides this expected warning
            self.assertTrue(mock_warn.call_count >= 1)

            expected_warn_msg = (
                "TextQuestion is using the make_page_data compatiblity "
                "hook, which is deprecated.")

            warned_with_expected_msg = False

            for args in mock_warn.call_args_list:
                if expected_warn_msg in args[0]:
                    warned_with_expected_msg = True
                    break

            if not warned_with_expected_msg:
                self.fail("'%s' is not warned as expected" % expected_warn_msg)
Example #12
0
    def test_send_email_failure_when_request_python_run_with_retries_raise_uncaught_error(self):  # noqa
        with mock.patch(
            RUNPY_WITH_RETRIES_PATH,
            autospec=True
        ) as mock_runpy:
            expected_error_str = ("This is an error raised with "
                                  "request_python_run_with_retries")
            mock_runpy.side_effect = RuntimeError(expected_error_str)

            with mock.patch("course.page.PageContext") as mock_page_context:
                mock_page_context.return_value.in_sandbox = False

                # This remove the warning caused by mocked commit_sha value
                # "CacheKeyWarning: Cache key contains characters that
                # will cause errors ..."
                mock_page_context.return_value.commit_sha = b"1234"

                with mock.patch("django.core.mail.message.EmailMessage.send") as mock_send:  # noqa
                    mock_send.side_effect = RuntimeError("some email send error")

                    resp = self.get_page_sandbox_submit_answer_response(
                        markdowns.CODE_MARKDWON,
                        answer_data={"answer": ['c = b + a\r']})
                    self.assertContains(resp, expected_error_str)
                    self.assertEqual(resp.status_code, 200)
                    self.assertResponseContextAnswerFeedbackCorrectnessEquals(resp,
                                                                              None)
                    self.assertEqual(len(mail.outbox), 0)
Example #13
0
    def setUp(self):
        super(FlowRuleExceptionTest, self).setUp()
        user = factories.UserFactory()
        self.participation = factories.ParticipationFactory(
            course=self.course,
            user=user)
        fake_get_course_repo = mock.patch("course.content.get_course_repo")
        self.mock_get_course_repo = fake_get_course_repo.start()
        self.mock_get_course_repo.return_value = mock.MagicMock()
        self.addCleanup(fake_get_course_repo.stop)

        fake_get_flow_desc = mock.patch("course.content.get_flow_desc")
        self.mock_get_flow_desc = fake_get_flow_desc.start()
        self.addCleanup(fake_get_flow_desc.stop)

        fake_validate_session_start_rule = mock.patch(
            "course.validation.validate_session_start_rule")
        self.mock_validate_session_start_rule = (
            fake_validate_session_start_rule.start())
        self.addCleanup(fake_validate_session_start_rule.stop)

        fake_validate_session_access_rule = mock.patch(
            "course.validation.validate_session_access_rule")
        self.mock_validate_session_access_rule = (
            fake_validate_session_access_rule.start())
        self.addCleanup(fake_validate_session_access_rule.stop)

        fake_validate_session_grading_rule = mock.patch(
            "course.validation.validate_session_grading_rule")
        self.mock_validate_session_grading_rule = (
            fake_validate_session_grading_rule.start())
        self.addCleanup(fake_validate_session_grading_rule.stop)
Example #14
0
    def test_validate_point_count_called(self):
        import random
        with mock.patch("course.page.base.validate_point_count")\
                as mock_validate_point_count,\
                mock.patch("course.page.base.get_auto_feedback")\
                as mock_get_auto_feedback:
            mock_validate_point_count.side_effect = lambda x: x

            mock_get_auto_feedback.side_effect = lambda x: x
            for i in range(10):
                correctness = random.uniform(0, 15)
                feedback = "some feedback"
                AnswerFeedback(correctness, feedback)
                mock_validate_point_count.assert_called_once_with(correctness)

                # because feedback is not None
                self.assertEqual(mock_get_auto_feedback.call_count, 0)
                mock_validate_point_count.reset_mock()

            for i in range(10):
                correctness = random.uniform(0, 15)
                AnswerFeedback(correctness)

                # because get_auto_feedback is mocked, the call_count of
                # mock_validate_point_count is only once
                mock_validate_point_count.assert_called_once_with(correctness)
                mock_validate_point_count.reset_mock()

                # because feedback is None
                self.assertEqual(mock_get_auto_feedback.call_count, 1)
                mock_get_auto_feedback.reset_mock()

            AnswerFeedback(correctness=None)
            mock_validate_point_count.assert_called_once_with(None)
Example #15
0
    def test_success_test_restrict_to_first_attempt_invalid(self):
        with mock.patch(
                "course.analytics.make_grade_histogram"
        ) as mock_make_g_his, mock.patch(
            "course.analytics.make_page_answer_stats_list"
        ) as mock_make_stats_list, mock.patch(
            "course.analytics.make_time_histogram"
        ) as mock_make_t_his, mock.patch(
            "course.analytics.count_participants"
        ) as mock_count_particpt:
            resp = self.get_flow_analytics_view(flow_id=self.flow_id,
                                                restrict_to_first_attempt="foo")
            self.assertEqual(resp.status_code, 200)
            self.assertResponseContextEqual(
                resp, "flow_identifier", self.flow_id)

            # make_page_answer_stats_list is called
            # using restrict_to_first_attempt = 0
            self.assertIn(0, mock_make_stats_list.call_args[0])
            self.assertResponseContextEqual(resp, "restrict_to_first_attempt", 0)

            self.assertEqual(mock_make_g_his.call_count, 1)
            self.assertEqual(mock_make_stats_list.call_count, 1)
            self.assertEqual(mock_make_t_his.call_count, 1)
            self.assertEqual(mock_count_particpt.call_count, 1)
Example #16
0
    def test_set_up_new_course(self):
        # In this test, we use client instead of request factory to simplify
        # the logic.

        with self.temporarily_switch_to_user(self.instructor):
            # the permission is cached, need to repopulated from db
            resp = self.get_set_up_new_course()
            self.assertTrue(resp.status_code, 200)

            with mock.patch("dulwich.client.GitClient.fetch",
                            return_value={b"HEAD": b"some_commit_sha"}), \
                  mock.patch("course.versioning.transfer_remote_refs",
                            return_value=None), \
                      mock.patch("course.validation.validate_course_content",
                               return_value=None):
                data = self.get_set_up_new_course_form_data()

                resp = self.post_create_course(data, raise_error=False,
                                               login_superuser=False)
                self.assertTrue(resp.status_code, 200)
                self.assertEqual(Course.objects.count(), 1)
                self.assertEqual(Participation.objects.count(), 1)
                self.assertEqual(Participation.objects.first().user.username,
                                 "test_instructor")
                self.assertAddMessageCalledWith(
                    "Course content validated, creation succeeded.")

                from course.enrollment import get_participation_role_identifiers

                # the user who setup the course has role instructor
                self.assertTrue(
                    get_participation_role_identifiers(
                        Course.objects.first(),
                        Participation.objects.first()),
                    "instructor")
Example #17
0
    def test_post_form_deprecated(self):
        page_id = "half"

        with mock.patch(
                "course.page.text.TextQuestionBase.process_form_post",
                autospec=True
        ) as mock_process_form_post, mock.patch(
                "course.page.text.TextQuestionBase.post_form",
                autospec=True) as mock_post_form, mock.patch(
                "warnings.warn") as mock_warn:

            mock_process_form_post.side_effect = process_form_post_side_effect_super
            mock_post_form.side_effect = post_form_side_effect

            self.post_answer_by_page_id(
                page_id, answer_data={"answer": "1/2"})

            self.assertTrue(mock_warn.call_count >= 1)

            expected_warn_msg = (
                "TextQuestion is using the post_form compatiblity hook, "
                "which is deprecated.")

            warned_with_expected_msg = False

            for args in mock_warn.call_args_list:
                if expected_warn_msg in args[0]:
                    warned_with_expected_msg = True
                    break

            if not warned_with_expected_msg:
                self.fail("'%s' is not warned as expected" % expected_warn_msg)

        self.assertEqual(self.end_flow().status_code, 200)
        self.assertSessionScoreEqual(5)
Example #18
0
    def test_languages_configured_course_has_force_lang_get_language_none(
            self):
        self.set_course_lang_to_ko()
        with mock.patch("course.utils.translation.get_language")\
                as mock_get_language,\
                mock.patch("course.utils.translation.deactivate_all")\
                        as mock_deactivate_all:
            mock_get_language.return_value = None
            home_visit_result = self.home_resp_contains_korean_with_diff_settings(
            )
            self.assertEqual(
                # Display Korean according to i18n, language_code and browser
                home_visit_result[0],
                [False, True, False, True])
            self.assertEqual(mock_deactivate_all.call_count, 0)

            mock_deactivate_all.reset_mock()
            course_page_visit_result = (
                self.course_resp_contains_korean_with_diff_settings())
            self.assertEqual(
                # All display Korean
                course_page_visit_result[0],
                [True, True, True, True])

            # There are 4 visit, each will call deactivate_all()
            self.assertEqual(mock_deactivate_all.call_count, 4)
Example #19
0
    def test_success_test_restrict_to_first_attempt_invalid(self):
        with mock.patch(
                "course.analytics.make_grade_histogram"
        ) as mock_make_g_his, mock.patch(
                "course.analytics.make_page_answer_stats_list"
        ) as mock_make_stats_list, mock.patch(
                "course.analytics.make_time_histogram"
        ) as mock_make_t_his, mock.patch(
                "course.analytics.count_participants") as mock_count_particpt:
            resp = self.get_flow_analytics_view(
                flow_id=self.flow_id, restrict_to_first_attempt="foo")
            self.assertEqual(resp.status_code, 200)
            self.assertResponseContextEqual(resp, "flow_identifier",
                                            self.flow_id)

            # make_page_answer_stats_list is called
            # using restrict_to_first_attempt = 0
            self.assertIn(0, mock_make_stats_list.call_args[0])
            self.assertResponseContextEqual(resp, "restrict_to_first_attempt",
                                            0)

            self.assertEqual(mock_make_g_his.call_count, 1)
            self.assertEqual(mock_make_stats_list.call_count, 1)
            self.assertEqual(mock_make_t_his.call_count, 1)
            self.assertEqual(mock_count_particpt.call_count, 1)
    def test_purge_page_view_superuser(self):
        with self.temporarily_switch_to_user(self.superuser):
            resp = self.get_purget_page_view()
            self.assertEqual(resp.status_code, 200)
            self.assertEqual(
                resp.context.get("form").fields["course"].queryset.count(), 2)

            with mock.patch("celery.app.task.Task.delay") \
                    as mocked_delay,\
                    mock.patch("course.views.monitor_task"):
                # post without "submit"
                resp = self.post_purget_page_view(self.course1.pk, add_submit=False)

                # Nothing happened
                self.assertEqual(resp.status_code, 200)
                self.assertEqual(mocked_delay.call_count, 0)

                # post with "submit"
                # Manually fake an async result id
                faked_async_result_id = "64907302-3166-43d8-b822"
                mocked_delay.return_value.id = faked_async_result_id

                resp = self.post_purget_page_view(self.course1.pk)
                self.assertRedirects(resp,
                                     reverse("relate-monitor_task",
                                             args=[faked_async_result_id]),
                                     fetch_redirect_response=False)

                self.assertEqual(mocked_delay.call_count, 1)
                self.assertTrue(self.course1.id in mocked_delay.call_args[0])
Example #21
0
    def test_deprecated_make_page_data_has_warning(self):
        with mock.patch("course.page.text.TextQuestionBase.make_page_data",
                        autospec=True) as mock_make_page_data, mock.patch(
                "warnings.warn") as mock_warn:

            mock_make_page_data.side_effect = make_page_data_side_effect_has_data
            resp = self.get_page_sandbox_preview_response(TEXT_QUESTION_MARKDOWN)
            self.assertEqual(resp.status_code, 200)
            self.assertSandboxHasValidPage(resp)
            self.assertSandboxWarningTextContain(resp, None)

            # There are other warnings besides this expected warning
            self.assertTrue(mock_warn.call_count >= 1)

            expected_warn_msg = (
                "TextQuestion is using the make_page_data compatiblity "
                "hook, which is deprecated.")

            warned_with_expected_msg = False

            for args in mock_warn.call_args_list:
                if expected_warn_msg in args[0]:
                    warned_with_expected_msg = True
                    break

            if not warned_with_expected_msg:
                self.fail("'%s' is not warned as expected" % expected_warn_msg)
Example #22
0
    def verify_result_with_configure(self, my_site_name):
        # home page
        with mock.patch(REAL_TRANSLATION_FUNCTION_TO_MOCK) as mock_gettext:
            mock_gettext.side_effect = real_trans_side_effect
            resp = self.c.get("/")
            self.assertEqual(resp.status_code, 200)
            self.assertContains(resp,
                                "<title>%s</title>" % my_site_name,
                                html=True)

            # Three translations in nav_bar brand, html title and
            # "Welcome to RELATE", respectively
            self.assertEqual(
                self.get_translation_count(mock_gettext, my_site_name), 3)
            mock_gettext.reset_mock()

            # course page
            resp = self.c.get(self.get_course_page_url())
            self.assertEqual(resp.status_code, 200)

            test_site_name_re = re.compile(
                ".+<title>.+-.+%s.+</title>.+" % my_site_name, re.DOTALL)
            self.assertRegex(resp.content.decode(), test_site_name_re)

            # One translation in html title
            self.assertEqual(
                self.get_translation_count(mock_gettext, my_site_name), 1)

        # email
        with override_settings(RELATE_REGISTRATION_ENABLED=True,
                               USE_I18N=True):
            # render() is mocked so as to count string translated in email rendering
            with \
                    mock.patch(REAL_TRANSLATION_FUNCTION_TO_MOCK) \
                    as mock_gettext_global, \
                    mock.patch("course.auth._") as mock_gettext_auth, \
                    mock.patch('course.auth.messages'), \
                    mock.patch('course.auth.render'):
                mock_gettext_global.return_value = "foo"
                mock_gettext_auth.return_value = "foo"
                with self.temporarily_switch_to_user(None):
                    resp = self.post_sign_up(data={
                        "username": "******",
                        "email": "*****@*****.**"
                    },
                                             follow=False)
                    self.assertTrue(resp.status_code, 200)
                    self.assertEqual(len(mail.outbox), 1)

                    # In the view, tranlating RELATE for email title.
                    self.assertEqual(
                        self.get_translation_count(mock_gettext_auth,
                                                   my_site_name), 1)

                    # Three RELATE in the email template
                    self.assertEqual(
                        self.get_translation_count(mock_gettext_global,
                                                   my_site_name), 3)
Example #23
0
    def setUp(self):
        super(RunCourseUpdateCommandTest, self).setUp()
        self.course = factories.CourseFactory(
            active_git_commit_sha=self.default_old_sha)
        user = factories.UserFactory()
        instructor_role = factories.ParticipationRoleFactory(
            course=self.course,
            identifier="instructor"
        )

        self.participation = factories.ParticipationFactory(
            course=self.course,
            preview_git_commit_sha=None,
            user=user)
        self.participation.roles.set([instructor_role])

        self.request = mock.MagicMock()
        self.request.user = user

        self.pctx = mock.MagicMock()
        self.pctx.course = self.course
        self.pctx.participation = self.participation

        self.repo = mock.MagicMock()
        self.content_repo = self.repo

        fake_get_dulwich_client_and_remote_path_from_course = mock.patch(
            "course.versioning.get_dulwich_client_and_remote_path_from_course")
        self.mock_get_dulwich_client_and_remote_path_from_course = (
            fake_get_dulwich_client_and_remote_path_from_course.start()
        )

        self.mock_client = mock.MagicMock()
        remote_path = "/remote/path"
        self.mock_get_dulwich_client_and_remote_path_from_course.return_value = (
            self.mock_client, remote_path
        )
        self.mock_client.fetch.return_value = {
            b"HEAD": self.default_switch_to_sha.encode()}

        self.addCleanup(fake_get_dulwich_client_and_remote_path_from_course.stop)

        fake_transfer_remote_refs = mock.patch(
            "course.versioning.transfer_remote_refs")
        self.mock_transfer_remote_refs = fake_transfer_remote_refs.start()
        self.addCleanup(fake_transfer_remote_refs.stop)

        fake_is_parent_commit = mock.patch("course.versioning.is_parent_commit")
        self.mock_is_parent_commit = fake_is_parent_commit.start()
        self.mock_is_parent_commit.return_value = False
        self.addCleanup(fake_is_parent_commit.stop)

        fake_validate_course_content = mock.patch(
            "course.validation.validate_course_content")
        self.mock_validate_course_content = fake_validate_course_content.start()
        self.mock_validate_course_content.return_value = []
        self.addCleanup(fake_validate_course_content.stop)
Example #24
0
 def test_attribute_error2(self):
     dtime = datetime.datetime(2019, 1, 1)
     with mock.patch("django.utils.formats.date_format"
                     ) as mock_date_format, mock.patch(
                         "django.utils.dateformat.format") as mock_format:
         mock_date_format.side_effect = date_format_side_effect
         mock_format.side_effect = format_side_effectformat
         result = format_datetime_local(dtime, format="foo")
     self.assertEqual(
         result, date_format(dtime, format=get_format("DATETIME_FORMAT")))
Example #25
0
 def test_form_not_valid(self):
     with mock.patch("course.versioning.GitUpdateForm.is_valid"
                     ) as mock_form_valid, mock.patch(
                         "course.versioning.run_course_update_command"
                     ) as mock_run_update:
         mock_form_valid.return_value = False
         resp = self.post_update_course_content("some_commit_sha",
                                                command="update")
         self.assertEqual(resp.status_code, 200)
         self.assertEqual(mock_run_update.call_count, 0)
Example #26
0
 def test_form_not_valid(self):
     with mock.patch(
             "course.versioning.GitUpdateForm.is_valid"
     ) as mock_form_valid, mock.patch(
         "course.versioning.run_course_update_command"
     ) as mock_run_update:
         mock_form_valid.return_value = False
         resp = self.post_update_course_content(
             "some_commit_sha", command="update")
         self.assertEqual(resp.status_code, 200)
         self.assertEqual(mock_run_update.call_count, 0)
Example #27
0
 def test_attribute_error2(self):
     dtime = datetime.datetime(2019, 1, 1)
     with mock.patch(
             "django.utils.formats.date_format"
     ) as mock_date_format, mock.patch(
         "django.utils.dateformat.format"
     ) as mock_format:
         mock_date_format.side_effect = date_format_side_effect
         mock_format.side_effect = format_side_effectformat
         result = format_datetime_local(
             dtime, format="foo")
     self.assertEqual(
         result, date_format(dtime, format=get_format("DATETIME_FORMAT")))
Example #28
0
 def test_set_up_new_course_git_source_invalid(self):
     data = self.get_set_up_new_course_form_data()
     request = self.rf.post(self.get_set_up_new_course_url(), data=data)
     request.user = self.instructor
     with mock.patch("dulwich.client.GitClient.fetch",
                     return_value=None), \
             mock.patch("course.models.Course.save") as mock_save, \
             mock.patch("course.versioning.render"):
         resp = versioning.set_up_new_course(request)
         self.assertTrue(resp.status_code, 200)
         self.assertEqual(mock_save.call_count, 0)
         self.assertAddMessageCalledWith(
             "No refs found in remote repository")
Example #29
0
 def test_set_up_new_course_git_source_invalid(self):
     data = self.get_set_up_new_course_form_data()
     request = self.rf.post(self.get_set_up_new_course_url(), data=data)
     request.user = self.instructor
     with mock.patch("dulwich.client.GitClient.fetch",
                     return_value=None), \
             mock.patch("course.models.Course.save") as mock_save, \
             mock.patch("course.versioning.render"):
         resp = versioning.set_up_new_course(request)
         self.assertTrue(resp.status_code, 200)
         self.assertEqual(mock_save.call_count, 0)
         self.assertAddMessageCalledWith(
             "No refs found in remote repository")
Example #30
0
    def verify_result_with_configure(self, my_site_name):
        # home page
        with mock.patch(REAL_TRANSLATION_FUNCTION_TO_MOCK) as mock_gettext:
            mock_gettext.side_effect = real_trans_side_effect
            resp = self.c.get("/")
            self.assertEqual(resp.status_code, 200)
            self.assertContains(resp, "<title>%s</title>" % my_site_name, html=True)

            # Three translations in nav_bar brand, html title and
            # "Welcome to RELATE", respectively
            self.assertEqual(
                self.get_translation_count(mock_gettext, my_site_name), 3)
            mock_gettext.reset_mock()

            # course page
            resp = self.c.get(self.get_course_page_url())
            self.assertEqual(resp.status_code, 200)

            test_site_name_re = re.compile(
                ".+<title>.+-.+%s.+</title>.+" % my_site_name, re.DOTALL)
            self.assertRegex(resp.content.decode(), test_site_name_re)

            # One translation in html title
            self.assertEqual(
                self.get_translation_count(mock_gettext, my_site_name), 1)

        # email
        with override_settings(RELATE_REGISTRATION_ENABLED=True, USE_I18N=True):
            # render() is mocked so as to count string translated in email rendering
            with mock.patch(REAL_TRANSLATION_FUNCTION_TO_MOCK) as mock_gettext,\
                    mock.patch("course.auth._") as mock_ugettext,\
                    mock.patch('course.auth.messages'),\
                    mock.patch('course.auth.render'):
                mock_gettext.return_value = "foo"
                with self.temporarily_switch_to_user(None):
                    resp = self.post_sign_up(
                        data={"username": "******", "email": "*****@*****.**"},
                        follow=False
                    )
                    self.assertTrue(resp.status_code, 200)
                    self.assertEqual(len(mail.outbox), 1)

                    # In the view, tranlating RELATE for email title.
                    self.assertEqual(
                        self.get_translation_count(mock_ugettext, my_site_name), 1)

                    # Three RELATE in the email template
                    self.assertEqual(
                        self.get_translation_count(mock_gettext, my_site_name), 3)
Example #31
0
 def test_update_course_user_not_active(self):
     user = factories.UserFactory(is_active=False)
     factories.ParticipationFactory(course=self.course,
                                    user=user,
                                    status=participation_status.requested)
     factories.ParticipationPreapprovalFactory(course=self.course,
                                               email=user.email)
     with mock.patch(
             "course.models.ParticipationPreapproval.objects.get")\
             as mock_pprvl_get,\
             mock.patch(HANDLE_ENROLLMENT_PATH) as mock_handle_enrollment:
         self.course.listed = not self.course.listed
         self.course.save()
         self.assertEqual(mock_pprvl_get.call_count, 0)
         self.assertEqual(mock_handle_enrollment.call_count, 0)
Example #32
0
    def test_custom_get_full_name_method_failed(self):
        """
        Test when RELATE_USER_FULL_NAME_FORMAT_METHOD failed, default method
        is used.
        """
        user = UserFactory.create(first_name="my_first", last_name="my_last")

        default_get_full_name = user.get_full_name()

        custom_get_full_name_path = (
            "tests.resource.my_customized_get_full_name_method")
        get_custom_full_name_method_path = (
            "accounts.utils.RelateUserMethodSettingsInitializer"
            ".custom_full_name_method")

        with override_settings(
                RELATE_USER_FULL_NAME_FORMAT_METHOD=custom_get_full_name_path):

            from accounts.utils import relate_user_method_settings
            # clear cached value
            relate_user_method_settings.__dict__ = {}

            # If custom method works, the returned value is different with
            # default value.
            self.assertNotEqual(default_get_full_name, user.get_full_name())

            with mock.patch(get_custom_full_name_method_path) as mock_custom_method:
                # clear cached value
                relate_user_method_settings.__dict__ = {}

                # raise an error when calling custom method
                mock_custom_method.side_effect = Exception()

                # the value falls back to default value
                self.assertEqual(user.get_full_name(), default_get_full_name)
Example #33
0
    def test_feedback_notify_with_grader_feedback_connection(self):
        grade_data_extra_kwargs = {
            "feedback_text": 'test feedback',
            "notify": "on"
        }

        from django.core.mail import get_connection
        connection = get_connection(
            backend='django.core.mail.backends.locmem.EmailBackend')

        with mock.patch(
                "django.core.mail.get_connection") as mock_get_connection:
            mock_get_connection.return_value = connection
            self.submit_page_human_grading_by_page_id_and_test(
                self.page_id, grade_data_extra_kwargs=grade_data_extra_kwargs)
            self.assertEqual(len(mail.outbox), 1)
            self.assertEqual(mail.outbox[0].from_email,
                             "*****@*****.**")
            self.assertEqual(mock_get_connection.call_args[1]["backend"],
                             "tests.resource.MyFakeEmailBackend")

        # make sure the name (appellation) is in the email body, not the masked one
        self.assertIn(self.student_participation.user.get_email_appellation(),
                      mail.outbox[0].body)
        self.assertNotIn(self.student_participation.user.get_masked_profile(),
                         mail.outbox[0].body)
        self.assertNotIn("Dear user", mail.outbox[0].body)
Example #34
0
    def test_choice_not_stringifiable(self):
        expected_page_error = (
            "choice 10: unable to convert to string")

        class BadChoice(object):
            def __str__(self):
                raise Exception

        from relate.utils import dict_to_struct
        fake_page_desc = dict_to_struct(
            {'type': 'SurveyChoiceQuestion', 'id': 'age_group_with_comment',
             'answer_comment': 'this is a survey question',
             'prompt': '\n# Age\n\nHow old are you?\n',
             'choices': [
                 '0-10 years', '11-20 years', '21-30 years', '31-40 years',
                 '41-50 years', '51-60 years', '61-70 years', '71-80 years',
                 '81-90 years', BadChoice()],
             '_field_names': ['type', 'id', 'answer_comment',
                              'prompt', 'choices']}
        )

        with mock.patch("relate.utils.dict_to_struct") as mock_dict_to_struct:
            mock_dict_to_struct.return_value = fake_page_desc

            markdown = SURVEY_CHOICE_QUESTION_MARKDOWN

            resp = (
                self.get_page_sandbox_preview_response(markdown))
            self.assertEqual(resp.status_code, 200)
            self.assertSandboxNotHasValidPage(resp)
            self.assertResponseContextContains(resp, PAGE_ERRORS,
                                               expected_page_error)
Example #35
0
    def test_finish_in_progress_sessions_past_due_only_dued(self):
        # now_datetime > grading_rule.due
        fake_grading_rule = self.get_hacked_session_grading_rule(
            due=now() + timedelta(days=1))
        with mock.patch("course.flow.get_session_grading_rule") as \
                mock_get_grading_rule:
            mock_get_grading_rule.return_value = fake_grading_rule
            finish_in_progress_sessions(self.gopp.course_id,
                                        self.gopp.flow_id,
                                        rule_tag=None,
                                        now_datetime=now() + timedelta(days=3),
                                        past_due_only=True)

        self.assertEqual(
            models.FlowSession.objects.filter(in_progress=True).count(), 0)

        self.assertEqual(
            models.FlowSession.objects.filter(in_progress=False).count(),
            self.all_sessions_count)

        self.assertEqual(
            models.FlowPageVisitGrade.objects.filter(
                visit__flow_session__in=self.ended_sessions).count(), 0)

        for ended_session in self.in_progress_sessions:
            self.assertTrue(
                models.FlowPageVisitGrade.objects.filter(
                    visit__flow_session=ended_session).count() > 0)

        self.assertEqual(self.mock_update_state.call_count,
                         self.in_progress_sessions_count)
Example #36
0
    def test_finish_in_progress_sessions_past_due_only_dued(self):
        # now_datetime > grading_rule.due
        fake_grading_rule = self.get_hacked_session_grading_rule(
            due=now() + timedelta(days=1))
        with mock.patch("course.flow.get_session_grading_rule") as \
                mock_get_grading_rule:
            mock_get_grading_rule.return_value = fake_grading_rule
            finish_in_progress_sessions(
                self.gopp.course_id, self.gopp.flow_id,
                rule_tag=None, now_datetime=now()+timedelta(days=3),
                past_due_only=True)

        self.assertEqual(
            models.FlowSession.objects.filter(in_progress=True).count(),
            0)

        self.assertEqual(
            models.FlowSession.objects.filter(in_progress=False).count(),
            self.all_sessions_count)

        self.assertEqual(
            models.FlowPageVisitGrade.objects.filter(
                visit__flow_session__in=self.ended_sessions).count(),
            0)

        for ended_session in self.in_progress_sessions:
            self.assertTrue(
                models.FlowPageVisitGrade.objects.filter(
                    visit__flow_session=ended_session).count() > 0)

        self.assertEqual(
            self.mock_update_state.call_count, self.in_progress_sessions_count)
Example #37
0
 def test_markup_to_html_plain_wrapp_by_p_tag(self):
     with mock.patch("course.page.choice.markup_to_html") as mock_mth:
         mock_mth.side_effect = lambda x, y: "<p>%s</p>" % y
         fake_page_context = object
         self.assertEqual(markup_to_html_plain(fake_page_context, "abcd"),
                          "abcd")
         self.assertEqual(markup_to_html_plain(fake_page_context, ""), "")
Example #38
0
 def test_no_pperm(self):
     with mock.patch(
             "course.utils.CoursePageContext.has_permission"
     ) as mock_has_pperm:
         mock_has_pperm.return_value = False
         resp = self.get_course_calendar_view()
         self.assertEqual(resp.status_code, 403)
Example #39
0
 def test_attribute_error1(self):
     dtime = datetime.datetime(2019, 1, 1)
     with mock.patch(
             "django.utils.formats.date_format") as mock_date_format:
         mock_date_format.side_effect = date_format_side_effect
         result = format_datetime_local(dtime, format="foo")
     self.assertEqual(result, date_format(dtime, format="foo"))
Example #40
0
    def test_post_form_not_valid(self):
        with mock.patch(
                "course.calendar.RenumberEventsForm.is_valid"
        ) as mock_form_valid:
            mock_form_valid.return_value = False

            resp = self.post_renumber_events_view(
                data=self.get_post_renumber_evt_data(starting_ordinal=3))
            self.assertEqual(resp.status_code, 200)

        all_default_evts = Event.objects.filter(kind=self.default_event_kind)
        self.assertEqual(all_default_evts.count(), 5)
        self.assertListEqual(
            list(all_default_evts.values_list("ordinal", flat=True)),
            [1, 3, 5, 7, 9])

        t = None
        for evt in all_default_evts:
            if t is None:
                t = evt.time
                continue
            else:
                self.assertEqual(evt.time - t, datetime.timedelta(weeks=1))
                t = evt.time

        # other events also not affected
        self.evt_another_kind1.refresh_from_db()
        self.evt_another_kind2.refresh_from_db()
        self.assertEqual(
            self.evt_another_kind1.ordinal, self.evt_another_kind1_ordinal)
        self.assertEqual(
            self.evt_another_kind2.ordinal, self.evt_another_kind2_ordinal)
Example #41
0
 def test_no_pperm(self):
     with mock.patch(
             "course.utils.CoursePageContext.has_permission"
     ) as mock_has_pperm:
         mock_has_pperm.return_value = False
         resp = self.get_course_calendar_view()
         self.assertEqual(resp.status_code, 403)
Example #42
0
 def test_form_invalid(self):
     with mock.patch(
             "course.exam.ExamCheckInForm.is_valid") as mock_is_valid:
         mock_is_valid.return_value = False
         resp = self.post_check_in_for_exam_view(data=self.get_post_data())
         self.assertEqual(resp.status_code, 200)
     self.assertEqual(self.ticket.state, constants.exam_ticket_states.valid)
Example #43
0
 def setUp(self):
     self.requset = mock.MagicMock()
     self.requset.relate_facilities = ["fa1", "fa2"]
     fake_get_facilities_config = mock.patch(
         "course.utils.get_facilities_config")
     self.mock_get_facilities_config = fake_get_facilities_config.start()
     self.addCleanup(fake_get_facilities_config.stop)
Example #44
0
    def test_update_course_no_requested(self):
        with mock.patch(HANDLE_ENROLLMENT_PATH) as mock_handle_enrollment:
            mock_handle_enrollment.return_value = None
            self.course.listed = not self.course.listed
            self.course.save()

            self.assertEqual(mock_handle_enrollment.call_count, 0)
Example #45
0
 def test_form_invalid(self):
     with mock.patch("course.exam.BatchIssueTicketsForm.is_valid"
                     ) as mock_is_valid:
         mock_is_valid.return_value = False
         resp = self.post_batch_issue_exam_ticket_view(data=self.get_post_data())
         self.assertEqual(resp.status_code, 200)
         self.assertEqual(ExamTicket.objects.count(), 0)
Example #46
0
    def test_post_form_not_valid(self):
        with mock.patch(
                "course.calendar.RenumberEventsForm.is_valid"
        ) as mock_form_valid:
            mock_form_valid.return_value = False

            resp = self.post_renumber_events_view(
                data=self.get_post_renumber_evt_data(starting_ordinal=3))
            self.assertEqual(resp.status_code, 200)

        all_default_evts = Event.objects.filter(kind=self.default_event_kind)
        self.assertEqual(all_default_evts.count(), 5)
        self.assertListEqual(
            list(all_default_evts.values_list("ordinal", flat=True)),
            [1, 3, 5, 7, 9])

        t = None
        for evt in all_default_evts:
            if t is None:
                t = evt.time
                continue
            else:
                self.assertEqual(evt.time - t, datetime.timedelta(weeks=1))
                t = evt.time

        # other events also not affected
        self.evt_another_kind1.refresh_from_db()
        self.evt_another_kind2.refresh_from_db()
        self.assertEqual(
            self.evt_another_kind1.ordinal, self.evt_another_kind1_ordinal)
        self.assertEqual(
            self.evt_another_kind2.ordinal, self.evt_another_kind2_ordinal)
Example #47
0
 def setUp(self):
     self.requset = mock.MagicMock()
     self.requset.relate_facilities = ["fa1", "fa2"]
     fake_get_facilities_config = mock.patch(
         "course.utils.get_facilities_config")
     self.mock_get_facilities_config = fake_get_facilities_config.start()
     self.addCleanup(fake_get_facilities_config.stop)
Example #48
0
    def test_expire_in_progress_sessions_past_due_only_not_dued(self):
        # now_datetime <= grading_rule.due
        fake_grading_rule = self.get_hacked_session_grading_rule(
            due=now() + timedelta(days=1))
        with mock.patch("course.flow.get_session_grading_rule") as \
                mock_get_grading_rule:
            mock_get_grading_rule.return_value = fake_grading_rule

            expire_in_progress_sessions(
                self.gopp.course.id, self.gopp.flow_id,
                rule_tag=None, now_datetime=now(),
                past_due_only=True)

        self.assertEqual(
            models.FlowSession.objects.filter(in_progress=True).count(),
            self.in_progress_sessions_count)

        self.assertEqual(
            models.FlowSession.objects.filter(in_progress=False).count(),
            self.ended_sessions_count)

        self.assertEqual(self.mock_update_state.call_count,
                         self.in_progress_sessions_count)

        self.assertEqual(
            self.mock_update_state.call_count, self.in_progress_sessions_count)
Example #49
0
 def test_form_invalid(self):
     with mock.patch("course.exam.ExamCheckInForm.is_valid"
                     ) as mock_is_valid:
         mock_is_valid.return_value = False
         resp = self.post_check_in_for_exam_view(data=self.get_post_data())
         self.assertEqual(resp.status_code, 200)
     self.assertEqual(self.ticket.state, constants.exam_ticket_states.valid)
Example #50
0
    def test_regrade_with_access_rules_tag(self):
        with mock.patch("course.flow.regrade_session") as mock_regrade:
            regrade_flow_sessions(self.gopp.course_id,
                                  self.gopp.flow_id,
                                  access_rules_tag="None exist tag",
                                  inprog_value=None
                                  )

            mock_regrade.return_value = None

            # no regrade happened
            self.assertEqual(mock_regrade.call_count, 0)

            first_session = models.FlowSession.objects.first()
            first_session.access_rules_tag = "some tag"
            first_session.save()

            regrade_flow_sessions(self.gopp.course_id,
                                  self.gopp.flow_id,
                                  access_rules_tag="some tag",
                                  inprog_value=None
                                  )

            self.assertEqual(mock_regrade.call_count, 1)
            self.assertIn(first_session, mock_regrade.call_args[0])

            self.assertEqual(self.mock_update_state.call_count, 1)
Example #51
0
 def test_symbolic_expression_matcher_validation_error(self):
     with mock.patch("pymbolic.parse") as mock_pymbolic_parse:
         expected_error_msg = "some error"
         mock_pymbolic_parse.side_effect = ValueError(expected_error_msg)
         with self.assertRaises(ValidationError) as cm:
             SymbolicExpressionMatcher(None, "", "abcd")
         self.assertIn(expected_error_msg, str(cm.exception))
Example #52
0
    def test_expire_in_progress_sessions_past_due_only_not_dued(self):
        # now_datetime <= grading_rule.due
        fake_grading_rule = self.get_hacked_session_grading_rule(
            due=now() + timedelta(days=1))
        with mock.patch("course.flow.get_session_grading_rule") as \
                mock_get_grading_rule:
            mock_get_grading_rule.return_value = fake_grading_rule

            expire_in_progress_sessions(self.gopp.course.id,
                                        self.gopp.flow_id,
                                        rule_tag=None,
                                        now_datetime=now(),
                                        past_due_only=True)

        self.assertEqual(
            models.FlowSession.objects.filter(in_progress=True).count(),
            self.in_progress_sessions_count)

        self.assertEqual(
            models.FlowSession.objects.filter(in_progress=False).count(),
            self.ended_sessions_count)

        self.assertEqual(self.mock_update_state.call_count,
                         self.in_progress_sessions_count)

        self.assertEqual(self.mock_update_state.call_count,
                         self.in_progress_sessions_count)
Example #53
0
    def test_notes_and_notify_with_grader_feedback_connection(self):
        grade_data_extra_kwargs = {
            "notes": 'test notes',
            "notify_instructor": "on"
        }

        from django.core.mail import get_connection
        connection = get_connection(
            backend='django.core.mail.backends.locmem.EmailBackend')

        with mock.patch("django.core.mail.get_connection") as mock_get_connection:
            mock_get_connection.return_value = connection
            with self.temporarily_switch_to_user(self.ta_participation.user):
                self.submit_page_human_grading_by_page_id_and_test(
                    self.page_id, grade_data_extra_kwargs=grade_data_extra_kwargs,
                    force_login_instructor=False)

            self.assertEqual(len(mail.outbox), 1)

        self.assertIn(self.course.notify_email, mail.outbox[0].recipients())
        self.assertEqual(mail.outbox[0].from_email,
                         "*****@*****.**")
        self.assertEqual(
            mock_get_connection.call_args[1]["backend"],
            "tests.resource.MyFakeEmailBackend"
        )

        # make sure the name (appellation) is in the email body, not the masked one
        self.assertIn(
            self.student_participation.user.get_email_appellation(),
            mail.outbox[0].body)
        self.assertNotIn(
            self.student_participation.user.get_masked_profile(),
            mail.outbox[0].body)
Example #54
0
    def test_regrade_with_access_rules_tag(self):
        with mock.patch("course.flow.regrade_session") as mock_regrade:
            regrade_flow_sessions(self.gopp.course_id,
                                  self.gopp.flow_id,
                                  access_rules_tag="None exist tag",
                                  inprog_value=None)

            mock_regrade.return_value = None

            # no regrade happened
            self.assertEqual(mock_regrade.call_count, 0)

            first_session = models.FlowSession.objects.first()
            first_session.access_rules_tag = "some tag"
            first_session.save()

            regrade_flow_sessions(self.gopp.course_id,
                                  self.gopp.flow_id,
                                  access_rules_tag="some tag",
                                  inprog_value=None)

            self.assertEqual(mock_regrade.call_count, 1)
            self.assertIn(first_session, mock_regrade.call_args[0])

            self.assertEqual(self.mock_update_state.call_count, 1)
Example #55
0
    def test_feedback_notify_with_grader_feedback_connection(self):
        grade_data_extra_kwargs = {
            "feedback_text": 'test feedback',
            "notify": "on"
        }

        from django.core.mail import get_connection
        connection = get_connection(
            backend='django.core.mail.backends.locmem.EmailBackend')

        with mock.patch("django.core.mail.get_connection") as mock_get_connection:
            mock_get_connection.return_value = connection
            self.submit_page_human_grading_by_page_id_and_test(
                self.page_id, grade_data_extra_kwargs=grade_data_extra_kwargs)
            self.assertEqual(len(mail.outbox), 1)
            self.assertEqual(mail.outbox[0].from_email,
                             "*****@*****.**")
            self.assertEqual(
                mock_get_connection.call_args[1]["backend"],
                "tests.resource.MyFakeEmailBackend"
            )

        # make sure the name (appellation) is in the email body, not the masked one
        self.assertIn(
            self.student_participation.user.get_email_appellation(),
            mail.outbox[0].body)
        self.assertNotIn(
            self.student_participation.user.get_masked_profile(),
            mail.outbox[0].body)
        self.assertNotIn(
            "Dear user",
            mail.outbox[0].body)
Example #56
0
 def test_markup_to_html_plain_wrapp_by_p_other_tag(self):
     with mock.patch("course.page.choice.markup_to_html") as mock_mth:
         mock_mth.side_effect = lambda x, y: "<div>%s</div>" % y
         fake_page_context = object
         self.assertEqual(
             markup_to_html_plain(fake_page_context, "abcd"),
             "<div>abcd</div>")
Example #57
0
 def test_symbolic_expression_matcher_validation_error(self):
     with mock.patch("pymbolic.parse") as mock_pymbolic_parse:
         expected_error_msg = "some error"
         mock_pymbolic_parse.side_effect = ValueError(expected_error_msg)
         with self.assertRaises(ValidationError) as cm:
             SymbolicExpressionMatcher(None, "", "abcd")
         self.assertIn(expected_error_msg, str(cm.exception))
Example #58
0
    def test_notes_and_notify_with_grader_feedback_connection(self):
        grade_data_extra_kwargs = {
            "notes": 'test notes',
            "notify_instructor": "on"
        }

        from django.core.mail import get_connection
        connection = get_connection(
            backend='django.core.mail.backends.locmem.EmailBackend')

        with mock.patch(
                "django.core.mail.get_connection") as mock_get_connection:
            mock_get_connection.return_value = connection
            with self.temporarily_switch_to_user(self.ta_participation.user):
                self.submit_page_human_grading_by_page_id_and_test(
                    self.page_id,
                    grade_data_extra_kwargs=grade_data_extra_kwargs,
                    force_login_instructor=False)

            self.assertEqual(len(mail.outbox), 1)

        self.assertIn(self.course.notify_email, mail.outbox[0].recipients())
        self.assertEqual(mail.outbox[0].from_email,
                         "*****@*****.**")
        self.assertEqual(mock_get_connection.call_args[1]["backend"],
                         "tests.resource.MyFakeEmailBackend")

        # make sure the name (appellation) is in the email body, not the masked one
        self.assertIn(self.student_participation.user.get_email_appellation(),
                      mail.outbox[0].body)
        self.assertNotIn(self.student_participation.user.get_masked_profile(),
                         mail.outbox[0].body)
Example #59
0
 def test_invalid_path(self):
     with override_settings(RELATE_OVERRIDE_TEMPLATES_DIRS=self.INVALID_CONF3):
         with mock.patch("relate.checks.os.path.isdir",
                         side_effect=is_dir_side_effect):
             self.assertCheckMessages(
                 ["relate_override_templates_dirs.W001",
                  "relate_override_templates_dirs.W001"])