| Línea 84... |
Línea 84... |
| 84 |
* @copyright 2016 Juan Leyva <juan@moodle.com>
|
84 |
* @copyright 2016 Juan Leyva <juan@moodle.com>
|
| 85 |
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
85 |
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
|
| 86 |
* @since Moodle 3.1
|
86 |
* @since Moodle 3.1
|
| 87 |
* @covers \mod_quiz_external
|
87 |
* @covers \mod_quiz_external
|
| 88 |
*/
|
88 |
*/
|
| 89 |
class external_test extends externallib_advanced_testcase {
|
89 |
final class external_test extends externallib_advanced_testcase {
|
| Línea 90... |
Línea 90... |
| 90 |
|
90 |
|
| Línea 91... |
Línea 91... |
| 91 |
use \quiz_question_helper_test_trait;
|
91 |
use \quiz_question_helper_test_trait;
|
| 92 |
|
92 |
|
| Línea 117... |
Línea 117... |
| 117 |
/**
|
117 |
/**
|
| 118 |
* Set up for every test
|
118 |
* Set up for every test
|
| 119 |
*/
|
119 |
*/
|
| 120 |
public function setUp(): void {
|
120 |
public function setUp(): void {
|
| 121 |
global $DB;
|
121 |
global $DB;
|
| - |
|
122 |
parent::setUp();
|
| 122 |
$this->resetAfterTest();
|
123 |
$this->resetAfterTest();
|
| 123 |
$this->setAdminUser();
|
124 |
$this->setAdminUser();
|
| Línea 124... |
Línea 125... |
| 124 |
|
125 |
|
| 125 |
// Setup test data.
|
126 |
// Setup test data.
|
| Línea 203... |
Línea 204... |
| 203 |
// Process some responses from the student.
|
204 |
// Process some responses from the student.
|
| 204 |
$tosubmit = [1 => ['answer' => '3.14']];
|
205 |
$tosubmit = [1 => ['answer' => '3.14']];
|
| 205 |
$attemptobj->process_submitted_actions(time(), false, $tosubmit);
|
206 |
$attemptobj->process_submitted_actions(time(), false, $tosubmit);
|
| Línea 206... |
Línea 207... |
| 206 |
|
207 |
|
| 207 |
// Finish the attempt.
|
208 |
// Finish the attempt.
|
| - |
|
209 |
$attemptobj->process_submit(time(), false);
|
| 208 |
$attemptobj->process_finish(time(), false);
|
210 |
$attemptobj->process_grade_submission(time());
|
| 209 |
}
|
211 |
}
|
| 210 |
return [$quiz, $context, $quizobj, $attempt, $attemptobj, $quba];
|
212 |
return [$quiz, $context, $quizobj, $attempt, $attemptobj, $quba];
|
| 211 |
} else {
|
213 |
} else {
|
| 212 |
return [$quiz, $context, $quizobj];
|
214 |
return [$quiz, $context, $quizobj];
|
| Línea 225... |
Línea 227... |
| 225 |
|
227 |
|
| 226 |
// Second quiz.
|
228 |
// Second quiz.
|
| 227 |
$record = new \stdClass();
|
229 |
$record = new \stdClass();
|
| 228 |
$record->course = $course2->id;
|
230 |
$record->course = $course2->id;
|
| - |
|
231 |
$record->intro = '<button>Test with HTML allowed.</button>';
|
| - |
|
232 |
$timeopen = time() - 1;
|
| - |
|
233 |
$record->timeopen = $timeopen;
|
| 229 |
$record->intro = '<button>Test with HTML allowed.</button>';
|
234 |
$record->precreateattempts = 1;
|
| Línea 230... |
Línea 235... |
| 230 |
$quiz2 = self::getDataGenerator()->create_module('quiz', $record);
|
235 |
$quiz2 = self::getDataGenerator()->create_module('quiz', $record);
|
| 231 |
|
236 |
|
| 232 |
// Execute real Moodle enrolment as we'll call unenrol() method on the instance later.
|
237 |
// Execute real Moodle enrolment as we'll call unenrol() method on the instance later.
|
| Línea 254... |
Línea 259... |
| 254 |
'reviewspecificfeedback', 'reviewgeneralfeedback', 'reviewrightanswer',
|
259 |
'reviewspecificfeedback', 'reviewgeneralfeedback', 'reviewrightanswer',
|
| 255 |
'reviewoverallfeedback', 'questionsperpage', 'navmethod',
|
260 |
'reviewoverallfeedback', 'questionsperpage', 'navmethod',
|
| 256 |
'browsersecurity', 'delay1', 'delay2', 'showuserpicture', 'showblocks',
|
261 |
'browsersecurity', 'delay1', 'delay2', 'showuserpicture', 'showblocks',
|
| 257 |
'completionattemptsexhausted', 'completionpass', 'autosaveperiod', 'hasquestions',
|
262 |
'completionattemptsexhausted', 'completionpass', 'autosaveperiod', 'hasquestions',
|
| 258 |
'overduehandling', 'graceperiod', 'canredoquestions', 'allowofflineattempts'];
|
263 |
'overduehandling', 'graceperiod', 'canredoquestions', 'allowofflineattempts'];
|
| 259 |
$managerfields = ['shuffleanswers', 'timecreated', 'timemodified', 'password', 'subnet'];
|
264 |
$managerfields = ['shuffleanswers', 'timecreated', 'timemodified', 'password', 'subnet', 'precreateattempts'];
|
| Línea 260... |
Línea 265... |
| 260 |
|
265 |
|
| 261 |
// Add expected coursemodule and other data.
|
266 |
// Add expected coursemodule and other data.
|
| 262 |
$quiz1 = $this->quiz;
|
267 |
$quiz1 = $this->quiz;
|
| 263 |
$quiz1->coursemodule = $quiz1->cmid;
|
268 |
$quiz1->coursemodule = $quiz1->cmid;
|
| Línea 422... |
Línea 427... |
| 422 |
$this->assertEquals('requireloginerror', $e->errorcode);
|
427 |
$this->assertEquals('requireloginerror', $e->errorcode);
|
| 423 |
}
|
428 |
}
|
| Línea 424... |
Línea 429... |
| 424 |
|
429 |
|
| Línea -... |
Línea 430... |
| - |
|
430 |
}
|
| - |
|
431 |
|
| - |
|
432 |
/**
|
| - |
|
433 |
* Test get_user_attempts
|
| - |
|
434 |
*
|
| 425 |
}
|
435 |
* @todo Remove in Moodle 6.0 as part of MDL-80956 final deprecations.
|
| Línea 426... |
Línea 436... |
| 426 |
|
436 |
*/
|
| 427 |
public function test_get_user_attempts(): void {
|
437 |
public function test_get_user_attempts(): void {
|
| Línea 428... |
Línea 438... |
| 428 |
|
438 |
|
| 429 |
// Create a quiz with one attempt finished.
|
439 |
// Create a quiz with one attempt finished.
|
| - |
|
440 |
[$quiz, $context, $quizobj, $attempt, $attemptobj] = $this->create_quiz_with_questions(true, true);
|
| 430 |
[$quiz, $context, $quizobj, $attempt, $attemptobj] = $this->create_quiz_with_questions(true, true);
|
441 |
|
| Línea 431... |
Línea 442... |
| 431 |
|
442 |
$this->setUser($this->student);
|
| 432 |
$this->setUser($this->student);
|
443 |
$result = mod_quiz_external::get_user_attempts($quiz->id);
|
| 433 |
$result = mod_quiz_external::get_user_attempts($quiz->id);
|
444 |
$this->assertDebuggingCalled();
|
| 434 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
445 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| 435 |
|
446 |
|
| 436 |
$this->assertCount(1, $result['attempts']);
|
447 |
$this->assertCount(1, $result['attempts']);
|
| 437 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
448 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
449 |
$this->assertEquals($quiz->id, $result['attempts'][0]['quiz']);
|
| Línea 438... |
Línea 450... |
| 438 |
$this->assertEquals($quiz->id, $result['attempts'][0]['quiz']);
|
450 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
451 |
$this->assertEquals(1, $result['attempts'][0]['attempt']);
|
| 439 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
452 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| 440 |
$this->assertEquals(1, $result['attempts'][0]['attempt']);
|
453 |
$this->assertEquals(1.0, $result['attempts'][0]['sumgrades']);
|
| - |
|
454 |
$this->assertEquals(quiz_attempt::FINISHED, $result['attempts'][0]['state']);
|
| Línea 441... |
Línea 455... |
| 441 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
455 |
|
| 442 |
$this->assertEquals(1.0, $result['attempts'][0]['sumgrades']);
|
456 |
// Test filters. Only finished.
|
| Línea 443... |
Línea 457... |
| 443 |
|
457 |
$this->resetDebugging();
|
| - |
|
458 |
$result = mod_quiz_external::get_user_attempts($quiz->id, 0, 'finished', false);
|
| 444 |
// Test filters. Only finished.
|
459 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| 445 |
$result = mod_quiz_external::get_user_attempts($quiz->id, 0, 'finished', false);
|
460 |
$this->assertDebuggingCalled();
|
| - |
|
461 |
|
| Línea 446... |
Línea 462... |
| 446 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
462 |
$this->assertCount(1, $result['attempts']);
|
| 447 |
|
463 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| Línea 448... |
Línea 464... |
| 448 |
$this->assertCount(1, $result['attempts']);
|
464 |
|
| - |
|
465 |
// Test filters. All attempts.
|
| 449 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
466 |
$this->resetDebugging();
|
| 450 |
|
467 |
$result = mod_quiz_external::get_user_attempts($quiz->id, 0, 'all', false);
|
| - |
|
468 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| Línea 451... |
Línea 469... |
| 451 |
// Test filters. All attempts.
|
469 |
$this->assertDebuggingCalled();
|
| Línea 452... |
Línea 470... |
| 452 |
$result = mod_quiz_external::get_user_attempts($quiz->id, 0, 'all', false);
|
470 |
|
| 453 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
471 |
$this->assertCount(1, $result['attempts']);
|
| Línea 469... |
Línea 487... |
| 469 |
|
487 |
|
| 470 |
quiz_start_new_attempt($quizobj, $quba, $attempt, 1, $timenow);
|
488 |
quiz_start_new_attempt($quizobj, $quba, $attempt, 1, $timenow);
|
| Línea 471... |
Línea 489... |
| 471 |
quiz_attempt_save_started($quizobj, $quba, $attempt);
|
489 |
quiz_attempt_save_started($quizobj, $quba, $attempt);
|
| - |
|
490 |
|
| 472 |
|
491 |
// Test filters. All attempts.
|
| 473 |
// Test filters. All attempts.
|
492 |
$this->resetDebugging();
|
| - |
|
493 |
$result = mod_quiz_external::get_user_attempts($quiz->id, 0, 'all', false);
|
| Línea 474... |
Línea 494... |
| 474 |
$result = mod_quiz_external::get_user_attempts($quiz->id, 0, 'all', false);
|
494 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| Línea 475... |
Línea 495... |
| 475 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
495 |
$this->assertDebuggingCalled();
|
| - |
|
496 |
|
| 476 |
|
497 |
$this->assertCount(2, $result['attempts']);
|
| 477 |
$this->assertCount(2, $result['attempts']);
|
498 |
|
| - |
|
499 |
// Test filters. Unfinished.
|
| Línea 478... |
Línea 500... |
| 478 |
|
500 |
$this->resetDebugging();
|
| Línea 479... |
Línea 501... |
| 479 |
// Test filters. Unfinished.
|
501 |
$result = mod_quiz_external::get_user_attempts($quiz->id, 0, 'unfinished', false);
|
| 480 |
$result = mod_quiz_external::get_user_attempts($quiz->id, 0, 'unfinished', false);
|
502 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| - |
|
503 |
$this->assertDebuggingCalled();
|
| 481 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
504 |
|
| 482 |
|
505 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
506 |
|
| Línea 483... |
Línea 507... |
| 483 |
$this->assertCount(1, $result['attempts']);
|
507 |
// Test manager can see user attempts.
|
| 484 |
|
508 |
$this->setUser($this->teacher);
|
| Línea -... |
Línea 509... |
| - |
|
509 |
$this->resetDebugging();
|
| 485 |
// Test manager can see user attempts.
|
510 |
$result = mod_quiz_external::get_user_attempts($quiz->id, $this->student->id);
|
| 486 |
$this->setUser($this->teacher);
|
511 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| - |
|
512 |
$this->assertDebuggingCalled();
|
| Línea 487... |
Línea 513... |
| 487 |
$result = mod_quiz_external::get_user_attempts($quiz->id, $this->student->id);
|
513 |
|
| 488 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
514 |
$this->assertCount(1, $result['attempts']);
|
| Línea 489... |
Línea 515... |
| 489 |
|
515 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| 490 |
$this->assertCount(1, $result['attempts']);
|
516 |
|
| - |
|
517 |
$this->resetDebugging();
|
| 491 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
518 |
$result = mod_quiz_external::get_user_attempts($quiz->id, $this->student->id, 'all');
|
| 492 |
|
519 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| 493 |
$result = mod_quiz_external::get_user_attempts($quiz->id, $this->student->id, 'all');
|
520 |
$this->assertDebuggingCalled();
|
| - |
|
521 |
|
| 494 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
522 |
$this->assertCount(2, $result['attempts']);
|
| 495 |
|
523 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| 496 |
$this->assertCount(2, $result['attempts']);
|
524 |
|
| Línea -... |
Línea 525... |
| - |
|
525 |
// Invalid parameters.
|
| - |
|
526 |
try {
|
| - |
|
527 |
$this->resetDebugging();
|
| - |
|
528 |
mod_quiz_external::get_user_attempts($quiz->id, $this->student->id, 'INVALID_PARAMETER');
|
| - |
|
529 |
$this->fail('Exception expected due to missing capability.');
|
| 497 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
530 |
} catch (\invalid_parameter_exception $e) {
|
| 498 |
|
531 |
$this->assertDebuggingCalled();
|
| Línea 499... |
Línea 532... |
| 499 |
// Invalid parameters.
|
532 |
$this->assertEquals('invalidparameter', $e->errorcode);
|
| 500 |
try {
|
533 |
}
|
| Línea 518... |
Línea 551... |
| 518 |
$structure = $attemptobj->get_quizobj()->get_structure();
|
551 |
$structure = $attemptobj->get_quizobj()->get_structure();
|
| 519 |
$structure->update_slot_grade_item($structure->get_slot_by_number(1), $listeninggrade->id);
|
552 |
$structure->update_slot_grade_item($structure->get_slot_by_number(1), $listeninggrade->id);
|
| 520 |
$structure->update_slot_grade_item($structure->get_slot_by_number(2), $readinggrade->id);
|
553 |
$structure->update_slot_grade_item($structure->get_slot_by_number(2), $readinggrade->id);
|
| Línea 521... |
Línea 554... |
| 521 |
|
554 |
|
| - |
|
555 |
$this->setUser($this->student);
|
| 522 |
$this->setUser($this->student);
|
556 |
$this->resetDebugging();
|
| 523 |
$result = mod_quiz_external::get_user_attempts($quiz->id);
|
557 |
$result = mod_quiz_external::get_user_attempts($quiz->id);
|
| - |
|
558 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| Línea 524... |
Línea 559... |
| 524 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
559 |
$this->assertDebuggingCalled();
|
| 525 |
|
560 |
|
| Línea 526... |
Línea 561... |
| 526 |
$this->assertCount(1, $result['attempts']);
|
561 |
$this->assertCount(1, $result['attempts']);
|
| 527 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
562 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| 528 |
|
563 |
|
| Línea 529... |
Línea 564... |
| 529 |
// Verify additional grades.
|
564 |
// Verify additional grades.
|
| 530 |
$this->assertEquals(['name' => 'Listening', 'grade' => 1, 'maxgrade' => 1], $result['attempts'][0]['gradeitemmarks'][0]);
|
565 |
$this->assertEquals(['name' => 'Listening', 'grade' => 1, 'maxgrade' => 1], $result['attempts'][0]['gradeitemmarks'][0]);
|
| - |
|
566 |
$this->assertEquals(['name' => 'Reading', 'grade' => 0, 'maxgrade' => 1], $result['attempts'][0]['gradeitemmarks'][1]);
|
| 531 |
$this->assertEquals(['name' => 'Reading', 'grade' => 0, 'maxgrade' => 1], $result['attempts'][0]['gradeitemmarks'][1]);
|
567 |
|
| 532 |
|
568 |
// Now change the review options, so marks are not displayed, and check the result.
|
| - |
|
569 |
$DB->set_field('quiz', 'reviewmarks', 0, ['id' => $quiz->id]);
|
| Línea 533... |
Línea 570... |
| 533 |
// Now change the review options, so marks are not displayed, and check the result.
|
570 |
$this->resetDebugging();
|
| 534 |
$DB->set_field('quiz', 'reviewmarks', 0, ['id' => $quiz->id]);
|
571 |
$result = mod_quiz_external::get_user_attempts($quiz->id);
|
| 535 |
$result = mod_quiz_external::get_user_attempts($quiz->id);
|
572 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| 536 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
573 |
$this->assertDebuggingCalled();
|
| Línea 537... |
Línea 574... |
| 537 |
|
574 |
|
| 538 |
$this->assertCount(1, $result['attempts']);
|
575 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
576 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
577 |
$this->assertArrayNotHasKey('gradeitemmarks', $result['attempts'][0]);
|
| 539 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
578 |
}
|
| 540 |
$this->assertArrayNotHasKey('gradeitemmarks', $result['attempts'][0]);
|
579 |
|
| 541 |
}
|
580 |
/**
|
| 542 |
|
581 |
* Test get_user_attempts with marks hidden
|
| 543 |
/**
|
582 |
*
|
| 544 |
* Test get_user_attempts with marks hidden
|
583 |
* @todo Remove in Moodle 6.0 as part of MDL-80956 final deprecations.
|
| Línea 545... |
Línea 584... |
| 545 |
*/
|
584 |
*/
|
| 546 |
public function test_get_user_attempts_with_marks_hidden(): void {
|
585 |
public function test_get_user_attempts_with_marks_hidden(): void {
|
| - |
|
586 |
// Create quiz with one attempt finished and hide the mark.
|
| 547 |
// Create quiz with one attempt finished and hide the mark.
|
587 |
list($quiz, $context, $quizobj, $attempt, $attemptobj) = $this->create_quiz_with_questions(
|
| 548 |
list($quiz, $context, $quizobj, $attempt, $attemptobj) = $this->create_quiz_with_questions(
|
588 |
true, true, 'deferredfeedback', false,
|
| - |
|
589 |
['marksduring' => 0, 'marksimmediately' => 0, 'marksopen' => 0, 'marksclosed' => 0]);
|
| Línea 549... |
Línea 590... |
| 549 |
true, true, 'deferredfeedback', false,
|
590 |
|
| 550 |
['marksduring' => 0, 'marksimmediately' => 0, 'marksopen' => 0, 'marksclosed' => 0]);
|
591 |
// Student cannot see the grades.
|
| 551 |
|
592 |
$this->setUser($this->student);
|
| 552 |
// Student cannot see the grades.
|
593 |
$this->resetDebugging();
|
| Línea 562... |
Línea 603... |
| 562 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
603 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| 563 |
$this->assertEquals(null, $result['attempts'][0]['sumgrades']);
|
604 |
$this->assertEquals(null, $result['attempts'][0]['sumgrades']);
|
| Línea 564... |
Línea 605... |
| 564 |
|
605 |
|
| 565 |
// Test manager can see user grades.
|
606 |
// Test manager can see user grades.
|
| - |
|
607 |
$this->setUser($this->teacher);
|
| 566 |
$this->setUser($this->teacher);
|
608 |
$this->resetDebugging();
|
| 567 |
$result = mod_quiz_external::get_user_attempts($quiz->id, $this->student->id);
|
609 |
$result = mod_quiz_external::get_user_attempts($quiz->id, $this->student->id);
|
| - |
|
610 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| - |
|
611 |
$this->assertDebuggingCalled();
|
| - |
|
612 |
|
| - |
|
613 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
614 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
615 |
$this->assertEquals($quiz->id, $result['attempts'][0]['quiz']);
|
| - |
|
616 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
617 |
$this->assertEquals(1, $result['attempts'][0]['attempt']);
|
| - |
|
618 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| - |
|
619 |
$this->assertEquals(1.0, $result['attempts'][0]['sumgrades']);
|
| - |
|
620 |
}
|
| - |
|
621 |
|
| - |
|
622 |
/**
|
| - |
|
623 |
* Test get_user_attempts when the attempt is in 'submitted' state.
|
| - |
|
624 |
*
|
| - |
|
625 |
* @todo Remove in Moodle 6.0 as part of MDL-80956 final deprecations.
|
| - |
|
626 |
* @covers \mod_quiz_external::get_user_attempts
|
| - |
|
627 |
*/
|
| - |
|
628 |
public function test_get_user_attempts_submitted(): void {
|
| - |
|
629 |
|
| - |
|
630 |
// Create a quiz with one attempt.
|
| - |
|
631 |
[$quiz, , , $attempt, $attemptobj] = $this->create_quiz_with_questions(true);
|
| - |
|
632 |
// Submit the attempt but do not finish it.
|
| - |
|
633 |
// Process some responses from the student.
|
| - |
|
634 |
$tosubmit = [1 => ['answer' => '3.14']];
|
| - |
|
635 |
$attemptobj->process_submitted_actions(time(), false, $tosubmit);
|
| - |
|
636 |
$attemptobj->process_submit(time(), false);
|
| - |
|
637 |
|
| - |
|
638 |
$this->setUser($this->student);
|
| - |
|
639 |
$result = mod_quiz_external::get_user_attempts($quiz->id);
|
| - |
|
640 |
$this->assertDebuggingCalled();
|
| - |
|
641 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| - |
|
642 |
|
| - |
|
643 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
644 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
645 |
$this->assertEquals($quiz->id, $result['attempts'][0]['quiz']);
|
| - |
|
646 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
647 |
$this->assertEquals(1, $result['attempts'][0]['attempt']);
|
| - |
|
648 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| - |
|
649 |
$this->assertNull($result['attempts'][0]['sumgrades']); // No grades.
|
| - |
|
650 |
$this->assertEquals(quiz_attempt::FINISHED, $result['attempts'][0]['state']); // State is returned as finished.
|
| - |
|
651 |
}
|
| - |
|
652 |
|
| - |
|
653 |
/**
|
| - |
|
654 |
* Test get_user_attempts when the attempt is in 'notstarted' state. The attempt should not be returned.
|
| - |
|
655 |
*
|
| - |
|
656 |
* @todo Remove in Moodle 6.0 as part of MDL-80956 final deprecations.
|
| - |
|
657 |
* @covers \mod_quiz_external::get_user_attempts
|
| - |
|
658 |
*/
|
| - |
|
659 |
public function test_get_user_attempts_notstarted(): void {
|
| - |
|
660 |
// Create a quiz.
|
| - |
|
661 |
[$quiz, , $quizobj, , ] = $this->create_quiz_with_questions();
|
| - |
|
662 |
// Create an attempt but do not start it.
|
| - |
|
663 |
// Now, do one attempt.
|
| - |
|
664 |
$quba = \question_engine::make_questions_usage_by_activity('mod_quiz', $quizobj->get_context());
|
| - |
|
665 |
$quba->set_preferred_behaviour($quizobj->get_quiz()->preferredbehaviour);
|
| - |
|
666 |
|
| - |
|
667 |
$timenow = time();
|
| - |
|
668 |
$attempt = quiz_create_attempt($quizobj, 1, false, $timenow, false, $this->student->id);
|
| - |
|
669 |
quiz_start_new_attempt($quizobj, $quba, $attempt, 1, $timenow);
|
| - |
|
670 |
quiz_attempt_save_not_started($quba, $attempt);
|
| - |
|
671 |
|
| - |
|
672 |
$this->setUser($this->student);
|
| - |
|
673 |
$result = mod_quiz_external::get_user_attempts($quiz->id, $this->student->id, 'all');
|
| - |
|
674 |
$this->assertDebuggingCalled();
|
| - |
|
675 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
| - |
|
676 |
|
| - |
|
677 |
$this->assertCount(0, $result['attempts']);
|
| - |
|
678 |
}
|
| - |
|
679 |
|
| - |
|
680 |
/**
|
| - |
|
681 |
* Test get_quiz_user_attempts
|
| - |
|
682 |
*
|
| - |
|
683 |
* @covers \mod_quiz_external::get_user_quiz_attempts
|
| - |
|
684 |
*/
|
| - |
|
685 |
public function test_get_user_quiz_attempts(): void {
|
| - |
|
686 |
|
| - |
|
687 |
// Create a quiz with one attempt finished.
|
| - |
|
688 |
[$quiz, , $quizobj, $attempt, ] = $this->create_quiz_with_questions(true, true);
|
| - |
|
689 |
|
| - |
|
690 |
$this->setUser($this->student);
|
| - |
|
691 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id);
|
| - |
|
692 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
693 |
|
| - |
|
694 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
695 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
696 |
$this->assertEquals($quiz->id, $result['attempts'][0]['quiz']);
|
| - |
|
697 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
698 |
$this->assertEquals(1, $result['attempts'][0]['attempt']);
|
| - |
|
699 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| - |
|
700 |
$this->assertEquals(1.0, $result['attempts'][0]['sumgrades']);
|
| - |
|
701 |
$this->assertEquals(quiz_attempt::FINISHED, $result['attempts'][0]['state']);
|
| - |
|
702 |
|
| - |
|
703 |
// Test filters. Only finished.
|
| - |
|
704 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, 0, 'finished', false);
|
| - |
|
705 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
706 |
|
| - |
|
707 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
708 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
709 |
|
| - |
|
710 |
// Test filters. All attempts.
|
| - |
|
711 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, 0, 'all', false);
|
| - |
|
712 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
713 |
|
| - |
|
714 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
715 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
716 |
|
| - |
|
717 |
// Test filters. Unfinished.
|
| - |
|
718 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, 0, 'unfinished', false);
|
| - |
|
719 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
720 |
|
| - |
|
721 |
$this->assertCount(0, $result['attempts']);
|
| - |
|
722 |
|
| - |
|
723 |
// Start a new attempt, but not finish it.
|
| - |
|
724 |
$timenow = time();
|
| - |
|
725 |
$attempt = quiz_create_attempt($quizobj, 2, false, $timenow, false, $this->student->id);
|
| - |
|
726 |
$quba = \question_engine::make_questions_usage_by_activity('mod_quiz', $quizobj->get_context());
|
| - |
|
727 |
$quba->set_preferred_behaviour($quizobj->get_quiz()->preferredbehaviour);
|
| - |
|
728 |
|
| - |
|
729 |
quiz_start_new_attempt($quizobj, $quba, $attempt, 1, $timenow);
|
| - |
|
730 |
quiz_attempt_save_started($quizobj, $quba, $attempt);
|
| - |
|
731 |
|
| - |
|
732 |
// Test filters. All attempts.
|
| - |
|
733 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, 0, 'all', false);
|
| - |
|
734 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
735 |
|
| - |
|
736 |
$this->assertCount(2, $result['attempts']);
|
| - |
|
737 |
|
| - |
|
738 |
// Test filters. Unfinished.
|
| - |
|
739 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, 0, 'unfinished', false);
|
| - |
|
740 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
741 |
|
| - |
|
742 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
743 |
|
| - |
|
744 |
// Test manager can see user attempts.
|
| - |
|
745 |
$this->setUser($this->teacher);
|
| - |
|
746 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, $this->student->id);
|
| - |
|
747 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
748 |
|
| - |
|
749 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
750 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
751 |
|
| - |
|
752 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, $this->student->id, 'all');
|
| - |
|
753 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
754 |
|
| - |
|
755 |
$this->assertCount(2, $result['attempts']);
|
| - |
|
756 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
757 |
|
| - |
|
758 |
// Invalid parameters.
|
| - |
|
759 |
try {
|
| - |
|
760 |
mod_quiz_external::get_user_quiz_attempts($quiz->id, $this->student->id, 'INVALID_PARAMETER');
|
| - |
|
761 |
$this->fail('Exception expected due to missing capability.');
|
| - |
|
762 |
} catch (\invalid_parameter_exception $e) {
|
| - |
|
763 |
$this->assertEquals('invalidparameter', $e->errorcode);
|
| - |
|
764 |
}
|
| - |
|
765 |
}
|
| - |
|
766 |
|
| - |
|
767 |
/**
|
| - |
|
768 |
* Test get_user_quiz_attempts with extra grades
|
| - |
|
769 |
*/
|
| - |
|
770 |
public function test_get_user_quiz_attempts_with_extra_grades(): void {
|
| - |
|
771 |
global $DB;
|
| - |
|
772 |
|
| - |
|
773 |
// Create a quiz with one attempt finished.
|
| - |
|
774 |
[$quiz, , , $attempt, $attemptobj] = $this->create_quiz_with_questions(true, true);
|
| - |
|
775 |
|
| - |
|
776 |
// Add some extra grade items.
|
| - |
|
777 |
$quizgenerator = $this->getDataGenerator()->get_plugin_generator('mod_quiz');
|
| - |
|
778 |
$listeninggrade = $quizgenerator->create_grade_item(['quizid' => $attemptobj->get_quizid(), 'name' => 'Listening']);
|
| - |
|
779 |
$readinggrade = $quizgenerator->create_grade_item(['quizid' => $attemptobj->get_quizid(), 'name' => 'Reading']);
|
| - |
|
780 |
$structure = $attemptobj->get_quizobj()->get_structure();
|
| - |
|
781 |
$structure->update_slot_grade_item($structure->get_slot_by_number(1), $listeninggrade->id);
|
| - |
|
782 |
$structure->update_slot_grade_item($structure->get_slot_by_number(2), $readinggrade->id);
|
| - |
|
783 |
|
| - |
|
784 |
$this->setUser($this->student);
|
| - |
|
785 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id);
|
| - |
|
786 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
787 |
|
| - |
|
788 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
789 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
790 |
|
| - |
|
791 |
// Verify additional grades.
|
| - |
|
792 |
$this->assertEquals(['name' => 'Listening', 'grade' => 1, 'maxgrade' => 1], $result['attempts'][0]['gradeitemmarks'][0]);
|
| - |
|
793 |
$this->assertEquals(['name' => 'Reading', 'grade' => 0, 'maxgrade' => 1], $result['attempts'][0]['gradeitemmarks'][1]);
|
| - |
|
794 |
|
| - |
|
795 |
// Now change the review options, so marks are not displayed, and check the result.
|
| - |
|
796 |
$DB->set_field('quiz', 'reviewmarks', 0, ['id' => $quiz->id]);
|
| - |
|
797 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id);
|
| - |
|
798 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
799 |
|
| - |
|
800 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
801 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
802 |
$this->assertArrayNotHasKey('gradeitemmarks', $result['attempts'][0]);
|
| - |
|
803 |
}
|
| - |
|
804 |
|
| - |
|
805 |
/**
|
| - |
|
806 |
* Test get_user_quiz_attempts with marks hidden
|
| - |
|
807 |
*
|
| - |
|
808 |
* @covers \mod_quiz_external::get_user_quiz_attempts
|
| - |
|
809 |
*/
|
| - |
|
810 |
public function test_get_user_quiz_attempts_with_marks_hidden(): void {
|
| - |
|
811 |
// Create quiz with one attempt finished and hide the mark.
|
| - |
|
812 |
[$quiz, , , $attempt, ] = $this->create_quiz_with_questions(
|
| - |
|
813 |
true, true, 'deferredfeedback', false,
|
| - |
|
814 |
['marksduring' => 0, 'marksimmediately' => 0, 'marksopen' => 0, 'marksclosed' => 0]);
|
| - |
|
815 |
|
| - |
|
816 |
// Student cannot see the grades.
|
| - |
|
817 |
$this->setUser($this->student);
|
| - |
|
818 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id);
|
| - |
|
819 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
820 |
|
| - |
|
821 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
822 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
823 |
$this->assertEquals($quiz->id, $result['attempts'][0]['quiz']);
|
| - |
|
824 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
825 |
$this->assertEquals(1, $result['attempts'][0]['attempt']);
|
| - |
|
826 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| - |
|
827 |
$this->assertEquals(null, $result['attempts'][0]['sumgrades']);
|
| - |
|
828 |
|
| - |
|
829 |
// Test manager can see user grades.
|
| - |
|
830 |
$this->setUser($this->teacher);
|
| - |
|
831 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, $this->student->id);
|
| Línea 568... |
Línea 832... |
| 568 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_attempts_returns(), $result);
|
832 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| 569 |
|
833 |
|
| 570 |
$this->assertCount(1, $result['attempts']);
|
834 |
$this->assertCount(1, $result['attempts']);
|
| 571 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
835 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| Línea 575... |
Línea 839... |
| 575 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
839 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| 576 |
$this->assertEquals(1.0, $result['attempts'][0]['sumgrades']);
|
840 |
$this->assertEquals(1.0, $result['attempts'][0]['sumgrades']);
|
| 577 |
}
|
841 |
}
|
| Línea 578... |
Línea 842... |
| 578 |
|
842 |
|
| - |
|
843 |
/**
|
| - |
|
844 |
* Test get_user_quiz_attempts when the attempt is in 'submitted' state.
|
| - |
|
845 |
*
|
| - |
|
846 |
* @covers \mod_quiz_external::get_user_quiz_attempts
|
| - |
|
847 |
*/
|
| - |
|
848 |
public function test_get_user_quiz_attempts_submitted(): void {
|
| - |
|
849 |
|
| - |
|
850 |
// Create a quiz with one attempt.
|
| - |
|
851 |
[$quiz, , , $attempt, $attemptobj] = $this->create_quiz_with_questions(true);
|
| - |
|
852 |
// Submit the attempt but do not finish it.
|
| - |
|
853 |
// Process some responses from the student.
|
| - |
|
854 |
$tosubmit = [1 => ['answer' => '3.14']];
|
| - |
|
855 |
$attemptobj->process_submitted_actions(time(), false, $tosubmit);
|
| - |
|
856 |
$attemptobj->process_submit(time(), false);
|
| - |
|
857 |
|
| - |
|
858 |
$this->setUser($this->student);
|
| - |
|
859 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id);
|
| - |
|
860 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
861 |
|
| - |
|
862 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
863 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
864 |
$this->assertEquals($quiz->id, $result['attempts'][0]['quiz']);
|
| - |
|
865 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
866 |
$this->assertEquals(1, $result['attempts'][0]['attempt']);
|
| - |
|
867 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| - |
|
868 |
$this->assertNull($result['attempts'][0]['sumgrades']); // No grades.
|
| - |
|
869 |
$this->assertEquals(quiz_attempt::SUBMITTED, $result['attempts'][0]['state']);
|
| - |
|
870 |
}
|
| - |
|
871 |
|
| - |
|
872 |
/**
|
| - |
|
873 |
* Test get_user_quiz_attempts when the attempt is in 'notstarted' state.
|
| - |
|
874 |
*
|
| - |
|
875 |
* @covers \mod_quiz_external::get_user_quiz_attempts
|
| - |
|
876 |
*/
|
| - |
|
877 |
public function test_get_user_quiz_attempts_notstarted(): void {
|
| - |
|
878 |
// Create a quiz.
|
| - |
|
879 |
[$quiz, , $quizobj, , ] = $this->create_quiz_with_questions();
|
| - |
|
880 |
// Create an attempt but do not start it.
|
| - |
|
881 |
// Now, do one attempt.
|
| - |
|
882 |
$quba = \question_engine::make_questions_usage_by_activity('mod_quiz', $quizobj->get_context());
|
| - |
|
883 |
$quba->set_preferred_behaviour($quizobj->get_quiz()->preferredbehaviour);
|
| - |
|
884 |
|
| - |
|
885 |
$timenow = time();
|
| - |
|
886 |
$attempt = quiz_create_attempt($quizobj, 1, false, $timenow, false, $this->student->id);
|
| - |
|
887 |
quiz_start_new_attempt($quizobj, $quba, $attempt, 1, $timenow);
|
| - |
|
888 |
quiz_attempt_save_not_started($quba, $attempt);
|
| - |
|
889 |
|
| - |
|
890 |
$this->setUser($this->student);
|
| - |
|
891 |
$result = mod_quiz_external::get_user_quiz_attempts($quiz->id, $this->student->id, 'all');
|
| - |
|
892 |
$result = external_api::clean_returnvalue(mod_quiz_external::get_user_quiz_attempts_returns(), $result);
|
| - |
|
893 |
|
| - |
|
894 |
$this->assertCount(1, $result['attempts']);
|
| - |
|
895 |
$this->assertEquals($attempt->id, $result['attempts'][0]['id']);
|
| - |
|
896 |
$this->assertEquals($quiz->id, $result['attempts'][0]['quiz']);
|
| - |
|
897 |
$this->assertEquals($this->student->id, $result['attempts'][0]['userid']);
|
| - |
|
898 |
$this->assertEquals(1, $result['attempts'][0]['attempt']);
|
| - |
|
899 |
$this->assertArrayHasKey('sumgrades', $result['attempts'][0]);
|
| - |
|
900 |
$this->assertNull($result['attempts'][0]['sumgrades']);
|
| - |
|
901 |
$this->assertEquals(quiz_attempt::NOT_STARTED, $result['attempts'][0]['state']);
|
| - |
|
902 |
}
|
| - |
|
903 |
|
| 579 |
/**
|
904 |
/**
|
| 580 |
* Test get_user_best_grade
|
905 |
* Test get_user_best_grade
|
| 581 |
*/
|
906 |
*/
|
| 582 |
public function test_get_user_best_grade(): void {
|
907 |
public function test_get_user_best_grade(): void {
|
| 583 |
$quizgenerator = $this->getDataGenerator()->get_plugin_generator('mod_quiz');
|
908 |
$quizgenerator = $this->getDataGenerator()->get_plugin_generator('mod_quiz');
|
| Línea 658... |
Línea 983... |
| 658 |
// Process some responses from the student.
|
983 |
// Process some responses from the student.
|
| 659 |
$attemptobj = quiz_attempt::create($attempt->id);
|
984 |
$attemptobj = quiz_attempt::create($attempt->id);
|
| 660 |
$attemptobj->process_submitted_actions($timenow, false, [1 => ['answer' => '3.14']]);
|
985 |
$attemptobj->process_submitted_actions($timenow, false, [1 => ['answer' => '3.14']]);
|
| Línea 661... |
Línea 986... |
| 661 |
|
986 |
|
| 662 |
// Finish the attempt.
|
987 |
// Finish the attempt.
|
| - |
|
988 |
$attemptobj->process_submit($timenow, false);
|
| Línea 663... |
Línea 989... |
| 663 |
$attemptobj->process_finish($timenow, false);
|
989 |
$attemptobj->process_grade_submission($timenow);
|
| 664 |
|
990 |
|
| Línea 665... |
Línea 991... |
| 665 |
$result = mod_quiz_external::get_user_best_grade($quizapi1->id);
|
991 |
$result = mod_quiz_external::get_user_best_grade($quizapi1->id);
|
| Línea 720... |
Línea 1046... |
| 720 |
// Process some responses from the student.
|
1046 |
// Process some responses from the student.
|
| 721 |
$attemptobj = quiz_attempt::create($attempt->id);
|
1047 |
$attemptobj = quiz_attempt::create($attempt->id);
|
| 722 |
$attemptobj->process_submitted_actions($timenow, false, [1 => ['answer' => '3.14']]);
|
1048 |
$attemptobj->process_submitted_actions($timenow, false, [1 => ['answer' => '3.14']]);
|
| Línea 723... |
Línea 1049... |
| 723 |
|
1049 |
|
| 724 |
// Finish the attempt.
|
1050 |
// Finish the attempt.
|
| - |
|
1051 |
$attemptobj->process_submit($timenow, false);
|
| Línea 725... |
Línea 1052... |
| 725 |
$attemptobj->process_finish($timenow, false);
|
1052 |
$attemptobj->process_grade_submission($timenow);
|
| 726 |
|
1053 |
|
| Línea 727... |
Línea 1054... |
| 727 |
$result = mod_quiz_external::get_user_best_grade($quizapi2->id);
|
1054 |
$result = mod_quiz_external::get_user_best_grade($quizapi2->id);
|
| Línea 806... |
Línea 1133... |
| 806 |
|
1133 |
|
| Línea 807... |
Línea 1134... |
| 807 |
$this->assertEquals($expected, $result);
|
1134 |
$this->assertEquals($expected, $result);
|
| 808 |
|
1135 |
|
| 809 |
// Now, finish the attempt.
|
1136 |
// Now, finish the attempt.
|
| - |
|
1137 |
$attemptobj = quiz_attempt::create($attempt->id);
|
| Línea 810... |
Línea 1138... |
| 810 |
$attemptobj = quiz_attempt::create($attempt->id);
|
1138 |
$attemptobj->process_submit($timenow, false);
|
| 811 |
$attemptobj->process_finish($timenow, false);
|
1139 |
$attemptobj->process_grade_submission($timenow);
|
| 812 |
|
1140 |
|
| 813 |
$expected = [
|
1141 |
$expected = [
|
| Línea 1023... |
Línea 1351... |
| 1023 |
$attemptobj->process_submitted_actions($timenow, false, $tosubmit);
|
1351 |
$attemptobj->process_submitted_actions($timenow, false, $tosubmit);
|
| Línea 1024... |
Línea 1352... |
| 1024 |
|
1352 |
|
| 1025 |
// Finish the attempt.
|
1353 |
// Finish the attempt.
|
| 1026 |
$attemptobj = quiz_attempt::create($attemptid);
|
1354 |
$attemptobj = quiz_attempt::create($attemptid);
|
| 1027 |
$this->assertTrue($attemptobj->has_response_to_at_least_one_graded_question());
|
1355 |
$this->assertTrue($attemptobj->has_response_to_at_least_one_graded_question());
|
| - |
|
1356 |
$attemptobj->process_submit($timenow, false);
|
| Línea 1028... |
Línea 1357... |
| 1028 |
$attemptobj->process_finish($timenow, false);
|
1357 |
$attemptobj->process_grade_submission($timenow);
|
| 1029 |
|
1358 |
|
| 1030 |
// We should be able to start a new attempt.
|
1359 |
// We should be able to start a new attempt.
|
| Línea 1124... |
Línea 1453... |
| 1124 |
$this->assertEquals('attempterror', $e->errorcode);
|
1453 |
$this->assertEquals('attempterror', $e->errorcode);
|
| 1125 |
}
|
1454 |
}
|
| Línea 1126... |
Línea 1455... |
| 1126 |
|
1455 |
|
| 1127 |
// Finish the attempt.
|
1456 |
// Finish the attempt.
|
| 1128 |
$attemptobj = quiz_attempt::create($attempt->id);
|
1457 |
$attemptobj = quiz_attempt::create($attempt->id);
|
| - |
|
1458 |
$attemptobj->process_submit(time(), false);
|
| Línea 1129... |
Línea 1459... |
| 1129 |
$attemptobj->process_finish(time(), false);
|
1459 |
$attemptobj->process_grade_submission(time());
|
| 1130 |
|
1460 |
|
| 1131 |
try {
|
1461 |
try {
|
| 1132 |
testable_mod_quiz_external::validate_attempt($params, false);
|
1462 |
testable_mod_quiz_external::validate_attempt($params, false);
|
| Línea 1205... |
Línea 1535... |
| 1205 |
$this->assertFalse($result['questions'][0]['flagged']);
|
1535 |
$this->assertFalse($result['questions'][0]['flagged']);
|
| 1206 |
$this->assertEquals(0, $result['questions'][0]['page']);
|
1536 |
$this->assertEquals(0, $result['questions'][0]['page']);
|
| 1207 |
$this->assertEmpty($result['questions'][0]['mark']);
|
1537 |
$this->assertEmpty($result['questions'][0]['mark']);
|
| 1208 |
$this->assertEquals(1, $result['questions'][0]['maxmark']);
|
1538 |
$this->assertEquals(1, $result['questions'][0]['maxmark']);
|
| 1209 |
$this->assertEquals(1, $result['questions'][0]['sequencecheck']);
|
1539 |
$this->assertEquals(1, $result['questions'][0]['sequencecheck']);
|
| 1210 |
$this->assertGreaterThanOrEqual($timenow, $result['questions'][0]['lastactiontime']);
|
1540 |
$this->assertEquals(\question_attempt_step::TIMECREATED_ON_FIRST_RENDER, $result['questions'][0]['lastactiontime']);
|
| 1211 |
$this->assertEquals(false, $result['questions'][0]['hasautosavedstep']);
|
1541 |
$this->assertEquals(false, $result['questions'][0]['hasautosavedstep']);
|
| Línea 1212... |
Línea 1542... |
| 1212 |
|
1542 |
|
| 1213 |
// Now try the last page.
|
1543 |
// Now try the last page.
|
| 1214 |
$result = mod_quiz_external::get_attempt_data($attempt->id, 1);
|
1544 |
$result = mod_quiz_external::get_attempt_data($attempt->id, 1);
|
| Línea 1226... |
Línea 1556... |
| 1226 |
$this->assertArrayNotHasKey('state', $result['questions'][0]); // We don't receive the state yet.
|
1556 |
$this->assertArrayNotHasKey('state', $result['questions'][0]); // We don't receive the state yet.
|
| 1227 |
$this->assertEquals(get_string('notyetanswered', 'question'), $result['questions'][0]['status']);
|
1557 |
$this->assertEquals(get_string('notyetanswered', 'question'), $result['questions'][0]['status']);
|
| 1228 |
$this->assertFalse($result['questions'][0]['flagged']);
|
1558 |
$this->assertFalse($result['questions'][0]['flagged']);
|
| 1229 |
$this->assertEquals(1, $result['questions'][0]['page']);
|
1559 |
$this->assertEquals(1, $result['questions'][0]['page']);
|
| 1230 |
$this->assertEquals(1, $result['questions'][0]['sequencecheck']);
|
1560 |
$this->assertEquals(1, $result['questions'][0]['sequencecheck']);
|
| 1231 |
$this->assertGreaterThanOrEqual($timenow, $result['questions'][0]['lastactiontime']);
|
1561 |
$this->assertEquals(\question_attempt_step::TIMECREATED_ON_FIRST_RENDER, $result['questions'][0]['lastactiontime']);
|
| 1232 |
$this->assertEquals(false, $result['questions'][0]['hasautosavedstep']);
|
1562 |
$this->assertEquals(false, $result['questions'][0]['hasautosavedstep']);
|
| Línea 1233... |
Línea 1563... |
| 1233 |
|
1563 |
|
| 1234 |
// Finish previous attempt.
|
1564 |
// Finish previous attempt.
|
| - |
|
1565 |
$attemptobj->process_submit(time(), false);
|
| Línea 1235... |
Línea 1566... |
| 1235 |
$attemptobj->process_finish(time(), false);
|
1566 |
$attemptobj->process_grade_submission(time());
|
| 1236 |
|
1567 |
|
| 1237 |
// Now we should receive the question state.
|
1568 |
// Now we should receive the question state.
|
| 1238 |
$result = mod_quiz_external::get_attempt_review($attempt->id, 1);
|
1569 |
$result = mod_quiz_external::get_attempt_review($attempt->id, 1);
|
| Línea 1343... |
Línea 1674... |
| 1343 |
$this->assertFalse($result['questions'][1]['flagged']);
|
1674 |
$this->assertFalse($result['questions'][1]['flagged']);
|
| 1344 |
$this->assertEmpty($result['questions'][0]['mark']);
|
1675 |
$this->assertEmpty($result['questions'][0]['mark']);
|
| 1345 |
$this->assertEmpty($result['questions'][1]['mark']);
|
1676 |
$this->assertEmpty($result['questions'][1]['mark']);
|
| 1346 |
$this->assertEquals(1, $result['questions'][0]['sequencecheck']);
|
1677 |
$this->assertEquals(1, $result['questions'][0]['sequencecheck']);
|
| 1347 |
$this->assertEquals(1, $result['questions'][1]['sequencecheck']);
|
1678 |
$this->assertEquals(1, $result['questions'][1]['sequencecheck']);
|
| 1348 |
$this->assertGreaterThanOrEqual($timenow, $result['questions'][0]['lastactiontime']);
|
1679 |
$this->assertEquals(\question_attempt_step::TIMECREATED_ON_FIRST_RENDER, $result['questions'][0]['lastactiontime']);
|
| 1349 |
$this->assertGreaterThanOrEqual($timenow, $result['questions'][1]['lastactiontime']);
|
1680 |
$this->assertEquals(\question_attempt_step::TIMECREATED_ON_FIRST_RENDER, $result['questions'][1]['lastactiontime']);
|
| 1350 |
$this->assertEquals(false, $result['questions'][0]['hasautosavedstep']);
|
1681 |
$this->assertEquals(false, $result['questions'][0]['hasautosavedstep']);
|
| 1351 |
$this->assertEquals(false, $result['questions'][1]['hasautosavedstep']);
|
1682 |
$this->assertEquals(false, $result['questions'][1]['hasautosavedstep']);
|
| Línea 1352... |
Línea 1683... |
| 1352 |
|
1683 |
|
| 1353 |
// Check question options.
|
1684 |
// Check question options.
|
| Línea 1422... |
Línea 1753... |
| 1422 |
$this->assertEmpty($result['questions'][0]['mark']);
|
1753 |
$this->assertEmpty($result['questions'][0]['mark']);
|
| 1423 |
$this->assertEmpty($result['questions'][1]['mark']);
|
1754 |
$this->assertEmpty($result['questions'][1]['mark']);
|
| 1424 |
$this->assertEquals(1, $result['questions'][0]['sequencecheck']);
|
1755 |
$this->assertEquals(1, $result['questions'][0]['sequencecheck']);
|
| 1425 |
$this->assertEquals(1, $result['questions'][1]['sequencecheck']);
|
1756 |
$this->assertEquals(1, $result['questions'][1]['sequencecheck']);
|
| 1426 |
$this->assertGreaterThanOrEqual($timenow, $result['questions'][0]['lastactiontime']);
|
1757 |
$this->assertGreaterThanOrEqual($timenow, $result['questions'][0]['lastactiontime']);
|
| 1427 |
$this->assertGreaterThanOrEqual($timenow, $result['questions'][1]['lastactiontime']);
|
1758 |
$this->assertEquals(\question_attempt_step::TIMECREATED_ON_FIRST_RENDER, $result['questions'][1]['lastactiontime']);
|
| 1428 |
$this->assertEquals(true, $result['questions'][0]['hasautosavedstep']);
|
1759 |
$this->assertEquals(true, $result['questions'][0]['hasautosavedstep']);
|
| 1429 |
$this->assertEquals(false, $result['questions'][1]['hasautosavedstep']);
|
1760 |
$this->assertEquals(false, $result['questions'][1]['hasautosavedstep']);
|
| Línea 1430... |
Línea 1761... |
| 1430 |
|
1761 |
|
| 1431 |
// Now, second slot.
|
1762 |
// Now, second slot.
|
| Línea 2123... |
Línea 2454... |
| 2123 |
$attemptobj->process_submitted_actions($timenow, false, $tosubmit);
|
2454 |
$attemptobj->process_submitted_actions($timenow, false, $tosubmit);
|
| Línea 2124... |
Línea 2455... |
| 2124 |
|
2455 |
|
| 2125 |
// Finish the attempt.
|
2456 |
// Finish the attempt.
|
| 2126 |
$attemptobj = quiz_attempt::create($attempt->id);
|
2457 |
$attemptobj = quiz_attempt::create($attempt->id);
|
| 2127 |
$this->assertTrue($attemptobj->has_response_to_at_least_one_graded_question());
|
2458 |
$this->assertTrue($attemptobj->has_response_to_at_least_one_graded_question());
|
| - |
|
2459 |
$attemptobj->process_submit($timenow, false);
|
| Línea 2128... |
Línea 2460... |
| 2128 |
$attemptobj->process_finish($timenow, false);
|
2460 |
$attemptobj->process_grade_submission($timenow);
|
| 2129 |
|
2461 |
|
| 2130 |
// Can we start a new attempt? We shall not!
|
2462 |
// Can we start a new attempt? We shall not!
|