def test_scheme_extends_list(self): alpha, digit, max_len = ( AlphaValidator(), DigitValidator(), MaxLengthValidator(10), ) my_scheme = Scheme( validators=[alpha], correct_answers=["SchemeAnswer", "SchemeAnswer2"], commands=[Skip], ) empty_question = Question("What?", scheme=my_scheme) self.assertEqual([alpha], empty_question.validators) self.assertEqual([Skip], empty_question.commands) self.assertEqual( ["SchemeAnswer", "SchemeAnswer2"], empty_question.correct_answers ) question = Question( "What?", validators=[digit, max_len], correct_answers=["RealAnswer"], commands=[Skip], scheme=my_scheme, ) self.assertEqual([digit, max_len, alpha], question.validators) self.assertEqual([Skip, Skip], question.commands) self.assertEqual( ["RealAnswer", "SchemeAnswer", "SchemeAnswer2"], question.correct_answers, )
def test_done_ready_api(self): q1, q2, q3 = ( Question("What?"), Question("What?", required=False), Question("What?"), ) quiz = Quiz(questions=[q1, q2, q3]) self.assertFalse(quiz.is_ready) self.assertFalse(quiz.is_done) q1.answer = q3.answer = "A" self.assertFalse(quiz.is_ready) self.assertFalse(quiz.is_done) quiz.inquiries = 2 self.assertTrue(quiz.is_ready) self.assertFalse(quiz.is_done) q2.answer = "A" self.assertTrue(quiz.is_ready) self.assertTrue(quiz.is_done) q1.answer = None self.assertFalse(quiz.is_ready) self.assertFalse(quiz.is_done)
def test_is_done(self, mock_stdout, *_): q1, q2, q3, q4 = ( Question("What?"), Question("What?"), Question("What?", required=False), Question("What?", required=False), ) q1.pre_ask = q2.pre_ask = ( lambda q: self.assertFalse(q.quiz.is_done) if q.attempt == 1 else self.assertTrue(q.quiz.is_done) ) q3.pre_ask = q4.pre_ask = lambda q: self.assertFalse(q.quiz.is_done) quiz = Quiz(questions=[q1, q2, q3, q4]) quiz.start() mock_stdout.assert_has_calls( [ call( "\nYou now have answered all the required questions on" " this test. You may finish, but There are still some" " optional questions left (3, 4).\n" ), call("\n[Ready, some optional questions left (4).]\n"), call( "\nYou now have answered all the questions on this test." " You may finish or revise your questions if you want.\n" ), call("\n[Completed, waiting for finish command.]\n"), ] )
def test_answers(self, mock_stdout, *_): q1, q2, q3, q4 = ( Question("What?"), Question("How?"), Question("When?", required=False), MultipleChoiceQuestion("Which?", choices=["This"]), ) quiz = Quiz( questions=[q1, q2, q3, q4], scheme=Scheme(commands=[Answers, Finish]), ) quiz.start() mock_stdout.assert_has_calls( [ ANY, call( "\nCurrent answers:\n" "1. What? -> [Me]\n" "2. How? -> [Handsome]\n" "~3. When? -> [No answer]\n" "4. Which? -> [a) This]\n" ), ANY, ] )
def test_quiz_inquiries_get_incremented(self, *_): questions = [Question("What?"), Question("Hello?")] quiz = Quiz(questions=questions) quiz.start() self.assertEqual(4, quiz.inquiries) self.assertEqual(sum(q.attempt for q in questions), quiz.inquiries)
def test_finish_error_on_uncompleted(self, mock_stdout, *_): q1, q2, q3 = ( Question("Hello?"), Question("World?"), Question("Hey?", required=False), ) quiz = Quiz(questions=[q1, q2, q3]) quiz.start() mock_stdout.assert_has_calls( [ call( "There are still some required questions to answer: (1, 2)" ), ANY, ] ) self.assertEqual("Answer", q1.answer) self.assertEqual("Cat", q2.answer) self.assertIsNone(q3.answer) self.assertEqual(2, q1.attempt) self.assertEqual(1, q2.attempt) self.assertEqual(1, q3.attempt)
def test_jump(self, mock_stdout, *_): q1, q2, q3, q4 = ( Question("What?"), MultipleChoiceQuestion("What?", choices=["a"], required=False), MultipleChoiceQuestion("What?", choices=["c"], required=False), Question("What?", required=False), ) quiz = Quiz( questions=[q1, q2, q3, q4], scheme=Scheme(commands=[Jump, Finish]) ) quiz.start() mock_stdout.assert_has_calls( [ call("Jumped to question 4."), call("Jumped to question 1."), call("Jumped to question 4."), call("Jumped to question 1."), ANY, ] ) self.assertEqual(3, q1.attempt) self.assertEqual(1, q2.attempt) self.assertEqual(2, q4.attempt) self.assertEqual(0, q3.attempt) self.assertEqual("Answer", q1.answer)
def test_is_ready(self, mock_stdout, *_): q1, q2, q3, q4 = ( Question("What?"), Question("What?"), Question("What?", required=False), Question("What?", required=False), ) q1.pre_ask = lambda q: self.assertFalse(q.quiz.is_ready) q2.pre_ask = lambda q: self.assertFalse(q.quiz.is_ready) q3.pre_ask = lambda q: self.assertTrue(q.quiz.is_ready) q4.pre_ask = lambda q: self.assertTrue(q.quiz.is_ready) quiz = Quiz(questions=[q1, q2, q3, q4]) quiz.start() mock_stdout.assert_has_calls( [ call( "\nYou now have answered all the required questions on" " this test. You may finish, but There are still some" " optional questions left (3, 4).\n" ), call("\n[Ready, some optional questions left (4).]\n"), ] )
def test_has_answer(self, *_): question = Question("What?") question.ask() self.assertTrue(question.has_answer) optional_question = Question("What?", required=False) optional_question.ask() self.assertFalse(optional_question.has_answer)
def test_quiz_index_corresponds_question_sequence(self, *_): question = Question("What?") question1 = Question("Hello?") question.pre_ask = question1.pre_ask = lambda q: self.assertEqual( q.sequence, q.quiz.index ) quiz = Quiz(questions=[question, question1]) quiz.start()
def test_update_scheme_force(self): my_scheme = Scheme(commands=[Skip]) a, b = Question("a"), Question("b", scheme=my_scheme) quiz = Quiz(questions=[a], scheme=my_scheme) quiz.questions.append(b) quiz.update(force_scheme=True) self.assertEqual([my_scheme, my_scheme], b.mounted_schemes)
def test_start(self, *_): q = Question("Hello?", required=False) q1 = Question("Hello?", required=False) quiz = Quiz(questions=[q, q1]) quiz.start() self.assertEqual(1, quiz.inquiries) self.assertEqual(1, q.attempt) self.assertEqual(0, q1.attempt)
def test_required_questions_and_min_inquiries(self): q = Question("Hello?") q1 = Question("Hello?", required=False) q2 = Question("Hello?") q3 = Question("Hello?") q4 = Question("Hello?", required=False) quiz = Quiz(questions=[q, q1, q2, q3, q4]) self.assertEqual([q, q2, q3], quiz.required_questions) self.assertEqual(3, quiz.min_inquiries)
def test_update_scheme_do_not_force(self): # Same scheme is not applied twice if force_scheme=False my_scheme = Scheme(commands=[Skip]) a, b = Question("a"), Question("b", scheme=my_scheme) quiz = Quiz(questions=[a], scheme=my_scheme) quiz.questions.append(b) quiz.update() self.assertEqual([my_scheme], b.mounted_schemes)
def test_empty_scheme_has_no_effect(self): from quizz import _field_names # noqa empty = Scheme() question = Question("What?", scheme=empty) question_no_scheme = Question("What?") for name in _field_names: if hasattr(question_no_scheme, name): self.assertEqual( getattr(question_no_scheme, name), getattr(question, name) )
def test_strip(self, *_): question = Question("What?") self.assertTrue(question.get_strip()) question_no_strip = Question("What? 2", strip=False) self.assertFalse(question_no_strip.get_strip()) question.ask() question_no_strip.ask() self.assertEqual("spaced", question.answer) self.assertEqual(" spaced ", question_no_strip.answer)
def test_scheme_extends_dict(self): my_scheme = Scheme(extra={"foo": "bar", "baz": "qux"}) question = Question("What?", scheme=my_scheme) question_with_extra = Question( "What?", extra={"hello": 5}, scheme=my_scheme ) self.assertEqual({"foo": "bar", "baz": "qux"}, question.extra) self.assertEqual( {"hello": 5, "foo": "bar", "baz": "qux"}, question_with_extra.extra, )
def test_question_prompt_changes_with_quiz(self): question = Question("What?") question2 = Question("Hello?") Quiz(questions=[question, question2]) self.assertEqual( "* Question 1/2. [No answer]\nWhat?", question.get_prompt() ) question.update_scheme(Scheme(suffix="Suf", prefix="Pre")) self.assertEqual( "* Question 1/2. [No answer]\nPreWhat?Suf", question.get_prompt() )
def test_suffix(self, mock_stdin): question = Question("What?") question_with_suffix = Question("What?", suffix="test") self.assertEqual("", question.get_suffix()) self.assertEqual("test", question_with_suffix.get_suffix()) self.assertEqual("What?", question.get_prompt()) self.assertEqual("What?test", question_with_suffix.get_prompt()) question.ask() mock_stdin.assert_called_with("What?") question_with_suffix.ask() mock_stdin.assert_called_with("What?test")
def test_update_manually(self): a, b = Question("A"), Question("B") quiz = Quiz(questions=[a]) quiz.questions.append(b) self.assertIsNone(b.quiz) self.assertEqual([a, b], quiz.required_questions) self.assertEqual(0, b.sequence) b.quiz = quiz # Manual assignment, instead of quiz.update() self.assertEqual(quiz, b.quiz) self.assertEqual(1, b.sequence) self.assertEqual([], b.mounted_schemes)
def test_quit(self, *_): question = Question("What", commands=[Quit]) with self.assertRaises(SystemExit) as cm: question.ask() self.assertEqual(0, cm.exception.code)
def test_next_previous(self, *_): q1, q2, q3 = ( Question("What?"), Question("What? 2"), Question("What? 3"), ) quiz = Quiz( questions=[q1, q2, q3], scheme=Scheme(commands=[Next, Previous, Finish], required=False), ) quiz.start() self.assertEqual(17, q1.attempt) self.assertEqual(16, q2.attempt) self.assertEqual(0, q3.attempt)
def test_finish(self, *_): question = Question("Hello?", required=False) quiz = Quiz(questions=[question]) quiz.start() self.assertIsNone(question.answer) self.assertEqual(1, question.attempt)
def test_default_instance_attribute_values(self): question = Question("What?") self.assertEqual("What?", question.prompt) self.assertIsNone(question.answer) self.assertIsNone(question.quiz) self.assertEqual(0, question.sequence) self.assertEqual(0, question.attempt) self.assertEqual([], question.validators) self.assertEqual([], question.options) self.assertEqual([], question.commands) self.assertEqual([], question.correct_answers) self.assertEqual({}, question.extra) self.assertTrue(question.required) self.assertTrue(question.strip) self.assertEqual("", question.suffix) self.assertEqual("", question.prefix) self.assertEqual("!", question.command_delimiter) self.assertEqual(") ", question.option_indicator) self.assertIsNone(question.scheme)
def test_command_strips(self, mock_stdout, *_): # Also tests: get_commands question = Question("What?", commands=[Help]) question.ask() mock_stdout.assert_called_with("Command not found: hello") self.assertEqual([Help], question.get_commands())
def test_help_no_command_list(self, mock_stdout, *_): question = Question( "What?", commands=[Help(message="Howdy?", with_command_list=False)] ) question.ask() mock_stdout.assert_called_with("Howdy?") self.assertEqual("Answer", question.answer)
def test_prefix(self, mock_stdin): question_with_prefix = Question("What?", prefix="test2") self.assertEqual("test2", question_with_prefix.get_prefix()) self.assertEqual("test2What?", question_with_prefix.get_prompt()) question_with_prefix.ask() mock_stdin.assert_called_with("test2What?")
def test_help_base(self, mock_stdout, *_): question = Question("What?", commands=[Help], required=False) question.ask() mock_stdout.assert_called_with( "\nAvailable commands are:\n!help: Shows the help message.\n" ) self.assertEqual("Answer", question.answer)
def test_update(self): a, b = Question("a"), Question("b") quiz = Quiz(questions=[a]) quiz.questions.append(b) self.assertIsNone(b.quiz) self.assertEqual([a, b], quiz.required_questions) self.assertEqual(0, b.sequence) quiz.update() self.assertEqual(quiz, b.quiz) self.assertEqual(1, b.sequence) # update() should add Quiz's scheme. (default scheme, in this case) self.assertEqual([Scheme(commands=[Finish])], b.mounted_schemes)
def test_command_no_context(self, mock_stdout, *_): question = Question("What?", required=False) question.ask() mock_stdout.assert_called_with( "Commands are disabled for this question." ) self.assertEqual("Answer", question.answer)