Search moodle.org's
Developer Documentation

See Release Notes

  • Bug fixes for general core bugs in 4.3.x will end 7 October 2024 (12 months).
  • Bug fixes for security issues in 4.3.x will end 21 April 2025 (18 months).
  • PHP version: minimum PHP 8.0.0 Note: minimum PHP version has increased since Moodle 4.1. PHP 8.2.x is supported too.

Differences Between: [Versions 310 and 403] [Versions 311 and 403] [Versions 39 and 403] [Versions 400 and 403] [Versions 401 and 403]

   1  <?php
   2  // This file is part of Moodle - http://moodle.org/
   3  //
   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.
   8  //
   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.
  13  //
  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/>.
  16  
  17  /**
  18   * Unit tests for the {@link \mod_quiz\repaginate} class.
  19   * @package   mod_quiz
  20   * @category  test
  21   * @copyright 2014 The Open Univsersity
  22   * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  23   */
  24  
  25  namespace mod_quiz;
  26  
  27  defined('MOODLE_INTERNAL') || die();
  28  
  29  global $CFG;
  30  require_once($CFG->dirroot . '/mod/quiz/locallib.php');
  31  require_once($CFG->dirroot . '/mod/quiz/classes/repaginate.php');
  32  
  33  /**
  34   * Test for {@see \mod_quiz\repaginate}
  35   * @copyright 2014 The Open Univsersity
  36   * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  37   */
  38  class mod_quiz_repaginate_testable extends repaginate {
  39  
  40      public function __construct($quizid = 0, $slots = null) {
  41          return parent::__construct($quizid, $slots);
  42      }
  43      public function get_this_slot($slots, $slotnumber) {
  44          return parent::get_this_slot($slots, $slotnumber);
  45      }
  46      public function get_slots_by_slotid($slots = null) {
  47          return parent::get_slots_by_slotid($slots);
  48      }
  49      public function get_slots_by_slot_number($slots = null) {
  50          return parent::get_slots_by_slot_number($slots);
  51      }
  52      public function repaginate_this_slot($slot, $newpagenumber) {
  53          return parent::repaginate_this_slot($slot, $newpagenumber);
  54      }
  55      public function repaginate_next_slot($nextslotnumber, $type) {
  56          return parent::repaginate_next_slot($nextslotnumber, $type);
  57      }
  58  }
  59  
  60  /**
  61   * Test for some parts of the repaginate class.
  62   * @copyright 2014 The Open University
  63   * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  64   */
  65  class repaginate_test extends \advanced_testcase {
  66  
  67      /** @var array stores the slots. */
  68      private $quizslots;
  69      /** @var mod_quiz_repaginate_testable the object being tested. */
  70      private $repaginate = null;
  71  
  72      public function setUp(): void {
  73          $this->set_quiz_slots($this->get_quiz_object()->get_slots());
  74          $this->repaginate = new mod_quiz_repaginate_testable(0, $this->quizslots);
  75      }
  76  
  77      /**
  78       * Create a quiz, add five questions to the quiz
  79       * which are all on one page and return the quiz object.
  80       */
  81      private function get_quiz_object() {
  82          global $SITE;
  83          $this->resetAfterTest(true);
  84  
  85          // Make a quiz.
  86          $quizgenerator = $this->getDataGenerator()->get_plugin_generator('mod_quiz');
  87  
  88          $quiz = $quizgenerator->create_instance([
  89                  'course' => $SITE->id, 'questionsperpage' => 0, 'grade' => 100.0, 'sumgrades' => 2]);
  90          $cm = get_coursemodule_from_instance('quiz', $quiz->id, $SITE->id);
  91  
  92          // Create five questions.
  93          $questiongenerator = $this->getDataGenerator()->get_plugin_generator('core_question');
  94          $cat = $questiongenerator->create_question_category();
  95  
  96          $shortanswer = $questiongenerator->create_question('shortanswer', null, ['category' => $cat->id]);
  97          $numerical = $questiongenerator->create_question('numerical', null, ['category' => $cat->id]);
  98          $essay = $questiongenerator->create_question('essay', null, ['category' => $cat->id]);
  99          $truefalse = $questiongenerator->create_question('truefalse', null, ['category' => $cat->id]);
 100          $match = $questiongenerator->create_question('match', null, ['category' => $cat->id]);
 101  
 102          // Add them to the quiz.
 103          quiz_add_quiz_question($shortanswer->id, $quiz);
 104          quiz_add_quiz_question($numerical->id, $quiz);
 105          quiz_add_quiz_question($essay->id, $quiz);
 106          quiz_add_quiz_question($truefalse->id, $quiz);
 107          quiz_add_quiz_question($match->id, $quiz);
 108  
 109          // Return the quiz object.
 110          $quizobj = new quiz_settings($quiz, $cm, $SITE);
 111          return structure::create_for_quiz($quizobj);
 112      }
 113  
 114      /**
 115       * Set the quiz slots
 116       * @param string $slots
 117       */
 118      private function set_quiz_slots($slots = null) {
 119          if (!$slots) {
 120              $this->quizslots = $this->get_quiz_object()->get_slots();
 121          } else {
 122              $this->quizslots = $slots;
 123          }
 124      }
 125  
 126      /**
 127       * Test the get_this_slot() method
 128       */
 129      public function test_get_this_slot() {
 130          $this->set_quiz_slots();
 131          $actual = [];
 132          $expected = $this->repaginate->get_slots_by_slot_number();
 133          $this->assertEquals($expected, $actual);
 134  
 135          $slotsbyno = $this->repaginate->get_slots_by_slot_number($this->quizslots);
 136          $slotnumber = 5;
 137          $thisslot = $this->repaginate->get_this_slot($this->quizslots, $slotnumber);
 138          $this->assertEquals($slotsbyno[$slotnumber], $thisslot);
 139      }
 140  
 141      public function test_get_slots_by_slotnumber() {
 142          $this->set_quiz_slots();
 143          $expected = [];
 144          $actual = $this->repaginate->get_slots_by_slot_number();
 145          $this->assertEquals($expected, $actual);
 146  
 147          foreach ($this->quizslots as $slot) {
 148              $expected[$slot->slot] = $slot;
 149          }
 150          $actual = $this->repaginate->get_slots_by_slot_number($this->quizslots);
 151          $this->assertEquals($expected, $actual);
 152      }
 153  
 154      public function test_get_slots_by_slotid() {
 155          $this->set_quiz_slots();
 156          $actual = $this->repaginate->get_slots_by_slotid();
 157          $this->assertEquals([], $actual);
 158  
 159          $slotsbyno = $this->repaginate->get_slots_by_slot_number($this->quizslots);
 160          $actual = $this->repaginate->get_slots_by_slotid($slotsbyno);
 161          $this->assertEquals($this->quizslots, $actual);
 162      }
 163  
 164      public function test_repaginate_n_questions_per_page() {
 165          $this->set_quiz_slots();
 166  
 167          // Expect 2 questions per page.
 168          $expected = [];
 169          foreach ($this->quizslots as $slot) {
 170              // Page 1 contains Slots 1 and 2.
 171              if ($slot->slot >= 1 && $slot->slot <= 2) {
 172                  $slot->page = 1;
 173              }
 174              // Page 2 contains slots 3 and 4.
 175              if ($slot->slot >= 3 && $slot->slot <= 4) {
 176                  $slot->page = 2;
 177              }
 178              // Page 3 contains slots 5.
 179              if ($slot->slot >= 5 && $slot->slot <= 6) {
 180                  $slot->page = 3;
 181              }
 182              $expected[$slot->id] = $slot;
 183          }
 184          $actual = $this->repaginate->repaginate_n_question_per_page($this->quizslots, 2);
 185          $this->assertEquals($expected, $actual);
 186  
 187          // Expect 3 questions per page.
 188          $expected = [];
 189          foreach ($this->quizslots as $slot) {
 190              // Page 1 contains Slots 1, 2 and 3.
 191              if ($slot->slot >= 1 && $slot->slot <= 3) {
 192                  $slot->page = 1;
 193              }
 194              // Page 2 contains slots 4 and 5.
 195              if ($slot->slot >= 4 && $slot->slot <= 6) {
 196                  $slot->page = 2;
 197              }
 198              $expected[$slot->id] = $slot;
 199          }
 200          $actual = $this->repaginate->repaginate_n_question_per_page($this->quizslots, 3);
 201          $this->assertEquals($expected, $actual);
 202  
 203          // Expect 5 questions per page.
 204          $expected = [];
 205          foreach ($this->quizslots as $slot) {
 206              // Page 1 contains Slots 1, 2, 3, 4 and 5.
 207              if ($slot->slot > 0 && $slot->slot < 6) {
 208                  $slot->page = 1;
 209              }
 210              // Page 2 contains slots 6, 7, 8, 9 and 10.
 211              if ($slot->slot > 5 && $slot->slot < 11) {
 212                  $slot->page = 2;
 213              }
 214              $expected[$slot->id] = $slot;
 215          }
 216          $actual = $this->repaginate->repaginate_n_question_per_page($this->quizslots, 5);
 217          $this->assertEquals($expected, $actual);
 218  
 219          // Expect 10 questions per page.
 220          $expected = [];
 221          foreach ($this->quizslots as $slot) {
 222              // Page 1 contains Slots 1 to 10.
 223              if ($slot->slot >= 1 && $slot->slot <= 10) {
 224                  $slot->page = 1;
 225              }
 226              // Page 2 contains slots 11 to 20.
 227              if ($slot->slot >= 11 && $slot->slot <= 20) {
 228                  $slot->page = 2;
 229              }
 230              $expected[$slot->id] = $slot;
 231          }
 232          $actual = $this->repaginate->repaginate_n_question_per_page($this->quizslots, 10);
 233          $this->assertEquals($expected, $actual);
 234  
 235          // Expect 1 questions per page.
 236          $expected = [];
 237          $page = 1;
 238          foreach ($this->quizslots as $slot) {
 239              $slot->page = $page++;
 240              $expected[$slot->id] = $slot;
 241          }
 242          $actual = $this->repaginate->repaginate_n_question_per_page($this->quizslots, 1);
 243          $this->assertEquals($expected, $actual);
 244      }
 245  
 246      public function test_repaginate_this_slot() {
 247          $this->set_quiz_slots();
 248          $slotsbyslotno = $this->repaginate->get_slots_by_slot_number($this->quizslots);
 249          $slotnumber = 3;
 250          $newpagenumber = 2;
 251          $thisslot = $slotsbyslotno[3];
 252          $thisslot->page = $newpagenumber;
 253          $expected = $thisslot;
 254          $actual = $this->repaginate->repaginate_this_slot($slotsbyslotno[3], $newpagenumber);
 255          $this->assertEquals($expected, $actual);
 256      }
 257  
 258      public function test_repaginate_the_rest() {
 259          $this->set_quiz_slots();
 260          $slotfrom = 1;
 261          $type = repaginate::LINK;
 262          $expected = [];
 263          foreach ($this->quizslots as $slot) {
 264              if ($slot->slot > $slotfrom) {
 265                  $slot->page = $slot->page - 1;
 266                  $expected[$slot->id] = $slot;
 267              }
 268          }
 269          $actual = $this->repaginate->repaginate_the_rest($this->quizslots, $slotfrom, $type, false);
 270          $this->assertEquals($expected, $actual);
 271  
 272          $slotfrom = 2;
 273          $newslots = [];
 274          foreach ($this->quizslots as $s) {
 275              if ($s->slot === $slotfrom) {
 276                  $s->page = $s->page - 1;
 277              }
 278              $newslots[$s->id] = $s;
 279          }
 280  
 281          $type = repaginate::UNLINK;
 282          $expected = [];
 283          foreach ($this->quizslots as $slot) {
 284              if ($slot->slot > ($slotfrom - 1)) {
 285                  $slot->page = $slot->page - 1;
 286                  $expected[$slot->id] = $slot;
 287              }
 288          }
 289          $actual = $this->repaginate->repaginate_the_rest($newslots, $slotfrom, $type, false);
 290          $this->assertEquals($expected, $actual);
 291      }
 292  
 293  }