2 // This file is part of Moodle - http://moodle.org/
4 // Moodle is free software: you can redistribute it and/or modify
5 // it under the terms of the GNU General Public License as published by
6 // the Free Software Foundation, either version 3 of the License, or
7 // (at your option) any later version.
9 // Moodle is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 // GNU General Public License for more details.
14 // You should have received a copy of the GNU General Public License
15 // along with Moodle. If not, see <http://www.gnu.org/licenses/>.
18 * This file contains tests that walks a question through the manual graded
22 * @subpackage manualgraded
23 * @copyright 2009 The Open University
24 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
28 defined('MOODLE_INTERNAL') || die();
31 require_once(dirname(__FILE__) . '/../../../engine/lib.php');
32 require_once(dirname(__FILE__) . '/../../../engine/tests/helpers.php');
36 * Unit tests for the manual graded behaviour.
38 * @copyright 2009 The Open University
39 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
41 class qbehaviour_manualgraded_walkthrough_testcase extends qbehaviour_walkthrough_test_base {
42 public function test_manual_graded_essay() {
44 $this->setAdminUser();
46 // Create an essay question.
47 $essay = test_question_maker::make_an_essay_question();
48 $this->start_attempt_at_question($essay, 'deferredfeedback', 10);
50 // Check the right model is being used.
51 $this->assertEquals('manualgraded', $this->quba->get_question_attempt(
52 $this->slot)->get_behaviour_name());
54 // Check the initial state.
55 $this->check_current_state(question_state::$todo);
56 $this->check_current_mark(null);
57 $this->check_current_output($this->get_contains_question_text_expectation($essay),
58 $this->get_does_not_contain_feedback_expectation());
60 // Simulate some data submitted by the student.
61 $this->process_submission(array('answer' => 'This is my wonderful essay!', 'answerformat' => FORMAT_HTML));
64 $this->check_current_state(question_state::$complete);
65 $this->check_current_mark(null);
66 $this->check_current_output(
67 new question_contains_tag_with_attribute('textarea', 'name',
68 $this->quba->get_question_attempt($this->slot)->get_qt_field_name('answer')),
69 $this->get_does_not_contain_feedback_expectation());
71 // Process the same data again, check it does not create a new step.
72 $numsteps = $this->get_step_count();
73 $this->process_submission(array('answer' => 'This is my wonderful essay!', 'answerformat' => FORMAT_HTML));
74 $this->check_step_count($numsteps);
76 // Process different data, check it creates a new step.
77 $this->process_submission(array('answer' => '', 'answerformat' => FORMAT_HTML));
78 $this->check_step_count($numsteps + 1);
79 $this->check_current_state(question_state::$todo);
81 // Change back, check it creates a new step.
82 $this->process_submission(array('answer' => 'This is my wonderful essay!', 'answerformat' => FORMAT_HTML));
83 $this->check_step_count($numsteps + 2);
85 // Finish the attempt.
86 $this->quba->finish_all_questions();
89 $this->check_current_state(question_state::$needsgrading);
90 $this->check_current_mark(null);
91 $this->assertEquals('This is my wonderful essay!',
92 $this->quba->get_response_summary($this->slot));
94 // Process a manual comment.
95 $this->manual_grade('Not good enough!', 10, FORMAT_HTML);
98 $this->check_current_state(question_state::$mangrright);
99 $this->check_current_mark(10);
100 $this->check_current_output(
101 new question_pattern_expectation('/' . preg_quote('Not good enough!', '/') . '/'));
103 // Now change the max mark for the question and regrade.
104 $this->quba->regrade_question($this->slot, true, 1);
107 $this->check_current_state(question_state::$mangrright);
108 $this->check_current_mark(1);
111 public function test_manual_graded_essay_not_answered() {
113 $this->setAdminUser();
115 // Create an essay question.
116 $essay = test_question_maker::make_an_essay_question();
117 $this->start_attempt_at_question($essay, 'deferredfeedback', 10);
119 // Check the right model is being used.
120 $this->assertEquals('manualgraded', $this->quba->get_question_attempt(
121 $this->slot)->get_behaviour_name());
123 // Check the initial state.
124 $this->check_current_state(question_state::$todo);
125 $this->check_current_mark(null);
126 $this->check_current_output($this->get_contains_question_text_expectation($essay),
127 $this->get_does_not_contain_feedback_expectation());
129 // Finish the attempt.
130 $this->quba->finish_all_questions();
133 $this->check_current_state(question_state::$gaveup);
134 $this->check_current_mark(null);
135 $this->assertEquals('',
136 $this->quba->get_response_summary($this->slot));
138 // Process a manual comment.
139 $this->manual_grade('Not good enough!', 1, FORMAT_HTML);
142 $this->check_current_state(question_state::$mangrpartial);
143 $this->check_current_mark(1);
144 $this->check_current_output(
145 new question_pattern_expectation('/' . preg_quote('Not good enough!') . '/'));
147 // Now change the max mark for the question and regrade.
148 $this->quba->regrade_question($this->slot, true, 1);
151 $this->check_current_state(question_state::$mangrpartial);
152 $this->check_current_mark(0.1);
155 public function test_manual_graded_truefalse() {
157 // Create a true-false question with correct answer true.
158 $tf = test_question_maker::make_question('truefalse', 'true');
159 $this->start_attempt_at_question($tf, 'manualgraded', 2);
161 // Check the initial state.
162 $this->check_current_state(question_state::$todo);
163 $this->check_current_mark(null);
164 $this->check_current_output(
165 $this->get_contains_question_text_expectation($tf),
166 $this->get_does_not_contain_feedback_expectation());
168 // Process a true answer and check the expected result.
169 $this->process_submission(array('answer' => 1));
171 $this->check_current_state(question_state::$complete);
172 $this->check_current_mark(null);
173 $this->check_current_output(
174 $this->get_contains_tf_true_radio_expectation(true, true),
175 $this->get_does_not_contain_correctness_expectation(),
176 $this->get_does_not_contain_feedback_expectation());
178 // Finish the attempt.
179 $this->quba->finish_all_questions();
182 $this->check_current_state(question_state::$needsgrading);
183 $this->check_current_mark(null);
184 $this->check_current_output(
185 $this->get_does_not_contain_correctness_expectation(),
186 $this->get_does_not_contain_specific_feedback_expectation());
188 // Process a manual comment.
189 $this->manual_grade('Not good enough!', 1, FORMAT_HTML);
191 $this->check_current_state(question_state::$mangrpartial);
192 $this->check_current_mark(1);
193 $this->check_current_output(
194 $this->get_does_not_contain_correctness_expectation(),
195 $this->get_does_not_contain_specific_feedback_expectation(),
196 new question_pattern_expectation('/' . preg_quote('Not good enough!', '/') . '/'));
199 public function test_manual_graded_ignore_repeat_sumbission() {
200 // Create an essay question.
201 $essay = test_question_maker::make_an_essay_question();
202 $this->start_attempt_at_question($essay, 'deferredfeedback', 10);
204 // Check the right model is being used.
205 $this->assertEquals('manualgraded', $this->quba->get_question_attempt(
206 $this->slot)->get_behaviour_name());
208 // Check the initial state.
209 $this->check_current_state(question_state::$todo);
210 $this->check_current_mark(null);
212 // Simulate some data submitted by the student.
213 $this->process_submission(array('answer' => 'This is my wonderful essay!', 'answerformat' => FORMAT_HTML));
216 $this->check_current_state(question_state::$complete);
217 $this->check_current_mark(null);
219 // Finish the attempt.
220 $this->quba->finish_all_questions();
223 $this->check_current_state(question_state::$needsgrading);
224 $this->check_current_mark(null);
225 $this->assertEquals('This is my wonderful essay!',
226 $this->quba->get_response_summary($this->slot));
228 // Process a blank manual comment. Ensure it does not change the state.
229 $numsteps = $this->get_step_count();
230 $this->manual_grade('', '', FORMAT_HTML);
231 $this->check_step_count($numsteps);
232 $this->check_current_state(question_state::$needsgrading);
233 $this->check_current_mark(null);
235 // Process a comment, but with the mark blank. Should be recorded, but
236 // not change the mark.
237 $this->manual_grade('I am not sure what grade to award.', '', FORMAT_HTML);
238 $this->check_step_count($numsteps + 1);
239 $this->check_current_state(question_state::$needsgrading);
240 $this->check_current_mark(null);
241 $this->check_current_output(
242 new question_pattern_expectation('/' .
243 preg_quote('I am not sure what grade to award.', '/') . '/'));
246 $this->manual_grade('Pretty good!', '9.00000', FORMAT_HTML);
247 $this->check_step_count($numsteps + 2);
248 $this->check_current_state(question_state::$mangrpartial);
249 $this->check_current_mark(9);
250 $this->check_current_output(
251 new question_pattern_expectation('/' . preg_quote('Pretty good!', '/') . '/'));
253 // Process the same data again, and make sure it does not add a step.
254 $this->manual_grade('Pretty good!', '9.00000', FORMAT_HTML);
255 $this->check_step_count($numsteps + 2);
256 $this->check_current_state(question_state::$mangrpartial);
257 $this->check_current_mark(9);
259 // Now set the mark back to blank.
260 $this->manual_grade('Actually, I am not sure any more.', '', FORMAT_HTML);
261 $this->check_step_count($numsteps + 3);
262 $this->check_current_state(question_state::$needsgrading);
263 $this->check_current_mark(null);
264 $this->check_current_output(
265 new question_pattern_expectation('/' .
266 preg_quote('Actually, I am not sure any more.', '/') . '/'));
268 $qa = $this->quba->get_question_attempt($this->slot);
269 $this->assertEquals('Commented: Actually, I am not sure any more.',
270 $qa->summarise_action($qa->get_last_step()));
273 public function test_manual_graded_essay_can_grade_0() {
275 $this->setAdminUser();
277 // Create an essay question.
278 $essay = test_question_maker::make_an_essay_question();
279 $this->start_attempt_at_question($essay, 'deferredfeedback', 10);
281 // Check the right model is being used.
282 $this->assertEquals('manualgraded', $this->quba->get_question_attempt(
283 $this->slot)->get_behaviour_name());
285 // Check the initial state.
286 $this->check_current_state(question_state::$todo);
287 $this->check_current_mark(null);
288 $this->check_current_output($this->get_contains_question_text_expectation($essay),
289 $this->get_does_not_contain_feedback_expectation());
291 // Simulate some data submitted by the student.
292 $this->process_submission(array('answer' => 'This is my wonderful essay!', 'answerformat' => FORMAT_HTML));
295 $this->check_current_state(question_state::$complete);
296 $this->check_current_mark(null);
297 $this->check_current_output(
298 new question_contains_tag_with_attribute('textarea', 'name',
299 $this->quba->get_question_attempt($this->slot)->get_qt_field_name('answer')),
300 $this->get_does_not_contain_feedback_expectation());
302 // Finish the attempt.
303 $this->quba->finish_all_questions();
306 $this->check_current_state(question_state::$needsgrading);
307 $this->check_current_mark(null);
308 $this->assertEquals('This is my wonderful essay!',
309 $this->quba->get_response_summary($this->slot));
311 // Process a blank comment and a grade of 0.
312 $this->manual_grade('', 0, FORMAT_HTML);
315 $this->check_current_state(question_state::$mangrwrong);
316 $this->check_current_mark(0);